/************************************************************** * * Licensed to the Apache Software Foundation (ASF) under one * or more contributor license agreements. See the NOTICE file * distributed with this work for additional information * regarding copyright ownership. The ASF licenses this file * to you under the Apache License, Version 2.0 (the * "License"); you may not use this file except in compliance * with the License. You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, * software distributed under the License is distributed on an * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY * KIND, either express or implied. See the License for the * specific language governing permissions and limitations * under the License. * *************************************************************/ // MARKER(update_precomp.py): autogen include statement, do not remove #include "precompiled_toolkit.hxx" #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include using namespace ::com::sun::star; using namespace ::com::sun::star::uno; using namespace ::com::sun::star::lang; using namespace ::com::sun::star::i18n; using ::com::sun::star::awt::FontDescriptor; struct ImplControlProperty { private: sal_uInt16 nId; ::com::sun::star::uno::Any aValue; public: ImplControlProperty( const ImplControlProperty& rProp ) : aValue( rProp.aValue ) { nId = rProp.nId; } ImplControlProperty( sal_uInt16 nT ) { nId = nT; } ImplControlProperty( sal_uInt16 nT, const ::com::sun::star::uno::Any& rValue ) : aValue( rValue ) { nId = nT; } sal_uInt16 GetId() const { return nId; } const ::com::sun::star::uno::Any& GetValue() const { return aValue; } void SetValue( const ::com::sun::star::uno::Any& rValue ) { aValue = rValue; } }; DECLARE_TABLE( ImplPropertyTable, ImplControlProperty* ) #define UNOCONTROL_STREAMVERSION (short)2 static void lcl_ImplMergeFontProperty( FontDescriptor& rFD, sal_uInt16 nPropId, const Any& rValue ) { // some props are defined with other types than the matching FontDescriptor members have // (e.g. FontWidth, FontSlant) // 78474 - 09/19/2000 - FS float nExtractFloat = 0; sal_Int16 nExtractShort = 0; switch ( nPropId ) { case BASEPROPERTY_FONTDESCRIPTORPART_NAME: rValue >>= rFD.Name; break; case BASEPROPERTY_FONTDESCRIPTORPART_STYLENAME: rValue >>= rFD.StyleName; break; case BASEPROPERTY_FONTDESCRIPTORPART_FAMILY: rValue >>= rFD.Family; break; case BASEPROPERTY_FONTDESCRIPTORPART_CHARSET: rValue >>= rFD.CharSet; break; case BASEPROPERTY_FONTDESCRIPTORPART_HEIGHT: rValue >>= nExtractFloat; rFD.Height = (sal_Int16)nExtractFloat; break; case BASEPROPERTY_FONTDESCRIPTORPART_WEIGHT: rValue >>= rFD.Weight; break; case BASEPROPERTY_FONTDESCRIPTORPART_SLANT: if ( rValue >>= nExtractShort ) rFD.Slant = (::com::sun::star::awt::FontSlant)nExtractShort; else rValue >>= rFD.Slant; break; case BASEPROPERTY_FONTDESCRIPTORPART_UNDERLINE: rValue >>= rFD.Underline; break; case BASEPROPERTY_FONTDESCRIPTORPART_STRIKEOUT: rValue >>= rFD.Strikeout; break; case BASEPROPERTY_FONTDESCRIPTORPART_WIDTH: rValue >>= rFD.Width; break; case BASEPROPERTY_FONTDESCRIPTORPART_PITCH: rValue >>= rFD.Pitch; break; case BASEPROPERTY_FONTDESCRIPTORPART_CHARWIDTH: rValue >>= rFD.CharacterWidth; break; case BASEPROPERTY_FONTDESCRIPTORPART_ORIENTATION: rValue >>= rFD.Orientation; break; case BASEPROPERTY_FONTDESCRIPTORPART_KERNING: rValue >>= rFD.Kerning; break; case BASEPROPERTY_FONTDESCRIPTORPART_WORDLINEMODE: rValue >>= rFD.WordLineMode; break; case BASEPROPERTY_FONTDESCRIPTORPART_TYPE: rValue >>= rFD.Type; break; default: DBG_ERROR( "FontProperty?!" ); } } // ---------------------------------------------------- // class UnoControlModel // ---------------------------------------------------- UnoControlModel::UnoControlModel() :UnoControlModel_Base() ,MutexAndBroadcastHelper() ,OPropertySetHelper( BrdcstHelper ) ,maDisposeListeners( *this ) ,maContext( ::comphelper::getProcessServiceFactory() ) { OSL_ENSURE( false, "UnoControlModel::UnoControlModel: not implemented. Well, not really." ); // just implemented to let the various FooImplInheritanceHelper compile, you should use the // version taking a service factory mpData = new ImplPropertyTable; } UnoControlModel::UnoControlModel( const Reference< XMultiServiceFactory >& i_factory ) :UnoControlModel_Base() ,MutexAndBroadcastHelper() ,OPropertySetHelper( BrdcstHelper ) ,maDisposeListeners( *this ) ,maContext( i_factory ) { // Die Properties muessen vom Model in die Tabelle gestopft werden, // nur vorhandene Properties sind gueltige Properties, auch wenn VOID. mpData = new ImplPropertyTable; } UnoControlModel::UnoControlModel( const UnoControlModel& rModel ) : UnoControlModel_Base() , MutexAndBroadcastHelper() , OPropertySetHelper( BrdcstHelper ) , maDisposeListeners( *this ) , maContext( rModel.maContext ) { mpData = new ImplPropertyTable; for ( sal_uInt32 n = rModel.mpData->Count(); n; ) { ImplControlProperty* pProp = rModel.mpData->GetObject( --n ); ImplControlProperty* pNew = new ImplControlProperty( *pProp ); mpData->Insert( pNew->GetId(), pNew ); } } UnoControlModel::~UnoControlModel() { for ( sal_uInt32 n = mpData->Count(); n; ) delete mpData->GetObject( --n ); delete mpData; } UnoControlModel* UnoControlModel::Clone() const { DBG_ERROR( "UnoControlModel::Clone() ?!" ); return NULL; } ::com::sun::star::uno::Sequence UnoControlModel::ImplGetPropertyIds() const { sal_uInt32 nIDs = mpData->Count(); ::com::sun::star::uno::Sequence aIDs( nIDs ); sal_Int32* pIDs = aIDs.getArray(); for ( sal_uInt32 n = 0; n < nIDs; n++ ) pIDs[n] = mpData->GetObjectKey( n ); return aIDs; } sal_Bool UnoControlModel::ImplHasProperty( sal_uInt16 nPropId ) const { if ( ( nPropId >= BASEPROPERTY_FONTDESCRIPTORPART_START ) && ( nPropId <= BASEPROPERTY_FONTDESCRIPTORPART_END ) ) nPropId = BASEPROPERTY_FONTDESCRIPTOR; return mpData->Get( nPropId ) ? sal_True : sal_False; } ::com::sun::star::uno::Any UnoControlModel::ImplGetDefaultValue( sal_uInt16 nPropId ) const { ::com::sun::star::uno::Any aDefault; if ( (nPropId == BASEPROPERTY_FONTDESCRIPTOR) || ( (nPropId >= BASEPROPERTY_FONTDESCRIPTORPART_START) && (nPropId <= BASEPROPERTY_FONTDESCRIPTORPART_END) ) ) { EmptyFontDescriptor aFD; switch ( nPropId ) { case BASEPROPERTY_FONTDESCRIPTOR: aDefault <<= aFD; break; case BASEPROPERTY_FONTDESCRIPTORPART_NAME: aDefault <<= aFD.Name; break; case BASEPROPERTY_FONTDESCRIPTORPART_STYLENAME: aDefault <<= aFD.StyleName; break; case BASEPROPERTY_FONTDESCRIPTORPART_FAMILY: aDefault <<= aFD.Family; break; case BASEPROPERTY_FONTDESCRIPTORPART_CHARSET: aDefault <<= aFD.CharSet; break; case BASEPROPERTY_FONTDESCRIPTORPART_HEIGHT: aDefault <<= (float)aFD.Height; break; case BASEPROPERTY_FONTDESCRIPTORPART_WEIGHT: aDefault <<= aFD.Weight; break; case BASEPROPERTY_FONTDESCRIPTORPART_SLANT: aDefault <<= (sal_Int16)aFD.Slant; break; case BASEPROPERTY_FONTDESCRIPTORPART_UNDERLINE: aDefault <<= aFD.Underline; break; case BASEPROPERTY_FONTDESCRIPTORPART_STRIKEOUT: aDefault <<= aFD.Strikeout; break; case BASEPROPERTY_FONTDESCRIPTORPART_WIDTH: aDefault <<= aFD.Width; break; case BASEPROPERTY_FONTDESCRIPTORPART_PITCH: aDefault <<= aFD.Pitch; break; case BASEPROPERTY_FONTDESCRIPTORPART_CHARWIDTH: aDefault <<= aFD.CharacterWidth; break; case BASEPROPERTY_FONTDESCRIPTORPART_ORIENTATION: aDefault <<= aFD.Orientation; break; case BASEPROPERTY_FONTDESCRIPTORPART_KERNING: aDefault <<= aFD.Kerning; break; case BASEPROPERTY_FONTDESCRIPTORPART_WORDLINEMODE: aDefault <<= aFD.WordLineMode; break; case BASEPROPERTY_FONTDESCRIPTORPART_TYPE: aDefault <<= aFD.Type; break; default: DBG_ERROR( "FontProperty?!" ); } } else { switch ( nPropId ) { case BASEPROPERTY_GRAPHIC: aDefault <<= Reference< graphic::XGraphic >(); break; case BASEPROPERTY_REFERENCE_DEVICE: aDefault <<= Reference< awt::XDevice >(); break; case BASEPROPERTY_ITEM_SEPARATOR_POS: case BASEPROPERTY_VERTICALALIGN: case BASEPROPERTY_BORDERCOLOR: case BASEPROPERTY_SYMBOL_COLOR: case BASEPROPERTY_TABSTOP: case BASEPROPERTY_TEXTCOLOR: case BASEPROPERTY_TEXTLINECOLOR: case BASEPROPERTY_DATE: case BASEPROPERTY_DATESHOWCENTURY: case BASEPROPERTY_TIME: case BASEPROPERTY_VALUE_DOUBLE: case BASEPROPERTY_PROGRESSVALUE: case BASEPROPERTY_SCROLLVALUE: case BASEPROPERTY_VISIBLESIZE: case BASEPROPERTY_BACKGROUNDCOLOR: case BASEPROPERTY_FILLCOLOR: break; // Void case BASEPROPERTY_FONTRELIEF: case BASEPROPERTY_FONTEMPHASISMARK: case BASEPROPERTY_MAXTEXTLEN: case BASEPROPERTY_STATE: case BASEPROPERTY_EXTDATEFORMAT: case BASEPROPERTY_EXTTIMEFORMAT: case BASEPROPERTY_ECHOCHAR: aDefault <<= (sal_Int16) 0; break; case BASEPROPERTY_BORDER: aDefault <<= (sal_Int16) 1; break; case BASEPROPERTY_DECIMALACCURACY: aDefault <<= (sal_Int16) 2; break; case BASEPROPERTY_LINECOUNT: aDefault <<= (sal_Int16) 5; break; case BASEPROPERTY_ALIGN: aDefault <<= (sal_Int16) PROPERTY_ALIGN_LEFT; break; case BASEPROPERTY_IMAGEALIGN: aDefault <<= (sal_Int16) 1 /*ImageAlign::TOP*/; break; case BASEPROPERTY_IMAGEPOSITION: aDefault <<= (sal_Int16) 12 /*ImagePosition::Centered*/; break; case BASEPROPERTY_PUSHBUTTONTYPE: aDefault <<= (sal_Int16) 0 /*PushButtonType::STANDARD*/; break; case BASEPROPERTY_MOUSE_WHEEL_BEHAVIOUR:aDefault <<= (sal_Int16) awt::MouseWheelBehavior::SCROLL_FOCUS_ONLY; break; case BASEPROPERTY_DATEMAX: aDefault <<= (sal_Int32) Date( 31, 12, 2200 ).GetDate(); break; case BASEPROPERTY_DATEMIN: aDefault <<= (sal_Int32) Date( 1, 1, 1900 ).GetDate(); break; case BASEPROPERTY_TIMEMAX: aDefault <<= (sal_Int32) Time( 23, 59 ).GetTime(); break; case BASEPROPERTY_TIMEMIN: aDefault <<= (sal_Int32) 0; break; case BASEPROPERTY_VALUEMAX_DOUBLE: aDefault <<= (double) 1000000; break; case BASEPROPERTY_VALUEMIN_DOUBLE: aDefault <<= (double) -1000000; break; case BASEPROPERTY_VALUESTEP_DOUBLE: aDefault <<= (double ) 1; break; case BASEPROPERTY_PROGRESSVALUE_MAX: aDefault <<= (sal_Int32) 100; break; case BASEPROPERTY_PROGRESSVALUE_MIN: aDefault <<= (sal_Int32) 0; break; case BASEPROPERTY_SCROLLVALUE_MAX: aDefault <<= (sal_Int32) 100; break; case BASEPROPERTY_SCROLLVALUE_MIN: aDefault <<= (sal_Int32) 0; break; case BASEPROPERTY_LINEINCREMENT: aDefault <<= (sal_Int32) 1; break; case BASEPROPERTY_BLOCKINCREMENT: aDefault <<= (sal_Int32) 10; break; case BASEPROPERTY_ORIENTATION: aDefault <<= (sal_Int32) 0; break; case BASEPROPERTY_SPINVALUE: aDefault <<= (sal_Int32) 0; break; case BASEPROPERTY_SPININCREMENT: aDefault <<= (sal_Int32) 1; break; case BASEPROPERTY_SPINVALUE_MIN: aDefault <<= (sal_Int32) 0; break; case BASEPROPERTY_SPINVALUE_MAX: aDefault <<= (sal_Int32) 100; break; case BASEPROPERTY_REPEAT_DELAY: aDefault <<= (sal_Int32) 50; break; // 50 milliseconds case BASEPROPERTY_DEFAULTCONTROL: aDefault <<= ((UnoControlModel*)this)->getServiceName(); break; case BASEPROPERTY_AUTOHSCROLL: case BASEPROPERTY_AUTOVSCROLL: case BASEPROPERTY_MOVEABLE: case BASEPROPERTY_CLOSEABLE: case BASEPROPERTY_SIZEABLE: case BASEPROPERTY_HSCROLL: case BASEPROPERTY_DEFAULTBUTTON: case BASEPROPERTY_MULTILINE: case BASEPROPERTY_MULTISELECTION: case BASEPROPERTY_TRISTATE: case BASEPROPERTY_DROPDOWN: case BASEPROPERTY_SPIN: case BASEPROPERTY_READONLY: case BASEPROPERTY_VSCROLL: case BASEPROPERTY_NUMSHOWTHOUSANDSEP: case BASEPROPERTY_STRICTFORMAT: case BASEPROPERTY_REPEAT: case BASEPROPERTY_PAINTTRANSPARENT: case BASEPROPERTY_DESKTOP_AS_PARENT: case BASEPROPERTY_HARDLINEBREAKS: case BASEPROPERTY_NOLABEL: aDefault <<= (sal_Bool) sal_False; break; case BASEPROPERTY_MULTISELECTION_SIMPLEMODE: case BASEPROPERTY_HIDEINACTIVESELECTION: case BASEPROPERTY_ENFORCE_FORMAT: case BASEPROPERTY_AUTOCOMPLETE: case BASEPROPERTY_SCALEIMAGE: case BASEPROPERTY_ENABLED: case BASEPROPERTY_PRINTABLE: case BASEPROPERTY_ENABLEVISIBLE: case BASEPROPERTY_DECORATION: aDefault <<= (sal_Bool) sal_True; break; case BASEPROPERTY_HELPTEXT: case BASEPROPERTY_HELPURL: case BASEPROPERTY_IMAGEURL: case BASEPROPERTY_DIALOGSOURCEURL: case BASEPROPERTY_EDITMASK: case BASEPROPERTY_LITERALMASK: case BASEPROPERTY_LABEL: case BASEPROPERTY_TITLE: case BASEPROPERTY_TEXT: aDefault <<= ::rtl::OUString(); break; case BASEPROPERTY_WRITING_MODE: case BASEPROPERTY_CONTEXT_WRITING_MODE: aDefault <<= text::WritingMode2::CONTEXT; break; case BASEPROPERTY_STRINGITEMLIST: { ::com::sun::star::uno::Sequence< ::rtl::OUString> aStringSeq; aDefault <<= aStringSeq; } break; case BASEPROPERTY_SELECTEDITEMS: { ::com::sun::star::uno::Sequence aINT16Seq; aDefault <<= aINT16Seq; } break; case BASEPROPERTY_CURRENCYSYMBOL: { Any aDefaultCurrency = ::utl::ConfigManager::GetDirectConfigProperty(::utl::ConfigManager::DEFAULTCURRENCY); DBG_ASSERT( TypeClass_STRING == aDefaultCurrency.getValueTypeClass(), "UnoControlModel::ImplGetDefaultValue: invalid currency config value!" ); ::rtl::OUString sDefaultCurrency; aDefaultCurrency >>= sDefaultCurrency; // extract the bank symbol sal_Int32 nSepPos = sDefaultCurrency.indexOf( '-' ); ::rtl::OUString sBankSymbol; if ( nSepPos >= 0 ) { sBankSymbol = sDefaultCurrency.copy( 0, nSepPos ); sDefaultCurrency = sDefaultCurrency.copy( nSepPos + 1 ); } // the remaming is the locale Locale aLocale; nSepPos = sDefaultCurrency.indexOf( '-' ); if ( nSepPos >= 0 ) { aLocale.Language = sDefaultCurrency.copy( 0, nSepPos ); aLocale.Country = sDefaultCurrency.copy( nSepPos + 1 ); } LocaleDataWrapper aLocaleInfo( maContext.getLegacyServiceFactory(), aLocale ); if ( !sBankSymbol.getLength() ) sBankSymbol = aLocaleInfo.getCurrBankSymbol(); // look for the currency entry (for this language) which has the given bank symbol Sequence< Currency2 > aAllCurrencies = aLocaleInfo.getAllCurrencies(); const Currency2* pAllCurrencies = aAllCurrencies.getConstArray(); const Currency2* pAllCurrenciesEnd = pAllCurrencies + aAllCurrencies.getLength(); ::rtl::OUString sCurrencySymbol = aLocaleInfo.getCurrSymbol(); if ( !sBankSymbol.getLength() ) { DBG_ASSERT( pAllCurrencies != pAllCurrenciesEnd, "UnoControlModel::ImplGetDefaultValue: no currencies at all!" ); if ( pAllCurrencies != pAllCurrenciesEnd ) { sBankSymbol = pAllCurrencies->BankSymbol; sCurrencySymbol = pAllCurrencies->Symbol; } } if ( sBankSymbol.getLength() ) { bool bLegacy = false; for ( ;pAllCurrencies != pAllCurrenciesEnd; ++pAllCurrencies ) if ( pAllCurrencies->BankSymbol == sBankSymbol ) { sCurrencySymbol = pAllCurrencies->Symbol; if ( pAllCurrencies->LegacyOnly ) bLegacy = true; else break; } DBG_ASSERT( bLegacy || pAllCurrencies != pAllCurrenciesEnd, "UnoControlModel::ImplGetDefaultValue: did not find the given bank symbol!" ); } aDefault <<= sCurrencySymbol; } break; default: DBG_ERROR( "ImplGetDefaultValue - unknown Property" ); } } return aDefault; } void UnoControlModel::ImplRegisterProperty( sal_uInt16 nPropId, const ::com::sun::star::uno::Any& rDefault ) { ImplControlProperty* pProp = new ImplControlProperty( nPropId, rDefault ); mpData->Insert( nPropId, pProp ); } void UnoControlModel::ImplRegisterProperty( sal_uInt16 nPropId ) { ImplRegisterProperty( nPropId, ImplGetDefaultValue( nPropId ) ); if ( nPropId == BASEPROPERTY_FONTDESCRIPTOR ) { // some properties are not included in the FontDescriptor, but every time // when we have a FontDescriptor we want to have these properties too. // => Easier to register the here, istead everywhere where I register the FontDescriptor... ImplRegisterProperty( BASEPROPERTY_TEXTCOLOR ); ImplRegisterProperty( BASEPROPERTY_TEXTLINECOLOR ); ImplRegisterProperty( BASEPROPERTY_FONTRELIEF ); ImplRegisterProperty( BASEPROPERTY_FONTEMPHASISMARK ); } } void UnoControlModel::ImplRegisterProperties( const std::list< sal_uInt16 > &rIds ) { std::list< sal_uInt16 >::const_iterator iter; for( iter = rIds.begin(); iter != rIds.end(); iter++) { if( !ImplHasProperty( *iter ) ) ImplRegisterProperty( *iter, ImplGetDefaultValue( *iter ) ); } } // ::com::sun::star::uno::XInterface ::com::sun::star::uno::Any UnoControlModel::queryAggregation( const ::com::sun::star::uno::Type & rType ) throw(::com::sun::star::uno::RuntimeException) { Any aRet = UnoControlModel_Base::queryAggregation( rType ); if ( !aRet.hasValue() ) aRet = ::cppu::OPropertySetHelper::queryInterface( rType ); return aRet; } // ::com::sun::star::lang::XUnoTunnel IMPL_XUNOTUNNEL( UnoControlModel ) // XInterface IMPLEMENT_FORWARD_REFCOUNT( UnoControlModel, UnoControlModel_Base ) // ::com::sun::star::lang::XTypeProvider IMPLEMENT_FORWARD_XTYPEPROVIDER2( UnoControlModel, UnoControlModel_Base, ::cppu::OPropertySetHelper ) uno::Reference< util::XCloneable > UnoControlModel::createClone() throw(::com::sun::star::uno::RuntimeException) { UnoControlModel* pClone = Clone(); uno::Reference< util::XCloneable > xClone( (::cppu::OWeakObject*) pClone, uno::UNO_QUERY ); return xClone; } // ::com::sun::star::lang::XComponent void UnoControlModel::dispose( ) throw(::com::sun::star::uno::RuntimeException) { ::osl::Guard< ::osl::Mutex > aGuard( GetMutex() ); ::com::sun::star::lang::EventObject aEvt; aEvt.Source = (::com::sun::star::uno::XAggregation*)(::cppu::OWeakAggObject*)this; maDisposeListeners.disposeAndClear( aEvt ); BrdcstHelper.aLC.disposeAndClear( aEvt ); // let the property set helper notify our property listeners OPropertySetHelper::disposing(); } void UnoControlModel::addEventListener( const ::com::sun::star::uno::Reference< ::com::sun::star::lang::XEventListener >& rxListener ) throw(::com::sun::star::uno::RuntimeException) { ::osl::Guard< ::osl::Mutex > aGuard( GetMutex() ); maDisposeListeners.addInterface( rxListener ); } void UnoControlModel::removeEventListener( const ::com::sun::star::uno::Reference< ::com::sun::star::lang::XEventListener >& rxListener ) throw(::com::sun::star::uno::RuntimeException) { ::osl::Guard< ::osl::Mutex > aGuard( GetMutex() ); maDisposeListeners.removeInterface( rxListener ); } // ::com::sun::star::beans::XPropertyState ::com::sun::star::beans::PropertyState UnoControlModel::getPropertyState( const ::rtl::OUString& PropertyName ) throw(::com::sun::star::beans::UnknownPropertyException, ::com::sun::star::uno::RuntimeException) { ::osl::Guard< ::osl::Mutex > aGuard( GetMutex() ); sal_uInt16 nPropId = GetPropertyId( PropertyName ); ::com::sun::star::uno::Any aValue = getPropertyValue( PropertyName ); ::com::sun::star::uno::Any aDefault = ImplGetDefaultValue( nPropId ); return CompareProperties( aValue, aDefault ) ? ::com::sun::star::beans::PropertyState_DEFAULT_VALUE : ::com::sun::star::beans::PropertyState_DIRECT_VALUE; } ::com::sun::star::uno::Sequence< ::com::sun::star::beans::PropertyState > UnoControlModel::getPropertyStates( const ::com::sun::star::uno::Sequence< ::rtl::OUString >& PropertyNames ) throw(::com::sun::star::beans::UnknownPropertyException, ::com::sun::star::uno::RuntimeException) { ::osl::Guard< ::osl::Mutex > aGuard( GetMutex() ); sal_uInt32 nNames = PropertyNames.getLength(); const ::rtl::OUString* pNames = PropertyNames.getConstArray(); ::com::sun::star::uno::Sequence< ::com::sun::star::beans::PropertyState > aStates( nNames ); ::com::sun::star::beans::PropertyState* pStates = aStates.getArray(); for ( sal_uInt32 n = 0; n < nNames; n++ ) pStates[n] = getPropertyState( pNames[n] ); return aStates; } void UnoControlModel::setPropertyToDefault( const ::rtl::OUString& PropertyName ) throw(::com::sun::star::beans::UnknownPropertyException, ::com::sun::star::uno::RuntimeException) { Any aDefaultValue; { ::osl::Guard< ::osl::Mutex > aGuard( GetMutex() ); aDefaultValue = ImplGetDefaultValue( GetPropertyId( PropertyName ) ); } setPropertyValue( PropertyName, aDefaultValue ); } ::com::sun::star::uno::Any UnoControlModel::getPropertyDefault( const ::rtl::OUString& rPropertyName ) throw(::com::sun::star::beans::UnknownPropertyException, ::com::sun::star::lang::WrappedTargetException, ::com::sun::star::uno::RuntimeException) { ::osl::Guard< ::osl::Mutex > aGuard( GetMutex() ); return ImplGetDefaultValue( GetPropertyId( rPropertyName ) ); } // ::com::sun::star::io::XPersistObjec ::rtl::OUString UnoControlModel::getServiceName( ) throw(::com::sun::star::uno::RuntimeException) { ::osl::Guard< ::osl::Mutex > aGuard( GetMutex() ); DBG_ERROR( "ServiceName von UnoControlModel ?!" ); return ::rtl::OUString(); } void UnoControlModel::write( const ::com::sun::star::uno::Reference< ::com::sun::star::io::XObjectOutputStream >& OutStream ) throw(::com::sun::star::io::IOException, ::com::sun::star::uno::RuntimeException) { ::osl::Guard< ::osl::Mutex > aGuard( GetMutex() ); ::com::sun::star::uno::Reference< ::com::sun::star::io::XMarkableStream > xMark( OutStream, ::com::sun::star::uno::UNO_QUERY ); DBG_ASSERT( xMark.is(), "write: no ::com::sun::star::io::XMarkableStream!" ); OutStream->writeShort( UNOCONTROL_STREAMVERSION ); ImplPropertyTable aProps; sal_uInt32 i; for ( i = mpData->Count(); i; ) { ImplControlProperty* pProp = mpData->GetObject( --i ); if ( ( ( GetPropertyAttribs( pProp->GetId() ) & ::com::sun::star::beans::PropertyAttribute::TRANSIENT ) == 0 ) && ( getPropertyState( GetPropertyName( pProp->GetId() ) ) != ::com::sun::star::beans::PropertyState_DEFAULT_VALUE ) ) { aProps.Insert( pProp->GetId(), pProp ); } } sal_uInt32 nProps = aProps.Count(); // FontProperty wegen fehlender Unterscheidung zwischen 5.0 / 5.1 // immer im alten Format mitspeichern. OutStream->writeLong( (long) aProps.IsKeyValid( BASEPROPERTY_FONTDESCRIPTOR ) ? ( nProps + 3 ) : nProps ); for ( i = 0; i < nProps; i++ ) { sal_Int32 nPropDataBeginMark = xMark->createMark(); OutStream->writeLong( 0L ); // DataLen ImplControlProperty* pProp = aProps.GetObject( i ); OutStream->writeShort( pProp->GetId() ); sal_Bool bVoid = pProp->GetValue().getValueType().getTypeClass() == ::com::sun::star::uno::TypeClass_VOID; OutStream->writeBoolean( bVoid ); if ( !bVoid ) { const ::com::sun::star::uno::Any& rValue = pProp->GetValue(); const ::com::sun::star::uno::Type& rType = rValue.getValueType(); if ( rType == ::getBooleanCppuType() ) { sal_Bool b = false; rValue >>= b; OutStream->writeBoolean( b ); } else if ( rType == ::getCppuType((const ::rtl::OUString*)0) ) { ::rtl::OUString aUString; rValue >>= aUString; OutStream->writeUTF( aUString ); } else if ( rType == ::getCppuType((const sal_uInt16*)0) ) { sal_uInt16 n = 0; rValue >>= n; OutStream->writeShort( n ); } else if ( rType == ::getCppuType((const sal_Int16*)0) ) { sal_Int16 n = 0; rValue >>= n; OutStream->writeShort( n ); } else if ( rType == ::getCppuType((const sal_uInt32*)0) ) { sal_uInt32 n = 0; rValue >>= n; OutStream->writeLong( n ); } else if ( rType == ::getCppuType((const sal_Int32*)0) ) { sal_Int32 n = 0; rValue >>= n; OutStream->writeLong( n ); } else if ( rType == ::getCppuType((const double*)0) ) { double n = 0; rValue >>= n; OutStream->writeDouble( n ); } else if ( rType == ::getCppuType((const ::com::sun::star::awt::FontDescriptor*)0) ) { ::com::sun::star::awt::FontDescriptor aFD; rValue >>= aFD; OutStream->writeUTF( aFD.Name ); OutStream->writeShort( aFD.Height ); OutStream->writeShort( aFD.Width ); OutStream->writeUTF( aFD.StyleName ); OutStream->writeShort( aFD.Family ); OutStream->writeShort( aFD.CharSet ); OutStream->writeShort( aFD.Pitch ); OutStream->writeDouble( aFD.CharacterWidth ); OutStream->writeDouble( aFD.Weight ); OutStream->writeShort( sal::static_int_cast< sal_Int16 >(aFD.Slant) ); OutStream->writeShort( aFD.Underline ); OutStream->writeShort( aFD.Strikeout ); OutStream->writeDouble( aFD.Orientation ); OutStream->writeBoolean( aFD.Kerning ); OutStream->writeBoolean( aFD.WordLineMode ); OutStream->writeShort( aFD.Type ); } else if ( rType == ::getCppuType((const ::com::sun::star::uno::Sequence< ::rtl::OUString>*)0 ) ) { ::com::sun::star::uno::Sequence< ::rtl::OUString> aSeq; rValue >>= aSeq; long nEntries = aSeq.getLength(); OutStream->writeLong( nEntries ); for ( long n = 0; n < nEntries; n++ ) OutStream->writeUTF( aSeq.getConstArray()[n] ); } else if ( rType == ::getCppuType((const ::com::sun::star::uno::Sequence*)0 ) ) { ::com::sun::star::uno::Sequence aSeq; rValue >>= aSeq; long nEntries = aSeq.getLength(); OutStream->writeLong( nEntries ); for ( long n = 0; n < nEntries; n++ ) OutStream->writeShort( aSeq.getConstArray()[n] ); } else if ( rType == ::getCppuType((const ::com::sun::star::uno::Sequence*)0 ) ) { ::com::sun::star::uno::Sequence aSeq; rValue >>= aSeq; long nEntries = aSeq.getLength(); OutStream->writeLong( nEntries ); for ( long n = 0; n < nEntries; n++ ) OutStream->writeShort( aSeq.getConstArray()[n] ); } else if ( rType.getTypeClass() == TypeClass_ENUM ) { sal_Int32 nAsInt = 0; ::cppu::enum2int( nAsInt, rValue ); OutStream->writeLong( nAsInt ); } #if OSL_DEBUG_LEVEL > 0 else { ::rtl::OString sMessage( "UnoControlModel::write: don't know how to handle a property of type '" ); ::rtl::OUString sTypeName( rType.getTypeName() ); sMessage += ::rtl::OString( sTypeName.getStr(), sTypeName.getLength(), RTL_TEXTENCODING_ASCII_US ); sMessage += "'.\n(Currently handling property '"; ::rtl::OUString sPropertyName( GetPropertyName( pProp->GetId() ) ); sMessage += ::rtl::OString( sPropertyName.getStr(), sPropertyName.getLength(), osl_getThreadTextEncoding() ); sMessage += "'.)"; DBG_ERROR( sMessage ); } #endif } sal_Int32 nPropDataLen = xMark->offsetToMark( nPropDataBeginMark ); xMark->jumpToMark( nPropDataBeginMark ); OutStream->writeLong( nPropDataLen ); xMark->jumpToFurthest(); xMark->deleteMark(nPropDataBeginMark); } ImplControlProperty* pProp = aProps.Get( BASEPROPERTY_FONTDESCRIPTOR ); if ( pProp ) { // Solange wir keinen 5.0-Export haben, muss das alte // Format mit rausgeschrieben werden... ::com::sun::star::awt::FontDescriptor aFD; pProp->GetValue() >>= aFD; for ( sal_uInt16 n = BASEPROPERTY_FONT_TYPE; n <= BASEPROPERTY_FONT_ATTRIBS; n++ ) { sal_Int32 nPropDataBeginMark = xMark->createMark(); OutStream->writeLong( 0L ); // DataLen OutStream->writeShort( n ); // PropId OutStream->writeBoolean( sal_False ); // Void if ( n == BASEPROPERTY_FONT_TYPE ) { OutStream->writeUTF( aFD.Name ); OutStream->writeUTF( aFD.StyleName ); OutStream->writeShort( aFD.Family ); OutStream->writeShort( aFD.CharSet ); OutStream->writeShort( aFD.Pitch ); } else if ( n == BASEPROPERTY_FONT_SIZE ) { OutStream->writeLong( aFD.Width ); OutStream->writeLong( aFD.Height ); OutStream->writeShort( sal::static_int_cast< sal_Int16 >( VCLUnoHelper::ConvertFontWidth( aFD.CharacterWidth )) ); } else if ( n == BASEPROPERTY_FONT_ATTRIBS ) { OutStream->writeShort( sal::static_int_cast< sal_Int16 >( VCLUnoHelper::ConvertFontWeight( aFD.Weight )) ); OutStream->writeShort( sal::static_int_cast< sal_Int16 >(aFD.Slant) ); OutStream->writeShort( aFD.Underline ); OutStream->writeShort( aFD.Strikeout ); OutStream->writeShort( (short)(aFD.Orientation * 10) ); OutStream->writeBoolean( aFD.Kerning ); OutStream->writeBoolean( aFD.WordLineMode ); } else { DBG_ERROR( "Property?!" ); } sal_Int32 nPropDataLen = xMark->offsetToMark( nPropDataBeginMark ); xMark->jumpToMark( nPropDataBeginMark ); OutStream->writeLong( nPropDataLen ); xMark->jumpToFurthest(); xMark->deleteMark(nPropDataBeginMark); } } } void UnoControlModel::read( const ::com::sun::star::uno::Reference< ::com::sun::star::io::XObjectInputStream >& InStream ) throw(::com::sun::star::io::IOException, ::com::sun::star::uno::RuntimeException) { ::osl::Guard< ::osl::Mutex > aGuard( GetMutex() ); ::com::sun::star::uno::Reference< ::com::sun::star::io::XMarkableStream > xMark( InStream, ::com::sun::star::uno::UNO_QUERY ); DBG_ASSERT( xMark.is(), "read: no ::com::sun::star::io::XMarkableStream!" ); short nVersion = InStream->readShort(); sal_uInt32 nProps = (sal_uInt32)InStream->readLong(); ::com::sun::star::uno::Sequence< ::rtl::OUString> aProps( nProps ); ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Any> aValues( nProps ); sal_Bool bInvalidEntries = sal_False; // Dummerweise kein Mark fuer den gesamten Block, es koennen also // nur Properties geaendert werden, es koennen aber nicht spaeter mal Daten // fuer das Model hinter den Properties geschrieben werden. // Fuer den Import der alten ::com::sun::star::awt::FontDescriptor-Teile ::com::sun::star::awt::FontDescriptor* pFD = NULL; sal_uInt32 i; for ( i = 0; i < nProps; i++ ) { sal_Int32 nPropDataBeginMark = xMark->createMark(); sal_Int32 nPropDataLen = InStream->readLong(); sal_uInt16 nPropId = (sal_uInt16)InStream->readShort(); ::com::sun::star::uno::Any aValue; sal_Bool bIsVoid = InStream->readBoolean(); if ( !bIsVoid ) { const ::com::sun::star::uno::Type* pType = mpData->Get( nPropId ) ? GetPropertyType( nPropId ) : NULL; if ( pType ) { if ( *pType == ::getBooleanCppuType() ) { sal_Bool b = InStream->readBoolean(); aValue <<= b; } else if ( *pType == ::getCppuType((const ::rtl::OUString*)0) ) { ::rtl::OUString aUTF = InStream->readUTF(); aValue <<= aUTF; } else if ( *pType == ::getCppuType((const sal_uInt16*)0) ) { sal_uInt16 n = InStream->readShort(); aValue <<= n; } else if ( *pType == ::getCppuType((const sal_Int16*)0) ) { sal_Int16 n = InStream->readShort(); aValue <<= n; } else if ( *pType == ::getCppuType((const sal_uInt32*)0) ) { sal_uInt32 n = InStream->readLong(); aValue <<= n; } else if ( *pType == ::getCppuType((const sal_Int32*)0) ) { sal_Int32 n = InStream->readLong(); aValue <<= n; } else if ( *pType == ::getCppuType((const double*)0) ) { double n = InStream->readDouble(); aValue <<= n; } else if ( *pType == ::getCppuType((const ::com::sun::star::awt::FontDescriptor*)0) ) { ::com::sun::star::awt::FontDescriptor aFD; aFD.Name = InStream->readUTF(); aFD.Height = InStream->readShort(); aFD.Width = InStream->readShort(); aFD.StyleName = InStream->readUTF(); aFD.Family = InStream->readShort(); aFD.CharSet = InStream->readShort(); aFD.Pitch = InStream->readShort(); aFD.CharacterWidth = (float)InStream->readDouble(); aFD.Weight = (float)InStream->readDouble(); aFD.Slant = (::com::sun::star::awt::FontSlant)InStream->readShort(); aFD.Underline = InStream->readShort(); aFD.Strikeout = InStream->readShort(); aFD.Orientation = (float)InStream->readDouble(); aFD.Kerning = InStream->readBoolean(); aFD.WordLineMode = InStream->readBoolean(); aFD.Type = InStream->readShort(); aValue <<= aFD; } else if ( *pType == ::getCppuType((const ::com::sun::star::uno::Sequence< ::rtl::OUString>*)0 ) ) { long nEntries = InStream->readLong(); ::com::sun::star::uno::Sequence< ::rtl::OUString> aSeq( nEntries ); for ( long n = 0; n < nEntries; n++ ) aSeq.getArray()[n] = InStream->readUTF(); aValue <<= aSeq; } else if ( *pType == ::getCppuType((const ::com::sun::star::uno::Sequence*)0 ) ) { long nEntries = InStream->readLong(); ::com::sun::star::uno::Sequence aSeq( nEntries ); for ( long n = 0; n < nEntries; n++ ) aSeq.getArray()[n] = (sal_uInt16)InStream->readShort(); aValue <<= aSeq; } else if ( *pType == ::getCppuType((const ::com::sun::star::uno::Sequence*)0 ) ) { long nEntries = InStream->readLong(); ::com::sun::star::uno::Sequence aSeq( nEntries ); for ( long n = 0; n < nEntries; n++ ) aSeq.getArray()[n] = (sal_Int16)InStream->readShort(); aValue <<= aSeq; } else if ( pType->getTypeClass() == TypeClass_ENUM ) { sal_Int32 nAsInt = InStream->readLong(); aValue = ::cppu::int2enum( nAsInt, *pType ); } else { ::rtl::OString sMessage( "UnoControlModel::read: don't know how to handle a property of type '" ); ::rtl::OUString sTypeName( pType->getTypeName() ); sMessage += ::rtl::OString( sTypeName.getStr(), sTypeName.getLength(), RTL_TEXTENCODING_ASCII_US ); sMessage += "'.\n(Currently handling property '"; ::rtl::OUString sPropertyName( GetPropertyName( nPropId ) ); sMessage += ::rtl::OString( sPropertyName.getStr(), sPropertyName.getLength(), osl_getThreadTextEncoding() ); sMessage += "'.)"; DBG_ERROR( sMessage ); } } else { // Altes Geraffel aus 5.0 if ( nPropId == BASEPROPERTY_FONT_TYPE ) { // Sonst ist es nur die redundante Info fuer alte Versionen // Daten werden durch MarkableStream geskippt. if ( nVersion < 2 ) { if ( !pFD ) { pFD = new ::com::sun::star::awt::FontDescriptor; ImplControlProperty* pProp = mpData->Get( BASEPROPERTY_FONTDESCRIPTOR ); if ( pProp ) // wegen den Defaults... pProp->GetValue() >>= *pFD; } pFD->Name = InStream->readUTF(); pFD->StyleName = InStream->readUTF(); pFD->Family = InStream->readShort(); pFD->CharSet = InStream->readShort(); pFD->Pitch = InStream->readShort(); } } else if ( nPropId == BASEPROPERTY_FONT_SIZE ) { if ( nVersion < 2 ) { if ( !pFD ) { pFD = new ::com::sun::star::awt::FontDescriptor; ImplControlProperty* pProp = mpData->Get( BASEPROPERTY_FONTDESCRIPTOR ); if ( pProp ) // wegen den Defaults... pProp->GetValue() >>= *pFD; } pFD->Width = (sal_Int16)InStream->readLong(); pFD->Height = (sal_Int16)InStream->readLong(); InStream->readShort(); // ::com::sun::star::awt::FontWidth ignorieren - wurde mal falsch geschrieben und wird nicht gebraucht. pFD->CharacterWidth = ::com::sun::star::awt::FontWidth::DONTKNOW; } } else if ( nPropId == BASEPROPERTY_FONT_ATTRIBS ) { if ( nVersion < 2 ) { if ( !pFD ) { pFD = new ::com::sun::star::awt::FontDescriptor; ImplControlProperty* pProp = mpData->Get( BASEPROPERTY_FONTDESCRIPTOR ); if ( pProp ) // wegen den Defaults... pProp->GetValue() >>= *pFD; } pFD->Weight = VCLUnoHelper::ConvertFontWeight( (FontWeight) InStream->readShort() ); pFD->Slant = (::com::sun::star::awt::FontSlant)InStream->readShort(); pFD->Underline = InStream->readShort(); pFD->Strikeout = InStream->readShort(); pFD->Orientation = ( (float)(double)InStream->readShort() ) / 10; pFD->Kerning = InStream->readBoolean(); pFD->WordLineMode = InStream->readBoolean(); } } else { DBG_ERROR( "read: unknown Property!" ); } } } else // bVoid { if ( nPropId == BASEPROPERTY_FONTDESCRIPTOR ) { EmptyFontDescriptor aFD; aValue <<= aFD; } } if ( mpData->Get( nPropId ) ) { aProps.getArray()[i] = GetPropertyName( nPropId ); aValues.getArray()[i] = aValue; } else { bInvalidEntries = sal_True; } // Falls bereits mehr drinsteht als diese Version kennt: xMark->jumpToMark( nPropDataBeginMark ); InStream->skipBytes( nPropDataLen ); xMark->deleteMark(nPropDataBeginMark); } if ( bInvalidEntries ) { for ( i = 0; i < (sal_uInt32)aProps.getLength(); i++ ) { if ( !aProps.getConstArray()[i].getLength() ) { ::comphelper::removeElementAt( aProps, i ); ::comphelper::removeElementAt( aValues, i ); i--; } } } try { setPropertyValues( aProps, aValues ); } catch ( const Exception& ) { DBG_UNHANDLED_EXCEPTION(); } if ( pFD ) { ::com::sun::star::uno::Any aValue; aValue <<= *pFD; setPropertyValue( GetPropertyName( BASEPROPERTY_FONTDESCRIPTOR ), aValue ); delete pFD; } } // ::com::sun::star::lang::XServiceInfo ::rtl::OUString UnoControlModel::getImplementationName( ) throw(::com::sun::star::uno::RuntimeException) { DBG_ERROR( "This method should be overloaded!" ); return ::rtl::OUString(); } sal_Bool UnoControlModel::supportsService( const ::rtl::OUString& rServiceName ) throw(::com::sun::star::uno::RuntimeException) { ::osl::Guard< ::osl::Mutex > aGuard( GetMutex() ); ::com::sun::star::uno::Sequence< ::rtl::OUString > aSNL = getSupportedServiceNames(); const ::rtl::OUString * pArray = aSNL.getConstArray(); for( sal_Int32 i = 0; i < aSNL.getLength(); i++ ) if( pArray[i] == rServiceName ) return sal_True; return sal_False; } ::com::sun::star::uno::Sequence< ::rtl::OUString > UnoControlModel::getSupportedServiceNames( ) throw(::com::sun::star::uno::RuntimeException) { ::rtl::OUString sName( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.awt.UnoControlModel" ) ); return Sequence< ::rtl::OUString >( &sName, 1 ); } // ::cppu::OPropertySetHelper ::cppu::IPropertyArrayHelper& UnoControlModel::getInfoHelper() { DBG_ERROR( "UnoControlModel::getInfoHelper() not possible!" ); return *(::cppu::IPropertyArrayHelper*) NULL; } // ------------------------------------------------------------------ template sal_Bool convertType(Any& _rConvertedValue, const Any& _rNewValueTest, const TYPE* /* _pTypeDisambiguation */) { TYPE tValue; if (_rNewValueTest >>= tValue) { _rConvertedValue <<= tValue; return sal_True; } } // .................................................................. sal_Bool UnoControlModel::convertFastPropertyValue( Any & rConvertedValue, Any & rOldValue, sal_Int32 nPropId, const Any& rValue ) throw (IllegalArgumentException) { ::osl::Guard< ::osl::Mutex > aGuard( GetMutex() ); sal_Bool bVoid = rValue.getValueType().getTypeClass() == ::com::sun::star::uno::TypeClass_VOID; if ( bVoid ) { rConvertedValue.clear(); } else { const ::com::sun::star::uno::Type* pDestType = GetPropertyType( (sal_uInt16)nPropId ); if ( pDestType->getTypeClass() == TypeClass_ANY ) { rConvertedValue = rValue; } else { if ( pDestType->equals( rValue.getValueType() ) ) { rConvertedValue = rValue; } else { sal_Bool bConverted = sal_False; // 13.03.2001 - 84923 - frank.schoenheit@germany.sun.com switch (pDestType->getTypeClass()) { case TypeClass_DOUBLE: { // try as double double nAsDouble = 0; bConverted = ( rValue >>= nAsDouble ); if ( bConverted ) rConvertedValue <<= nAsDouble; else { // try as integer - 96136 - 2002-10-08 - fs@openoffice.org sal_Int32 nAsInteger = 0; bConverted = ( rValue >>= nAsInteger ); if ( bConverted ) rConvertedValue <<= (double)nAsInteger; } } break; case TypeClass_SHORT: { sal_Int16 n; bConverted = ( rValue >>= n ); if ( bConverted ) rConvertedValue <<= n; } break; case TypeClass_UNSIGNED_SHORT: { sal_uInt16 n; bConverted = ( rValue >>= n ); if ( bConverted ) rConvertedValue <<= n; } break; case TypeClass_LONG: { sal_Int32 n; bConverted = ( rValue >>= n ); if ( bConverted ) rConvertedValue <<= n; } break; case TypeClass_UNSIGNED_LONG: { sal_uInt32 n; bConverted = ( rValue >>= n ); if ( bConverted ) rConvertedValue <<= n; } break; case TypeClass_INTERFACE: { if ( rValue.getValueType().getTypeClass() == TypeClass_INTERFACE ) { Reference< XInterface > xPure( rValue, UNO_QUERY ); if ( xPure.is() ) rConvertedValue = xPure->queryInterface( *pDestType ); else rConvertedValue.setValue( NULL, *pDestType ); bConverted = sal_True; } } break; case TypeClass_ENUM: { sal_Int32 nValue = 0; bConverted = ( rValue >>= nValue ); if ( bConverted ) rConvertedValue = ::cppu::int2enum( nValue, *pDestType ); } break; default: ; // avoid compiler warning } if (!bConverted) { ::rtl::OUStringBuffer aErrorMessage; aErrorMessage.appendAscii( "Unable to convert the given value for the property " ); aErrorMessage.append ( GetPropertyName( (sal_uInt16)nPropId ) ); aErrorMessage.appendAscii( ".\n" ); aErrorMessage.appendAscii( "Expected type: " ); aErrorMessage.append ( pDestType->getTypeName() ); aErrorMessage.appendAscii( "\n" ); aErrorMessage.appendAscii( "Found type: " ); aErrorMessage.append ( rValue.getValueType().getTypeName() ); throw ::com::sun::star::lang::IllegalArgumentException( aErrorMessage.makeStringAndClear(), static_cast< ::com::sun::star::beans::XPropertySet* >(this), 1); } } } } // the current value getFastPropertyValue( rOldValue, nPropId ); return !CompareProperties( rConvertedValue, rOldValue ); } void UnoControlModel::setFastPropertyValue_NoBroadcast( sal_Int32 nPropId, const ::com::sun::star::uno::Any& rValue ) throw (::com::sun::star::uno::Exception) { // Fehlt: Die gefakten Einzelproperties des FontDescriptors... ImplControlProperty* pProp = mpData->Get( nPropId ); ENSURE_OR_RETURN_VOID( pProp, "UnoControlModel::setFastPropertyValue_NoBroadcast: invalid property id!" ); DBG_ASSERT( ( rValue.getValueType().getTypeClass() != ::com::sun::star::uno::TypeClass_VOID ) || ( GetPropertyAttribs( (sal_uInt16)nPropId ) & ::com::sun::star::beans::PropertyAttribute::MAYBEVOID ), "Property darf nicht VOID sein!" ); pProp->SetValue( rValue ); } void UnoControlModel::getFastPropertyValue( ::com::sun::star::uno::Any& rValue, sal_Int32 nPropId ) const { ::osl::Guard< ::osl::Mutex > aGuard( ((UnoControlModel*)this)->GetMutex() ); ImplControlProperty* pProp = mpData->Get( nPropId ); if ( pProp ) rValue = pProp->GetValue(); else if ( ( nPropId >= BASEPROPERTY_FONTDESCRIPTORPART_START ) && ( nPropId <= BASEPROPERTY_FONTDESCRIPTORPART_END ) ) { pProp = mpData->Get( BASEPROPERTY_FONTDESCRIPTOR ); ::com::sun::star::awt::FontDescriptor aFD; pProp->GetValue() >>= aFD; switch ( nPropId ) { case BASEPROPERTY_FONTDESCRIPTORPART_NAME: rValue <<= aFD.Name; break; case BASEPROPERTY_FONTDESCRIPTORPART_STYLENAME: rValue <<= aFD.StyleName; break; case BASEPROPERTY_FONTDESCRIPTORPART_FAMILY: rValue <<= aFD.Family; break; case BASEPROPERTY_FONTDESCRIPTORPART_CHARSET: rValue <<= aFD.CharSet; break; case BASEPROPERTY_FONTDESCRIPTORPART_HEIGHT: rValue <<= (float)aFD.Height; break; case BASEPROPERTY_FONTDESCRIPTORPART_WEIGHT: rValue <<= aFD.Weight; break; case BASEPROPERTY_FONTDESCRIPTORPART_SLANT: rValue <<= (sal_Int16)aFD.Slant; break; case BASEPROPERTY_FONTDESCRIPTORPART_UNDERLINE: rValue <<= aFD.Underline; break; case BASEPROPERTY_FONTDESCRIPTORPART_STRIKEOUT: rValue <<= aFD.Strikeout; break; case BASEPROPERTY_FONTDESCRIPTORPART_WIDTH: rValue <<= aFD.Width; break; case BASEPROPERTY_FONTDESCRIPTORPART_PITCH: rValue <<= aFD.Pitch; break; case BASEPROPERTY_FONTDESCRIPTORPART_CHARWIDTH: rValue <<= aFD.CharacterWidth; break; case BASEPROPERTY_FONTDESCRIPTORPART_ORIENTATION: rValue <<= aFD.Orientation; break; case BASEPROPERTY_FONTDESCRIPTORPART_KERNING: rValue <<= aFD.Kerning; break; case BASEPROPERTY_FONTDESCRIPTORPART_WORDLINEMODE: rValue <<= aFD.WordLineMode; break; case BASEPROPERTY_FONTDESCRIPTORPART_TYPE: rValue <<= aFD.Type; break; default: DBG_ERROR( "FontProperty?!" ); } } else { DBG_ERROR( "getFastPropertyValue - invalid Property!" ); } } // ::com::sun::star::beans::XPropertySet void UnoControlModel::setPropertyValue( const ::rtl::OUString& rPropertyName, const ::com::sun::star::uno::Any& rValue ) throw(::com::sun::star::beans::UnknownPropertyException, ::com::sun::star::beans::PropertyVetoException, ::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::lang::WrappedTargetException, ::com::sun::star::uno::RuntimeException) { sal_Int32 nPropId = 0; { ::osl::Guard< ::osl::Mutex > aGuard( GetMutex() ); nPropId = (sal_Int32) GetPropertyId( rPropertyName ); DBG_ASSERT( nPropId, "Invalid ID in UnoControlModel::setPropertyValue" ); } if( nPropId ) setFastPropertyValue( nPropId, rValue ); else throw ::com::sun::star::beans::UnknownPropertyException(); } // ::com::sun::star::beans::XFastPropertySet void UnoControlModel::setFastPropertyValue( sal_Int32 nPropId, const ::com::sun::star::uno::Any& rValue ) throw(::com::sun::star::beans::UnknownPropertyException, ::com::sun::star::beans::PropertyVetoException, ::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::lang::WrappedTargetException, ::com::sun::star::uno::RuntimeException) { if ( ( nPropId >= BASEPROPERTY_FONTDESCRIPTORPART_START ) && ( nPropId <= BASEPROPERTY_FONTDESCRIPTORPART_END ) ) { ::osl::ClearableMutexGuard aGuard( GetMutex() ); Any aOldSingleValue; getFastPropertyValue( aOldSingleValue, BASEPROPERTY_FONTDESCRIPTORPART_START ); ImplControlProperty* pProp = mpData->Get( BASEPROPERTY_FONTDESCRIPTOR ); FontDescriptor aOldFontDescriptor; pProp->GetValue() >>= aOldFontDescriptor; FontDescriptor aNewFontDescriptor( aOldFontDescriptor ); lcl_ImplMergeFontProperty( aNewFontDescriptor, (sal_uInt16)nPropId, rValue ); Any aNewValue; aNewValue <<= aNewFontDescriptor; sal_Int32 nDescriptorId( BASEPROPERTY_FONTDESCRIPTOR ); nDescriptorId = BASEPROPERTY_FONTDESCRIPTOR; // also, we need fire a propertyChange event for the single property, since with // the above line, only an event for the FontDescriptor property will be fired Any aNewSingleValue; getFastPropertyValue( aNewSingleValue, BASEPROPERTY_FONTDESCRIPTORPART_START ); aGuard.clear(); setFastPropertyValues( 1, &nDescriptorId, &aNewValue, 1 ); fire( &nPropId, &aNewSingleValue, &aOldSingleValue, 1, sal_False ); } else setFastPropertyValues( 1, &nPropId, &rValue, 1 ); } // ::com::sun::star::beans::XMultiPropertySet ::com::sun::star::uno::Reference< ::com::sun::star::beans::XPropertySetInfo > UnoControlModel::getPropertySetInfo( ) throw(::com::sun::star::uno::RuntimeException) { DBG_ERROR( "UnoControlModel::getPropertySetInfo() not possible!" ); return ::com::sun::star::uno::Reference< ::com::sun::star::beans::XPropertySetInfo >(); } void UnoControlModel::setPropertyValues( const ::com::sun::star::uno::Sequence< ::rtl::OUString >& rPropertyNames, const ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Any >& Values ) throw(::com::sun::star::beans::PropertyVetoException, ::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::lang::WrappedTargetException, ::com::sun::star::uno::RuntimeException) { ::osl::ClearableMutexGuard aGuard( GetMutex() ); sal_Int32 nProps = rPropertyNames.getLength(); // sal_Int32* pHandles = new sal_Int32[nProps]; // don't do this - it leaks in case of an exception Sequence< sal_Int32 > aHandles( nProps ); sal_Int32* pHandles = aHandles.getArray(); // may need to change the order in the sequence, for this we need a non-const value sequence // 15.05.2002 - 99314 - fs@openoffice.org uno::Sequence< uno::Any > aValues( Values ); uno::Any* pValues = aValues.getArray(); sal_Int32 nValidHandles = getInfoHelper().fillHandles( pHandles, rPropertyNames ); if ( nValidHandles ) { // if somebody sets properties which are single aspects of a font descriptor, // remove them, and build a font descriptor instead ::std::auto_ptr< awt::FontDescriptor > pFD; for ( sal_uInt16 n = 0; n < nProps; ++n ) { if ( ( pHandles[n] >= BASEPROPERTY_FONTDESCRIPTORPART_START ) && ( pHandles[n] <= BASEPROPERTY_FONTDESCRIPTORPART_END ) ) { if ( !pFD.get() ) { ImplControlProperty* pProp = mpData->Get( BASEPROPERTY_FONTDESCRIPTOR ); pFD.reset( new awt::FontDescriptor ); pProp->GetValue() >>= *pFD; } lcl_ImplMergeFontProperty( *pFD, (sal_uInt16)pHandles[n], pValues[n] ); pHandles[n] = -1; nValidHandles--; } } if ( nValidHandles ) { ImplNormalizePropertySequence( nProps, pHandles, pValues, &nValidHandles ); aGuard.clear(); // clear our guard before calling into setFastPropertyValues - this method // will implicitly call property listeners, and this should not happen with // our mutex locked // #i23451# - 2004-03-18 - fs@openoffice.org setFastPropertyValues( nProps, pHandles, pValues, nValidHandles ); } else aGuard.clear(); // same as a few lines above // FD-Propertie nicht in das Array mergen, weil sortiert... if ( pFD.get() ) { ::com::sun::star::uno::Any aValue; aValue <<= *pFD; sal_Int32 nHandle = BASEPROPERTY_FONTDESCRIPTOR; setFastPropertyValues( 1, &nHandle, &aValue, 1 ); } } } void UnoControlModel::ImplNormalizePropertySequence( const sal_Int32, sal_Int32*, uno::Any*, sal_Int32* ) const SAL_THROW(()) { // nothing to do here } void UnoControlModel::ImplEnsureHandleOrder( const sal_Int32 _nCount, sal_Int32* _pHandles, uno::Any* _pValues, sal_Int32 _nFirstHandle, sal_Int32 _nSecondHandle ) const { for ( sal_Int32 i=0; i < _nCount; ++_pHandles, ++_pValues, ++i ) { if ( _nSecondHandle == *_pHandles ) { sal_Int32* pLaterHandles = _pHandles + 1; uno::Any* pLaterValues = _pValues + 1; for ( sal_Int32 j = i + 1; j < _nCount; ++j, ++pLaterHandles, ++pLaterValues ) { if ( _nFirstHandle == *pLaterHandles ) { // indeed it is -> exchange the both places in the sequences sal_Int32 nHandle( *_pHandles ); *_pHandles = *pLaterHandles; *pLaterHandles = nHandle; uno::Any aValue( *_pValues ); *_pValues = *pLaterValues; *pLaterValues = aValue; break; // this will leave the inner loop, and continue with the outer loop. // Note that this means we will encounter the _nSecondHandle handle, again, once we reached // (in the outer loop) the place where we just put it. } } } } }