Data-aware ListBox: add SelectedValue and SelectedValues properties

Change-Id: Id081e4f6bb765056f17babcfec52a1aedcd7b5d5
This commit is contained in:
Lionel Elie Mamane 2013-04-21 19:20:31 +02:00
parent 13a159896e
commit a16bb08013
5 changed files with 153 additions and 23 deletions

View file

@ -274,6 +274,14 @@ namespace frm
_rValue <<= lcl_convertToStringSequence( m_aBoundValues );
break;
case PROPERTY_ID_SELECT_VALUE_SEQ:
_rValue = getCurrentMultiValue();
break;
case PROPERTY_ID_SELECT_VALUE:
_rValue = getCurrentSingleValue();
break;
case PROPERTY_ID_DEFAULT_SELECT_SEQ:
_rValue <<= m_aDefaultSelectSeq;
break;
@ -337,6 +345,24 @@ namespace frm
OSL_FAIL( "ValueItemList is read-only!" );
throw PropertyVetoException();
case PROPERTY_ID_SELECT_VALUE_SEQ :
{
Sequence< const Any > v;
_rValue >>= v;
Any newSelectSeq(translateBindingValuesToControlValue(v));
setPropertyValue( PROPERTY_SELECT_SEQ, newSelectSeq );
}
break;
case PROPERTY_ID_SELECT_VALUE :
{
ORowSetValue v;
v.fill(_rValue);
Any newSelectSeq(translateDbValueToControlValue(v));
setPropertyValue( PROPERTY_SELECT_SEQ, newSelectSeq );
}
break;
case PROPERTY_ID_DEFAULT_SELECT_SEQ :
DBG_ASSERT(_rValue.getValueType().equals(::getCppuType(static_cast< Sequence<sal_Int16>*>(0))),
"OListBoxModel::setFastPropertyValue_NoBroadcast : invalid type !" );
@ -388,6 +414,14 @@ namespace frm
OSL_FAIL( "ValueItemList is read-only!" );
throw PropertyVetoException();
case PROPERTY_ID_SELECT_VALUE_SEQ :
bModified = tryPropertyValue(_rConvertedValue, _rOldValue, _rValue, getCurrentMultiValue());
break;
case PROPERTY_ID_SELECT_VALUE :
bModified = tryPropertyValue(_rConvertedValue, _rOldValue, _rValue, getCurrentSingleValue());
break;
case PROPERTY_ID_DEFAULT_SELECT_SEQ :
bModified = tryPropertyValue(_rConvertedValue, _rOldValue, _rValue, m_aDefaultSelectSeq);
break;
@ -441,12 +475,14 @@ namespace frm
//------------------------------------------------------------------------------
void OListBoxModel::describeFixedProperties( Sequence< Property >& _rProps ) const
{
BEGIN_DESCRIBE_PROPERTIES( 7, OBoundControlModel )
BEGIN_DESCRIBE_PROPERTIES( 9, OBoundControlModel )
DECL_PROP1(TABINDEX, sal_Int16, BOUND);
DECL_PROP2(BOUNDCOLUMN, sal_Int16, BOUND, MAYBEVOID);
DECL_PROP1(LISTSOURCETYPE, ListSourceType, BOUND);
DECL_PROP1(LISTSOURCE, StringSequence, BOUND);
DECL_PROP3(VALUE_SEQ, StringSequence, BOUND, READONLY, TRANSIENT);
DECL_PROP2(SELECT_VALUE_SEQ, Sequence< Any >, BOUND, TRANSIENT);
DECL_PROP2(SELECT_VALUE, Any, BOUND, TRANSIENT);
DECL_PROP1(DEFAULT_SELECT_SEQ, Sequence<sal_Int16>, BOUND);
DECL_PROP1(STRINGITEMLIST, Sequence< OUString >, BOUND);
END_DESCRIBE_PROPERTIES();
@ -1078,24 +1114,13 @@ namespace frm
return sal_True;
}
// XPropertiesChangeListener
//------------------------------------------------------------------------------
Any OListBoxModel::translateDbColumnToControlValue()
Sequence< sal_Int16 > OListBoxModel::translateDbValueToControlValue(const ORowSetValue &i_aValue) const
{
Reference< XPropertySet > xBoundField( getField() );
if ( !xBoundField.is() )
{
OSL_FAIL( "OListBoxModel::translateDbColumnToControlValue: no field? How could that happen?!" );
return Any();
}
Sequence< sal_Int16 > aSelectionIndicies;
ORowSetValue aCurrentValue;
aCurrentValue.fill( getValueType(), m_xColumn );
// reset selection for NULL values
if ( aCurrentValue.isNull() )
if ( i_aValue.isNull() )
{
if ( m_nNULLPos != -1 )
{
@ -1106,7 +1131,10 @@ namespace frm
else
{
ValueList aValues( impl_getValues() );
ValueList::const_iterator curValuePos = ::std::find( aValues.begin(), aValues.end(), aCurrentValue );
assert( m_nConvertedBoundValuesType == getValueType());
ORowSetValue v(i_aValue);
v.setTypeKind( m_nConvertedBoundValuesType );
ValueList::const_iterator curValuePos = ::std::find( aValues.begin(), aValues.end(), v );
if ( curValuePos != aValues.end() )
{
aSelectionIndicies.realloc( 1 );
@ -1114,9 +1142,64 @@ namespace frm
}
}
return aSelectionIndicies;
}
//------------------------------------------------------------------------------
Sequence< sal_Int16 > OListBoxModel::translateBindingValuesToControlValue(const Sequence< const Any > &i_aValues) const
{
const ValueList aValues( impl_getValues() );
assert( m_nConvertedBoundValuesType == getValueType());
Sequence< sal_Int16 > aSelectionIndicies(i_aValues.getLength());
sal_Int32 nCount(0);
sal_Int16 *pIndex = aSelectionIndicies.getArray();
const Any *pValue = i_aValues.getConstArray();
const Any * const pValueEnd = i_aValues.getConstArray() + i_aValues.getLength();
for (;pValue < pValueEnd; ++pValue)
{
if ( pValue->hasValue() )
{
ORowSetValue v;
v.fill(*pValue);
v.setTypeKind( m_nConvertedBoundValuesType );
ValueList::const_iterator curValuePos = ::std::find( aValues.begin(), aValues.end(), v );
if ( curValuePos != aValues.end() )
{
*pIndex = curValuePos - aValues.begin();
++pIndex;
++nCount;
}
}
else
{
if ( m_nNULLPos != -1 )
{
*pIndex = m_nNULLPos;
++pIndex;
++nCount;
}
}
}
assert(aSelectionIndicies.getArray() + nCount == pIndex);
aSelectionIndicies.realloc(nCount);
return aSelectionIndicies;
}
//------------------------------------------------------------------------------
Any OListBoxModel::translateDbColumnToControlValue()
{
Reference< XPropertySet > xBoundField( getField() );
if ( !xBoundField.is() )
{
OSL_FAIL( "OListBoxModel::translateDbColumnToControlValue: no field? How could that happen?!" );
return Any();
}
ORowSetValue aCurrentValue;
aCurrentValue.fill( getValueType(), m_xColumn );
m_aSaveValue = aCurrentValue;
return makeAny( aSelectionIndicies );
return makeAny( translateDbValueToControlValue(aCurrentValue) );
}
// XReset
@ -1430,6 +1513,42 @@ namespace frm
return aReturn;
}
//--------------------------------------------------------------------
Any OListBoxModel::getCurrentSingleValue() const
{
Any aCurrentValue;
try
{
Sequence< sal_Int16 > aSelectSequence;
OSL_VERIFY( const_cast< OListBoxModel* >( this )->getPropertyValue( PROPERTY_SELECT_SEQ ) >>= aSelectSequence );
aCurrentValue = lcl_getSingleSelectedEntryAny( aSelectSequence, impl_getValues() );
}
catch( const Exception& )
{
DBG_UNHANDLED_EXCEPTION();
}
return aCurrentValue;
}
//--------------------------------------------------------------------
Any OListBoxModel::getCurrentMultiValue() const
{
Any aCurrentValue;
try
{
Sequence< sal_Int16 > aSelectSequence;
OSL_VERIFY( const_cast< OListBoxModel* >( this )->getPropertyValue( PROPERTY_SELECT_SEQ ) >>= aSelectSequence );
aCurrentValue = lcl_getMultiSelectedEntriesAny( aSelectSequence, impl_getValues() );
}
catch( const Exception& )
{
DBG_UNHANDLED_EXCEPTION();
}
return aCurrentValue;
}
//--------------------------------------------------------------------
Any OListBoxModel::getCurrentFormComponentValue() const
{
@ -1440,16 +1559,13 @@ namespace frm
try
{
Sequence< sal_Int16 > aSelectSequence;
OSL_VERIFY( const_cast< OListBoxModel* >( this )->getPropertyValue( PROPERTY_SELECT_SEQ ) >>= aSelectSequence );
sal_Bool bMultiSelection( sal_False );
OSL_VERIFY( const_cast< OListBoxModel* >( this )->getPropertyValue( PROPERTY_MULTISELECTION ) >>= bMultiSelection );
if ( bMultiSelection )
aCurrentValue = lcl_getMultiSelectedEntriesAny( aSelectSequence, impl_getValues() );
aCurrentValue = getCurrentMultiValue();
else
aCurrentValue = lcl_getSingleSelectedEntryAny( aSelectSequence, impl_getValues() );
aCurrentValue = getCurrentSingleValue();
}
catch( const Exception& )
{

View file

@ -206,7 +206,17 @@ protected:
protected:
DECLARE_XCLONEABLE();
void init();
::com::sun::star::uno::Any getCurrentSingleValue() const;
::com::sun::star::uno::Any getCurrentMultiValue() const;
::com::sun::star::uno::Sequence< sal_Int16 > translateBindingValuesToControlValue(
const ::com::sun::star::uno::Sequence< const ::com::sun::star::uno::Any > &i_aValues)
const;
::com::sun::star::uno::Sequence< sal_Int16 > translateDbValueToControlValue(
const ::connectivity::ORowSetValue &aValue)
const;
private:
void loadData( bool _bForce );

View file

@ -104,6 +104,8 @@ namespace frm
FORMS_CONSTASCII_STRING( PROPERTY_LISTSOURCE, "ListSource" );
FORMS_CONSTASCII_STRING( PROPERTY_SELECT_SEQ, "SelectedItems" );
FORMS_CONSTASCII_STRING( PROPERTY_VALUE_SEQ, "ValueItemList" );
FORMS_CONSTASCII_STRING( PROPERTY_SELECT_VALUE_SEQ, "SelectedValues" );
FORMS_CONSTASCII_STRING( PROPERTY_SELECT_VALUE, "SelectedValue" );
FORMS_CONSTASCII_STRING( PROPERTY_DEFAULT_SELECT_SEQ, "DefaultSelection" );
FORMS_CONSTASCII_STRING( PROPERTY_MULTISELECTION, "MultiSelection" );
FORMS_CONSTASCII_STRING( PROPERTY_ALIGN, "Align" );

View file

@ -105,8 +105,8 @@ namespace frm
#define PROPERTY_ID_DEFAULT_STATE (PROPERTY_ID_START + 77) // UINT16
#define PROPERTY_ID_VALUE_SEQ (PROPERTY_ID_START + 78) // StringSeq
#define PROPERTY_ID_IMAGE_URL (PROPERTY_ID_START + 79) // ::rtl::OUString
// free
// free
#define PROPERTY_ID_SELECT_VALUE (PROPERTY_ID_START + 80) // StringSeq
#define PROPERTY_ID_SELECT_VALUE_SEQ (PROPERTY_ID_START + 81) // StringSeq
// free
// free
// free

View file

@ -127,6 +127,8 @@ void PropertyInfoService::initialize()
ADD_PROP_ASSIGNMENT(LISTSOURCE);
ADD_PROP_ASSIGNMENT(SELECT_SEQ);
ADD_PROP_ASSIGNMENT(VALUE_SEQ);
ADD_PROP_ASSIGNMENT(SELECT_VALUE);
ADD_PROP_ASSIGNMENT(SELECT_VALUE_SEQ);
ADD_PROP_ASSIGNMENT(DEFAULT_SELECT_SEQ);
ADD_PROP_ASSIGNMENT(MULTISELECTION);
ADD_PROP_ASSIGNMENT(DECIMAL_ACCURACY);