124acc546SAndrew Rist /************************************************************** 2cdf0e10cSrcweir * 324acc546SAndrew Rist * Licensed to the Apache Software Foundation (ASF) under one 424acc546SAndrew Rist * or more contributor license agreements. See the NOTICE file 524acc546SAndrew Rist * distributed with this work for additional information 624acc546SAndrew Rist * regarding copyright ownership. The ASF licenses this file 724acc546SAndrew Rist * to you under the Apache License, Version 2.0 (the 824acc546SAndrew Rist * "License"); you may not use this file except in compliance 924acc546SAndrew Rist * with the License. You may obtain a copy of the License at 1024acc546SAndrew Rist * 1124acc546SAndrew Rist * http://www.apache.org/licenses/LICENSE-2.0 1224acc546SAndrew Rist * 1324acc546SAndrew Rist * Unless required by applicable law or agreed to in writing, 1424acc546SAndrew Rist * software distributed under the License is distributed on an 1524acc546SAndrew Rist * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 1624acc546SAndrew Rist * KIND, either express or implied. See the License for the 1724acc546SAndrew Rist * specific language governing permissions and limitations 1824acc546SAndrew Rist * under the License. 1924acc546SAndrew Rist * 2024acc546SAndrew Rist *************************************************************/ 2124acc546SAndrew Rist 2224acc546SAndrew Rist 23cdf0e10cSrcweir 24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove 25cdf0e10cSrcweir #include "precompiled_forms.hxx" 26cdf0e10cSrcweir 27cdf0e10cSrcweir #include "componenttools.hxx" 28cdf0e10cSrcweir #include "FormComponent.hxx" 29cdf0e10cSrcweir #include "frm_resource.hrc" 30cdf0e10cSrcweir #include "frm_resource.hxx" 31cdf0e10cSrcweir #include "property.hrc" 32cdf0e10cSrcweir #include "services.hxx" 33cdf0e10cSrcweir 34cdf0e10cSrcweir /** === begin UNO includes === **/ 35cdf0e10cSrcweir #include <com/sun/star/awt/XTextComponent.hpp> 36cdf0e10cSrcweir #include <com/sun/star/awt/XVclWindowPeer.hpp> 37cdf0e10cSrcweir #include <com/sun/star/awt/XWindow.hpp> 38cdf0e10cSrcweir #include <com/sun/star/form/XForm.hpp> 39cdf0e10cSrcweir #include <com/sun/star/form/XLoadable.hpp> 40cdf0e10cSrcweir #include <com/sun/star/io/XMarkableStream.hpp> 41cdf0e10cSrcweir #include <com/sun/star/lang/DisposedException.hpp> 42cdf0e10cSrcweir #include <com/sun/star/sdb/XRowSetChangeBroadcaster.hpp> 43cdf0e10cSrcweir #include <com/sun/star/sdb/XRowSetSupplier.hpp> 44cdf0e10cSrcweir #include <com/sun/star/sdbc/ColumnValue.hpp> 45cdf0e10cSrcweir #include <com/sun/star/sdbc/DataType.hpp> 46cdf0e10cSrcweir #include <com/sun/star/util/XModifyBroadcaster.hpp> 47cdf0e10cSrcweir /** === end UNO includes === **/ 48cdf0e10cSrcweir 49cdf0e10cSrcweir #include <comphelper/basicio.hxx> 50cdf0e10cSrcweir #include <comphelper/guarding.hxx> 51cdf0e10cSrcweir #include <comphelper/listenernotification.hxx> 52cdf0e10cSrcweir #include <comphelper/property.hxx> 53cdf0e10cSrcweir #include <connectivity/dbtools.hxx> 54cdf0e10cSrcweir #include <cppuhelper/queryinterface.hxx> 55cdf0e10cSrcweir #include <rtl/logfile.hxx> 56cdf0e10cSrcweir #include <toolkit/helper/emptyfontdescriptor.hxx> 57cdf0e10cSrcweir #include <tools/debug.hxx> 58cdf0e10cSrcweir #include <tools/diagnose_ex.h> 59cdf0e10cSrcweir 60cdf0e10cSrcweir #include <functional> 61cdf0e10cSrcweir #include <algorithm> 62cdf0e10cSrcweir 63cdf0e10cSrcweir #include <functional> 64cdf0e10cSrcweir #include <algorithm> 65cdf0e10cSrcweir 66cdf0e10cSrcweir 67cdf0e10cSrcweir //... namespace frm ....................................................... 68cdf0e10cSrcweir namespace frm 69cdf0e10cSrcweir { 70cdf0e10cSrcweir //......................................................................... 71cdf0e10cSrcweir 72cdf0e10cSrcweir using namespace ::com::sun::star::uno; 73cdf0e10cSrcweir using namespace ::com::sun::star::sdb; 74cdf0e10cSrcweir using namespace ::com::sun::star::sdbc; 75cdf0e10cSrcweir using namespace ::com::sun::star::sdbcx; 76cdf0e10cSrcweir using namespace ::com::sun::star::beans; 77cdf0e10cSrcweir using namespace ::com::sun::star::container; 78cdf0e10cSrcweir using namespace ::com::sun::star::form; 79cdf0e10cSrcweir using namespace ::com::sun::star::awt; 80cdf0e10cSrcweir using namespace ::com::sun::star::io; 81cdf0e10cSrcweir using namespace ::com::sun::star::lang; 82cdf0e10cSrcweir using namespace ::com::sun::star::util; 83cdf0e10cSrcweir using namespace ::com::sun::star::form::binding; 84cdf0e10cSrcweir using namespace ::com::sun::star::form::validation; 85cdf0e10cSrcweir using namespace ::dbtools; 86cdf0e10cSrcweir using namespace ::comphelper; 87cdf0e10cSrcweir 88cdf0e10cSrcweir //========================================================================= 89cdf0e10cSrcweir //= FieldChangeNotifier 90cdf0e10cSrcweir //========================================================================= 91cdf0e10cSrcweir //------------------------------------------------------------------------- 92cdf0e10cSrcweir void ControlModelLock::impl_notifyAll_nothrow() 93cdf0e10cSrcweir { 94cdf0e10cSrcweir m_rModel.firePropertyChanges( m_aHandles, m_aOldValues, m_aNewValues, OControlModel::LockAccess() ); 95cdf0e10cSrcweir } 96cdf0e10cSrcweir 97cdf0e10cSrcweir //------------------------------------------------------------------------- 98cdf0e10cSrcweir void ControlModelLock::addPropertyNotification( const sal_Int32 _nHandle, const Any& _rOldValue, const Any& _rNewValue ) 99cdf0e10cSrcweir { 100cdf0e10cSrcweir sal_Int32 nOldLength = m_aHandles.getLength(); 101cdf0e10cSrcweir if ( ( nOldLength != m_aOldValues.getLength() ) 102cdf0e10cSrcweir || ( nOldLength != m_aNewValues.getLength() ) 103cdf0e10cSrcweir ) 104cdf0e10cSrcweir throw RuntimeException( ::rtl::OUString(), m_rModel ); 105cdf0e10cSrcweir 106cdf0e10cSrcweir m_aHandles.realloc( nOldLength + 1 ); 107cdf0e10cSrcweir m_aHandles[ nOldLength ] = _nHandle; 108cdf0e10cSrcweir m_aOldValues.realloc( nOldLength + 1 ); 109cdf0e10cSrcweir m_aOldValues[ nOldLength ] = _rOldValue; 110cdf0e10cSrcweir m_aNewValues.realloc( nOldLength + 1 ); 111cdf0e10cSrcweir m_aNewValues[ nOldLength ] = _rNewValue; 112cdf0e10cSrcweir } 113cdf0e10cSrcweir 114cdf0e10cSrcweir //========================================================================= 115cdf0e10cSrcweir //= FieldChangeNotifier 116cdf0e10cSrcweir //========================================================================= 117cdf0e10cSrcweir //------------------------------------------------------------------------- 118cdf0e10cSrcweir class FieldChangeNotifier 119cdf0e10cSrcweir { 120cdf0e10cSrcweir public: 121cdf0e10cSrcweir FieldChangeNotifier( ControlModelLock& _rLock ) 122cdf0e10cSrcweir :m_rLock( _rLock ) 123cdf0e10cSrcweir ,m_rModel( dynamic_cast< OBoundControlModel& >( _rLock.getModel() ) ) 124cdf0e10cSrcweir { 125cdf0e10cSrcweir m_xOldField = m_rModel.getField(); 126cdf0e10cSrcweir } 127cdf0e10cSrcweir 128cdf0e10cSrcweir ~FieldChangeNotifier() 129cdf0e10cSrcweir { 130cdf0e10cSrcweir Reference< XPropertySet > xNewField( m_rModel.getField() ); 131cdf0e10cSrcweir if ( m_xOldField != xNewField ) 132cdf0e10cSrcweir m_rLock.addPropertyNotification( PROPERTY_ID_BOUNDFIELD, makeAny( m_xOldField ), makeAny( xNewField ) ); 133cdf0e10cSrcweir } 134cdf0e10cSrcweir 135cdf0e10cSrcweir private: 136cdf0e10cSrcweir ControlModelLock& m_rLock; 137cdf0e10cSrcweir OBoundControlModel& m_rModel; 138cdf0e10cSrcweir Reference< XPropertySet > m_xOldField; 139cdf0e10cSrcweir }; 140cdf0e10cSrcweir 141cdf0e10cSrcweir //============================================================================= 142cdf0e10cSrcweir //= base class for form layer controls 143cdf0e10cSrcweir //============================================================================= 144cdf0e10cSrcweir DBG_NAME(frm_OControl) 145cdf0e10cSrcweir //------------------------------------------------------------------------------ 146cdf0e10cSrcweir OControl::OControl( const Reference< XMultiServiceFactory >& _rxFactory, const rtl::OUString& _rAggregateService, const sal_Bool _bSetDelegator ) 147cdf0e10cSrcweir :OComponentHelper(m_aMutex) 148cdf0e10cSrcweir ,m_aContext( _rxFactory ) 149cdf0e10cSrcweir { 150cdf0e10cSrcweir DBG_CTOR(frm_OControl, NULL); 151cdf0e10cSrcweir // VCL-Control aggregieren 152cdf0e10cSrcweir // bei Aggregation den Refcount um eins erhoehen da im setDelegator 153cdf0e10cSrcweir // das Aggregat selbst den Refcount erhoeht 154cdf0e10cSrcweir increment( m_refCount ); 155cdf0e10cSrcweir { 156cdf0e10cSrcweir m_xAggregate = m_xAggregate.query( _rxFactory->createInstance( _rAggregateService ) ); 157cdf0e10cSrcweir m_xControl = m_xControl.query( m_xAggregate ); 158cdf0e10cSrcweir } 159cdf0e10cSrcweir decrement( m_refCount ); 160cdf0e10cSrcweir 161cdf0e10cSrcweir if ( _bSetDelegator ) 162cdf0e10cSrcweir doSetDelegator(); 163cdf0e10cSrcweir } 164cdf0e10cSrcweir 165cdf0e10cSrcweir //------------------------------------------------------------------------------ 166cdf0e10cSrcweir OControl::~OControl() 167cdf0e10cSrcweir { 168cdf0e10cSrcweir DBG_DTOR(frm_OControl, NULL); 169cdf0e10cSrcweir doResetDelegator(); 170cdf0e10cSrcweir } 171cdf0e10cSrcweir 172cdf0e10cSrcweir //------------------------------------------------------------------------------ 173cdf0e10cSrcweir void OControl::doResetDelegator() 174cdf0e10cSrcweir { 175cdf0e10cSrcweir if ( m_xAggregate.is() ) 176cdf0e10cSrcweir m_xAggregate->setDelegator( NULL ); 177cdf0e10cSrcweir } 178cdf0e10cSrcweir 179cdf0e10cSrcweir //------------------------------------------------------------------------------ 180cdf0e10cSrcweir void OControl::doSetDelegator() 181cdf0e10cSrcweir { 182cdf0e10cSrcweir increment( m_refCount ); 183cdf0e10cSrcweir if ( m_xAggregate.is() ) 184cdf0e10cSrcweir { // those brackets are important for some compilers, don't remove! 185cdf0e10cSrcweir // (they ensure that the temporary object created in the line below 186cdf0e10cSrcweir // is destroyed *before* the refcount-decrement) 187cdf0e10cSrcweir m_xAggregate->setDelegator( static_cast< XWeak* >( this ) ); 188cdf0e10cSrcweir } 189cdf0e10cSrcweir decrement( m_refCount ); 190cdf0e10cSrcweir } 191cdf0e10cSrcweir 192cdf0e10cSrcweir // UNO Anbindung 193cdf0e10cSrcweir //------------------------------------------------------------------------------ 194cdf0e10cSrcweir Any SAL_CALL OControl::queryAggregation( const Type& _rType ) throw(RuntimeException) 195cdf0e10cSrcweir { 196cdf0e10cSrcweir // ask the base class 197cdf0e10cSrcweir Any aReturn( OComponentHelper::queryAggregation(_rType) ); 198cdf0e10cSrcweir // ask our own interfaces 199cdf0e10cSrcweir if (!aReturn.hasValue()) 200cdf0e10cSrcweir { 201cdf0e10cSrcweir aReturn = OControl_BASE::queryInterface(_rType); 202cdf0e10cSrcweir // ask our aggregate 203cdf0e10cSrcweir if (!aReturn.hasValue() && m_xAggregate.is()) 204cdf0e10cSrcweir aReturn = m_xAggregate->queryAggregation(_rType); 205cdf0e10cSrcweir } 206cdf0e10cSrcweir 207cdf0e10cSrcweir return aReturn; 208cdf0e10cSrcweir } 209cdf0e10cSrcweir 210cdf0e10cSrcweir //------------------------------------------------------------------------------ 211cdf0e10cSrcweir Sequence<sal_Int8> SAL_CALL OControl::getImplementationId() throw(RuntimeException) 212cdf0e10cSrcweir { 213cdf0e10cSrcweir return OImplementationIds::getImplementationId(getTypes()); 214cdf0e10cSrcweir } 215cdf0e10cSrcweir 216cdf0e10cSrcweir //------------------------------------------------------------------------------ 217cdf0e10cSrcweir Sequence<Type> SAL_CALL OControl::getTypes() throw(RuntimeException) 218cdf0e10cSrcweir { 219cdf0e10cSrcweir TypeBag aTypes( _getTypes() ); 220cdf0e10cSrcweir 221cdf0e10cSrcweir Reference< XTypeProvider > xProv; 222cdf0e10cSrcweir if ( query_aggregation( m_xAggregate, xProv ) ) 223cdf0e10cSrcweir aTypes.addTypes( xProv->getTypes() ); 224cdf0e10cSrcweir 225cdf0e10cSrcweir return aTypes.getTypes(); 226cdf0e10cSrcweir } 227cdf0e10cSrcweir 228cdf0e10cSrcweir //------------------------------------------------------------------------------ 229cdf0e10cSrcweir Sequence<Type> OControl::_getTypes() 230cdf0e10cSrcweir { 231cdf0e10cSrcweir return TypeBag( OComponentHelper::getTypes(), OControl_BASE::getTypes() ).getTypes(); 232cdf0e10cSrcweir } 233cdf0e10cSrcweir 234cdf0e10cSrcweir //------------------------------------------------------------------------------ 235cdf0e10cSrcweir void OControl::initFormControlPeer( const Reference< XWindowPeer >& /*_rxPeer*/ ) 236cdf0e10cSrcweir { 237cdf0e10cSrcweir // nothing to do here 238cdf0e10cSrcweir } 239cdf0e10cSrcweir 240cdf0e10cSrcweir // OComponentHelper 241cdf0e10cSrcweir //------------------------------------------------------------------------------ 242cdf0e10cSrcweir void OControl::disposing() 243cdf0e10cSrcweir { 244cdf0e10cSrcweir OComponentHelper::disposing(); 245cdf0e10cSrcweir 246cdf0e10cSrcweir m_aWindowStateGuard.attach( NULL, NULL ); 247cdf0e10cSrcweir 248cdf0e10cSrcweir Reference< XComponent > xComp; 249cdf0e10cSrcweir if (query_aggregation(m_xAggregate, xComp)) 250cdf0e10cSrcweir xComp->dispose(); 251cdf0e10cSrcweir } 252cdf0e10cSrcweir 253cdf0e10cSrcweir // XServiceInfo 254cdf0e10cSrcweir //------------------------------------------------------------------------------ 255cdf0e10cSrcweir sal_Bool SAL_CALL OControl::supportsService(const rtl::OUString& _rsServiceName) throw ( RuntimeException) 256cdf0e10cSrcweir { 257cdf0e10cSrcweir Sequence<rtl::OUString> aSupported = getSupportedServiceNames(); 258cdf0e10cSrcweir const rtl::OUString* pSupported = aSupported.getConstArray(); 259cdf0e10cSrcweir for (sal_Int32 i=0; i<aSupported.getLength(); ++i, ++pSupported) 260cdf0e10cSrcweir if (pSupported->equals(_rsServiceName)) 261cdf0e10cSrcweir return sal_True; 262cdf0e10cSrcweir return sal_False; 263cdf0e10cSrcweir } 264cdf0e10cSrcweir 265cdf0e10cSrcweir //------------------------------------------------------------------------------ 266cdf0e10cSrcweir Sequence< ::rtl::OUString > OControl::getAggregateServiceNames() 267cdf0e10cSrcweir { 268cdf0e10cSrcweir Sequence< ::rtl::OUString > aAggServices; 269cdf0e10cSrcweir Reference< XServiceInfo > xInfo; 270cdf0e10cSrcweir if ( query_aggregation( m_xAggregate, xInfo ) ) 271cdf0e10cSrcweir aAggServices = xInfo->getSupportedServiceNames(); 272cdf0e10cSrcweir return aAggServices; 273cdf0e10cSrcweir } 274cdf0e10cSrcweir 275cdf0e10cSrcweir //------------------------------------------------------------------------------ 276cdf0e10cSrcweir Sequence<rtl::OUString> SAL_CALL OControl::getSupportedServiceNames() throw(RuntimeException) 277cdf0e10cSrcweir { 278cdf0e10cSrcweir return ::comphelper::concatSequences( 279cdf0e10cSrcweir getAggregateServiceNames(), 280cdf0e10cSrcweir getSupportedServiceNames_Static() 281cdf0e10cSrcweir ); 282cdf0e10cSrcweir } 283cdf0e10cSrcweir 284cdf0e10cSrcweir //------------------------------------------------------------------------------ 285cdf0e10cSrcweir Sequence< ::rtl::OUString > SAL_CALL OControl::getSupportedServiceNames_Static() throw( RuntimeException ) 286cdf0e10cSrcweir { 287cdf0e10cSrcweir // no own supported service names 288cdf0e10cSrcweir return Sequence< ::rtl::OUString >(); 289cdf0e10cSrcweir } 290cdf0e10cSrcweir 291cdf0e10cSrcweir // XEventListener 292cdf0e10cSrcweir //------------------------------------------------------------------------------ 293cdf0e10cSrcweir void SAL_CALL OControl::disposing(const com::sun::star::lang::EventObject& _rEvent) throw (RuntimeException) 294cdf0e10cSrcweir { 295cdf0e10cSrcweir Reference< XInterface > xAggAsIface; 296cdf0e10cSrcweir query_aggregation(m_xAggregate, xAggAsIface); 297cdf0e10cSrcweir 298cdf0e10cSrcweir // does the disposing come from the aggregate ? 299cdf0e10cSrcweir if (xAggAsIface != Reference< XInterface >(_rEvent.Source, UNO_QUERY)) 300cdf0e10cSrcweir { // no -> forward it 301cdf0e10cSrcweir Reference<com::sun::star::lang::XEventListener> xListener; 302cdf0e10cSrcweir if (query_aggregation(m_xAggregate, xListener)) 303cdf0e10cSrcweir xListener->disposing(_rEvent); 304cdf0e10cSrcweir } 305cdf0e10cSrcweir } 306cdf0e10cSrcweir 307cdf0e10cSrcweir // XControl 308cdf0e10cSrcweir //------------------------------------------------------------------------------ 309cdf0e10cSrcweir void SAL_CALL OControl::setContext(const Reference< XInterface >& Context) throw (RuntimeException) 310cdf0e10cSrcweir { 311cdf0e10cSrcweir if (m_xControl.is()) 312cdf0e10cSrcweir m_xControl->setContext(Context); 313cdf0e10cSrcweir } 314cdf0e10cSrcweir 315cdf0e10cSrcweir //------------------------------------------------------------------------------ 316cdf0e10cSrcweir Reference< XInterface > SAL_CALL OControl::getContext() throw (RuntimeException) 317cdf0e10cSrcweir { 318cdf0e10cSrcweir return m_xControl.is() ? m_xControl->getContext() : Reference< XInterface >(); 319cdf0e10cSrcweir } 320cdf0e10cSrcweir 321cdf0e10cSrcweir //------------------------------------------------------------------------------ 322cdf0e10cSrcweir void OControl::impl_resetStateGuard_nothrow() 323cdf0e10cSrcweir { 324cdf0e10cSrcweir Reference< XWindow2 > xWindow; 325cdf0e10cSrcweir Reference< XControlModel > xModel; 326cdf0e10cSrcweir try 327cdf0e10cSrcweir { 328cdf0e10cSrcweir xWindow.set( getPeer(), UNO_QUERY ); 329cdf0e10cSrcweir xModel.set( getModel(), UNO_QUERY ); 330cdf0e10cSrcweir } 331cdf0e10cSrcweir catch( const Exception& ) 332cdf0e10cSrcweir { 333cdf0e10cSrcweir DBG_UNHANDLED_EXCEPTION(); 334cdf0e10cSrcweir } 335cdf0e10cSrcweir m_aWindowStateGuard.attach( xWindow, xModel ); 336cdf0e10cSrcweir } 337cdf0e10cSrcweir 338cdf0e10cSrcweir //------------------------------------------------------------------------------ 339cdf0e10cSrcweir void SAL_CALL OControl::createPeer(const Reference<XToolkit>& _rxToolkit, const Reference<XWindowPeer>& _rxParent) throw (RuntimeException) 340cdf0e10cSrcweir { 341cdf0e10cSrcweir if ( m_xControl.is() ) 342cdf0e10cSrcweir { 343cdf0e10cSrcweir m_xControl->createPeer( _rxToolkit, _rxParent ); 344cdf0e10cSrcweir 345cdf0e10cSrcweir initFormControlPeer( getPeer() ); 346cdf0e10cSrcweir 347cdf0e10cSrcweir impl_resetStateGuard_nothrow(); 348cdf0e10cSrcweir } 349cdf0e10cSrcweir } 350cdf0e10cSrcweir 351cdf0e10cSrcweir //------------------------------------------------------------------------------ 352cdf0e10cSrcweir Reference<XWindowPeer> SAL_CALL OControl::getPeer() throw ( RuntimeException) 353cdf0e10cSrcweir { 354cdf0e10cSrcweir return m_xControl.is() ? m_xControl->getPeer() : Reference<XWindowPeer>(); 355cdf0e10cSrcweir } 356cdf0e10cSrcweir 357cdf0e10cSrcweir //------------------------------------------------------------------------------ 358cdf0e10cSrcweir sal_Bool SAL_CALL OControl::setModel(const Reference<XControlModel>& Model) throw ( RuntimeException) 359cdf0e10cSrcweir { 360cdf0e10cSrcweir if ( !m_xControl.is() ) 361cdf0e10cSrcweir return sal_False; 362cdf0e10cSrcweir 363cdf0e10cSrcweir sal_Bool bSuccess = m_xControl->setModel( Model ); 364cdf0e10cSrcweir impl_resetStateGuard_nothrow(); 365cdf0e10cSrcweir return bSuccess; 366cdf0e10cSrcweir } 367cdf0e10cSrcweir 368cdf0e10cSrcweir //------------------------------------------------------------------------------ 369cdf0e10cSrcweir Reference<XControlModel> SAL_CALL OControl::getModel() throw ( RuntimeException) 370cdf0e10cSrcweir { 371cdf0e10cSrcweir return m_xControl.is() ? m_xControl->getModel() : Reference<XControlModel>(); 372cdf0e10cSrcweir } 373cdf0e10cSrcweir 374cdf0e10cSrcweir //------------------------------------------------------------------------------ 375cdf0e10cSrcweir Reference<XView> SAL_CALL OControl::getView() throw ( RuntimeException) 376cdf0e10cSrcweir { 377cdf0e10cSrcweir return m_xControl.is() ? m_xControl->getView() : Reference<XView>(); 378cdf0e10cSrcweir } 379cdf0e10cSrcweir 380cdf0e10cSrcweir //------------------------------------------------------------------------------ 381cdf0e10cSrcweir void SAL_CALL OControl::setDesignMode(sal_Bool bOn) throw ( RuntimeException) 382cdf0e10cSrcweir { 383cdf0e10cSrcweir if (m_xControl.is()) 384cdf0e10cSrcweir m_xControl->setDesignMode(bOn); 385cdf0e10cSrcweir } 386cdf0e10cSrcweir 387cdf0e10cSrcweir //------------------------------------------------------------------------------ 388cdf0e10cSrcweir sal_Bool SAL_CALL OControl::isDesignMode() throw ( RuntimeException) 389cdf0e10cSrcweir { 390cdf0e10cSrcweir return m_xControl.is() ? m_xControl->isDesignMode() : sal_True; 391cdf0e10cSrcweir } 392cdf0e10cSrcweir 393cdf0e10cSrcweir //------------------------------------------------------------------------------ 394cdf0e10cSrcweir sal_Bool SAL_CALL OControl::isTransparent() throw ( RuntimeException) 395cdf0e10cSrcweir { 396cdf0e10cSrcweir return m_xControl.is() ? m_xControl->isTransparent() : sal_True; 397cdf0e10cSrcweir } 398cdf0e10cSrcweir 399cdf0e10cSrcweir //================================================================== 400cdf0e10cSrcweir //= OBoundControl 401cdf0e10cSrcweir //================================================================== 402cdf0e10cSrcweir DBG_NAME(frm_OBoundControl); 403cdf0e10cSrcweir //------------------------------------------------------------------ 404cdf0e10cSrcweir OBoundControl::OBoundControl( const Reference< XMultiServiceFactory >& _rxFactory, 405cdf0e10cSrcweir const ::rtl::OUString& _rAggregateService, const sal_Bool _bSetDelegator ) 406cdf0e10cSrcweir :OControl( _rxFactory, _rAggregateService, _bSetDelegator ) 407cdf0e10cSrcweir ,m_bLocked(sal_False) 408cdf0e10cSrcweir ,m_aOriginalFont( EmptyFontDescriptor() ) 409cdf0e10cSrcweir ,m_nOriginalTextLineColor( 0 ) 410cdf0e10cSrcweir { 411cdf0e10cSrcweir DBG_CTOR(frm_OBoundControl, NULL); 412cdf0e10cSrcweir } 413cdf0e10cSrcweir 414cdf0e10cSrcweir //------------------------------------------------------------------ 415cdf0e10cSrcweir OBoundControl::~OBoundControl() 416cdf0e10cSrcweir { 417cdf0e10cSrcweir DBG_DTOR(frm_OBoundControl, NULL); 418cdf0e10cSrcweir } 419cdf0e10cSrcweir // ----------------------------------------------------------------------------- 420cdf0e10cSrcweir Sequence< Type> OBoundControl::_getTypes() 421cdf0e10cSrcweir { 422cdf0e10cSrcweir return TypeBag( OControl::_getTypes(), OBoundControl_BASE::getTypes() ).getTypes(); 423cdf0e10cSrcweir } 424cdf0e10cSrcweir //------------------------------------------------------------------ 425cdf0e10cSrcweir Any SAL_CALL OBoundControl::queryAggregation(const Type& _rType) throw(RuntimeException) 426cdf0e10cSrcweir { 427cdf0e10cSrcweir Any aReturn; 428cdf0e10cSrcweir 429cdf0e10cSrcweir // XTypeProvider first - don't ask the OBoundControl_BASE, it would deliver incomplete types 430cdf0e10cSrcweir if ( _rType.equals( ::getCppuType( static_cast< Reference< XTypeProvider >* >( NULL ) ) ) ) 431cdf0e10cSrcweir aReturn = OControl::queryAggregation( _rType ); 432cdf0e10cSrcweir 433cdf0e10cSrcweir // ask our own interfaces 434cdf0e10cSrcweir // (do this first (except XTypeProvider ) - we want to "overwrite" XPropertiesChangeListener) 435cdf0e10cSrcweir if ( !aReturn.hasValue() ) 436cdf0e10cSrcweir aReturn = OBoundControl_BASE::queryInterface( _rType ); 437cdf0e10cSrcweir 438cdf0e10cSrcweir // ask the base class 439cdf0e10cSrcweir if ( !aReturn.hasValue() ) 440cdf0e10cSrcweir aReturn = OControl::queryAggregation( _rType ); 441cdf0e10cSrcweir 442cdf0e10cSrcweir return aReturn; 443cdf0e10cSrcweir } 444cdf0e10cSrcweir 445cdf0e10cSrcweir //------------------------------------------------------------------ 446cdf0e10cSrcweir sal_Bool SAL_CALL OBoundControl::getLock() throw(RuntimeException) 447cdf0e10cSrcweir { 448cdf0e10cSrcweir return m_bLocked; 449cdf0e10cSrcweir } 450cdf0e10cSrcweir 451cdf0e10cSrcweir //------------------------------------------------------------------ 452cdf0e10cSrcweir void SAL_CALL OBoundControl::setLock(sal_Bool _bLock) throw(RuntimeException) 453cdf0e10cSrcweir { 454cdf0e10cSrcweir if (m_bLocked == _bLock) 455cdf0e10cSrcweir return; 456cdf0e10cSrcweir 457cdf0e10cSrcweir osl::MutexGuard aGuard(m_aMutex); 458cdf0e10cSrcweir _setLock(_bLock); 459cdf0e10cSrcweir m_bLocked = _bLock; 460cdf0e10cSrcweir } 461cdf0e10cSrcweir 462cdf0e10cSrcweir //------------------------------------------------------------------ 463cdf0e10cSrcweir void OBoundControl::_setLock(sal_Bool _bLock) 464cdf0e10cSrcweir { 465cdf0e10cSrcweir // try to set the text component to readonly 466cdf0e10cSrcweir Reference< XWindowPeer > xPeer = getPeer(); 467cdf0e10cSrcweir Reference< XTextComponent > xText( xPeer, UNO_QUERY ); 468cdf0e10cSrcweir 469cdf0e10cSrcweir if ( xText.is() ) 470cdf0e10cSrcweir xText->setEditable( !_bLock ); 471cdf0e10cSrcweir else 472cdf0e10cSrcweir { 473cdf0e10cSrcweir // disable the window 474cdf0e10cSrcweir Reference< XWindow > xComp( xPeer, UNO_QUERY ); 475cdf0e10cSrcweir if ( xComp.is() ) 476cdf0e10cSrcweir xComp->setEnable( !_bLock ); 477cdf0e10cSrcweir } 478cdf0e10cSrcweir } 479cdf0e10cSrcweir 480cdf0e10cSrcweir //-------------------------------------------------------------------- 481cdf0e10cSrcweir sal_Bool SAL_CALL OBoundControl::setModel( const Reference< XControlModel >& _rxModel ) throw (RuntimeException) 482cdf0e10cSrcweir { 483cdf0e10cSrcweir return OControl::setModel( _rxModel ); 484cdf0e10cSrcweir } 485cdf0e10cSrcweir 486cdf0e10cSrcweir //-------------------------------------------------------------------- 487cdf0e10cSrcweir void SAL_CALL OBoundControl::disposing(const EventObject& Source) throw (RuntimeException) 488cdf0e10cSrcweir { 489cdf0e10cSrcweir // just disambiguate 490cdf0e10cSrcweir OControl::disposing(Source); 491cdf0e10cSrcweir } 492cdf0e10cSrcweir 493cdf0e10cSrcweir //-------------------------------------------------------------------- 494cdf0e10cSrcweir void OBoundControl::disposing() 495cdf0e10cSrcweir { 496cdf0e10cSrcweir OControl::disposing(); 497cdf0e10cSrcweir } 498cdf0e10cSrcweir 499cdf0e10cSrcweir //================================================================== 500cdf0e10cSrcweir //= OControlModel 501cdf0e10cSrcweir //================================================================== 502cdf0e10cSrcweir DBG_NAME(OControlModel) 503cdf0e10cSrcweir //------------------------------------------------------------------ 504cdf0e10cSrcweir Sequence<sal_Int8> SAL_CALL OControlModel::getImplementationId() throw(RuntimeException) 505cdf0e10cSrcweir { 506cdf0e10cSrcweir return OImplementationIds::getImplementationId(getTypes()); 507cdf0e10cSrcweir } 508cdf0e10cSrcweir 509cdf0e10cSrcweir //------------------------------------------------------------------ 510cdf0e10cSrcweir Sequence<Type> SAL_CALL OControlModel::getTypes() throw(RuntimeException) 511cdf0e10cSrcweir { 512cdf0e10cSrcweir TypeBag aTypes( _getTypes() ); 513cdf0e10cSrcweir 514cdf0e10cSrcweir Reference< XTypeProvider > xProv; 515cdf0e10cSrcweir if ( query_aggregation( m_xAggregate, xProv ) ) 516cdf0e10cSrcweir aTypes.addTypes( xProv->getTypes() ); 517cdf0e10cSrcweir 518cdf0e10cSrcweir return aTypes.getTypes(); 519cdf0e10cSrcweir } 520cdf0e10cSrcweir 521cdf0e10cSrcweir //------------------------------------------------------------------------------ 522cdf0e10cSrcweir Sequence<Type> OControlModel::_getTypes() 523cdf0e10cSrcweir { 524cdf0e10cSrcweir return TypeBag( OComponentHelper::getTypes(), 525cdf0e10cSrcweir OPropertySetAggregationHelper::getTypes(), 526cdf0e10cSrcweir OControlModel_BASE::getTypes() 527cdf0e10cSrcweir ).getTypes(); 528cdf0e10cSrcweir } 529cdf0e10cSrcweir 530cdf0e10cSrcweir //------------------------------------------------------------------ 531cdf0e10cSrcweir Any SAL_CALL OControlModel::queryAggregation(const Type& _rType) throw (RuntimeException) 532cdf0e10cSrcweir { 533cdf0e10cSrcweir // base class 1 534cdf0e10cSrcweir Any aReturn(OComponentHelper::queryAggregation(_rType)); 535cdf0e10cSrcweir 536cdf0e10cSrcweir // base class 2 537cdf0e10cSrcweir if (!aReturn.hasValue()) 538cdf0e10cSrcweir { 539cdf0e10cSrcweir aReturn = OControlModel_BASE::queryInterface(_rType); 540cdf0e10cSrcweir 541cdf0e10cSrcweir // our own interfaces 542cdf0e10cSrcweir if (!aReturn.hasValue()) 543cdf0e10cSrcweir { 544cdf0e10cSrcweir aReturn = OPropertySetAggregationHelper::queryInterface(_rType); 545cdf0e10cSrcweir // our aggregate 546cdf0e10cSrcweir if (!aReturn.hasValue() && m_xAggregate.is() && !_rType.equals(::getCppuType(static_cast< Reference< XCloneable>* >(NULL)))) 547cdf0e10cSrcweir aReturn = m_xAggregate->queryAggregation(_rType); 548cdf0e10cSrcweir } 549cdf0e10cSrcweir } 550cdf0e10cSrcweir return aReturn; 551cdf0e10cSrcweir } 552cdf0e10cSrcweir 553cdf0e10cSrcweir //------------------------------------------------------------------------------ 554cdf0e10cSrcweir void OControlModel::readHelpTextCompatibly(const staruno::Reference< stario::XObjectInputStream >& _rxInStream) 555cdf0e10cSrcweir { 556cdf0e10cSrcweir ::rtl::OUString sHelpText; 557cdf0e10cSrcweir ::comphelper::operator>>( _rxInStream, sHelpText); 558cdf0e10cSrcweir try 559cdf0e10cSrcweir { 560cdf0e10cSrcweir if (m_xAggregateSet.is()) 561cdf0e10cSrcweir m_xAggregateSet->setPropertyValue(PROPERTY_HELPTEXT, makeAny(sHelpText)); 562cdf0e10cSrcweir } 563cdf0e10cSrcweir catch(const Exception&) 564cdf0e10cSrcweir { 565cdf0e10cSrcweir OSL_ENSURE(sal_False, "OControlModel::readHelpTextCompatibly: could not forward the property value to the aggregate!"); 566cdf0e10cSrcweir } 567cdf0e10cSrcweir } 568cdf0e10cSrcweir 569cdf0e10cSrcweir //------------------------------------------------------------------------------ 570cdf0e10cSrcweir void OControlModel::writeHelpTextCompatibly(const staruno::Reference< stario::XObjectOutputStream >& _rxOutStream) 571cdf0e10cSrcweir { 572cdf0e10cSrcweir ::rtl::OUString sHelpText; 573cdf0e10cSrcweir try 574cdf0e10cSrcweir { 575cdf0e10cSrcweir if (m_xAggregateSet.is()) 576cdf0e10cSrcweir m_xAggregateSet->getPropertyValue(PROPERTY_HELPTEXT) >>= sHelpText; 577cdf0e10cSrcweir } 578cdf0e10cSrcweir catch(const Exception&) 579cdf0e10cSrcweir { 580cdf0e10cSrcweir OSL_ENSURE(sal_False, "OControlModel::writeHelpTextCompatibly: could not retrieve the property value from the aggregate!"); 581cdf0e10cSrcweir } 582cdf0e10cSrcweir ::comphelper::operator<<( _rxOutStream, sHelpText); 583cdf0e10cSrcweir } 584cdf0e10cSrcweir 585cdf0e10cSrcweir //------------------------------------------------------------------ 586cdf0e10cSrcweir OControlModel::OControlModel( 587cdf0e10cSrcweir const Reference<com::sun::star::lang::XMultiServiceFactory>& _rxFactory, 588cdf0e10cSrcweir const ::rtl::OUString& _rUnoControlModelTypeName, 589cdf0e10cSrcweir const ::rtl::OUString& rDefault, const sal_Bool _bSetDelegator) 590cdf0e10cSrcweir :OComponentHelper(m_aMutex) 591cdf0e10cSrcweir ,OPropertySetAggregationHelper(OComponentHelper::rBHelper) 592cdf0e10cSrcweir ,m_aContext( _rxFactory ) 593cdf0e10cSrcweir ,m_lockCount( 0 ) 594cdf0e10cSrcweir ,m_aPropertyBagHelper( *this ) 595cdf0e10cSrcweir ,m_nTabIndex(FRM_DEFAULT_TABINDEX) 596cdf0e10cSrcweir ,m_nClassId(FormComponentType::CONTROL) 597cdf0e10cSrcweir ,m_bNativeLook( sal_False ) 5980de526bdSJianyuan Li ,m_nControlTypeinMSO(0) // 0 : default value is create from AOO 5990de526bdSJianyuan Li ,m_nObjIDinMSO(INVALID_OBJ_ID_IN_MSO) 600cdf0e10cSrcweir // form controls are usually embedded into documents, not dialogs, and in documents 601cdf0e10cSrcweir // the native look is ugly .... 602cdf0e10cSrcweir // #i37342# / 2004-11-19 / frank.schoenheit@sun.com 603cdf0e10cSrcweir { 604cdf0e10cSrcweir DBG_CTOR(OControlModel, NULL); 605cdf0e10cSrcweir if (_rUnoControlModelTypeName.getLength()) // the is a model we have to aggregate 606cdf0e10cSrcweir { 607cdf0e10cSrcweir increment(m_refCount); 608cdf0e10cSrcweir 609cdf0e10cSrcweir { 610cdf0e10cSrcweir m_xAggregate = Reference<XAggregation>(_rxFactory->createInstance(_rUnoControlModelTypeName), UNO_QUERY); 611cdf0e10cSrcweir setAggregation(m_xAggregate); 612cdf0e10cSrcweir 613cdf0e10cSrcweir if ( m_xAggregateSet.is() ) 614cdf0e10cSrcweir { 615cdf0e10cSrcweir try 616cdf0e10cSrcweir { 617cdf0e10cSrcweir if ( rDefault.getLength() ) 618cdf0e10cSrcweir m_xAggregateSet->setPropertyValue( PROPERTY_DEFAULTCONTROL, makeAny( rDefault ) ); 619cdf0e10cSrcweir } 620cdf0e10cSrcweir catch( const Exception& ) 621cdf0e10cSrcweir { 622cdf0e10cSrcweir OSL_ENSURE( sal_False, "OControlModel::OControlModel: caught an exception!" ); 623cdf0e10cSrcweir } 624cdf0e10cSrcweir } 625cdf0e10cSrcweir } 626cdf0e10cSrcweir 627cdf0e10cSrcweir if (_bSetDelegator) 628cdf0e10cSrcweir doSetDelegator(); 629cdf0e10cSrcweir 630cdf0e10cSrcweir // Refcount wieder bei NULL 631cdf0e10cSrcweir decrement(m_refCount); 632cdf0e10cSrcweir } 633cdf0e10cSrcweir } 634cdf0e10cSrcweir 635cdf0e10cSrcweir //------------------------------------------------------------------ 636cdf0e10cSrcweir OControlModel::OControlModel( const OControlModel* _pOriginal, const Reference< XMultiServiceFactory>& _rxFactory, const sal_Bool _bCloneAggregate, const sal_Bool _bSetDelegator ) 637cdf0e10cSrcweir :OComponentHelper( m_aMutex ) 638cdf0e10cSrcweir ,OPropertySetAggregationHelper( OComponentHelper::rBHelper ) 639cdf0e10cSrcweir ,m_aContext( _rxFactory ) 640cdf0e10cSrcweir ,m_lockCount( 0 ) 641cdf0e10cSrcweir ,m_aPropertyBagHelper( *this ) 642cdf0e10cSrcweir ,m_nTabIndex( FRM_DEFAULT_TABINDEX ) 643cdf0e10cSrcweir ,m_nClassId( FormComponentType::CONTROL ) 644cdf0e10cSrcweir { 645cdf0e10cSrcweir DBG_CTOR( OControlModel, NULL ); 646cdf0e10cSrcweir DBG_ASSERT( _pOriginal, "OControlModel::OControlModel: invalid original!" ); 647cdf0e10cSrcweir 648cdf0e10cSrcweir // copy members 649cdf0e10cSrcweir m_aName = _pOriginal->m_aName; 650cdf0e10cSrcweir m_aTag = _pOriginal->m_aTag; 651cdf0e10cSrcweir m_nTabIndex = _pOriginal->m_nTabIndex; 652cdf0e10cSrcweir m_nClassId = _pOriginal->m_nClassId; 653cdf0e10cSrcweir m_bNativeLook = _pOriginal->m_bNativeLook; 6540de526bdSJianyuan Li m_nControlTypeinMSO = _pOriginal->m_nControlTypeinMSO; 6550de526bdSJianyuan Li m_nObjIDinMSO = _pOriginal->m_nObjIDinMSO; 656cdf0e10cSrcweir 657cdf0e10cSrcweir if ( _bCloneAggregate ) 658cdf0e10cSrcweir { 659cdf0e10cSrcweir // temporarily increment refcount because of temporary references to ourself in the following 660cdf0e10cSrcweir increment( m_refCount ); 661cdf0e10cSrcweir 662cdf0e10cSrcweir { 663cdf0e10cSrcweir // transfer the (only, at the very moment!) ref count 664cdf0e10cSrcweir m_xAggregate = createAggregateClone( _pOriginal ); 665cdf0e10cSrcweir 666cdf0e10cSrcweir // set aggregation (retrieve other direct interfaces of the aggregate) 667cdf0e10cSrcweir setAggregation( m_xAggregate ); 668cdf0e10cSrcweir } 669cdf0e10cSrcweir 670cdf0e10cSrcweir // set the delegator, if allowed by our derived class 671cdf0e10cSrcweir if ( _bSetDelegator ) 672cdf0e10cSrcweir doSetDelegator(); 673cdf0e10cSrcweir 674cdf0e10cSrcweir // decrement ref count 675cdf0e10cSrcweir decrement( m_refCount ); 676cdf0e10cSrcweir } 677cdf0e10cSrcweir } 678cdf0e10cSrcweir 679cdf0e10cSrcweir //------------------------------------------------------------------ 680cdf0e10cSrcweir OControlModel::~OControlModel() 681cdf0e10cSrcweir { 682cdf0e10cSrcweir // release the aggregate 683cdf0e10cSrcweir doResetDelegator( ); 684cdf0e10cSrcweir 685cdf0e10cSrcweir DBG_DTOR(OControlModel, NULL); 686cdf0e10cSrcweir } 687cdf0e10cSrcweir 688cdf0e10cSrcweir //------------------------------------------------------------------ 689cdf0e10cSrcweir void OControlModel::clonedFrom( const OControlModel* /*_pOriginal*/ ) 690cdf0e10cSrcweir { 691cdf0e10cSrcweir // nothing to do in this base class 692cdf0e10cSrcweir } 693cdf0e10cSrcweir 694cdf0e10cSrcweir //------------------------------------------------------------------------------ 695cdf0e10cSrcweir void OControlModel::doResetDelegator() 696cdf0e10cSrcweir { 697cdf0e10cSrcweir if (m_xAggregate.is()) 698cdf0e10cSrcweir m_xAggregate->setDelegator(NULL); 699cdf0e10cSrcweir } 700cdf0e10cSrcweir 701cdf0e10cSrcweir //------------------------------------------------------------------------------ 702cdf0e10cSrcweir void OControlModel::doSetDelegator() 703cdf0e10cSrcweir { 704cdf0e10cSrcweir increment(m_refCount); 705cdf0e10cSrcweir if (m_xAggregate.is()) 706cdf0e10cSrcweir { 707cdf0e10cSrcweir m_xAggregate->setDelegator(static_cast<XWeak*>(this)); 708cdf0e10cSrcweir } 709cdf0e10cSrcweir decrement(m_refCount); 710cdf0e10cSrcweir } 711cdf0e10cSrcweir 712cdf0e10cSrcweir // XChild 713cdf0e10cSrcweir //------------------------------------------------------------------------------ 714cdf0e10cSrcweir Reference< XInterface > SAL_CALL OControlModel::getParent() throw(RuntimeException) 715cdf0e10cSrcweir { 716cdf0e10cSrcweir return m_xParent; 717cdf0e10cSrcweir } 718cdf0e10cSrcweir 719cdf0e10cSrcweir //------------------------------------------------------------------------------ 720cdf0e10cSrcweir void SAL_CALL OControlModel::setParent(const Reference< XInterface >& _rxParent) throw(com::sun::star::lang::NoSupportException, RuntimeException) 721cdf0e10cSrcweir { 722cdf0e10cSrcweir osl::MutexGuard aGuard(m_aMutex); 723cdf0e10cSrcweir 724cdf0e10cSrcweir Reference<XComponent> xComp(m_xParent, UNO_QUERY); 725cdf0e10cSrcweir if (xComp.is()) 726cdf0e10cSrcweir xComp->removeEventListener(static_cast<XPropertiesChangeListener*>(this)); 727cdf0e10cSrcweir 728cdf0e10cSrcweir m_xParent = _rxParent; 729cdf0e10cSrcweir xComp = xComp.query( m_xParent ); 730cdf0e10cSrcweir 731cdf0e10cSrcweir if ( xComp.is() ) 732cdf0e10cSrcweir xComp->addEventListener(static_cast<XPropertiesChangeListener*>(this)); 733cdf0e10cSrcweir } 734cdf0e10cSrcweir 735cdf0e10cSrcweir // XNamed 736cdf0e10cSrcweir //------------------------------------------------------------------------------ 737cdf0e10cSrcweir ::rtl::OUString SAL_CALL OControlModel::getName() throw(RuntimeException) 738cdf0e10cSrcweir { 739cdf0e10cSrcweir ::rtl::OUString aReturn; 740cdf0e10cSrcweir OPropertySetHelper::getFastPropertyValue(PROPERTY_ID_NAME) >>= aReturn; 741cdf0e10cSrcweir return aReturn; 742cdf0e10cSrcweir } 743cdf0e10cSrcweir 744cdf0e10cSrcweir //------------------------------------------------------------------------------ 745cdf0e10cSrcweir void SAL_CALL OControlModel::setName(const ::rtl::OUString& _rName) throw(RuntimeException) 746cdf0e10cSrcweir { 747cdf0e10cSrcweir setFastPropertyValue(PROPERTY_ID_NAME, makeAny(_rName)); 748cdf0e10cSrcweir } 749cdf0e10cSrcweir 750cdf0e10cSrcweir // XServiceInfo 751cdf0e10cSrcweir //------------------------------------------------------------------------------ 752cdf0e10cSrcweir sal_Bool SAL_CALL OControlModel::supportsService(const rtl::OUString& _rServiceName) throw ( RuntimeException) 753cdf0e10cSrcweir { 754cdf0e10cSrcweir Sequence<rtl::OUString> aSupported = getSupportedServiceNames(); 755cdf0e10cSrcweir const rtl::OUString* pSupported = aSupported.getConstArray(); 756cdf0e10cSrcweir for (sal_Int32 i=0; i<aSupported.getLength(); ++i, ++pSupported) 757cdf0e10cSrcweir if (pSupported->equals(_rServiceName)) 758cdf0e10cSrcweir return sal_True; 759cdf0e10cSrcweir return sal_False; 760cdf0e10cSrcweir } 761cdf0e10cSrcweir 762cdf0e10cSrcweir //------------------------------------------------------------------------------ 763cdf0e10cSrcweir Sequence< ::rtl::OUString > OControlModel::getAggregateServiceNames() 764cdf0e10cSrcweir { 765cdf0e10cSrcweir Sequence< ::rtl::OUString > aAggServices; 766cdf0e10cSrcweir Reference< XServiceInfo > xInfo; 767cdf0e10cSrcweir if ( query_aggregation( m_xAggregate, xInfo ) ) 768cdf0e10cSrcweir aAggServices = xInfo->getSupportedServiceNames(); 769cdf0e10cSrcweir return aAggServices; 770cdf0e10cSrcweir } 771cdf0e10cSrcweir 772cdf0e10cSrcweir //------------------------------------------------------------------------------ 773cdf0e10cSrcweir Sequence<rtl::OUString> SAL_CALL OControlModel::getSupportedServiceNames() throw(RuntimeException) 774cdf0e10cSrcweir { 775cdf0e10cSrcweir return ::comphelper::concatSequences( 776cdf0e10cSrcweir getAggregateServiceNames(), 777cdf0e10cSrcweir getSupportedServiceNames_Static() 778cdf0e10cSrcweir ); 779cdf0e10cSrcweir } 780cdf0e10cSrcweir 781cdf0e10cSrcweir //------------------------------------------------------------------------------ 782cdf0e10cSrcweir Sequence< ::rtl::OUString > SAL_CALL OControlModel::getSupportedServiceNames_Static() throw( RuntimeException ) 783cdf0e10cSrcweir { 784cdf0e10cSrcweir Sequence< ::rtl::OUString > aServiceNames( 2 ); 785cdf0e10cSrcweir aServiceNames[ 0 ] = FRM_SUN_FORMCOMPONENT; 786cdf0e10cSrcweir aServiceNames[ 1 ] = ::rtl::OUString::createFromAscii( "com.sun.star.form.FormControlModel" ); 787cdf0e10cSrcweir return aServiceNames; 788cdf0e10cSrcweir } 789cdf0e10cSrcweir 790cdf0e10cSrcweir // XEventListener 791cdf0e10cSrcweir //------------------------------------------------------------------------------ 792cdf0e10cSrcweir void SAL_CALL OControlModel::disposing(const com::sun::star::lang::EventObject& _rSource) throw (RuntimeException) 793cdf0e10cSrcweir { 794cdf0e10cSrcweir // release the parent 795cdf0e10cSrcweir if (_rSource.Source == m_xParent) 796cdf0e10cSrcweir { 797cdf0e10cSrcweir osl::MutexGuard aGuard(m_aMutex); 798cdf0e10cSrcweir m_xParent = NULL; 799cdf0e10cSrcweir } 800cdf0e10cSrcweir else 801cdf0e10cSrcweir { 802cdf0e10cSrcweir Reference<com::sun::star::lang::XEventListener> xEvtLst; 803cdf0e10cSrcweir if (query_aggregation(m_xAggregate, xEvtLst)) 804cdf0e10cSrcweir { 805cdf0e10cSrcweir osl::MutexGuard aGuard(m_aMutex); 806cdf0e10cSrcweir xEvtLst->disposing(_rSource); 807cdf0e10cSrcweir } 808cdf0e10cSrcweir } 809cdf0e10cSrcweir } 810cdf0e10cSrcweir 811cdf0e10cSrcweir // OComponentHelper 812cdf0e10cSrcweir //----------------------------------------------------------------------------- 813cdf0e10cSrcweir void OControlModel::disposing() 814cdf0e10cSrcweir { 815cdf0e10cSrcweir OPropertySetAggregationHelper::disposing(); 816cdf0e10cSrcweir 817cdf0e10cSrcweir Reference<com::sun::star::lang::XComponent> xComp; 818cdf0e10cSrcweir if (query_aggregation(m_xAggregate, xComp)) 819cdf0e10cSrcweir xComp->dispose(); 820cdf0e10cSrcweir 821cdf0e10cSrcweir setParent(Reference<XFormComponent>()); 822cdf0e10cSrcweir 823cdf0e10cSrcweir m_aPropertyBagHelper.dispose(); 824cdf0e10cSrcweir } 825cdf0e10cSrcweir 826cdf0e10cSrcweir //------------------------------------------------------------------------------ 827cdf0e10cSrcweir void OControlModel::writeAggregate( const Reference< XObjectOutputStream >& _rxOutStream ) const 828cdf0e10cSrcweir { 829cdf0e10cSrcweir Reference< XPersistObject > xPersist; 830cdf0e10cSrcweir if ( query_aggregation( m_xAggregate, xPersist ) ) 831cdf0e10cSrcweir xPersist->write( _rxOutStream ); 832cdf0e10cSrcweir } 833cdf0e10cSrcweir 834cdf0e10cSrcweir //------------------------------------------------------------------------------ 835cdf0e10cSrcweir void OControlModel::readAggregate( const Reference< XObjectInputStream >& _rxInStream ) 836cdf0e10cSrcweir { 837cdf0e10cSrcweir Reference< XPersistObject > xPersist; 838cdf0e10cSrcweir if ( query_aggregation( m_xAggregate, xPersist ) ) 839cdf0e10cSrcweir xPersist->read( _rxInStream ); 840cdf0e10cSrcweir } 841cdf0e10cSrcweir 842cdf0e10cSrcweir //------------------------------------------------------------------------------ 843cdf0e10cSrcweir void SAL_CALL OControlModel::write(const Reference<stario::XObjectOutputStream>& _rxOutStream) 844cdf0e10cSrcweir throw(stario::IOException, RuntimeException) 845cdf0e10cSrcweir { 846cdf0e10cSrcweir osl::MutexGuard aGuard(m_aMutex); 847cdf0e10cSrcweir 848cdf0e10cSrcweir // 1. Schreiben des UnoControls 849cdf0e10cSrcweir Reference<stario::XMarkableStream> xMark(_rxOutStream, UNO_QUERY); 850cdf0e10cSrcweir if ( !xMark.is() ) 851cdf0e10cSrcweir { 852cdf0e10cSrcweir throw IOException( 853cdf0e10cSrcweir FRM_RES_STRING( RID_STR_INVALIDSTREAM ), 854cdf0e10cSrcweir static_cast< ::cppu::OWeakObject* >( this ) 855cdf0e10cSrcweir ); 856cdf0e10cSrcweir } 857cdf0e10cSrcweir 858cdf0e10cSrcweir sal_Int32 nMark = xMark->createMark(); 859cdf0e10cSrcweir sal_Int32 nLen = 0; 860cdf0e10cSrcweir 861cdf0e10cSrcweir _rxOutStream->writeLong(nLen); 862cdf0e10cSrcweir 863cdf0e10cSrcweir writeAggregate( _rxOutStream ); 864cdf0e10cSrcweir 865cdf0e10cSrcweir // feststellen der Laenge 866cdf0e10cSrcweir nLen = xMark->offsetToMark(nMark) - 4; 867cdf0e10cSrcweir xMark->jumpToMark(nMark); 868cdf0e10cSrcweir _rxOutStream->writeLong(nLen); 869cdf0e10cSrcweir xMark->jumpToFurthest(); 870cdf0e10cSrcweir xMark->deleteMark(nMark); 871cdf0e10cSrcweir 872cdf0e10cSrcweir // 2. Schreiben einer VersionsNummer 873cdf0e10cSrcweir _rxOutStream->writeShort(0x0003); 874cdf0e10cSrcweir 875cdf0e10cSrcweir // 3. Schreiben der allgemeinen Properties 876cdf0e10cSrcweir ::comphelper::operator<<( _rxOutStream, m_aName); 877cdf0e10cSrcweir _rxOutStream->writeShort(m_nTabIndex); 878cdf0e10cSrcweir ::comphelper::operator<<( _rxOutStream, m_aTag); // 3. version 879cdf0e10cSrcweir 880cdf0e10cSrcweir // !!! IMPORTANT NOTE !!! 881cdf0e10cSrcweir // don't write any new members here : this wouldn't be compatible with older versions, as OControlModel 882cdf0e10cSrcweir // is a base class which is called in derived classes "read" method. So if you increment the version 883cdf0e10cSrcweir // and write new stuff, older office versions will read this in the _derived_ classes, which may result 884cdf0e10cSrcweir // in anything from data loss to crash. 885cdf0e10cSrcweir // !!! EOIN !!! 886cdf0e10cSrcweir } 887cdf0e10cSrcweir 888cdf0e10cSrcweir //------------------------------------------------------------------------------ 889cdf0e10cSrcweir void OControlModel::read(const Reference<stario::XObjectInputStream>& InStream) throw (::com::sun::star::io::IOException, RuntimeException) 890cdf0e10cSrcweir { 891cdf0e10cSrcweir osl::MutexGuard aGuard(m_aMutex); 892cdf0e10cSrcweir 893cdf0e10cSrcweir Reference<stario::XMarkableStream> xMark(InStream, UNO_QUERY); 894cdf0e10cSrcweir if ( !xMark.is() ) 895cdf0e10cSrcweir { 896cdf0e10cSrcweir throw IOException( 897cdf0e10cSrcweir FRM_RES_STRING( RID_STR_INVALIDSTREAM ), 898cdf0e10cSrcweir static_cast< ::cppu::OWeakObject* >( this ) 899cdf0e10cSrcweir ); 900cdf0e10cSrcweir } 901cdf0e10cSrcweir 902cdf0e10cSrcweir // 1. Lesen des UnoControls 903cdf0e10cSrcweir sal_Int32 nLen = InStream->readLong(); 904cdf0e10cSrcweir if (nLen) 905cdf0e10cSrcweir { 906cdf0e10cSrcweir sal_Int32 nMark = xMark->createMark(); 907cdf0e10cSrcweir 908cdf0e10cSrcweir try 909cdf0e10cSrcweir { 910cdf0e10cSrcweir readAggregate( InStream ); 911cdf0e10cSrcweir } 912cdf0e10cSrcweir catch( const Exception& ) 913cdf0e10cSrcweir { 914cdf0e10cSrcweir DBG_UNHANDLED_EXCEPTION(); 915cdf0e10cSrcweir } 916cdf0e10cSrcweir 917cdf0e10cSrcweir xMark->jumpToMark(nMark); 918cdf0e10cSrcweir InStream->skipBytes(nLen); 919cdf0e10cSrcweir xMark->deleteMark(nMark); 920cdf0e10cSrcweir } 921cdf0e10cSrcweir 922cdf0e10cSrcweir // 2. Lesen des Versionsnummer 923cdf0e10cSrcweir sal_uInt16 nVersion = InStream->readShort(); 924cdf0e10cSrcweir 925cdf0e10cSrcweir // 3. Lesen der allgemeinen Properties 926cdf0e10cSrcweir ::comphelper::operator>>( InStream, m_aName); 927cdf0e10cSrcweir m_nTabIndex = InStream->readShort(); 928cdf0e10cSrcweir 929cdf0e10cSrcweir if (nVersion > 0x0002) 930cdf0e10cSrcweir ::comphelper::operator>>( InStream, m_aTag); 931cdf0e10cSrcweir 932cdf0e10cSrcweir // we had a version where we wrote the help text 933cdf0e10cSrcweir if (nVersion == 0x0004) 934cdf0e10cSrcweir readHelpTextCompatibly(InStream); 935cdf0e10cSrcweir 936cdf0e10cSrcweir DBG_ASSERT(nVersion < 5, "OControlModel::read : suspicious version number !"); 937cdf0e10cSrcweir // 4 was the version where we wrote the help text 938cdf0e10cSrcweir // later versions shouldn't exist (see write for a detailed comment) 939cdf0e10cSrcweir } 940cdf0e10cSrcweir 941cdf0e10cSrcweir //------------------------------------------------------------------------------ 942cdf0e10cSrcweir PropertyState OControlModel::getPropertyStateByHandle( sal_Int32 _nHandle ) 943cdf0e10cSrcweir { 944cdf0e10cSrcweir // simply compare the current and the default value 945cdf0e10cSrcweir Any aCurrentValue = getPropertyDefaultByHandle( _nHandle ); 946cdf0e10cSrcweir Any aDefaultValue; getFastPropertyValue( aDefaultValue, _nHandle ); 947cdf0e10cSrcweir 948cdf0e10cSrcweir sal_Bool bEqual = uno_type_equalData( 949cdf0e10cSrcweir const_cast< void* >( aCurrentValue.getValue() ), aCurrentValue.getValueType().getTypeLibType(), 950cdf0e10cSrcweir const_cast< void* >( aDefaultValue.getValue() ), aDefaultValue.getValueType().getTypeLibType(), 951cdf0e10cSrcweir reinterpret_cast< uno_QueryInterfaceFunc >(cpp_queryInterface), 952cdf0e10cSrcweir reinterpret_cast< uno_ReleaseFunc >(cpp_release) 953cdf0e10cSrcweir ); 954cdf0e10cSrcweir return bEqual ? PropertyState_DEFAULT_VALUE : PropertyState_DIRECT_VALUE; 955cdf0e10cSrcweir } 956cdf0e10cSrcweir 957cdf0e10cSrcweir //------------------------------------------------------------------------------ 958cdf0e10cSrcweir void OControlModel::setPropertyToDefaultByHandle( sal_Int32 _nHandle) 959cdf0e10cSrcweir { 960cdf0e10cSrcweir Any aDefault = getPropertyDefaultByHandle( _nHandle ); 961cdf0e10cSrcweir 962cdf0e10cSrcweir Any aConvertedValue, aOldValue; 963cdf0e10cSrcweir if ( convertFastPropertyValue( aConvertedValue, aOldValue, _nHandle, aDefault ) ) 964cdf0e10cSrcweir { 965cdf0e10cSrcweir setFastPropertyValue_NoBroadcast( _nHandle, aConvertedValue ); 966cdf0e10cSrcweir // TODO: fire the property change 967cdf0e10cSrcweir } 968cdf0e10cSrcweir } 969cdf0e10cSrcweir 970cdf0e10cSrcweir //------------------------------------------------------------------------------ 971cdf0e10cSrcweir Any OControlModel::getPropertyDefaultByHandle( sal_Int32 _nHandle ) const 972cdf0e10cSrcweir { 973cdf0e10cSrcweir Any aReturn; 974cdf0e10cSrcweir switch ( _nHandle ) 975cdf0e10cSrcweir { 976cdf0e10cSrcweir case PROPERTY_ID_NAME: 977cdf0e10cSrcweir case PROPERTY_ID_TAG: 978cdf0e10cSrcweir aReturn <<= ::rtl::OUString(); 979cdf0e10cSrcweir break; 980cdf0e10cSrcweir 981cdf0e10cSrcweir case PROPERTY_ID_CLASSID: 982cdf0e10cSrcweir aReturn <<= (sal_Int16)FormComponentType::CONTROL; 983cdf0e10cSrcweir break; 984cdf0e10cSrcweir 985cdf0e10cSrcweir case PROPERTY_ID_TABINDEX: 986cdf0e10cSrcweir aReturn <<= (sal_Int16)FRM_DEFAULT_TABINDEX; 987cdf0e10cSrcweir break; 988cdf0e10cSrcweir 989cdf0e10cSrcweir case PROPERTY_ID_NATIVE_LOOK: 990cdf0e10cSrcweir aReturn <<= (sal_Bool)sal_True; 991cdf0e10cSrcweir break; 9920de526bdSJianyuan Li //added for exporting OCX control 9930de526bdSJianyuan Li case PROPERTY_ID_CONTROL_TYPE_IN_MSO: 9940de526bdSJianyuan Li aReturn <<= (sal_Int16)0; 9950de526bdSJianyuan Li break; 9960de526bdSJianyuan Li case PROPERTY_ID_OBJ_ID_IN_MSO: 9970de526bdSJianyuan Li aReturn <<= (sal_uInt16)INVALID_OBJ_ID_IN_MSO; 9980de526bdSJianyuan Li break; 999cdf0e10cSrcweir default: 1000cdf0e10cSrcweir if ( m_aPropertyBagHelper.hasDynamicPropertyByHandle( _nHandle ) ) 1001cdf0e10cSrcweir m_aPropertyBagHelper.getDynamicPropertyDefaultByHandle( _nHandle, aReturn ); 1002cdf0e10cSrcweir else 1003cdf0e10cSrcweir OSL_ENSURE( false, "OControlModel::convertFastPropertyValue: unknown handle!" ); 1004cdf0e10cSrcweir } 1005cdf0e10cSrcweir return aReturn; 1006cdf0e10cSrcweir } 1007cdf0e10cSrcweir 1008cdf0e10cSrcweir //------------------------------------------------------------------------------ 1009cdf0e10cSrcweir void OControlModel::getFastPropertyValue( Any& _rValue, sal_Int32 _nHandle ) const 1010cdf0e10cSrcweir { 1011cdf0e10cSrcweir switch ( _nHandle ) 1012cdf0e10cSrcweir { 1013cdf0e10cSrcweir case PROPERTY_ID_NAME: 1014cdf0e10cSrcweir _rValue <<= m_aName; 1015cdf0e10cSrcweir break; 1016cdf0e10cSrcweir case PROPERTY_ID_TAG: 1017cdf0e10cSrcweir _rValue <<= m_aTag; 1018cdf0e10cSrcweir break; 1019cdf0e10cSrcweir case PROPERTY_ID_CLASSID: 1020cdf0e10cSrcweir _rValue <<= m_nClassId; 1021cdf0e10cSrcweir break; 1022cdf0e10cSrcweir case PROPERTY_ID_TABINDEX: 1023cdf0e10cSrcweir _rValue <<= m_nTabIndex; 1024cdf0e10cSrcweir break; 1025cdf0e10cSrcweir case PROPERTY_ID_NATIVE_LOOK: 1026cdf0e10cSrcweir _rValue <<= (sal_Bool)m_bNativeLook; 1027cdf0e10cSrcweir break; 10280de526bdSJianyuan Li //added for exporting OCX control 10290de526bdSJianyuan Li case PROPERTY_ID_CONTROL_TYPE_IN_MSO: 10300de526bdSJianyuan Li _rValue <<= (sal_Int16)m_nControlTypeinMSO; 10310de526bdSJianyuan Li break; 10320de526bdSJianyuan Li case PROPERTY_ID_OBJ_ID_IN_MSO: 10330de526bdSJianyuan Li _rValue <<= (sal_uInt16)m_nObjIDinMSO; 10340de526bdSJianyuan Li break; 1035cdf0e10cSrcweir default: 1036cdf0e10cSrcweir if ( m_aPropertyBagHelper.hasDynamicPropertyByHandle( _nHandle ) ) 1037cdf0e10cSrcweir m_aPropertyBagHelper.getDynamicFastPropertyValue( _nHandle, _rValue ); 1038cdf0e10cSrcweir else 1039cdf0e10cSrcweir OPropertySetAggregationHelper::getFastPropertyValue( _rValue, _nHandle ); 1040cdf0e10cSrcweir break; 1041cdf0e10cSrcweir } 1042cdf0e10cSrcweir } 1043cdf0e10cSrcweir 1044cdf0e10cSrcweir //------------------------------------------------------------------------------ 1045cdf0e10cSrcweir sal_Bool OControlModel::convertFastPropertyValue( 1046cdf0e10cSrcweir Any& _rConvertedValue, Any& _rOldValue, sal_Int32 _nHandle, const Any& _rValue) 1047cdf0e10cSrcweir throw (com::sun::star::lang::IllegalArgumentException) 1048cdf0e10cSrcweir { 1049cdf0e10cSrcweir sal_Bool bModified(sal_False); 1050cdf0e10cSrcweir switch (_nHandle) 1051cdf0e10cSrcweir { 1052cdf0e10cSrcweir case PROPERTY_ID_NAME: 1053cdf0e10cSrcweir bModified = tryPropertyValue(_rConvertedValue, _rOldValue, _rValue, m_aName); 1054cdf0e10cSrcweir break; 1055cdf0e10cSrcweir case PROPERTY_ID_TAG: 1056cdf0e10cSrcweir bModified = tryPropertyValue(_rConvertedValue, _rOldValue, _rValue, m_aTag); 1057cdf0e10cSrcweir break; 1058cdf0e10cSrcweir case PROPERTY_ID_TABINDEX: 1059cdf0e10cSrcweir bModified = tryPropertyValue(_rConvertedValue, _rOldValue, _rValue, m_nTabIndex); 1060cdf0e10cSrcweir break; 1061cdf0e10cSrcweir case PROPERTY_ID_NATIVE_LOOK: 1062cdf0e10cSrcweir bModified = tryPropertyValue(_rConvertedValue, _rOldValue, _rValue, m_bNativeLook); 1063cdf0e10cSrcweir break; 10640de526bdSJianyuan Li //added for exporting OCX control 10650de526bdSJianyuan Li case PROPERTY_ID_CONTROL_TYPE_IN_MSO: 10660de526bdSJianyuan Li bModified = tryPropertyValue(_rConvertedValue, _rOldValue, _rValue, m_nControlTypeinMSO); 10670de526bdSJianyuan Li break; 10680de526bdSJianyuan Li case PROPERTY_ID_OBJ_ID_IN_MSO: 10690de526bdSJianyuan Li bModified = tryPropertyValue(_rConvertedValue, _rOldValue, _rValue, m_nObjIDinMSO); 10700de526bdSJianyuan Li break; 1071cdf0e10cSrcweir default: 1072cdf0e10cSrcweir if ( m_aPropertyBagHelper.hasDynamicPropertyByHandle( _nHandle ) ) 1073cdf0e10cSrcweir bModified = m_aPropertyBagHelper.convertDynamicFastPropertyValue( _nHandle, _rValue, _rConvertedValue, _rOldValue ); 1074cdf0e10cSrcweir else 1075cdf0e10cSrcweir OSL_ENSURE( false, "OControlModel::convertFastPropertyValue: unknown handle!" ); 1076cdf0e10cSrcweir break; 1077cdf0e10cSrcweir } 1078cdf0e10cSrcweir return bModified; 1079cdf0e10cSrcweir } 1080cdf0e10cSrcweir 1081cdf0e10cSrcweir //------------------------------------------------------------------------------ 1082cdf0e10cSrcweir void OControlModel::setFastPropertyValue_NoBroadcast(sal_Int32 _nHandle, const Any& _rValue) 1083cdf0e10cSrcweir throw (Exception) 1084cdf0e10cSrcweir { 1085cdf0e10cSrcweir switch (_nHandle) 1086cdf0e10cSrcweir { 1087cdf0e10cSrcweir case PROPERTY_ID_NAME: 1088cdf0e10cSrcweir DBG_ASSERT(_rValue.getValueType() == getCppuType((const ::rtl::OUString*)NULL), 1089cdf0e10cSrcweir "OControlModel::setFastPropertyValue_NoBroadcast : invalid type" ); 1090cdf0e10cSrcweir _rValue >>= m_aName; 1091cdf0e10cSrcweir break; 1092cdf0e10cSrcweir case PROPERTY_ID_TAG: 1093cdf0e10cSrcweir DBG_ASSERT(_rValue.getValueType() == getCppuType((const ::rtl::OUString*)NULL), 1094cdf0e10cSrcweir "OControlModel::setFastPropertyValue_NoBroadcast : invalid type" ); 1095cdf0e10cSrcweir _rValue >>= m_aTag; 1096cdf0e10cSrcweir break; 1097cdf0e10cSrcweir case PROPERTY_ID_TABINDEX: 1098cdf0e10cSrcweir DBG_ASSERT(_rValue.getValueType() == getCppuType((const sal_Int16*)NULL), 1099cdf0e10cSrcweir "OControlModel::setFastPropertyValue_NoBroadcast : invalid type" ); 1100cdf0e10cSrcweir _rValue >>= m_nTabIndex; 1101cdf0e10cSrcweir break; 1102cdf0e10cSrcweir case PROPERTY_ID_NATIVE_LOOK: 1103cdf0e10cSrcweir OSL_VERIFY( _rValue >>= m_bNativeLook ); 1104cdf0e10cSrcweir break; 11050de526bdSJianyuan Li //added for exporting OCX control 11060de526bdSJianyuan Li case PROPERTY_ID_CONTROL_TYPE_IN_MSO: 11070de526bdSJianyuan Li OSL_VERIFY( _rValue >>= m_nControlTypeinMSO ); 11080de526bdSJianyuan Li break; 11090de526bdSJianyuan Li case PROPERTY_ID_OBJ_ID_IN_MSO: 11100de526bdSJianyuan Li OSL_VERIFY( _rValue >>= m_nObjIDinMSO ); 11110de526bdSJianyuan Li break; 1112cdf0e10cSrcweir default: 1113cdf0e10cSrcweir if ( m_aPropertyBagHelper.hasDynamicPropertyByHandle( _nHandle ) ) 1114cdf0e10cSrcweir m_aPropertyBagHelper.setDynamicFastPropertyValue( _nHandle, _rValue ); 1115cdf0e10cSrcweir else 1116cdf0e10cSrcweir OSL_ENSURE( false, "OControlModel::setFastPropertyValue_NoBroadcast: unknown handle!" ); 1117cdf0e10cSrcweir break; 1118cdf0e10cSrcweir } 1119cdf0e10cSrcweir } 1120cdf0e10cSrcweir 1121cdf0e10cSrcweir //------------------------------------------------------------------------------ 1122cdf0e10cSrcweir void OControlModel::describeFixedProperties( Sequence< Property >& _rProps ) const 1123cdf0e10cSrcweir { 11240de526bdSJianyuan Li //BEGIN_DESCRIBE_BASE_PROPERTIES( 4 ) 11250de526bdSJianyuan Li BEGIN_DESCRIBE_BASE_PROPERTIES( 6 ) 1126cdf0e10cSrcweir DECL_PROP2 (CLASSID, sal_Int16, READONLY, TRANSIENT); 1127cdf0e10cSrcweir DECL_PROP1 (NAME, ::rtl::OUString, BOUND); 1128cdf0e10cSrcweir DECL_BOOL_PROP2 (NATIVE_LOOK, BOUND, TRANSIENT); 1129cdf0e10cSrcweir DECL_PROP1 (TAG, ::rtl::OUString, BOUND); 11300de526bdSJianyuan Li DECL_PROP1 (CONTROL_TYPE_IN_MSO,sal_Int16, BOUND); 11310de526bdSJianyuan Li DECL_PROP1 (OBJ_ID_IN_MSO,sal_uInt16, BOUND); 1132cdf0e10cSrcweir END_DESCRIBE_PROPERTIES() 1133cdf0e10cSrcweir } 1134cdf0e10cSrcweir 1135cdf0e10cSrcweir //------------------------------------------------------------------------------ 1136cdf0e10cSrcweir void OControlModel::describeAggregateProperties( Sequence< Property >& /* [out] */ _rAggregateProps ) const 1137cdf0e10cSrcweir { 1138cdf0e10cSrcweir if ( m_xAggregateSet.is() ) 1139cdf0e10cSrcweir { 1140cdf0e10cSrcweir Reference< XPropertySetInfo > xPSI( m_xAggregateSet->getPropertySetInfo() ); 1141cdf0e10cSrcweir if ( xPSI.is() ) 1142cdf0e10cSrcweir _rAggregateProps = xPSI->getProperties(); 1143cdf0e10cSrcweir } 1144cdf0e10cSrcweir } 1145cdf0e10cSrcweir 1146cdf0e10cSrcweir //------------------------------------------------------------------------------ 1147cdf0e10cSrcweir ::osl::Mutex& OControlModel::getMutex() 1148cdf0e10cSrcweir { 1149cdf0e10cSrcweir return m_aMutex; 1150cdf0e10cSrcweir } 1151cdf0e10cSrcweir 1152cdf0e10cSrcweir //------------------------------------------------------------------------------ 1153cdf0e10cSrcweir void OControlModel::describeFixedAndAggregateProperties( Sequence< Property >& _out_rFixedProperties, Sequence< Property >& _out_rAggregateProperties ) const 1154cdf0e10cSrcweir { 1155cdf0e10cSrcweir describeFixedProperties( _out_rFixedProperties ); 1156cdf0e10cSrcweir describeAggregateProperties( _out_rAggregateProperties ); 1157cdf0e10cSrcweir } 1158cdf0e10cSrcweir 1159cdf0e10cSrcweir //------------------------------------------------------------------------------ 1160cdf0e10cSrcweir Reference< XMultiPropertySet > OControlModel::getPropertiesInterface() 1161cdf0e10cSrcweir { 1162cdf0e10cSrcweir return Reference< XMultiPropertySet >( *this, UNO_QUERY ); 1163cdf0e10cSrcweir } 1164cdf0e10cSrcweir 1165cdf0e10cSrcweir //------------------------------------------------------------------------------ 1166cdf0e10cSrcweir Reference< XPropertySetInfo> SAL_CALL OControlModel::getPropertySetInfo() throw( RuntimeException) 1167cdf0e10cSrcweir { 1168cdf0e10cSrcweir return createPropertySetInfo( getInfoHelper() ); 1169cdf0e10cSrcweir } 1170cdf0e10cSrcweir 1171cdf0e10cSrcweir //------------------------------------------------------------------------------ 1172cdf0e10cSrcweir ::cppu::IPropertyArrayHelper& OControlModel::getInfoHelper() 1173cdf0e10cSrcweir { 1174cdf0e10cSrcweir return m_aPropertyBagHelper.getInfoHelper(); 1175cdf0e10cSrcweir } 1176cdf0e10cSrcweir 1177cdf0e10cSrcweir //-------------------------------------------------------------------- 1178cdf0e10cSrcweir void SAL_CALL OControlModel::addProperty( const ::rtl::OUString& _rName, ::sal_Int16 _nAttributes, const Any& _rInitialValue ) throw (PropertyExistException, IllegalTypeException, IllegalArgumentException, RuntimeException) 1179cdf0e10cSrcweir { 1180cdf0e10cSrcweir m_aPropertyBagHelper.addProperty( _rName, _nAttributes, _rInitialValue ); 1181cdf0e10cSrcweir } 1182cdf0e10cSrcweir 1183cdf0e10cSrcweir //-------------------------------------------------------------------- 1184cdf0e10cSrcweir void SAL_CALL OControlModel::removeProperty( const ::rtl::OUString& _rName ) throw (UnknownPropertyException, NotRemoveableException, RuntimeException) 1185cdf0e10cSrcweir { 1186cdf0e10cSrcweir m_aPropertyBagHelper.removeProperty( _rName ); 1187cdf0e10cSrcweir } 1188cdf0e10cSrcweir 1189cdf0e10cSrcweir //-------------------------------------------------------------------- 1190cdf0e10cSrcweir Sequence< PropertyValue > SAL_CALL OControlModel::getPropertyValues() throw (RuntimeException) 1191cdf0e10cSrcweir { 1192cdf0e10cSrcweir return m_aPropertyBagHelper.getPropertyValues(); 1193cdf0e10cSrcweir } 1194cdf0e10cSrcweir 1195cdf0e10cSrcweir //-------------------------------------------------------------------- 1196cdf0e10cSrcweir void SAL_CALL OControlModel::setPropertyValues( const Sequence< PropertyValue >& _rProps ) throw (UnknownPropertyException, PropertyVetoException, IllegalArgumentException, WrappedTargetException, RuntimeException) 1197cdf0e10cSrcweir { 1198cdf0e10cSrcweir m_aPropertyBagHelper.setPropertyValues( _rProps ); 1199cdf0e10cSrcweir } 1200cdf0e10cSrcweir 1201cdf0e10cSrcweir //-------------------------------------------------------------------- 1202cdf0e10cSrcweir void OControlModel::lockInstance( LockAccess ) 1203cdf0e10cSrcweir { 1204cdf0e10cSrcweir m_aMutex.acquire(); 1205cdf0e10cSrcweir osl_incrementInterlockedCount( &m_lockCount ); 1206cdf0e10cSrcweir } 1207cdf0e10cSrcweir 1208cdf0e10cSrcweir //-------------------------------------------------------------------- 1209cdf0e10cSrcweir oslInterlockedCount OControlModel::unlockInstance( LockAccess ) 1210cdf0e10cSrcweir { 1211cdf0e10cSrcweir OSL_ENSURE( m_lockCount > 0, "OControlModel::unlockInstance: not locked!" ); 1212cdf0e10cSrcweir oslInterlockedCount lockCount = osl_decrementInterlockedCount( &m_lockCount ); 1213cdf0e10cSrcweir m_aMutex.release(); 1214cdf0e10cSrcweir return lockCount; 1215cdf0e10cSrcweir } 1216cdf0e10cSrcweir 1217cdf0e10cSrcweir //-------------------------------------------------------------------- 1218cdf0e10cSrcweir void OControlModel::firePropertyChanges( const Sequence< sal_Int32 >& _rHandles, const Sequence< Any >& _rOldValues, 1219cdf0e10cSrcweir const Sequence< Any >& _rNewValues, LockAccess ) 1220cdf0e10cSrcweir { 1221cdf0e10cSrcweir OPropertySetHelper::fire( 1222cdf0e10cSrcweir const_cast< Sequence< sal_Int32 >& >( _rHandles ).getArray(), 1223cdf0e10cSrcweir _rNewValues.getConstArray(), 1224cdf0e10cSrcweir _rOldValues.getConstArray(), 1225cdf0e10cSrcweir _rHandles.getLength(), 1226cdf0e10cSrcweir sal_False 1227cdf0e10cSrcweir ); 1228cdf0e10cSrcweir } 1229cdf0e10cSrcweir 1230cdf0e10cSrcweir //================================================================== 1231cdf0e10cSrcweir //= OBoundControlModel 1232cdf0e10cSrcweir //================================================================== 1233cdf0e10cSrcweir DBG_NAME(frm_OBoundControlModel); 1234cdf0e10cSrcweir //------------------------------------------------------------------ 1235cdf0e10cSrcweir Any SAL_CALL OBoundControlModel::queryAggregation( const Type& _rType ) throw (RuntimeException) 1236cdf0e10cSrcweir { 1237cdf0e10cSrcweir Any aReturn( OControlModel::queryAggregation(_rType) ); 1238cdf0e10cSrcweir if (!aReturn.hasValue()) 1239cdf0e10cSrcweir { 1240cdf0e10cSrcweir aReturn = OBoundControlModel_BASE1::queryInterface(_rType); 1241cdf0e10cSrcweir 1242cdf0e10cSrcweir if ( !aReturn.hasValue() && m_bCommitable ) 1243cdf0e10cSrcweir aReturn = OBoundControlModel_COMMITTING::queryInterface( _rType ); 1244cdf0e10cSrcweir 1245cdf0e10cSrcweir if ( !aReturn.hasValue() && m_bSupportsExternalBinding ) 1246cdf0e10cSrcweir aReturn = OBoundControlModel_BINDING::queryInterface( _rType ); 1247cdf0e10cSrcweir 1248cdf0e10cSrcweir if ( !aReturn.hasValue() && m_bSupportsValidation ) 1249cdf0e10cSrcweir aReturn = OBoundControlModel_VALIDATION::queryInterface( _rType ); 1250cdf0e10cSrcweir } 1251cdf0e10cSrcweir 1252cdf0e10cSrcweir return aReturn; 1253cdf0e10cSrcweir } 1254cdf0e10cSrcweir 1255cdf0e10cSrcweir //------------------------------------------------------------------ 1256cdf0e10cSrcweir OBoundControlModel::OBoundControlModel( 1257cdf0e10cSrcweir const Reference< XMultiServiceFactory>& _rxFactory, 1258cdf0e10cSrcweir const ::rtl::OUString& _rUnoControlModelTypeName, const ::rtl::OUString& _rDefault, 1259cdf0e10cSrcweir const sal_Bool _bCommitable, const sal_Bool _bSupportExternalBinding, const sal_Bool _bSupportsValidation ) 1260cdf0e10cSrcweir :OControlModel( _rxFactory, _rUnoControlModelTypeName, _rDefault, sal_False ) 1261cdf0e10cSrcweir ,OPropertyChangeListener( m_aMutex ) 1262cdf0e10cSrcweir ,m_xField() 1263cdf0e10cSrcweir ,m_xAmbientForm() 1264cdf0e10cSrcweir ,m_nValuePropertyAggregateHandle( -1 ) 1265cdf0e10cSrcweir ,m_nFieldType( DataType::OTHER ) 1266cdf0e10cSrcweir ,m_bValuePropertyMayBeVoid( false ) 1267cdf0e10cSrcweir ,m_aResetHelper( *this, m_aMutex ) 1268cdf0e10cSrcweir ,m_aUpdateListeners(m_aMutex) 1269cdf0e10cSrcweir ,m_aFormComponentListeners( m_aMutex ) 1270cdf0e10cSrcweir ,m_bInputRequired( sal_True ) 1271cdf0e10cSrcweir ,m_pAggPropMultiplexer( NULL ) 1272cdf0e10cSrcweir ,m_bFormListening( false ) 1273cdf0e10cSrcweir ,m_bLoaded(sal_False) 1274cdf0e10cSrcweir ,m_bRequired(sal_False) 1275cdf0e10cSrcweir ,m_bCommitable(_bCommitable) 1276cdf0e10cSrcweir ,m_bSupportsExternalBinding( _bSupportExternalBinding ) 1277cdf0e10cSrcweir ,m_bSupportsValidation( _bSupportsValidation ) 1278cdf0e10cSrcweir ,m_bForwardValueChanges(sal_True) 1279cdf0e10cSrcweir ,m_bTransferingValue( sal_False ) 1280cdf0e10cSrcweir ,m_bIsCurrentValueValid( sal_True ) 1281cdf0e10cSrcweir ,m_bBindingControlsRO( sal_False ) 1282cdf0e10cSrcweir ,m_bBindingControlsEnable( sal_False ) 1283cdf0e10cSrcweir ,m_eControlValueChangeInstigator( eOther ) 1284cdf0e10cSrcweir ,m_aLabelServiceName(FRM_SUN_COMPONENT_FIXEDTEXT) 1285cdf0e10cSrcweir { 1286cdf0e10cSrcweir DBG_CTOR(frm_OBoundControlModel, NULL); 1287cdf0e10cSrcweir 1288cdf0e10cSrcweir // start property listening at the aggregate 1289cdf0e10cSrcweir implInitAggMultiplexer( ); 1290cdf0e10cSrcweir } 1291cdf0e10cSrcweir 1292cdf0e10cSrcweir //------------------------------------------------------------------ 1293cdf0e10cSrcweir OBoundControlModel::OBoundControlModel( 1294cdf0e10cSrcweir const OBoundControlModel* _pOriginal, const Reference< XMultiServiceFactory>& _rxFactory ) 1295cdf0e10cSrcweir :OControlModel( _pOriginal, _rxFactory, sal_True, sal_False ) 1296cdf0e10cSrcweir ,OPropertyChangeListener( m_aMutex ) 1297cdf0e10cSrcweir ,m_xField() 1298cdf0e10cSrcweir ,m_xAmbientForm() 1299cdf0e10cSrcweir ,m_nValuePropertyAggregateHandle( _pOriginal->m_nValuePropertyAggregateHandle ) 1300cdf0e10cSrcweir ,m_nFieldType( DataType::OTHER ) 1301cdf0e10cSrcweir ,m_bValuePropertyMayBeVoid( _pOriginal->m_bValuePropertyMayBeVoid ) 1302cdf0e10cSrcweir ,m_aResetHelper( *this, m_aMutex ) 1303cdf0e10cSrcweir ,m_aUpdateListeners( m_aMutex ) 1304cdf0e10cSrcweir ,m_aFormComponentListeners( m_aMutex ) 1305cdf0e10cSrcweir ,m_xValidator( _pOriginal->m_xValidator ) 1306cdf0e10cSrcweir ,m_bInputRequired( sal_True ) 1307cdf0e10cSrcweir ,m_pAggPropMultiplexer( NULL ) 1308cdf0e10cSrcweir ,m_bFormListening( false ) 1309cdf0e10cSrcweir ,m_bLoaded( sal_False ) 1310cdf0e10cSrcweir ,m_bRequired( sal_False ) 1311cdf0e10cSrcweir ,m_bCommitable( _pOriginal->m_bCommitable ) 1312cdf0e10cSrcweir ,m_bSupportsExternalBinding( _pOriginal->m_bSupportsExternalBinding ) 1313cdf0e10cSrcweir ,m_bSupportsValidation( _pOriginal->m_bSupportsValidation ) 1314cdf0e10cSrcweir ,m_bForwardValueChanges( sal_True ) 1315cdf0e10cSrcweir ,m_bTransferingValue( sal_False ) 1316cdf0e10cSrcweir ,m_bIsCurrentValueValid( _pOriginal->m_bIsCurrentValueValid ) 1317cdf0e10cSrcweir ,m_bBindingControlsRO( sal_False ) 1318cdf0e10cSrcweir ,m_bBindingControlsEnable( sal_False ) 1319cdf0e10cSrcweir ,m_eControlValueChangeInstigator( eOther ) 1320cdf0e10cSrcweir { 1321cdf0e10cSrcweir DBG_CTOR(frm_OBoundControlModel, NULL); 1322cdf0e10cSrcweir 1323cdf0e10cSrcweir // start property listening at the aggregate 1324cdf0e10cSrcweir implInitAggMultiplexer( ); 1325cdf0e10cSrcweir 1326cdf0e10cSrcweir m_aLabelServiceName = _pOriginal->m_aLabelServiceName; 1327cdf0e10cSrcweir m_sValuePropertyName = _pOriginal->m_sValuePropertyName; 1328cdf0e10cSrcweir m_nValuePropertyAggregateHandle = _pOriginal->m_nValuePropertyAggregateHandle; 1329cdf0e10cSrcweir m_bValuePropertyMayBeVoid = _pOriginal->m_bValuePropertyMayBeVoid; 1330cdf0e10cSrcweir m_aValuePropertyType = _pOriginal->m_aValuePropertyType; 1331cdf0e10cSrcweir m_aControlSource = _pOriginal->m_aControlSource; 1332cdf0e10cSrcweir m_bInputRequired = _pOriginal->m_bInputRequired; 1333*07a3d7f1SPedro Giffuni // m_xLabelControl, though being a property, is not to be cloned, not even the reference will be transferred. 1334cdf0e10cSrcweir // (the former should be clear - a clone of the object we're only referencing does not make sense) 1335cdf0e10cSrcweir // (the second would violate the restriction for label controls that they're part of the 1336cdf0e10cSrcweir // same form component hierarchy - we ourself are no part, yet, so we can't have a label control) 1337cdf0e10cSrcweir 1338cdf0e10cSrcweir // start listening for changes at the value property 1339cdf0e10cSrcweir implInitValuePropertyListening( ); 1340cdf0e10cSrcweir } 1341cdf0e10cSrcweir 1342cdf0e10cSrcweir //------------------------------------------------------------------ 1343cdf0e10cSrcweir OBoundControlModel::~OBoundControlModel() 1344cdf0e10cSrcweir { 1345cdf0e10cSrcweir if ( !OComponentHelper::rBHelper.bDisposed ) 1346cdf0e10cSrcweir { 1347cdf0e10cSrcweir acquire(); 1348cdf0e10cSrcweir dispose(); 1349cdf0e10cSrcweir } 1350cdf0e10cSrcweir 1351cdf0e10cSrcweir doResetDelegator( ); 1352cdf0e10cSrcweir 1353cdf0e10cSrcweir OSL_ENSURE( m_pAggPropMultiplexer, "OBoundControlModel::~OBoundControlModel: what about my property multiplexer?" ); 1354cdf0e10cSrcweir if ( m_pAggPropMultiplexer ) 1355cdf0e10cSrcweir { 1356cdf0e10cSrcweir m_pAggPropMultiplexer->dispose(); 1357cdf0e10cSrcweir m_pAggPropMultiplexer->release(); 1358cdf0e10cSrcweir m_pAggPropMultiplexer = NULL; 1359cdf0e10cSrcweir } 1360cdf0e10cSrcweir 1361cdf0e10cSrcweir DBG_DTOR(frm_OBoundControlModel, NULL); 1362cdf0e10cSrcweir } 1363cdf0e10cSrcweir 1364cdf0e10cSrcweir //------------------------------------------------------------------ 1365cdf0e10cSrcweir void OBoundControlModel::clonedFrom( const OControlModel* _pOriginal ) 1366cdf0e10cSrcweir { 1367cdf0e10cSrcweir const OBoundControlModel* pBoundOriginal = static_cast< const OBoundControlModel* >( _pOriginal ); 1368cdf0e10cSrcweir // the value binding can be handled as if somebody called setValueBinding here 1369cdf0e10cSrcweir // By definition, bindings can be share between bindables 1370cdf0e10cSrcweir if ( pBoundOriginal && pBoundOriginal->m_xExternalBinding.is() ) 1371cdf0e10cSrcweir { 1372cdf0e10cSrcweir try 1373cdf0e10cSrcweir { 1374cdf0e10cSrcweir setValueBinding( pBoundOriginal->m_xExternalBinding ); 1375cdf0e10cSrcweir } 1376cdf0e10cSrcweir catch( const Exception& ) 1377cdf0e10cSrcweir { 1378cdf0e10cSrcweir DBG_UNHANDLED_EXCEPTION(); 1379cdf0e10cSrcweir } 1380cdf0e10cSrcweir } 1381cdf0e10cSrcweir } 1382cdf0e10cSrcweir 1383cdf0e10cSrcweir //----------------------------------------------------------------------------- 1384cdf0e10cSrcweir void OBoundControlModel::implInitAggMultiplexer( ) 1385cdf0e10cSrcweir { 1386cdf0e10cSrcweir increment( m_refCount ); 1387cdf0e10cSrcweir if ( m_xAggregateSet.is() ) 1388cdf0e10cSrcweir { 1389cdf0e10cSrcweir m_pAggPropMultiplexer = new OPropertyChangeMultiplexer( this, m_xAggregateSet, sal_False ); 1390cdf0e10cSrcweir m_pAggPropMultiplexer->acquire(); 1391cdf0e10cSrcweir } 1392cdf0e10cSrcweir decrement( m_refCount ); 1393cdf0e10cSrcweir 1394cdf0e10cSrcweir doSetDelegator(); 1395cdf0e10cSrcweir } 1396cdf0e10cSrcweir 1397cdf0e10cSrcweir //----------------------------------------------------------------------------- 1398cdf0e10cSrcweir void OBoundControlModel::implInitValuePropertyListening( ) const 1399cdf0e10cSrcweir { 1400cdf0e10cSrcweir // start listening for changes at the value property 1401cdf0e10cSrcweir // There are three pre-requisites for this to be done: 1402cdf0e10cSrcweir // 1. We support external value bindings. In this case, the changes in the control value need to 1403cdf0e10cSrcweir // be propagated to the external binding immediately when they happen 1404cdf0e10cSrcweir // 2. We support external validation. In this case, we need to listen for changes in the value 1405cdf0e10cSrcweir // property, since we need to revalidate then. 1406cdf0e10cSrcweir // 3. We are not committable. In this case, changes in the control value need to be propagated 1407cdf0e10cSrcweir // to the database column immediately when they happen. 1408cdf0e10cSrcweir if ( m_bSupportsExternalBinding || m_bSupportsValidation || !m_bCommitable ) 1409cdf0e10cSrcweir { 1410cdf0e10cSrcweir OSL_ENSURE( m_pAggPropMultiplexer, "OBoundControlModel::implInitValuePropertyListening: no multiplexer!" ); 1411cdf0e10cSrcweir if ( m_pAggPropMultiplexer && m_sValuePropertyName.getLength() ) 1412cdf0e10cSrcweir m_pAggPropMultiplexer->addProperty( m_sValuePropertyName ); 1413cdf0e10cSrcweir } 1414cdf0e10cSrcweir } 1415cdf0e10cSrcweir 1416cdf0e10cSrcweir //----------------------------------------------------------------------------- 1417cdf0e10cSrcweir void OBoundControlModel::initOwnValueProperty( const ::rtl::OUString& i_rValuePropertyName ) 1418cdf0e10cSrcweir { 1419cdf0e10cSrcweir OSL_PRECOND( !m_sValuePropertyName.getLength() && -1 == m_nValuePropertyAggregateHandle, 1420cdf0e10cSrcweir "OBoundControlModel::initOwnValueProperty: value property is already initialized!" ); 1421cdf0e10cSrcweir OSL_ENSURE( i_rValuePropertyName.getLength(), "OBoundControlModel::initOwnValueProperty: invalid property name!" ); 1422cdf0e10cSrcweir m_sValuePropertyName = i_rValuePropertyName; 1423cdf0e10cSrcweir } 1424cdf0e10cSrcweir 1425cdf0e10cSrcweir //----------------------------------------------------------------------------- 1426cdf0e10cSrcweir void OBoundControlModel::initValueProperty( const ::rtl::OUString& _rValuePropertyName, sal_Int32 _nValuePropertyExternalHandle ) 1427cdf0e10cSrcweir { 1428cdf0e10cSrcweir OSL_PRECOND( !m_sValuePropertyName.getLength() && -1 == m_nValuePropertyAggregateHandle, 1429cdf0e10cSrcweir "OBoundControlModel::initValueProperty: value property is already initialized!" ); 1430cdf0e10cSrcweir OSL_ENSURE( _rValuePropertyName.getLength(), "OBoundControlModel::initValueProperty: invalid property name!" ); 1431cdf0e10cSrcweir OSL_ENSURE( _nValuePropertyExternalHandle != -1, "OBoundControlModel::initValueProperty: invalid property handle!" ); 1432cdf0e10cSrcweir 1433cdf0e10cSrcweir m_sValuePropertyName = _rValuePropertyName; 1434cdf0e10cSrcweir m_nValuePropertyAggregateHandle = getOriginalHandle( _nValuePropertyExternalHandle ); 1435cdf0e10cSrcweir OSL_ENSURE( m_nValuePropertyAggregateHandle != -1, "OBoundControlModel::initValueProperty: unable to find the original handle!" ); 1436cdf0e10cSrcweir 1437cdf0e10cSrcweir if ( m_nValuePropertyAggregateHandle != -1 ) 1438cdf0e10cSrcweir { 1439cdf0e10cSrcweir Reference< XPropertySetInfo > xPropInfo( m_xAggregateSet->getPropertySetInfo(), UNO_SET_THROW ); 1440cdf0e10cSrcweir Property aValuePropDesc = xPropInfo->getPropertyByName( m_sValuePropertyName ); 1441cdf0e10cSrcweir m_aValuePropertyType = aValuePropDesc.Type; 1442cdf0e10cSrcweir m_bValuePropertyMayBeVoid = ( aValuePropDesc.Attributes & PropertyAttribute::MAYBEVOID ) != 0; 1443cdf0e10cSrcweir } 1444cdf0e10cSrcweir 1445cdf0e10cSrcweir // start listening for changes at the value property 1446cdf0e10cSrcweir implInitValuePropertyListening( ); 1447cdf0e10cSrcweir } 1448cdf0e10cSrcweir 1449cdf0e10cSrcweir //----------------------------------------------------------------------------- 1450cdf0e10cSrcweir void OBoundControlModel::suspendValueListening( ) 1451cdf0e10cSrcweir { 1452cdf0e10cSrcweir OSL_PRECOND( m_sValuePropertyName.getLength(), "OBoundControlModel::suspendValueListening: don't have a value property!" ); 1453cdf0e10cSrcweir OSL_PRECOND( m_pAggPropMultiplexer, "OBoundControlModel::suspendValueListening: I *am* not listening!" ); 1454cdf0e10cSrcweir 1455cdf0e10cSrcweir if ( m_pAggPropMultiplexer ) 1456cdf0e10cSrcweir m_pAggPropMultiplexer->lock(); 1457cdf0e10cSrcweir } 1458cdf0e10cSrcweir 1459cdf0e10cSrcweir //----------------------------------------------------------------------------- 1460cdf0e10cSrcweir void OBoundControlModel::resumeValueListening( ) 1461cdf0e10cSrcweir { 1462cdf0e10cSrcweir OSL_PRECOND( m_sValuePropertyName.getLength(), "OBoundControlModel::resumeValueListening: don't have a value property!" ); 1463cdf0e10cSrcweir OSL_PRECOND( m_pAggPropMultiplexer, "OBoundControlModel::resumeValueListening: I *am* not listening at all!" ); 1464cdf0e10cSrcweir OSL_PRECOND( !m_pAggPropMultiplexer || m_pAggPropMultiplexer->locked(), "OBoundControlModel::resumeValueListening: listening not suspended currently!" ); 1465cdf0e10cSrcweir 1466cdf0e10cSrcweir if ( m_pAggPropMultiplexer ) 1467cdf0e10cSrcweir m_pAggPropMultiplexer->unlock(); 1468cdf0e10cSrcweir } 1469cdf0e10cSrcweir 1470cdf0e10cSrcweir //----------------------------------------------------------------------------- 1471cdf0e10cSrcweir Sequence< Type > OBoundControlModel::_getTypes() 1472cdf0e10cSrcweir { 1473cdf0e10cSrcweir TypeBag aTypes( 1474cdf0e10cSrcweir OControlModel::_getTypes(), 1475cdf0e10cSrcweir OBoundControlModel_BASE1::getTypes() 1476cdf0e10cSrcweir ); 1477cdf0e10cSrcweir 1478cdf0e10cSrcweir if ( m_bCommitable ) 1479cdf0e10cSrcweir aTypes.addTypes( OBoundControlModel_COMMITTING::getTypes() ); 1480cdf0e10cSrcweir 1481cdf0e10cSrcweir if ( m_bSupportsExternalBinding ) 1482cdf0e10cSrcweir aTypes.addTypes( OBoundControlModel_BINDING::getTypes() ); 1483cdf0e10cSrcweir 1484cdf0e10cSrcweir if ( m_bSupportsValidation ) 1485cdf0e10cSrcweir aTypes.addTypes( OBoundControlModel_VALIDATION::getTypes() ); 1486cdf0e10cSrcweir 1487cdf0e10cSrcweir return aTypes.getTypes(); 1488cdf0e10cSrcweir } 1489cdf0e10cSrcweir 1490cdf0e10cSrcweir // OComponentHelper 1491cdf0e10cSrcweir //----------------------------------------------------------------------------- 1492cdf0e10cSrcweir void OBoundControlModel::disposing() 1493cdf0e10cSrcweir { 1494cdf0e10cSrcweir OControlModel::disposing(); 1495cdf0e10cSrcweir 1496cdf0e10cSrcweir ::osl::ClearableMutexGuard aGuard(m_aMutex); 1497cdf0e10cSrcweir 1498cdf0e10cSrcweir if ( m_pAggPropMultiplexer ) 1499cdf0e10cSrcweir m_pAggPropMultiplexer->dispose(); 1500cdf0e10cSrcweir 1501cdf0e10cSrcweir // notify all our listeners 1502cdf0e10cSrcweir com::sun::star::lang::EventObject aEvt( static_cast< XWeak* >( this ) ); 1503cdf0e10cSrcweir m_aUpdateListeners.disposeAndClear( aEvt ); 1504cdf0e10cSrcweir m_aResetHelper.disposing(); 1505cdf0e10cSrcweir 1506cdf0e10cSrcweir // disconnect from our database column 1507cdf0e10cSrcweir // TODO: could we replace the following 5 lines with a call to impl_disconnectDatabaseColumn_noNotify? 1508cdf0e10cSrcweir // The only more thing which it does is calling onDisconnectedDbColumn - could this 1509cdf0e10cSrcweir // cause trouble? At least when we continue to call OControlModel::disposing before, it *may*. 1510cdf0e10cSrcweir if ( hasField() ) 1511cdf0e10cSrcweir { 1512cdf0e10cSrcweir getField()->removePropertyChangeListener( PROPERTY_VALUE, this ); 1513cdf0e10cSrcweir resetField(); 1514cdf0e10cSrcweir } 1515cdf0e10cSrcweir m_xCursor = NULL; 1516cdf0e10cSrcweir 1517cdf0e10cSrcweir Reference< XComponent > xComp( m_xLabelControl, UNO_QUERY ); 1518cdf0e10cSrcweir if ( xComp.is() ) 1519cdf0e10cSrcweir xComp->removeEventListener(static_cast< XEventListener* >( static_cast< XPropertyChangeListener* >( this ) ) ); 1520cdf0e10cSrcweir 1521cdf0e10cSrcweir // disconnect from our external value binding 1522cdf0e10cSrcweir if ( hasExternalValueBinding() ) 1523cdf0e10cSrcweir disconnectExternalValueBinding(); 1524cdf0e10cSrcweir 1525cdf0e10cSrcweir // dito for the validator 1526cdf0e10cSrcweir if ( hasValidator() ) 1527cdf0e10cSrcweir disconnectValidator( ); 1528cdf0e10cSrcweir } 1529cdf0e10cSrcweir 1530cdf0e10cSrcweir //------------------------------------------------------------------------------ 1531cdf0e10cSrcweir void OBoundControlModel::onValuePropertyChange( ControlModelLock& i_rControLock ) 1532cdf0e10cSrcweir { 1533cdf0e10cSrcweir if ( hasExternalValueBinding() ) 1534cdf0e10cSrcweir { // the control value changed, while we have an external value binding 1535cdf0e10cSrcweir // -> forward the value to it 1536cdf0e10cSrcweir if ( m_eControlValueChangeInstigator != eExternalBinding ) 1537cdf0e10cSrcweir transferControlValueToExternal( i_rControLock ); 1538cdf0e10cSrcweir } 1539cdf0e10cSrcweir else if ( !m_bCommitable && m_xColumnUpdate.is() ) 1540cdf0e10cSrcweir { // the control value changed, while we are bound to a database column, 1541cdf0e10cSrcweir // but not committable (which means changes in the control have to be reflected to 1542cdf0e10cSrcweir // the underlying database column immediately) 1543cdf0e10cSrcweir // -> forward the value to the database column 1544cdf0e10cSrcweir if ( m_eControlValueChangeInstigator != eDbColumnBinding ) 1545cdf0e10cSrcweir commitControlValueToDbColumn( false ); 1546cdf0e10cSrcweir } 1547cdf0e10cSrcweir 1548cdf0e10cSrcweir // validate the new value 1549cdf0e10cSrcweir if ( m_bSupportsValidation ) 1550cdf0e10cSrcweir recheckValidity( true ); 1551cdf0e10cSrcweir } 1552cdf0e10cSrcweir 1553cdf0e10cSrcweir //------------------------------------------------------------------------------ 1554cdf0e10cSrcweir void OBoundControlModel::_propertyChanged( const PropertyChangeEvent& _rEvt ) throw ( RuntimeException ) 1555cdf0e10cSrcweir { 1556cdf0e10cSrcweir ControlModelLock aLock( *this ); 1557cdf0e10cSrcweir 1558cdf0e10cSrcweir OSL_ENSURE( _rEvt.PropertyName == m_sValuePropertyName, 1559cdf0e10cSrcweir "OBoundControlModel::_propertyChanged: where did this come from (1)?" ); 1560cdf0e10cSrcweir OSL_ENSURE( m_pAggPropMultiplexer && !m_pAggPropMultiplexer->locked(), 1561cdf0e10cSrcweir "OBoundControlModel::_propertyChanged: where did this come from (2)?" ); 1562cdf0e10cSrcweir 1563cdf0e10cSrcweir if ( _rEvt.PropertyName == m_sValuePropertyName ) 1564cdf0e10cSrcweir { 1565cdf0e10cSrcweir onValuePropertyChange( aLock ); 1566cdf0e10cSrcweir } 1567cdf0e10cSrcweir } 1568cdf0e10cSrcweir 1569cdf0e10cSrcweir //------------------------------------------------------------------------------ 1570cdf0e10cSrcweir void OBoundControlModel::startAggregatePropertyListening( const ::rtl::OUString& _rPropertyName ) 1571cdf0e10cSrcweir { 1572cdf0e10cSrcweir OSL_PRECOND( m_pAggPropMultiplexer, "OBoundControlModel::startAggregatePropertyListening: no multiplexer!" ); 1573cdf0e10cSrcweir OSL_ENSURE( _rPropertyName.getLength(), "OBoundControlModel::startAggregatePropertyListening: invalid property name!" ); 1574cdf0e10cSrcweir 1575cdf0e10cSrcweir if ( m_pAggPropMultiplexer && _rPropertyName.getLength() ) 1576cdf0e10cSrcweir { 1577cdf0e10cSrcweir m_pAggPropMultiplexer->addProperty( _rPropertyName ); 1578cdf0e10cSrcweir } 1579cdf0e10cSrcweir } 1580cdf0e10cSrcweir 1581cdf0e10cSrcweir //------------------------------------------------------------------------------ 1582cdf0e10cSrcweir void OBoundControlModel::doFormListening( const bool _bStart ) 1583cdf0e10cSrcweir { 1584cdf0e10cSrcweir OSL_PRECOND( !hasExternalValueBinding(), "OBoundControlModel::doFormListening: external value binding should overrule the database binding!" ); 1585cdf0e10cSrcweir 1586cdf0e10cSrcweir if ( isFormListening() == _bStart ) 1587cdf0e10cSrcweir return; 1588cdf0e10cSrcweir 1589cdf0e10cSrcweir if ( m_xAmbientForm.is() ) 1590cdf0e10cSrcweir _bStart ? m_xAmbientForm->addLoadListener( this ) : m_xAmbientForm->removeLoadListener( this ); 1591cdf0e10cSrcweir 1592cdf0e10cSrcweir Reference< XLoadable > xParentLoadable( getParent(), UNO_QUERY ); 1593cdf0e10cSrcweir if ( getParent().is() && !xParentLoadable.is() ) 1594cdf0e10cSrcweir { 1595cdf0e10cSrcweir // if our parent does not directly support the XLoadable interface, then it might support the 1596cdf0e10cSrcweir // XRowSetSupplier/XRowSetChangeBroadcaster interfaces. In this case we have to listen for changes 1597cdf0e10cSrcweir // broadcasted by the latter. 1598cdf0e10cSrcweir Reference< XRowSetChangeBroadcaster > xRowSetBroadcaster( getParent(), UNO_QUERY ); 1599cdf0e10cSrcweir if ( xRowSetBroadcaster.is() ) 1600cdf0e10cSrcweir _bStart ? xRowSetBroadcaster->addRowSetChangeListener( this ) : xRowSetBroadcaster->removeRowSetChangeListener( this ); 1601cdf0e10cSrcweir } 1602cdf0e10cSrcweir 1603cdf0e10cSrcweir m_bFormListening = _bStart && m_xAmbientForm.is(); 1604cdf0e10cSrcweir } 1605cdf0e10cSrcweir 1606cdf0e10cSrcweir // XChild 1607cdf0e10cSrcweir //------------------------------------------------------------------------------ 1608cdf0e10cSrcweir void SAL_CALL OBoundControlModel::setParent(const Reference<XInterface>& _rxParent) throw(com::sun::star::lang::NoSupportException, RuntimeException) 1609cdf0e10cSrcweir { 1610cdf0e10cSrcweir ControlModelLock aLock( *this ); 1611cdf0e10cSrcweir FieldChangeNotifier aBoundFieldNotifier( aLock ); 1612cdf0e10cSrcweir 1613cdf0e10cSrcweir if ( getParent() == _rxParent ) 1614cdf0e10cSrcweir return; 1615cdf0e10cSrcweir 1616cdf0e10cSrcweir // disconnect from database column (which is controlled by parent, directly or indirectly) 1617cdf0e10cSrcweir if ( hasField() ) 1618cdf0e10cSrcweir impl_disconnectDatabaseColumn_noNotify(); 1619cdf0e10cSrcweir 1620cdf0e10cSrcweir // log off old listeners 1621cdf0e10cSrcweir if ( isFormListening() ) 1622cdf0e10cSrcweir doFormListening( false ); 1623cdf0e10cSrcweir 1624cdf0e10cSrcweir // actually set the new parent 1625cdf0e10cSrcweir OControlModel::setParent( _rxParent ); 1626cdf0e10cSrcweir 1627cdf0e10cSrcweir // a new parent means a new ambient form 1628cdf0e10cSrcweir impl_determineAmbientForm_nothrow(); 1629cdf0e10cSrcweir 1630cdf0e10cSrcweir if ( !hasExternalValueBinding() ) 1631cdf0e10cSrcweir { 1632cdf0e10cSrcweir // log on new listeners 1633cdf0e10cSrcweir doFormListening( true ); 1634cdf0e10cSrcweir 1635cdf0e10cSrcweir // re-connect to database column of the new parent 1636cdf0e10cSrcweir if ( m_xAmbientForm.is() && m_xAmbientForm->isLoaded() ) 1637cdf0e10cSrcweir impl_connectDatabaseColumn_noNotify( false ); 1638cdf0e10cSrcweir } 1639cdf0e10cSrcweir } 1640cdf0e10cSrcweir 1641cdf0e10cSrcweir // XEventListener 1642cdf0e10cSrcweir //------------------------------------------------------------------------------ 1643cdf0e10cSrcweir void SAL_CALL OBoundControlModel::disposing(const com::sun::star::lang::EventObject& _rEvent) throw (RuntimeException) 1644cdf0e10cSrcweir { 1645cdf0e10cSrcweir ControlModelLock aLock( *this ); 1646cdf0e10cSrcweir 1647cdf0e10cSrcweir if ( _rEvent.Source == getField() ) 1648cdf0e10cSrcweir { 1649cdf0e10cSrcweir resetField(); 1650cdf0e10cSrcweir } 1651cdf0e10cSrcweir else if ( _rEvent.Source == m_xLabelControl ) 1652cdf0e10cSrcweir { 1653cdf0e10cSrcweir Reference<XPropertySet> xOldValue = m_xLabelControl; 1654cdf0e10cSrcweir m_xLabelControl = NULL; 1655cdf0e10cSrcweir 1656cdf0e10cSrcweir // fire a propertyChanged (when we leave aLock's scope) 1657cdf0e10cSrcweir aLock.addPropertyNotification( PROPERTY_ID_CONTROLLABEL, makeAny( xOldValue ), makeAny( m_xLabelControl ) ); 1658cdf0e10cSrcweir } 1659cdf0e10cSrcweir else if ( _rEvent.Source == m_xExternalBinding ) 1660cdf0e10cSrcweir { // *first* check for the external binding 1661cdf0e10cSrcweir disconnectExternalValueBinding( ); 1662cdf0e10cSrcweir } 1663cdf0e10cSrcweir else if ( _rEvent.Source == m_xValidator ) 1664cdf0e10cSrcweir { // *then* check for the validator. Reason is that bindings may also act as validator at the same 1665cdf0e10cSrcweir // time, in this case, the validator is automatically revoked when the binding is revoked 1666cdf0e10cSrcweir disconnectValidator( ); 1667cdf0e10cSrcweir } 1668cdf0e10cSrcweir else 1669cdf0e10cSrcweir OControlModel::disposing(_rEvent); 1670cdf0e10cSrcweir } 1671cdf0e10cSrcweir 1672cdf0e10cSrcweir // XServiceInfo 1673cdf0e10cSrcweir //------------------------------------------------------------------------------ 1674cdf0e10cSrcweir StringSequence SAL_CALL OBoundControlModel::getSupportedServiceNames() throw(RuntimeException) 1675cdf0e10cSrcweir { 1676cdf0e10cSrcweir return ::comphelper::concatSequences( 1677cdf0e10cSrcweir getAggregateServiceNames(), 1678cdf0e10cSrcweir getSupportedServiceNames_Static() 1679cdf0e10cSrcweir ); 1680cdf0e10cSrcweir } 1681cdf0e10cSrcweir 1682cdf0e10cSrcweir //------------------------------------------------------------------------------ 1683cdf0e10cSrcweir Sequence< ::rtl::OUString > SAL_CALL OBoundControlModel::getSupportedServiceNames_Static() throw( RuntimeException ) 1684cdf0e10cSrcweir { 1685cdf0e10cSrcweir Sequence< ::rtl::OUString > aOwnServiceNames( 1 ); 1686cdf0e10cSrcweir aOwnServiceNames[ 0 ] = ::rtl::OUString::createFromAscii( "com.sun.star.form.DataAwareControlModel" ); 1687cdf0e10cSrcweir 1688cdf0e10cSrcweir return ::comphelper::concatSequences( 1689cdf0e10cSrcweir OControlModel::getSupportedServiceNames_Static(), 1690cdf0e10cSrcweir aOwnServiceNames 1691cdf0e10cSrcweir ); 1692cdf0e10cSrcweir } 1693cdf0e10cSrcweir 1694cdf0e10cSrcweir // XPersist 1695cdf0e10cSrcweir //------------------------------------------------------------------------------ 1696cdf0e10cSrcweir void SAL_CALL OBoundControlModel::write( const Reference<stario::XObjectOutputStream>& _rxOutStream ) throw(stario::IOException, RuntimeException) 1697cdf0e10cSrcweir { 1698cdf0e10cSrcweir OControlModel::write(_rxOutStream); 1699cdf0e10cSrcweir 1700cdf0e10cSrcweir osl::MutexGuard aGuard(m_aMutex); 1701cdf0e10cSrcweir 1702cdf0e10cSrcweir // Version 1703cdf0e10cSrcweir _rxOutStream->writeShort(0x0002); 1704cdf0e10cSrcweir 1705cdf0e10cSrcweir // Controlsource 1706cdf0e10cSrcweir ::comphelper::operator<<( _rxOutStream, m_aControlSource); 1707cdf0e10cSrcweir 1708cdf0e10cSrcweir // !!! IMPORTANT NOTE !!! 1709cdf0e10cSrcweir // don't write any new members here : this wouldn't be compatible with older versions, as OBoundControlModel 1710cdf0e10cSrcweir // is a base class which is called in derived classes "read" method. So if you increment the version 1711cdf0e10cSrcweir // and write new stuff, older office versions will read this in the _derived_ classes, which may result 1712cdf0e10cSrcweir // in anything from data loss to crash. 1713cdf0e10cSrcweir // (use writeCommonProperties instead, this is called in derived classes write-method) 1714cdf0e10cSrcweir // !!! EOIN !!! 1715cdf0e10cSrcweir // FS - 68876 - 28.09.1999 1716cdf0e10cSrcweir } 1717cdf0e10cSrcweir 1718cdf0e10cSrcweir //------------------------------------------------------------------------------ 1719cdf0e10cSrcweir void OBoundControlModel::defaultCommonProperties() 1720cdf0e10cSrcweir { 1721cdf0e10cSrcweir Reference<com::sun::star::lang::XComponent> xComp(m_xLabelControl, UNO_QUERY); 1722cdf0e10cSrcweir if (xComp.is()) 1723cdf0e10cSrcweir xComp->removeEventListener(static_cast<com::sun::star::lang::XEventListener*>(static_cast<XPropertyChangeListener*>(this))); 1724cdf0e10cSrcweir m_xLabelControl = NULL; 1725cdf0e10cSrcweir } 1726cdf0e10cSrcweir 1727cdf0e10cSrcweir //------------------------------------------------------------------------------ 1728cdf0e10cSrcweir void OBoundControlModel::readCommonProperties(const Reference<stario::XObjectInputStream>& _rxInStream) 1729cdf0e10cSrcweir { 1730cdf0e10cSrcweir sal_Int32 nLen = _rxInStream->readLong(); 1731cdf0e10cSrcweir 1732cdf0e10cSrcweir Reference<stario::XMarkableStream> xMark(_rxInStream, UNO_QUERY); 1733cdf0e10cSrcweir DBG_ASSERT(xMark.is(), "OBoundControlModel::readCommonProperties : can only work with markable streams !"); 1734cdf0e10cSrcweir sal_Int32 nMark = xMark->createMark(); 1735cdf0e10cSrcweir 1736cdf0e10cSrcweir // read the reference to the label control 1737cdf0e10cSrcweir Reference<stario::XPersistObject> xPersist; 1738cdf0e10cSrcweir sal_Int32 nUsedFlag; 1739cdf0e10cSrcweir nUsedFlag = _rxInStream->readLong(); 1740cdf0e10cSrcweir if (nUsedFlag) 1741cdf0e10cSrcweir xPersist = _rxInStream->readObject(); 1742cdf0e10cSrcweir m_xLabelControl = m_xLabelControl.query( xPersist ); 1743cdf0e10cSrcweir Reference< XComponent > xComp( m_xLabelControl, UNO_QUERY ); 1744cdf0e10cSrcweir if (xComp.is()) 1745cdf0e10cSrcweir xComp->addEventListener(static_cast<com::sun::star::lang::XEventListener*>(static_cast<XPropertyChangeListener*>(this))); 1746cdf0e10cSrcweir 1747cdf0e10cSrcweir // read any other new common properties here 1748cdf0e10cSrcweir 1749cdf0e10cSrcweir // skip the remaining bytes 1750cdf0e10cSrcweir xMark->jumpToMark(nMark); 1751cdf0e10cSrcweir _rxInStream->skipBytes(nLen); 1752cdf0e10cSrcweir xMark->deleteMark(nMark); 1753cdf0e10cSrcweir } 1754cdf0e10cSrcweir 1755cdf0e10cSrcweir //------------------------------------------------------------------------------ 1756cdf0e10cSrcweir void OBoundControlModel::writeCommonProperties(const Reference<stario::XObjectOutputStream>& _rxOutStream) 1757cdf0e10cSrcweir { 1758cdf0e10cSrcweir Reference<stario::XMarkableStream> xMark(_rxOutStream, UNO_QUERY); 1759cdf0e10cSrcweir DBG_ASSERT(xMark.is(), "OBoundControlModel::writeCommonProperties : can only work with markable streams !"); 1760cdf0e10cSrcweir sal_Int32 nMark = xMark->createMark(); 1761cdf0e10cSrcweir 1762cdf0e10cSrcweir // a placeholder where we will write the overall length (later in this method) 1763cdf0e10cSrcweir sal_Int32 nLen = 0; 1764cdf0e10cSrcweir _rxOutStream->writeLong(nLen); 1765cdf0e10cSrcweir 1766cdf0e10cSrcweir // write the reference to the label control 1767cdf0e10cSrcweir Reference<stario::XPersistObject> xPersist(m_xLabelControl, UNO_QUERY); 1768cdf0e10cSrcweir sal_Int32 nUsedFlag = 0; 1769cdf0e10cSrcweir if (xPersist.is()) 1770cdf0e10cSrcweir nUsedFlag = 1; 1771cdf0e10cSrcweir _rxOutStream->writeLong(nUsedFlag); 1772cdf0e10cSrcweir if (xPersist.is()) 1773cdf0e10cSrcweir _rxOutStream->writeObject(xPersist); 1774cdf0e10cSrcweir 1775cdf0e10cSrcweir // write any other new common properties here 1776cdf0e10cSrcweir 1777cdf0e10cSrcweir // write the correct length at the beginning of the block 1778cdf0e10cSrcweir nLen = xMark->offsetToMark(nMark) - sizeof(nLen); 1779cdf0e10cSrcweir xMark->jumpToMark(nMark); 1780cdf0e10cSrcweir _rxOutStream->writeLong(nLen); 1781cdf0e10cSrcweir xMark->jumpToFurthest(); 1782cdf0e10cSrcweir xMark->deleteMark(nMark); 1783cdf0e10cSrcweir } 1784cdf0e10cSrcweir 1785cdf0e10cSrcweir //------------------------------------------------------------------------------ 1786cdf0e10cSrcweir void SAL_CALL OBoundControlModel::read( const Reference< stario::XObjectInputStream >& _rxInStream ) throw(stario::IOException, RuntimeException) 1787cdf0e10cSrcweir { 1788cdf0e10cSrcweir OControlModel::read(_rxInStream); 1789cdf0e10cSrcweir 1790cdf0e10cSrcweir osl::MutexGuard aGuard(m_aMutex); 1791cdf0e10cSrcweir sal_uInt16 nVersion = _rxInStream->readShort(); (void)nVersion; 1792cdf0e10cSrcweir ::comphelper::operator>>( _rxInStream, m_aControlSource); 1793cdf0e10cSrcweir } 1794cdf0e10cSrcweir 1795cdf0e10cSrcweir //------------------------------------------------------------------------------ 1796cdf0e10cSrcweir void OBoundControlModel::getFastPropertyValue(Any& rValue, sal_Int32 nHandle) const 1797cdf0e10cSrcweir { 1798cdf0e10cSrcweir switch (nHandle) 1799cdf0e10cSrcweir { 1800cdf0e10cSrcweir case PROPERTY_ID_INPUT_REQUIRED: 1801cdf0e10cSrcweir rValue <<= m_bInputRequired; 1802cdf0e10cSrcweir break; 1803cdf0e10cSrcweir case PROPERTY_ID_CONTROLSOURCEPROPERTY: 1804cdf0e10cSrcweir rValue <<= m_sValuePropertyName; 1805cdf0e10cSrcweir break; 1806cdf0e10cSrcweir case PROPERTY_ID_CONTROLSOURCE: 1807cdf0e10cSrcweir rValue <<= m_aControlSource; 1808cdf0e10cSrcweir break; 1809cdf0e10cSrcweir case PROPERTY_ID_BOUNDFIELD: 1810cdf0e10cSrcweir rValue <<= getField(); 1811cdf0e10cSrcweir break; 1812cdf0e10cSrcweir case PROPERTY_ID_CONTROLLABEL: 1813cdf0e10cSrcweir if (!m_xLabelControl.is()) 1814cdf0e10cSrcweir rValue.clear(); 1815cdf0e10cSrcweir else 1816cdf0e10cSrcweir rValue <<= m_xLabelControl; 1817cdf0e10cSrcweir break; 1818cdf0e10cSrcweir default: 1819cdf0e10cSrcweir OControlModel::getFastPropertyValue(rValue, nHandle); 1820cdf0e10cSrcweir } 1821cdf0e10cSrcweir } 1822cdf0e10cSrcweir 1823cdf0e10cSrcweir //------------------------------------------------------------------------------ 1824cdf0e10cSrcweir sal_Bool OBoundControlModel::convertFastPropertyValue( 1825cdf0e10cSrcweir Any& _rConvertedValue, Any& _rOldValue, 1826cdf0e10cSrcweir sal_Int32 _nHandle, 1827cdf0e10cSrcweir const Any& _rValue) 1828cdf0e10cSrcweir throw (com::sun::star::lang::IllegalArgumentException) 1829cdf0e10cSrcweir { 1830cdf0e10cSrcweir sal_Bool bModified(sal_False); 1831cdf0e10cSrcweir switch (_nHandle) 1832cdf0e10cSrcweir { 1833cdf0e10cSrcweir case PROPERTY_ID_INPUT_REQUIRED: 1834cdf0e10cSrcweir bModified = tryPropertyValue( _rConvertedValue, _rOldValue, _rValue, m_bInputRequired ); 1835cdf0e10cSrcweir break; 1836cdf0e10cSrcweir case PROPERTY_ID_CONTROLSOURCE: 1837cdf0e10cSrcweir bModified = tryPropertyValue(_rConvertedValue, _rOldValue, _rValue, m_aControlSource); 1838cdf0e10cSrcweir break; 1839cdf0e10cSrcweir case PROPERTY_ID_BOUNDFIELD: 1840cdf0e10cSrcweir DBG_ERROR( "OBoundControlModel::convertFastPropertyValue: BoundField should be a read-only property !" ); 1841cdf0e10cSrcweir throw com::sun::star::lang::IllegalArgumentException(); 1842cdf0e10cSrcweir case PROPERTY_ID_CONTROLLABEL: 1843cdf0e10cSrcweir if (!_rValue.hasValue()) 1844cdf0e10cSrcweir { // property set to void 1845cdf0e10cSrcweir _rConvertedValue = Any(); 1846cdf0e10cSrcweir getFastPropertyValue(_rOldValue, _nHandle); 1847cdf0e10cSrcweir bModified = m_xLabelControl.is(); 1848cdf0e10cSrcweir } 1849cdf0e10cSrcweir else 1850cdf0e10cSrcweir { 1851cdf0e10cSrcweir bModified = tryPropertyValue(_rConvertedValue, _rOldValue, _rValue, m_xLabelControl); 1852cdf0e10cSrcweir if (!m_xLabelControl.is()) 1853cdf0e10cSrcweir // an empty interface is interpreted as VOID 1854cdf0e10cSrcweir _rOldValue.clear(); 1855cdf0e10cSrcweir } 1856cdf0e10cSrcweir break; 1857cdf0e10cSrcweir default: 1858cdf0e10cSrcweir bModified = OControlModel::convertFastPropertyValue(_rConvertedValue, _rOldValue, _nHandle, _rValue); 1859cdf0e10cSrcweir } 1860cdf0e10cSrcweir return bModified; 1861cdf0e10cSrcweir } 1862cdf0e10cSrcweir 1863cdf0e10cSrcweir //------------------------------------------------------------------------------ 1864cdf0e10cSrcweir Any OBoundControlModel::getPropertyDefaultByHandle( sal_Int32 _nHandle ) const 1865cdf0e10cSrcweir { 1866cdf0e10cSrcweir Any aDefault; 1867cdf0e10cSrcweir switch ( _nHandle ) 1868cdf0e10cSrcweir { 1869cdf0e10cSrcweir case PROPERTY_ID_INPUT_REQUIRED: 1870cdf0e10cSrcweir aDefault <<= sal_Bool( sal_True ); 1871cdf0e10cSrcweir break; 1872cdf0e10cSrcweir 1873cdf0e10cSrcweir case PROPERTY_ID_CONTROLSOURCE: 1874cdf0e10cSrcweir aDefault <<= ::rtl::OUString(); 1875cdf0e10cSrcweir break; 1876cdf0e10cSrcweir 1877cdf0e10cSrcweir case PROPERTY_ID_CONTROLLABEL: 1878cdf0e10cSrcweir aDefault <<= Reference< XPropertySet >(); 1879cdf0e10cSrcweir break; 1880cdf0e10cSrcweir } 1881cdf0e10cSrcweir return aDefault; 1882cdf0e10cSrcweir } 1883cdf0e10cSrcweir 1884cdf0e10cSrcweir //------------------------------------------------------------------------------ 1885cdf0e10cSrcweir void OBoundControlModel::setFastPropertyValue_NoBroadcast( sal_Int32 nHandle, const Any& rValue ) throw (Exception) 1886cdf0e10cSrcweir { 1887cdf0e10cSrcweir switch (nHandle) 1888cdf0e10cSrcweir { 1889cdf0e10cSrcweir case PROPERTY_ID_INPUT_REQUIRED: 1890cdf0e10cSrcweir OSL_VERIFY( rValue >>= m_bInputRequired ); 1891cdf0e10cSrcweir break; 1892cdf0e10cSrcweir case PROPERTY_ID_CONTROLSOURCE: 1893cdf0e10cSrcweir OSL_VERIFY( rValue >>= m_aControlSource ); 1894cdf0e10cSrcweir break; 1895cdf0e10cSrcweir case PROPERTY_ID_BOUNDFIELD: 1896cdf0e10cSrcweir DBG_ERROR("OBoundControlModel::setFastPropertyValue_NoBroadcast : BoundField should be a read-only property !"); 1897cdf0e10cSrcweir throw com::sun::star::lang::IllegalArgumentException(); 1898cdf0e10cSrcweir case PROPERTY_ID_CONTROLLABEL: 1899cdf0e10cSrcweir { 1900cdf0e10cSrcweir if ( rValue.hasValue() && ( rValue.getValueTypeClass() != TypeClass_INTERFACE ) ) 1901cdf0e10cSrcweir throw com::sun::star::lang::IllegalArgumentException(); 1902cdf0e10cSrcweir 1903cdf0e10cSrcweir Reference< XInterface > xNewValue( rValue, UNO_QUERY ); 1904cdf0e10cSrcweir if ( !xNewValue.is() ) 1905cdf0e10cSrcweir { // set property to "void" 1906cdf0e10cSrcweir Reference< XComponent > xComp( m_xLabelControl, UNO_QUERY ); 1907cdf0e10cSrcweir if ( xComp.is() ) 1908cdf0e10cSrcweir xComp->removeEventListener( static_cast< XPropertyChangeListener* >( this ) ); 1909cdf0e10cSrcweir m_xLabelControl = NULL; 1910cdf0e10cSrcweir break; 1911cdf0e10cSrcweir } 1912cdf0e10cSrcweir 1913cdf0e10cSrcweir Reference< XControlModel > xAsModel ( xNewValue, UNO_QUERY ); 1914cdf0e10cSrcweir Reference< XServiceInfo > xAsServiceInfo ( xAsModel, UNO_QUERY ); 1915cdf0e10cSrcweir Reference< XPropertySet > xAsPropSet ( xAsServiceInfo, UNO_QUERY ); 1916cdf0e10cSrcweir Reference< XChild > xAsChild ( xAsPropSet, UNO_QUERY ); 1917cdf0e10cSrcweir if ( !xAsChild.is() || !xAsServiceInfo->supportsService( m_aLabelServiceName ) ) 1918cdf0e10cSrcweir { 1919cdf0e10cSrcweir throw com::sun::star::lang::IllegalArgumentException(); 1920cdf0e10cSrcweir } 1921cdf0e10cSrcweir 1922cdf0e10cSrcweir // check if weself and the given model have a common anchestor (up to the forms collection) 1923cdf0e10cSrcweir Reference<XChild> xCont; 1924cdf0e10cSrcweir query_interface(static_cast<XWeak*>(this), xCont); 1925cdf0e10cSrcweir Reference< XInterface > xMyTopLevel = xCont->getParent(); 1926cdf0e10cSrcweir while (xMyTopLevel.is()) 1927cdf0e10cSrcweir { 1928cdf0e10cSrcweir Reference<XForm> xAsForm(xMyTopLevel, UNO_QUERY); 1929cdf0e10cSrcweir if (!xAsForm.is()) 1930cdf0e10cSrcweir // found my root 1931cdf0e10cSrcweir break; 1932cdf0e10cSrcweir 1933cdf0e10cSrcweir Reference<XChild> xLoopAsChild(xMyTopLevel, UNO_QUERY); 1934cdf0e10cSrcweir xMyTopLevel = xLoopAsChild.is() ? xLoopAsChild->getParent() : Reference< XInterface >(); 1935cdf0e10cSrcweir } 1936cdf0e10cSrcweir Reference< XInterface > xNewTopLevel = xAsChild->getParent(); 1937cdf0e10cSrcweir while (xNewTopLevel.is()) 1938cdf0e10cSrcweir { 1939cdf0e10cSrcweir Reference<XForm> xAsForm(xNewTopLevel, UNO_QUERY); 1940cdf0e10cSrcweir if (!xAsForm.is()) 1941cdf0e10cSrcweir break; 1942cdf0e10cSrcweir 1943cdf0e10cSrcweir Reference<XChild> xLoopAsChild(xNewTopLevel, UNO_QUERY); 1944cdf0e10cSrcweir xNewTopLevel = xLoopAsChild.is() ? xLoopAsChild->getParent() : Reference< XInterface >(); 1945cdf0e10cSrcweir } 1946cdf0e10cSrcweir if (xNewTopLevel != xMyTopLevel) 1947cdf0e10cSrcweir { 1948cdf0e10cSrcweir // the both objects don't belong to the same forms collection -> not acceptable 1949cdf0e10cSrcweir throw com::sun::star::lang::IllegalArgumentException(); 1950cdf0e10cSrcweir } 1951cdf0e10cSrcweir 1952cdf0e10cSrcweir m_xLabelControl = xAsPropSet; 1953cdf0e10cSrcweir Reference<com::sun::star::lang::XComponent> xComp(m_xLabelControl, UNO_QUERY); 1954cdf0e10cSrcweir if (xComp.is()) 1955cdf0e10cSrcweir xComp->addEventListener(static_cast<com::sun::star::lang::XEventListener*>(static_cast<XPropertyChangeListener*>(this))); 1956cdf0e10cSrcweir } 1957cdf0e10cSrcweir break; 1958cdf0e10cSrcweir default: 1959cdf0e10cSrcweir OControlModel::setFastPropertyValue_NoBroadcast(nHandle, rValue ); 1960cdf0e10cSrcweir } 1961cdf0e10cSrcweir } 1962cdf0e10cSrcweir 1963cdf0e10cSrcweir // XPropertyChangeListener 1964cdf0e10cSrcweir //------------------------------------------------------------------------------ 1965cdf0e10cSrcweir void SAL_CALL OBoundControlModel::propertyChange( const PropertyChangeEvent& evt ) throw(RuntimeException) 1966cdf0e10cSrcweir { 1967cdf0e10cSrcweir // if the DBColumn value changed, transfer it to the control 1968cdf0e10cSrcweir if ( evt.PropertyName.equals( PROPERTY_VALUE ) ) 1969cdf0e10cSrcweir { 1970*07a3d7f1SPedro Giffuni OSL_ENSURE( evt.Source == getField(), "OBoundControlModel::propertyChange: value changes from components other than our database column?" ); 1971cdf0e10cSrcweir osl::MutexGuard aGuard(m_aMutex); 1972cdf0e10cSrcweir if ( m_bForwardValueChanges && m_xColumn.is() ) 1973cdf0e10cSrcweir transferDbValueToControl(); 1974cdf0e10cSrcweir } 1975cdf0e10cSrcweir else 1976cdf0e10cSrcweir { 1977cdf0e10cSrcweir OSL_ENSURE( evt.Source == m_xExternalBinding, "OBoundControlModel::propertyChange: where did this come from?" ); 1978cdf0e10cSrcweir 1979cdf0e10cSrcweir // our binding has properties which can control properties of ourself 1980cdf0e10cSrcweir ::rtl::OUString sBindingControlledProperty; 1981cdf0e10cSrcweir bool bForwardToLabelControl = false; 1982cdf0e10cSrcweir if ( evt.PropertyName.equals( PROPERTY_READONLY ) ) 1983cdf0e10cSrcweir { 1984cdf0e10cSrcweir sBindingControlledProperty = PROPERTY_READONLY; 1985cdf0e10cSrcweir } 1986cdf0e10cSrcweir else if ( evt.PropertyName.equals( PROPERTY_RELEVANT ) ) 1987cdf0e10cSrcweir { 1988cdf0e10cSrcweir sBindingControlledProperty = PROPERTY_ENABLED; 1989cdf0e10cSrcweir bForwardToLabelControl = true; 1990cdf0e10cSrcweir } 1991cdf0e10cSrcweir else 1992cdf0e10cSrcweir return; 1993cdf0e10cSrcweir 1994cdf0e10cSrcweir try 1995cdf0e10cSrcweir { 1996cdf0e10cSrcweir setPropertyValue( sBindingControlledProperty, evt.NewValue ); 1997cdf0e10cSrcweir if ( bForwardToLabelControl && m_xLabelControl.is() ) 1998cdf0e10cSrcweir m_xLabelControl->setPropertyValue( sBindingControlledProperty, evt.NewValue ); 1999cdf0e10cSrcweir } 2000cdf0e10cSrcweir catch( const Exception& ) 2001cdf0e10cSrcweir { 2002cdf0e10cSrcweir OSL_ENSURE( sal_False, "OBoundControlModel::propertyChange: could not adjust my binding-controlled property!" ); 2003cdf0e10cSrcweir } 2004cdf0e10cSrcweir } 2005cdf0e10cSrcweir } 2006cdf0e10cSrcweir 2007cdf0e10cSrcweir //------------------------------------------------------------------------------ 2008cdf0e10cSrcweir void SAL_CALL OBoundControlModel::onRowSetChanged( const EventObject& /*i_Event*/ ) throw (RuntimeException) 2009cdf0e10cSrcweir { 2010cdf0e10cSrcweir ControlModelLock aLock( *this ); 2011cdf0e10cSrcweir FieldChangeNotifier aBoundFieldNotifier( aLock ); 2012cdf0e10cSrcweir 2013cdf0e10cSrcweir // disconnect from database column (which is controlled by parent, directly or indirectly) 2014cdf0e10cSrcweir if ( hasField() ) 2015cdf0e10cSrcweir impl_disconnectDatabaseColumn_noNotify(); 2016cdf0e10cSrcweir 2017cdf0e10cSrcweir // log off old listeners 2018cdf0e10cSrcweir if ( isFormListening() ) 2019cdf0e10cSrcweir doFormListening( false ); 2020cdf0e10cSrcweir 2021cdf0e10cSrcweir // determine the new ambient form 2022cdf0e10cSrcweir impl_determineAmbientForm_nothrow(); 2023cdf0e10cSrcweir 2024cdf0e10cSrcweir // log on new listeners 2025cdf0e10cSrcweir doFormListening( true ); 2026cdf0e10cSrcweir 2027cdf0e10cSrcweir // re-connect to database column if needed and possible 2028cdf0e10cSrcweir if ( m_xAmbientForm.is() && m_xAmbientForm->isLoaded() ) 2029cdf0e10cSrcweir impl_connectDatabaseColumn_noNotify( false ); 2030cdf0e10cSrcweir } 2031cdf0e10cSrcweir 2032cdf0e10cSrcweir // XBoundComponent 2033cdf0e10cSrcweir //------------------------------------------------------------------------------ 2034cdf0e10cSrcweir void SAL_CALL OBoundControlModel::addUpdateListener(const Reference<XUpdateListener>& _rxListener) throw(RuntimeException) 2035cdf0e10cSrcweir { 2036cdf0e10cSrcweir m_aUpdateListeners.addInterface(_rxListener); 2037cdf0e10cSrcweir } 2038cdf0e10cSrcweir 2039cdf0e10cSrcweir //------------------------------------------------------------------------------ 2040cdf0e10cSrcweir void SAL_CALL OBoundControlModel::removeUpdateListener(const Reference< XUpdateListener>& _rxListener) throw(RuntimeException) 2041cdf0e10cSrcweir { 2042cdf0e10cSrcweir m_aUpdateListeners.removeInterface(_rxListener); 2043cdf0e10cSrcweir } 2044cdf0e10cSrcweir 2045cdf0e10cSrcweir //------------------------------------------------------------------------------ 2046cdf0e10cSrcweir sal_Bool SAL_CALL OBoundControlModel::commit() throw(RuntimeException) 2047cdf0e10cSrcweir { 2048cdf0e10cSrcweir ControlModelLock aLock( *this ); 2049cdf0e10cSrcweir 2050cdf0e10cSrcweir OSL_PRECOND( m_bCommitable, "OBoundControlModel::commit: invalid call (I'm not commitable !) " ); 2051cdf0e10cSrcweir if ( hasExternalValueBinding() ) 2052cdf0e10cSrcweir { 2053cdf0e10cSrcweir // in most cases, no action is required: For most derivees, we know the value property of 2054cdf0e10cSrcweir // our control (see initValueProperty), and when an external binding is active, we 2055cdf0e10cSrcweir // instantly forward all changes in this property to the external binding. 2056cdf0e10cSrcweir if ( !m_sValuePropertyName.getLength() ) 2057cdf0e10cSrcweir // but for those derivees which did not use this feature, we need an 2058cdf0e10cSrcweir // explicit transfer 2059cdf0e10cSrcweir transferControlValueToExternal( aLock ); 2060cdf0e10cSrcweir return sal_True; 2061cdf0e10cSrcweir } 2062cdf0e10cSrcweir 2063cdf0e10cSrcweir OSL_ENSURE( !hasExternalValueBinding(), "OBoundControlModel::commit: control flow broken!" ); 2064cdf0e10cSrcweir // we reach this only if we're not working with an external binding 2065cdf0e10cSrcweir 2066cdf0e10cSrcweir if ( !hasField() ) 2067cdf0e10cSrcweir return sal_True; 2068cdf0e10cSrcweir 2069cdf0e10cSrcweir ::cppu::OInterfaceIteratorHelper aIter( m_aUpdateListeners ); 2070cdf0e10cSrcweir EventObject aEvent; 2071cdf0e10cSrcweir aEvent.Source = static_cast< XWeak* >( this ); 2072cdf0e10cSrcweir sal_Bool bSuccess = sal_True; 2073cdf0e10cSrcweir 2074cdf0e10cSrcweir aLock.release(); 2075cdf0e10cSrcweir // >>>>>>>> ----- UNSAFE ----- >>>>>>>> 2076cdf0e10cSrcweir while (aIter.hasMoreElements() && bSuccess) 2077cdf0e10cSrcweir bSuccess = static_cast< XUpdateListener* >( aIter.next() )->approveUpdate( aEvent ); 2078cdf0e10cSrcweir // <<<<<<<< ----- UNSAFE ----- <<<<<<<< 2079cdf0e10cSrcweir aLock.acquire(); 2080cdf0e10cSrcweir 2081cdf0e10cSrcweir if ( bSuccess ) 2082cdf0e10cSrcweir { 2083cdf0e10cSrcweir try 2084cdf0e10cSrcweir { 2085cdf0e10cSrcweir if ( m_xColumnUpdate.is() ) 2086cdf0e10cSrcweir bSuccess = commitControlValueToDbColumn( sal_False ); 2087cdf0e10cSrcweir } 2088cdf0e10cSrcweir catch(Exception&) 2089cdf0e10cSrcweir { 2090cdf0e10cSrcweir bSuccess = sal_False; 2091cdf0e10cSrcweir } 2092cdf0e10cSrcweir } 2093cdf0e10cSrcweir 2094cdf0e10cSrcweir if ( bSuccess ) 2095cdf0e10cSrcweir { 2096cdf0e10cSrcweir aLock.release(); 2097cdf0e10cSrcweir m_aUpdateListeners.notifyEach( &XUpdateListener::updated, aEvent ); 2098cdf0e10cSrcweir } 2099cdf0e10cSrcweir 2100cdf0e10cSrcweir return bSuccess; 2101cdf0e10cSrcweir } 2102cdf0e10cSrcweir 2103cdf0e10cSrcweir //------------------------------------------------------------------------------ 2104cdf0e10cSrcweir void OBoundControlModel::resetField() 2105cdf0e10cSrcweir { 2106cdf0e10cSrcweir m_xColumnUpdate.clear(); 2107cdf0e10cSrcweir m_xColumn.clear(); 2108cdf0e10cSrcweir m_xField.clear(); 2109cdf0e10cSrcweir m_nFieldType = DataType::OTHER; 2110cdf0e10cSrcweir } 2111cdf0e10cSrcweir 2112cdf0e10cSrcweir //------------------------------------------------------------------------------ 2113cdf0e10cSrcweir sal_Bool OBoundControlModel::connectToField(const Reference<XRowSet>& rForm) 2114cdf0e10cSrcweir { 2115cdf0e10cSrcweir OSL_PRECOND( !hasExternalValueBinding(), "OBoundControlModel::connectToField: invalid call (have an external binding)!" ); 2116cdf0e10cSrcweir 2117cdf0e10cSrcweir // wenn eine Verbindung zur Datenbank existiert 2118cdf0e10cSrcweir if (rForm.is() && getConnection(rForm).is()) 2119cdf0e10cSrcweir { 2120cdf0e10cSrcweir // Feld bestimmen und PropertyChangeListener 2121cdf0e10cSrcweir m_xCursor = rForm; 2122cdf0e10cSrcweir Reference<XPropertySet> xFieldCandidate; 2123cdf0e10cSrcweir 2124cdf0e10cSrcweir if (m_xCursor.is()) 2125cdf0e10cSrcweir { 2126cdf0e10cSrcweir Reference<XColumnsSupplier> xColumnsSupplier(m_xCursor, UNO_QUERY); 2127cdf0e10cSrcweir DBG_ASSERT(xColumnsSupplier.is(), "OBoundControlModel::connectToField : the row set should support the com::sun::star::sdb::ResultSet service !"); 2128cdf0e10cSrcweir if (xColumnsSupplier.is()) 2129cdf0e10cSrcweir { 2130cdf0e10cSrcweir Reference<XNameAccess> xColumns(xColumnsSupplier->getColumns(), UNO_QUERY); 2131cdf0e10cSrcweir if (xColumns.is() && xColumns->hasByName(m_aControlSource)) 2132cdf0e10cSrcweir { 2133cdf0e10cSrcweir OSL_VERIFY( xColumns->getByName(m_aControlSource) >>= xFieldCandidate ); 2134cdf0e10cSrcweir } 2135cdf0e10cSrcweir } 2136cdf0e10cSrcweir } 2137cdf0e10cSrcweir 2138cdf0e10cSrcweir try 2139cdf0e10cSrcweir { 2140cdf0e10cSrcweir sal_Int32 nFieldType = DataType::OTHER; 2141cdf0e10cSrcweir if ( xFieldCandidate.is() ) 2142cdf0e10cSrcweir { 2143cdf0e10cSrcweir xFieldCandidate->getPropertyValue( PROPERTY_FIELDTYPE ) >>= nFieldType; 2144cdf0e10cSrcweir if ( approveDbColumnType( nFieldType ) ) 2145cdf0e10cSrcweir impl_setField_noNotify( xFieldCandidate ); 2146cdf0e10cSrcweir } 2147cdf0e10cSrcweir else 2148cdf0e10cSrcweir impl_setField_noNotify( NULL ); 2149cdf0e10cSrcweir 2150cdf0e10cSrcweir if ( m_xField.is() ) 2151cdf0e10cSrcweir { 2152cdf0e10cSrcweir if( m_xField->getPropertySetInfo()->hasPropertyByName( PROPERTY_VALUE ) ) 2153cdf0e10cSrcweir { 2154cdf0e10cSrcweir m_nFieldType = nFieldType; 2155cdf0e10cSrcweir 2156cdf0e10cSrcweir // an wertaenderungen horchen 2157cdf0e10cSrcweir m_xField->addPropertyChangeListener( PROPERTY_VALUE, this ); 2158cdf0e10cSrcweir m_xColumnUpdate = Reference< XColumnUpdate >( m_xField, UNO_QUERY ); 2159cdf0e10cSrcweir m_xColumn = Reference< XColumn >( m_xField, UNO_QUERY ); 2160cdf0e10cSrcweir 2161cdf0e10cSrcweir sal_Int32 nNullableFlag = ColumnValue::NO_NULLS; 2162cdf0e10cSrcweir m_xField->getPropertyValue(PROPERTY_ISNULLABLE) >>= nNullableFlag; 2163cdf0e10cSrcweir m_bRequired = (ColumnValue::NO_NULLS == nNullableFlag); 2164cdf0e10cSrcweir // we're optimistic : in case of ColumnValue_NULLABLE_UNKNOWN we assume nullability .... 2165cdf0e10cSrcweir } 2166cdf0e10cSrcweir else 2167cdf0e10cSrcweir { 2168cdf0e10cSrcweir OSL_ENSURE(sal_False, "OBoundControlModel::connectToField: property NAME not supported!"); 2169cdf0e10cSrcweir impl_setField_noNotify( NULL ); 2170cdf0e10cSrcweir } 2171cdf0e10cSrcweir } 2172cdf0e10cSrcweir } 2173cdf0e10cSrcweir catch( const Exception& ) 2174cdf0e10cSrcweir { 2175cdf0e10cSrcweir DBG_UNHANDLED_EXCEPTION(); 2176cdf0e10cSrcweir resetField(); 2177cdf0e10cSrcweir } 2178cdf0e10cSrcweir } 2179cdf0e10cSrcweir return hasField(); 2180cdf0e10cSrcweir } 2181cdf0e10cSrcweir 2182cdf0e10cSrcweir //------------------------------------------------------------------------------ 2183cdf0e10cSrcweir void OBoundControlModel::initFromField( const Reference< XRowSet >& _rxRowSet ) 2184cdf0e10cSrcweir { 2185cdf0e10cSrcweir // but only if the rowset if posisitioned on a valid record 2186cdf0e10cSrcweir if ( hasField() && _rxRowSet.is() ) 2187cdf0e10cSrcweir { 2188cdf0e10cSrcweir if ( !_rxRowSet->isBeforeFirst() && !_rxRowSet->isAfterLast() ) 2189cdf0e10cSrcweir transferDbValueToControl(); 2190cdf0e10cSrcweir else 2191cdf0e10cSrcweir // reset the field if the row set is empty 2192cdf0e10cSrcweir // #i30661# / 2004-12-16 / frank.schoenheit@sun.com 2193cdf0e10cSrcweir resetNoBroadcast(); 2194cdf0e10cSrcweir } 2195cdf0e10cSrcweir } 2196cdf0e10cSrcweir 2197cdf0e10cSrcweir //------------------------------------------------------------------------------ 2198cdf0e10cSrcweir sal_Bool OBoundControlModel::approveDbColumnType(sal_Int32 _nColumnType) 2199cdf0e10cSrcweir { 2200cdf0e10cSrcweir OSL_PRECOND( !hasExternalValueBinding(), "OBoundControlModel::approveDbColumnType: invalid call (have an external binding)!" ); 2201cdf0e10cSrcweir 2202cdf0e10cSrcweir if ((_nColumnType == DataType::BINARY) || (_nColumnType == DataType::VARBINARY) 2203cdf0e10cSrcweir || (_nColumnType == DataType::LONGVARBINARY) || (_nColumnType == DataType::OTHER) 2204cdf0e10cSrcweir || (_nColumnType == DataType::OBJECT) || (_nColumnType == DataType::DISTINCT) 2205cdf0e10cSrcweir || (_nColumnType == DataType::STRUCT) || (_nColumnType == DataType::ARRAY) 2206cdf0e10cSrcweir || (_nColumnType == DataType::BLOB) /*|| (_nColumnType == DataType::CLOB)*/ 2207cdf0e10cSrcweir || (_nColumnType == DataType::REF) || (_nColumnType == DataType::SQLNULL)) 2208cdf0e10cSrcweir return sal_False; 2209cdf0e10cSrcweir 2210cdf0e10cSrcweir return sal_True; 2211cdf0e10cSrcweir } 2212cdf0e10cSrcweir 2213cdf0e10cSrcweir //------------------------------------------------------------------------------ 2214cdf0e10cSrcweir void OBoundControlModel::impl_determineAmbientForm_nothrow() 2215cdf0e10cSrcweir { 2216cdf0e10cSrcweir Reference< XInterface > xParent( const_cast< OBoundControlModel* >( this )->getParent() ); 2217cdf0e10cSrcweir 2218cdf0e10cSrcweir m_xAmbientForm.set( xParent, UNO_QUERY ); 2219cdf0e10cSrcweir if ( !m_xAmbientForm.is() ) 2220cdf0e10cSrcweir { 2221cdf0e10cSrcweir Reference< XRowSetSupplier > xSupRowSet( xParent, UNO_QUERY ); 2222cdf0e10cSrcweir if ( xSupRowSet.is() ) 2223cdf0e10cSrcweir m_xAmbientForm.set( xSupRowSet->getRowSet(), UNO_QUERY ); 2224cdf0e10cSrcweir } 2225cdf0e10cSrcweir } 2226cdf0e10cSrcweir 2227cdf0e10cSrcweir //------------------------------------------------------------------------------ 2228cdf0e10cSrcweir void OBoundControlModel::impl_connectDatabaseColumn_noNotify( bool _bFromReload ) 2229cdf0e10cSrcweir { 2230cdf0e10cSrcweir OSL_PRECOND( !hasExternalValueBinding(), "OBoundControlModel::impl_connectDatabaseColumn_noNotify: not to be called with an external value binding!" ); 2231cdf0e10cSrcweir 2232cdf0e10cSrcweir // consistency checks 2233cdf0e10cSrcweir DBG_ASSERT( !( hasField() && !_bFromReload ), 2234cdf0e10cSrcweir "OBoundControlModel::impl_connectDatabaseColumn_noNotify: the form is just *loaded*, but we already have a field!" ); 2235cdf0e10cSrcweir (void)_bFromReload; 2236cdf0e10cSrcweir 2237cdf0e10cSrcweir Reference< XRowSet > xRowSet( m_xAmbientForm, UNO_QUERY ); 2238cdf0e10cSrcweir OSL_ENSURE( xRowSet.is(), "OBoundControlModel::impl_connectDatabaseColumn_noNotify: no row set!" ); 2239cdf0e10cSrcweir if ( !xRowSet.is() ) 2240cdf0e10cSrcweir return; 2241cdf0e10cSrcweir 2242cdf0e10cSrcweir if ( !hasField() ) 2243cdf0e10cSrcweir { 2244cdf0e10cSrcweir // connect to the column 2245cdf0e10cSrcweir connectToField( xRowSet ); 2246cdf0e10cSrcweir } 2247cdf0e10cSrcweir 2248cdf0e10cSrcweir // now that we're connected (more or less, even if we did not find a column), 2249*07a3d7f1SPedro Giffuni // we definitely want to forward any potentially occurring value changes 2250cdf0e10cSrcweir m_bForwardValueChanges = sal_True; 2251cdf0e10cSrcweir 2252cdf0e10cSrcweir // let derived classes react on this new connection 2253cdf0e10cSrcweir m_bLoaded = sal_True; 2254cdf0e10cSrcweir onConnectedDbColumn( xRowSet ); 2255cdf0e10cSrcweir 2256cdf0e10cSrcweir // initially transfer the db column value to the control, if we successfully connected to a database column 2257cdf0e10cSrcweir if ( hasField() ) 2258cdf0e10cSrcweir initFromField( xRowSet ); 2259cdf0e10cSrcweir } 2260cdf0e10cSrcweir 2261cdf0e10cSrcweir //------------------------------------------------------------------------------ 2262cdf0e10cSrcweir void OBoundControlModel::impl_disconnectDatabaseColumn_noNotify() 2263cdf0e10cSrcweir { 2264cdf0e10cSrcweir OSL_PRECOND( !hasExternalValueBinding(), "OBoundControlModel::impl_disconnectDatabaseColumn_noNotify: not to be called with an external value binding!" ); 2265cdf0e10cSrcweir 2266cdf0e10cSrcweir // let derived classes react on this 2267cdf0e10cSrcweir onDisconnectedDbColumn(); 2268cdf0e10cSrcweir 2269cdf0e10cSrcweir if ( hasField() ) 2270cdf0e10cSrcweir { 2271cdf0e10cSrcweir getField()->removePropertyChangeListener( PROPERTY_VALUE, this ); 2272cdf0e10cSrcweir resetField(); 2273cdf0e10cSrcweir } 2274cdf0e10cSrcweir 2275cdf0e10cSrcweir m_xCursor = NULL; 2276cdf0e10cSrcweir m_bLoaded = sal_False; 2277cdf0e10cSrcweir } 2278cdf0e10cSrcweir 2279cdf0e10cSrcweir //============================================================================== 2280cdf0e10cSrcweir // XLoadListener 2281cdf0e10cSrcweir //------------------------------------------------------------------------------ 2282cdf0e10cSrcweir void SAL_CALL OBoundControlModel::loaded( const EventObject& _rEvent ) throw(RuntimeException) 2283cdf0e10cSrcweir { 2284cdf0e10cSrcweir ControlModelLock aLock( *this ); 2285cdf0e10cSrcweir FieldChangeNotifier aBoundFieldNotifier( aLock ); 2286cdf0e10cSrcweir 2287cdf0e10cSrcweir OSL_ENSURE( _rEvent.Source == m_xAmbientForm, "OBoundControlModel::loaded: where does this come from?" ); 2288cdf0e10cSrcweir (void)_rEvent; 2289cdf0e10cSrcweir 2290cdf0e10cSrcweir OSL_PRECOND( !hasExternalValueBinding(), "OBoundControlModel::loaded: we should never reach this with an external value binding!" ); 2291cdf0e10cSrcweir if ( hasExternalValueBinding() ) 2292cdf0e10cSrcweir return; 2293cdf0e10cSrcweir 2294cdf0e10cSrcweir impl_connectDatabaseColumn_noNotify( false ); 2295cdf0e10cSrcweir } 2296cdf0e10cSrcweir 2297cdf0e10cSrcweir 2298cdf0e10cSrcweir //------------------------------------------------------------------------------ 2299cdf0e10cSrcweir void SAL_CALL OBoundControlModel::unloaded( const com::sun::star::lang::EventObject& /*aEvent*/ ) throw(RuntimeException) 2300cdf0e10cSrcweir { 2301cdf0e10cSrcweir OSL_PRECOND( !hasExternalValueBinding(), "OBoundControlModel::unloaded: we should never reach this with an external value binding!" ); 2302cdf0e10cSrcweir } 2303cdf0e10cSrcweir 2304cdf0e10cSrcweir //------------------------------------------------------------------------------ 2305cdf0e10cSrcweir void SAL_CALL OBoundControlModel::reloading( const com::sun::star::lang::EventObject& /*aEvent*/ ) throw(RuntimeException) 2306cdf0e10cSrcweir { 2307cdf0e10cSrcweir OSL_PRECOND( !hasExternalValueBinding(), "OBoundControlModel::reloading: we should never reach this with an external value binding!" ); 2308cdf0e10cSrcweir if ( hasExternalValueBinding() ) 2309cdf0e10cSrcweir return; 2310cdf0e10cSrcweir 2311cdf0e10cSrcweir osl::MutexGuard aGuard(m_aMutex); 2312cdf0e10cSrcweir m_bForwardValueChanges = sal_False; 2313cdf0e10cSrcweir } 2314cdf0e10cSrcweir 2315cdf0e10cSrcweir //------------------------------------------------------------------------------ 2316cdf0e10cSrcweir void SAL_CALL OBoundControlModel::unloading(const com::sun::star::lang::EventObject& /*aEvent*/) throw(RuntimeException) 2317cdf0e10cSrcweir { 2318cdf0e10cSrcweir ControlModelLock aLock( *this ); 2319cdf0e10cSrcweir FieldChangeNotifier aBoundFieldNotifier( aLock ); 2320cdf0e10cSrcweir 2321cdf0e10cSrcweir OSL_PRECOND( !hasExternalValueBinding(), "OBoundControlModel::unloading: we should never reach this with an external value binding!" ); 2322cdf0e10cSrcweir if ( hasExternalValueBinding() ) 2323cdf0e10cSrcweir return; 2324cdf0e10cSrcweir 2325cdf0e10cSrcweir impl_disconnectDatabaseColumn_noNotify(); 2326cdf0e10cSrcweir } 2327cdf0e10cSrcweir 2328cdf0e10cSrcweir //------------------------------------------------------------------------------ 2329cdf0e10cSrcweir void SAL_CALL OBoundControlModel::reloaded( const EventObject& _rEvent ) throw(RuntimeException) 2330cdf0e10cSrcweir { 2331cdf0e10cSrcweir ControlModelLock aLock( *this ); 2332cdf0e10cSrcweir FieldChangeNotifier aBoundFieldNotifier( aLock ); 2333cdf0e10cSrcweir 2334cdf0e10cSrcweir OSL_ENSURE( _rEvent.Source == m_xAmbientForm, "OBoundControlModel::reloaded: where does this come from?" ); 2335cdf0e10cSrcweir (void)_rEvent; 2336cdf0e10cSrcweir 2337cdf0e10cSrcweir OSL_PRECOND( !hasExternalValueBinding(), "OBoundControlModel::reloaded: we should never reach this with an external value binding!" ); 2338cdf0e10cSrcweir if ( hasExternalValueBinding() ) 2339cdf0e10cSrcweir return; 2340cdf0e10cSrcweir 2341cdf0e10cSrcweir impl_connectDatabaseColumn_noNotify( true ); 2342cdf0e10cSrcweir } 2343cdf0e10cSrcweir 2344cdf0e10cSrcweir //------------------------------------------------------------------------------ 2345cdf0e10cSrcweir void OBoundControlModel::setControlValue( const Any& _rValue, ValueChangeInstigator _eInstigator ) 2346cdf0e10cSrcweir { 2347cdf0e10cSrcweir m_eControlValueChangeInstigator = _eInstigator; 2348cdf0e10cSrcweir doSetControlValue( _rValue ); 2349cdf0e10cSrcweir m_eControlValueChangeInstigator = eOther; 2350cdf0e10cSrcweir } 2351cdf0e10cSrcweir 2352cdf0e10cSrcweir //------------------------------------------------------------------------------ 2353cdf0e10cSrcweir void OBoundControlModel::doSetControlValue( const Any& _rValue ) 2354cdf0e10cSrcweir { 2355cdf0e10cSrcweir OSL_PRECOND( m_xAggregateFastSet.is() && m_xAggregateSet.is(), 2356cdf0e10cSrcweir "OBoundControlModel::doSetControlValue: invalid aggregate !" ); 2357cdf0e10cSrcweir OSL_PRECOND( m_sValuePropertyName.getLength() || ( m_nValuePropertyAggregateHandle != -1 ), 2358cdf0e10cSrcweir "OBoundControlModel::doSetControlValue: please override if you have own value property handling!" ); 2359cdf0e10cSrcweir 2360cdf0e10cSrcweir try 2361cdf0e10cSrcweir { 2362cdf0e10cSrcweir // release our mutex once (it's acquired in one of the the calling methods), as setting aggregate properties 2363cdf0e10cSrcweir // may cause any uno controls belonging to us to lock the solar mutex, which is potentially dangerous with 2364cdf0e10cSrcweir // our own mutex locked 2365cdf0e10cSrcweir // #72451# / 2000-01-31 / frank.schoenheit@sun.com 2366cdf0e10cSrcweir MutexRelease aRelease( m_aMutex ); 2367cdf0e10cSrcweir if ( ( m_nValuePropertyAggregateHandle != -1 ) && m_xAggregateFastSet.is() ) 2368cdf0e10cSrcweir { 2369cdf0e10cSrcweir m_xAggregateFastSet->setFastPropertyValue( m_nValuePropertyAggregateHandle, _rValue ); 2370cdf0e10cSrcweir } 2371cdf0e10cSrcweir else if ( m_sValuePropertyName.getLength() && m_xAggregateSet.is() ) 2372cdf0e10cSrcweir { 2373cdf0e10cSrcweir m_xAggregateSet->setPropertyValue( m_sValuePropertyName, _rValue ); 2374cdf0e10cSrcweir } 2375cdf0e10cSrcweir } 2376cdf0e10cSrcweir catch( const Exception& ) 2377cdf0e10cSrcweir { 2378cdf0e10cSrcweir OSL_ENSURE( sal_False, "OBoundControlModel::doSetControlValue: caught an exception!" ); 2379cdf0e10cSrcweir } 2380cdf0e10cSrcweir } 2381cdf0e10cSrcweir 2382cdf0e10cSrcweir //------------------------------------------------------------------------------ 2383cdf0e10cSrcweir void OBoundControlModel::onConnectedValidator( ) 2384cdf0e10cSrcweir { 2385cdf0e10cSrcweir try 2386cdf0e10cSrcweir { 2387cdf0e10cSrcweir // if we have an external validator, we do not want the control to force invalid 2388cdf0e10cSrcweir // inputs to the default value. Instead, invalid inputs should be translated 2389cdf0e10cSrcweir // to NaN (not a number) 2390cdf0e10cSrcweir Reference< XPropertySetInfo > xAggregatePropertyInfo; 2391cdf0e10cSrcweir if ( m_xAggregateSet.is() ) 2392cdf0e10cSrcweir xAggregatePropertyInfo = m_xAggregateSet->getPropertySetInfo(); 2393cdf0e10cSrcweir if ( xAggregatePropertyInfo.is() && xAggregatePropertyInfo->hasPropertyByName( PROPERTY_ENFORCE_FORMAT ) ) 2394cdf0e10cSrcweir m_xAggregateSet->setPropertyValue( PROPERTY_ENFORCE_FORMAT, makeAny( (sal_Bool)sal_False ) ); 2395cdf0e10cSrcweir } 2396cdf0e10cSrcweir catch( const Exception& ) 2397cdf0e10cSrcweir { 2398cdf0e10cSrcweir OSL_ENSURE( sal_False, "OBoundControlModel::onConnectedValidator: caught an exception!" ); 2399cdf0e10cSrcweir } 2400cdf0e10cSrcweir recheckValidity( false ); 2401cdf0e10cSrcweir } 2402cdf0e10cSrcweir 2403cdf0e10cSrcweir //------------------------------------------------------------------------------ 2404cdf0e10cSrcweir void OBoundControlModel::onDisconnectedValidator( ) 2405cdf0e10cSrcweir { 2406cdf0e10cSrcweir try 2407cdf0e10cSrcweir { 2408cdf0e10cSrcweir Reference< XPropertySetInfo > xAggregatePropertyInfo; 2409cdf0e10cSrcweir if ( m_xAggregateSet.is() ) 2410cdf0e10cSrcweir xAggregatePropertyInfo = m_xAggregateSet->getPropertySetInfo(); 2411cdf0e10cSrcweir if ( xAggregatePropertyInfo.is() && xAggregatePropertyInfo->hasPropertyByName( PROPERTY_ENFORCE_FORMAT ) ) 2412cdf0e10cSrcweir m_xAggregateSet->setPropertyValue( PROPERTY_ENFORCE_FORMAT, makeAny( (sal_Bool)sal_True ) ); 2413cdf0e10cSrcweir } 2414cdf0e10cSrcweir catch( const Exception& ) 2415cdf0e10cSrcweir { 2416cdf0e10cSrcweir OSL_ENSURE( sal_False, "OBoundControlModel::onDisconnectedValidator: caught an exception!" ); 2417cdf0e10cSrcweir } 2418cdf0e10cSrcweir recheckValidity( false ); 2419cdf0e10cSrcweir } 2420cdf0e10cSrcweir 2421cdf0e10cSrcweir //------------------------------------------------------------------------------ 2422cdf0e10cSrcweir void OBoundControlModel::onConnectedExternalValue( ) 2423cdf0e10cSrcweir { 2424cdf0e10cSrcweir calculateExternalValueType(); 2425cdf0e10cSrcweir } 2426cdf0e10cSrcweir 2427cdf0e10cSrcweir //------------------------------------------------------------------------------ 2428cdf0e10cSrcweir void OBoundControlModel::onDisconnectedExternalValue( ) 2429cdf0e10cSrcweir { 2430cdf0e10cSrcweir } 2431cdf0e10cSrcweir 2432cdf0e10cSrcweir //------------------------------------------------------------------------------ 2433cdf0e10cSrcweir void OBoundControlModel::onConnectedDbColumn( const Reference< XInterface >& /*_rxForm*/ ) 2434cdf0e10cSrcweir { 2435cdf0e10cSrcweir OSL_PRECOND( !hasExternalValueBinding(), "OBoundControlModel::onConnectedDbColumn: how this? There's an external value binding!" ); 2436cdf0e10cSrcweir } 2437cdf0e10cSrcweir 2438cdf0e10cSrcweir //------------------------------------------------------------------------------ 2439cdf0e10cSrcweir void OBoundControlModel::onDisconnectedDbColumn() 2440cdf0e10cSrcweir { 2441cdf0e10cSrcweir OSL_PRECOND( !hasExternalValueBinding(), "OBoundControlModel::onDisconnectedDbColumn: how this? There's an external value binding!" ); 2442cdf0e10cSrcweir } 2443cdf0e10cSrcweir 2444cdf0e10cSrcweir // XReset 2445cdf0e10cSrcweir //----------------------------------------------------------------------------- 2446cdf0e10cSrcweir Any OBoundControlModel::getDefaultForReset() const 2447cdf0e10cSrcweir { 2448cdf0e10cSrcweir return Any(); 2449cdf0e10cSrcweir } 2450cdf0e10cSrcweir 2451cdf0e10cSrcweir //----------------------------------------------------------------------------- 2452cdf0e10cSrcweir void OBoundControlModel::resetNoBroadcast() 2453cdf0e10cSrcweir { 2454cdf0e10cSrcweir setControlValue( getDefaultForReset(), eOther ); 2455cdf0e10cSrcweir } 2456cdf0e10cSrcweir 2457cdf0e10cSrcweir //----------------------------------------------------------------------------- 2458cdf0e10cSrcweir void OBoundControlModel::addResetListener(const Reference<XResetListener>& l) throw (RuntimeException) 2459cdf0e10cSrcweir { 2460cdf0e10cSrcweir m_aResetHelper.addResetListener( l ); 2461cdf0e10cSrcweir } 2462cdf0e10cSrcweir 2463cdf0e10cSrcweir //----------------------------------------------------------------------------- 2464cdf0e10cSrcweir void OBoundControlModel::removeResetListener(const Reference<XResetListener>& l) throw (RuntimeException) 2465cdf0e10cSrcweir { 2466cdf0e10cSrcweir m_aResetHelper.removeResetListener( l ); 2467cdf0e10cSrcweir } 2468cdf0e10cSrcweir 2469cdf0e10cSrcweir //----------------------------------------------------------------------------- 2470cdf0e10cSrcweir void OBoundControlModel::reset() throw (RuntimeException) 2471cdf0e10cSrcweir { 2472cdf0e10cSrcweir if ( !m_aResetHelper.approveReset() ) 2473cdf0e10cSrcweir return; 2474cdf0e10cSrcweir 2475cdf0e10cSrcweir ControlModelLock aLock( *this ); 2476cdf0e10cSrcweir 2477cdf0e10cSrcweir // on a new record? 2478cdf0e10cSrcweir sal_Bool bIsNewRecord = sal_False; 2479cdf0e10cSrcweir Reference<XPropertySet> xSet( m_xCursor, UNO_QUERY ); 2480cdf0e10cSrcweir if ( xSet.is() ) 2481cdf0e10cSrcweir { 2482cdf0e10cSrcweir try 2483cdf0e10cSrcweir { 2484cdf0e10cSrcweir xSet->getPropertyValue( PROPERTY_ISNEW ) >>= bIsNewRecord; 2485cdf0e10cSrcweir } 2486cdf0e10cSrcweir catch( const Exception& ) 2487cdf0e10cSrcweir { 2488cdf0e10cSrcweir DBG_UNHANDLED_EXCEPTION(); 2489cdf0e10cSrcweir } 2490cdf0e10cSrcweir } 2491cdf0e10cSrcweir 2492cdf0e10cSrcweir // cursor on an invalid row? 2493cdf0e10cSrcweir sal_Bool bInvalidCursorPosition = sal_True; 2494cdf0e10cSrcweir try 2495cdf0e10cSrcweir { 2496cdf0e10cSrcweir bInvalidCursorPosition = m_xCursor.is() 2497cdf0e10cSrcweir && ( m_xCursor->isAfterLast() 2498cdf0e10cSrcweir || m_xCursor->isBeforeFirst() 2499cdf0e10cSrcweir ) 2500cdf0e10cSrcweir && !bIsNewRecord; 2501cdf0e10cSrcweir } 2502cdf0e10cSrcweir catch( const SQLException& ) 2503cdf0e10cSrcweir { 2504cdf0e10cSrcweir OSL_ENSURE( sal_False, "OBoundControlModel::reset: caught an SQL exception!" ); 2505cdf0e10cSrcweir } 2506cdf0e10cSrcweir // don't count the insert row as "invalid" 2507cdf0e10cSrcweir // @since #i24495# 2508cdf0e10cSrcweir // @date 2004-05-14 2509cdf0e10cSrcweir // @author fs@openoffice.org 2510cdf0e10cSrcweir 2511cdf0e10cSrcweir sal_Bool bSimpleReset = 2512cdf0e10cSrcweir ( !m_xColumn.is() // no connection to a database column 2513cdf0e10cSrcweir || ( m_xCursor.is() // OR we have an improperly positioned cursor 2514cdf0e10cSrcweir && bInvalidCursorPosition 2515cdf0e10cSrcweir ) 2516cdf0e10cSrcweir || hasExternalValueBinding() // OR we have an external value binding 2517cdf0e10cSrcweir ); 2518cdf0e10cSrcweir 2519cdf0e10cSrcweir if ( !bSimpleReset ) 2520cdf0e10cSrcweir { 2521cdf0e10cSrcweir // The default values will be set if and only if the current value of the field which we're bound 2522cdf0e10cSrcweir // to is NULL. 2523cdf0e10cSrcweir // Else, the current field value should be refreshed 2524cdf0e10cSrcweir // This behaviour is not completely ... "matured": What should happen if the field as well as the 2525cdf0e10cSrcweir // control have a default value? 2526cdf0e10cSrcweir 2527cdf0e10cSrcweir sal_Bool bIsNull = sal_True; 2528cdf0e10cSrcweir // we have to access the field content at least once to get a reliable result by XColumn::wasNull 2529cdf0e10cSrcweir try 2530cdf0e10cSrcweir { 2531cdf0e10cSrcweir // normally, we'd do a getString here. However, this is extremely expensive in the case 2532cdf0e10cSrcweir // of binary fields. Unfortunately, getString is the only method which is guaranteed 2533cdf0e10cSrcweir // to *always* succeed, all other getXXX methods may fail if the column is asked for a 2534cdf0e10cSrcweir // non-convertible type 2535cdf0e10cSrcweir sal_Int32 nFieldType = DataType::OBJECT; 2536cdf0e10cSrcweir getField()->getPropertyValue( PROPERTY_FIELDTYPE ) >>= nFieldType; 2537cdf0e10cSrcweir if ( ( nFieldType == DataType::BINARY ) 2538cdf0e10cSrcweir || ( nFieldType == DataType::VARBINARY ) 2539cdf0e10cSrcweir || ( nFieldType == DataType::LONGVARBINARY ) 2540cdf0e10cSrcweir || ( nFieldType == DataType::OBJECT ) 2541cdf0e10cSrcweir /*|| ( nFieldType == DataType::CLOB )*/ 2542cdf0e10cSrcweir ) 2543cdf0e10cSrcweir m_xColumn->getBinaryStream(); 2544cdf0e10cSrcweir else if ( nFieldType == DataType::BLOB ) 2545cdf0e10cSrcweir m_xColumn->getBlob(); 2546cdf0e10cSrcweir else 2547cdf0e10cSrcweir m_xColumn->getString(); 2548cdf0e10cSrcweir 2549cdf0e10cSrcweir bIsNull = m_xColumn->wasNull(); 2550cdf0e10cSrcweir } 2551cdf0e10cSrcweir catch(Exception&) 2552cdf0e10cSrcweir { 2553cdf0e10cSrcweir DBG_ERROR("OBoundControlModel::reset: this should have succeeded in all cases!"); 2554cdf0e10cSrcweir } 2555cdf0e10cSrcweir 2556cdf0e10cSrcweir sal_Bool bNeedValueTransfer = sal_True; 2557cdf0e10cSrcweir 2558cdf0e10cSrcweir if ( bIsNull ) 2559cdf0e10cSrcweir { 2560cdf0e10cSrcweir if ( bIsNewRecord ) 2561cdf0e10cSrcweir { 2562cdf0e10cSrcweir // reset the control to it's default 2563cdf0e10cSrcweir resetNoBroadcast(); 2564cdf0e10cSrcweir // and immediately commit the changes to the DB column, to keep consistency 2565cdf0e10cSrcweir commitControlValueToDbColumn( sal_True ); 2566cdf0e10cSrcweir 2567cdf0e10cSrcweir bNeedValueTransfer = sal_False; 2568cdf0e10cSrcweir } 2569cdf0e10cSrcweir } 2570cdf0e10cSrcweir 2571cdf0e10cSrcweir if ( bNeedValueTransfer ) 2572cdf0e10cSrcweir transferDbValueToControl(); 2573cdf0e10cSrcweir } 2574cdf0e10cSrcweir else 2575cdf0e10cSrcweir { 2576cdf0e10cSrcweir resetNoBroadcast(); 2577cdf0e10cSrcweir 2578cdf0e10cSrcweir // transfer to the external binding, if necessary 2579cdf0e10cSrcweir if ( hasExternalValueBinding() ) 2580cdf0e10cSrcweir transferControlValueToExternal( aLock ); 2581cdf0e10cSrcweir } 2582cdf0e10cSrcweir 2583cdf0e10cSrcweir // revalidate, if necessary 2584cdf0e10cSrcweir if ( hasValidator() ) 2585cdf0e10cSrcweir recheckValidity( true ); 2586cdf0e10cSrcweir 2587cdf0e10cSrcweir aLock.release(); 2588cdf0e10cSrcweir 2589cdf0e10cSrcweir m_aResetHelper.notifyResetted(); 2590cdf0e10cSrcweir } 2591cdf0e10cSrcweir 2592cdf0e10cSrcweir // ----------------------------------------------------------------------------- 2593cdf0e10cSrcweir void OBoundControlModel::impl_setField_noNotify( const Reference< XPropertySet>& _rxField ) 2594cdf0e10cSrcweir { 2595cdf0e10cSrcweir DBG_ASSERT( !hasExternalValueBinding(), "OBoundControlModel::impl_setField_noNotify: We have an external value binding!" ); 2596cdf0e10cSrcweir m_xField = _rxField; 2597cdf0e10cSrcweir } 2598cdf0e10cSrcweir 2599cdf0e10cSrcweir //-------------------------------------------------------------------- 2600cdf0e10cSrcweir sal_Bool OBoundControlModel::impl_approveValueBinding_nolock( const Reference< XValueBinding >& _rxBinding ) 2601cdf0e10cSrcweir { 2602cdf0e10cSrcweir if ( !_rxBinding.is() ) 2603cdf0e10cSrcweir return sal_False; 2604cdf0e10cSrcweir 2605cdf0e10cSrcweir Sequence< Type > aTypeCandidates; 2606cdf0e10cSrcweir { 2607cdf0e10cSrcweir // SYNCHRONIZED --> 2608cdf0e10cSrcweir ::osl::MutexGuard aGuard( m_aMutex ); 2609cdf0e10cSrcweir aTypeCandidates = getSupportedBindingTypes(); 2610cdf0e10cSrcweir // <-- SYNCHRONIZED 2611cdf0e10cSrcweir } 2612cdf0e10cSrcweir 2613cdf0e10cSrcweir for ( const Type* pType = aTypeCandidates.getConstArray(); 2614cdf0e10cSrcweir pType != aTypeCandidates.getConstArray() + aTypeCandidates.getLength(); 2615cdf0e10cSrcweir ++pType 2616cdf0e10cSrcweir ) 2617cdf0e10cSrcweir { 2618cdf0e10cSrcweir if ( _rxBinding->supportsType( *pType ) ) 2619cdf0e10cSrcweir return sal_True; 2620cdf0e10cSrcweir } 2621cdf0e10cSrcweir 2622cdf0e10cSrcweir return sal_False; 2623cdf0e10cSrcweir } 2624cdf0e10cSrcweir 2625cdf0e10cSrcweir //-------------------------------------------------------------------- 2626cdf0e10cSrcweir void OBoundControlModel::connectExternalValueBinding( 2627cdf0e10cSrcweir const Reference< XValueBinding >& _rxBinding, ControlModelLock& _rInstanceLock ) 2628cdf0e10cSrcweir { 2629cdf0e10cSrcweir OSL_PRECOND( _rxBinding.is(), "OBoundControlModel::connectExternalValueBinding: invalid binding instance!" ); 2630cdf0e10cSrcweir OSL_PRECOND( !hasExternalValueBinding( ), "OBoundControlModel::connectExternalValueBinding: precond not met (currently have a binding)!" ); 2631cdf0e10cSrcweir 2632cdf0e10cSrcweir // if we're connected to a database column, suspend this 2633cdf0e10cSrcweir if ( hasField() ) 2634cdf0e10cSrcweir impl_disconnectDatabaseColumn_noNotify(); 2635cdf0e10cSrcweir 2636cdf0e10cSrcweir // suspend listening for load-related events at out ambient form. 2637cdf0e10cSrcweir // This is because an external value binding overrules a possible database binding. 2638cdf0e10cSrcweir if ( isFormListening() ) 2639cdf0e10cSrcweir doFormListening( false ); 2640cdf0e10cSrcweir 2641cdf0e10cSrcweir // remember this new binding 2642cdf0e10cSrcweir m_xExternalBinding = _rxBinding; 2643cdf0e10cSrcweir 2644cdf0e10cSrcweir // tell the derivee 2645cdf0e10cSrcweir onConnectedExternalValue(); 2646cdf0e10cSrcweir 2647cdf0e10cSrcweir try 2648cdf0e10cSrcweir { 2649cdf0e10cSrcweir // add as value listener so we get notified when the value changes 2650cdf0e10cSrcweir Reference< XModifyBroadcaster > xModifiable( m_xExternalBinding, UNO_QUERY ); 2651cdf0e10cSrcweir if ( xModifiable.is() ) 2652cdf0e10cSrcweir xModifiable->addModifyListener( this ); 2653cdf0e10cSrcweir 2654cdf0e10cSrcweir // add as property change listener for some (possibly present) properties we're 2655cdf0e10cSrcweir // interested in 2656cdf0e10cSrcweir Reference< XPropertySet > xBindingProps( m_xExternalBinding, UNO_QUERY ); 2657cdf0e10cSrcweir Reference< XPropertySetInfo > xBindingPropsInfo( xBindingProps.is() ? xBindingProps->getPropertySetInfo() : Reference< XPropertySetInfo >() ); 2658cdf0e10cSrcweir if ( xBindingPropsInfo.is() ) 2659cdf0e10cSrcweir { 2660cdf0e10cSrcweir if ( xBindingPropsInfo->hasPropertyByName( PROPERTY_READONLY ) ) 2661cdf0e10cSrcweir { 2662cdf0e10cSrcweir xBindingProps->addPropertyChangeListener( PROPERTY_READONLY, this ); 2663cdf0e10cSrcweir m_bBindingControlsRO = sal_True; 2664cdf0e10cSrcweir } 2665cdf0e10cSrcweir if ( xBindingPropsInfo->hasPropertyByName( PROPERTY_RELEVANT ) ) 2666cdf0e10cSrcweir { 2667cdf0e10cSrcweir xBindingProps->addPropertyChangeListener( PROPERTY_RELEVANT, this ); 2668cdf0e10cSrcweir m_bBindingControlsEnable = sal_True; 2669cdf0e10cSrcweir } 2670cdf0e10cSrcweir } 2671cdf0e10cSrcweir } 2672cdf0e10cSrcweir catch( const Exception& ) 2673cdf0e10cSrcweir { 2674cdf0e10cSrcweir DBG_UNHANDLED_EXCEPTION(); 2675cdf0e10cSrcweir } 2676cdf0e10cSrcweir 2677cdf0e10cSrcweir // propagate our new value 2678cdf0e10cSrcweir transferExternalValueToControl( _rInstanceLock ); 2679cdf0e10cSrcweir 2680cdf0e10cSrcweir // if the binding is also a validator, use it, too. This is a constraint of the 2681cdf0e10cSrcweir // com.sun.star.form.binding.ValidatableBindableFormComponent service 2682cdf0e10cSrcweir if ( m_bSupportsValidation ) 2683cdf0e10cSrcweir { 2684cdf0e10cSrcweir try 2685cdf0e10cSrcweir { 2686cdf0e10cSrcweir Reference< XValidator > xAsValidator( _rxBinding, UNO_QUERY ); 2687cdf0e10cSrcweir if ( xAsValidator.is() ) 2688cdf0e10cSrcweir setValidator( xAsValidator ); 2689cdf0e10cSrcweir } 2690cdf0e10cSrcweir catch( const Exception& ) 2691cdf0e10cSrcweir { 2692cdf0e10cSrcweir DBG_UNHANDLED_EXCEPTION(); 2693cdf0e10cSrcweir } 2694cdf0e10cSrcweir } 2695cdf0e10cSrcweir } 2696cdf0e10cSrcweir 2697cdf0e10cSrcweir //-------------------------------------------------------------------- 2698cdf0e10cSrcweir void OBoundControlModel::disconnectExternalValueBinding( ) 2699cdf0e10cSrcweir { 2700cdf0e10cSrcweir try 2701cdf0e10cSrcweir { 2702cdf0e10cSrcweir // not listening at the binding anymore 2703cdf0e10cSrcweir Reference< XModifyBroadcaster > xModifiable( m_xExternalBinding, UNO_QUERY ); 2704cdf0e10cSrcweir if ( xModifiable.is() ) 2705cdf0e10cSrcweir xModifiable->removeModifyListener( this ); 2706cdf0e10cSrcweir 2707cdf0e10cSrcweir // remove as property change listener 2708cdf0e10cSrcweir Reference< XPropertySet > xBindingProps( m_xExternalBinding, UNO_QUERY ); 2709cdf0e10cSrcweir if ( m_bBindingControlsRO ) 2710cdf0e10cSrcweir xBindingProps->removePropertyChangeListener( PROPERTY_READONLY, this ); 2711cdf0e10cSrcweir if ( m_bBindingControlsEnable ) 2712cdf0e10cSrcweir xBindingProps->removePropertyChangeListener( PROPERTY_RELEVANT, this ); 2713cdf0e10cSrcweir } 2714cdf0e10cSrcweir catch( const Exception& ) 2715cdf0e10cSrcweir { 2716cdf0e10cSrcweir OSL_ENSURE( sal_False, "OBoundControlModel::disconnectExternalValueBinding: caught an exception!" ); 2717cdf0e10cSrcweir } 2718cdf0e10cSrcweir 2719cdf0e10cSrcweir // if the binding also acts as our validator, disconnect the validator, too 2720cdf0e10cSrcweir if ( ( m_xExternalBinding == m_xValidator ) && m_xValidator.is() ) 2721cdf0e10cSrcweir disconnectValidator( ); 2722cdf0e10cSrcweir 2723cdf0e10cSrcweir // no binding anymore 2724cdf0e10cSrcweir m_xExternalBinding.clear(); 2725cdf0e10cSrcweir 2726cdf0e10cSrcweir // be a load listener at our form, again. This was suspended while we had 2727cdf0e10cSrcweir // an external value binding in place. 2728cdf0e10cSrcweir doFormListening( true ); 2729cdf0e10cSrcweir 2730cdf0e10cSrcweir // re-connect to database column of the new parent 2731cdf0e10cSrcweir if ( m_xAmbientForm.is() && m_xAmbientForm->isLoaded() ) 2732cdf0e10cSrcweir impl_connectDatabaseColumn_noNotify( false ); 2733cdf0e10cSrcweir 2734cdf0e10cSrcweir // tell the derivee 2735cdf0e10cSrcweir onDisconnectedExternalValue(); 2736cdf0e10cSrcweir } 2737cdf0e10cSrcweir 2738cdf0e10cSrcweir //-------------------------------------------------------------------- 2739cdf0e10cSrcweir void SAL_CALL OBoundControlModel::setValueBinding( const Reference< XValueBinding >& _rxBinding ) throw (IncompatibleTypesException, RuntimeException) 2740cdf0e10cSrcweir { 2741cdf0e10cSrcweir OSL_PRECOND( m_bSupportsExternalBinding, "OBoundControlModel::setValueBinding: How did you reach this method?" ); 2742cdf0e10cSrcweir // the interface for this method should not have been exposed if we do not 2743cdf0e10cSrcweir // support binding to external data 2744cdf0e10cSrcweir 2745cdf0e10cSrcweir if ( !impl_approveValueBinding_nolock( _rxBinding ) ) 2746cdf0e10cSrcweir { 2747cdf0e10cSrcweir throw IncompatibleTypesException( 2748cdf0e10cSrcweir FRM_RES_STRING( RID_STR_INCOMPATIBLE_TYPES ), 2749cdf0e10cSrcweir *this 2750cdf0e10cSrcweir ); 2751cdf0e10cSrcweir } 2752cdf0e10cSrcweir 2753cdf0e10cSrcweir ControlModelLock aLock( *this ); 2754cdf0e10cSrcweir 2755cdf0e10cSrcweir // since a ValueBinding overrules any potentially active database binding, the change in a ValueBinding 2756cdf0e10cSrcweir // might trigger a change in our BoundField. 2757cdf0e10cSrcweir FieldChangeNotifier aBoundFieldNotifier( aLock ); 2758cdf0e10cSrcweir 2759cdf0e10cSrcweir // disconnect from the old binding 2760cdf0e10cSrcweir if ( hasExternalValueBinding() ) 2761cdf0e10cSrcweir disconnectExternalValueBinding( ); 2762cdf0e10cSrcweir 2763cdf0e10cSrcweir // connect to the new binding 2764cdf0e10cSrcweir if ( _rxBinding.is() ) 2765cdf0e10cSrcweir connectExternalValueBinding( _rxBinding, aLock ); 2766cdf0e10cSrcweir } 2767cdf0e10cSrcweir 2768cdf0e10cSrcweir //-------------------------------------------------------------------- 2769cdf0e10cSrcweir Reference< XValueBinding > SAL_CALL OBoundControlModel::getValueBinding( ) throw (RuntimeException) 2770cdf0e10cSrcweir { 2771cdf0e10cSrcweir ::osl::MutexGuard aGuard( m_aMutex ); 2772cdf0e10cSrcweir OSL_PRECOND( m_bSupportsExternalBinding, "OBoundControlModel::getValueBinding: How did you reach this method?" ); 2773cdf0e10cSrcweir // the interface for this method should not have been exposed if we do not 2774cdf0e10cSrcweir // support binding to external data 2775cdf0e10cSrcweir 2776cdf0e10cSrcweir return m_xExternalBinding; 2777cdf0e10cSrcweir } 2778cdf0e10cSrcweir 2779cdf0e10cSrcweir //-------------------------------------------------------------------- 2780cdf0e10cSrcweir void SAL_CALL OBoundControlModel::modified( const EventObject& _rEvent ) throw ( RuntimeException ) 2781cdf0e10cSrcweir { 2782cdf0e10cSrcweir ControlModelLock aLock( *this ); 2783cdf0e10cSrcweir 2784cdf0e10cSrcweir OSL_PRECOND( hasExternalValueBinding(), "OBoundControlModel::modified: Where did this come from?" ); 2785cdf0e10cSrcweir if ( !m_bTransferingValue && ( m_xExternalBinding == _rEvent.Source ) && m_xExternalBinding.is() ) 2786cdf0e10cSrcweir { 2787cdf0e10cSrcweir transferExternalValueToControl( aLock ); 2788cdf0e10cSrcweir } 2789cdf0e10cSrcweir } 2790cdf0e10cSrcweir 2791cdf0e10cSrcweir //-------------------------------------------------------------------- 2792cdf0e10cSrcweir void OBoundControlModel::transferDbValueToControl( ) 2793cdf0e10cSrcweir { 2794cdf0e10cSrcweir try 2795cdf0e10cSrcweir { 2796cdf0e10cSrcweir setControlValue( translateDbColumnToControlValue(), eDbColumnBinding ); 2797cdf0e10cSrcweir } 2798cdf0e10cSrcweir catch( const Exception& ) 2799cdf0e10cSrcweir { 2800cdf0e10cSrcweir DBG_UNHANDLED_EXCEPTION(); 2801cdf0e10cSrcweir } 2802cdf0e10cSrcweir } 2803cdf0e10cSrcweir 2804cdf0e10cSrcweir //------------------------------------------------------------------------------ 2805cdf0e10cSrcweir void OBoundControlModel::transferExternalValueToControl( ControlModelLock& _rInstanceLock ) 2806cdf0e10cSrcweir { 2807cdf0e10cSrcweir Reference< XValueBinding > xExternalBinding( m_xExternalBinding ); 2808cdf0e10cSrcweir Type aValueExchangeType( getExternalValueType() ); 2809cdf0e10cSrcweir 2810cdf0e10cSrcweir _rInstanceLock.release(); 2811cdf0e10cSrcweir // >>>>>>>> ----- UNSAFE ----- >>>>>>>> 2812cdf0e10cSrcweir Any aExternalValue; 2813cdf0e10cSrcweir try 2814cdf0e10cSrcweir { 2815cdf0e10cSrcweir aExternalValue = xExternalBinding->getValue( aValueExchangeType ); 2816cdf0e10cSrcweir } 2817cdf0e10cSrcweir catch( const Exception& ) 2818cdf0e10cSrcweir { 2819cdf0e10cSrcweir DBG_UNHANDLED_EXCEPTION(); 2820cdf0e10cSrcweir } 2821cdf0e10cSrcweir // <<<<<<<< ----- UNSAFE ----- <<<<<<<< 2822cdf0e10cSrcweir _rInstanceLock.acquire(); 2823cdf0e10cSrcweir 2824cdf0e10cSrcweir setControlValue( translateExternalValueToControlValue( aExternalValue ), eExternalBinding ); 2825cdf0e10cSrcweir } 2826cdf0e10cSrcweir 2827cdf0e10cSrcweir //------------------------------------------------------------------------------ 2828cdf0e10cSrcweir void OBoundControlModel::transferControlValueToExternal( ControlModelLock& _rInstanceLock ) 2829cdf0e10cSrcweir { 2830cdf0e10cSrcweir OSL_PRECOND( m_bSupportsExternalBinding && hasExternalValueBinding(), 2831cdf0e10cSrcweir "OBoundControlModel::transferControlValueToExternal: precondition not met!" ); 2832cdf0e10cSrcweir 2833cdf0e10cSrcweir if ( m_xExternalBinding.is() ) 2834cdf0e10cSrcweir { 2835cdf0e10cSrcweir Any aExternalValue( translateControlValueToExternalValue() ); 2836cdf0e10cSrcweir m_bTransferingValue = sal_True; 2837cdf0e10cSrcweir 2838cdf0e10cSrcweir _rInstanceLock.release(); 2839cdf0e10cSrcweir // >>>>>>>> ----- UNSAFE ----- >>>>>>>> 2840cdf0e10cSrcweir try 2841cdf0e10cSrcweir { 2842cdf0e10cSrcweir m_xExternalBinding->setValue( aExternalValue ); 2843cdf0e10cSrcweir } 2844cdf0e10cSrcweir catch( const Exception& ) 2845cdf0e10cSrcweir { 2846cdf0e10cSrcweir DBG_UNHANDLED_EXCEPTION(); 2847cdf0e10cSrcweir } 2848cdf0e10cSrcweir // <<<<<<<< ----- UNSAFE ----- <<<<<<<< 2849cdf0e10cSrcweir _rInstanceLock.acquire(); 2850cdf0e10cSrcweir 2851cdf0e10cSrcweir m_bTransferingValue = sal_False; 2852cdf0e10cSrcweir } 2853cdf0e10cSrcweir } 2854cdf0e10cSrcweir 2855cdf0e10cSrcweir // ----------------------------------------------------------------------------- 2856cdf0e10cSrcweir Sequence< Type > OBoundControlModel::getSupportedBindingTypes() 2857cdf0e10cSrcweir { 2858cdf0e10cSrcweir return Sequence< Type >( &m_aValuePropertyType, 1 ); 2859cdf0e10cSrcweir } 2860cdf0e10cSrcweir 2861cdf0e10cSrcweir //----------------------------------------------------------------------------- 2862cdf0e10cSrcweir void OBoundControlModel::calculateExternalValueType() 2863cdf0e10cSrcweir { 2864cdf0e10cSrcweir m_aExternalValueType = Type(); 2865cdf0e10cSrcweir if ( !m_xExternalBinding.is() ) 2866cdf0e10cSrcweir return; 2867cdf0e10cSrcweir 2868cdf0e10cSrcweir Sequence< Type > aTypeCandidates( getSupportedBindingTypes() ); 2869cdf0e10cSrcweir for ( const Type* pTypeCandidate = aTypeCandidates.getConstArray(); 2870cdf0e10cSrcweir pTypeCandidate != aTypeCandidates.getConstArray() + aTypeCandidates.getLength(); 2871cdf0e10cSrcweir ++pTypeCandidate 2872cdf0e10cSrcweir ) 2873cdf0e10cSrcweir { 2874cdf0e10cSrcweir if ( m_xExternalBinding->supportsType( *pTypeCandidate ) ) 2875cdf0e10cSrcweir { 2876cdf0e10cSrcweir m_aExternalValueType = *pTypeCandidate; 2877cdf0e10cSrcweir break; 2878cdf0e10cSrcweir } 2879cdf0e10cSrcweir } 2880cdf0e10cSrcweir } 2881cdf0e10cSrcweir 2882cdf0e10cSrcweir //----------------------------------------------------------------------------- 2883cdf0e10cSrcweir Any OBoundControlModel::translateExternalValueToControlValue( const Any& _rExternalValue ) const 2884cdf0e10cSrcweir { 2885cdf0e10cSrcweir OSL_PRECOND( m_bSupportsExternalBinding && hasExternalValueBinding(), 2886cdf0e10cSrcweir "OBoundControlModel::translateExternalValueToControlValue: precondition not met!" ); 2887cdf0e10cSrcweir 2888cdf0e10cSrcweir Any aControlValue( _rExternalValue ); 2889cdf0e10cSrcweir 2890cdf0e10cSrcweir // if the external value is VOID, and our value property is not allowed to be VOID, 2891cdf0e10cSrcweir // then default-construct a value 2892cdf0e10cSrcweir if ( !aControlValue.hasValue() && !m_bValuePropertyMayBeVoid ) 2893cdf0e10cSrcweir aControlValue.setValue( NULL, m_aValuePropertyType ); 2894cdf0e10cSrcweir 2895cdf0e10cSrcweir // outta here 2896cdf0e10cSrcweir return aControlValue; 2897cdf0e10cSrcweir } 2898cdf0e10cSrcweir 2899cdf0e10cSrcweir //------------------------------------------------------------------------------ 2900cdf0e10cSrcweir Any OBoundControlModel::translateControlValueToExternalValue( ) const 2901cdf0e10cSrcweir { 2902cdf0e10cSrcweir return getControlValue( ); 2903cdf0e10cSrcweir } 2904cdf0e10cSrcweir 2905cdf0e10cSrcweir //------------------------------------------------------------------------------ 2906cdf0e10cSrcweir Any OBoundControlModel::translateControlValueToValidatableValue( ) const 2907cdf0e10cSrcweir { 2908cdf0e10cSrcweir OSL_PRECOND( m_xValidator.is(), "OBoundControlModel::translateControlValueToValidatableValue: no validator, so why should I?" ); 2909cdf0e10cSrcweir if ( ( m_xValidator == m_xExternalBinding ) && m_xValidator.is() ) 2910cdf0e10cSrcweir return translateControlValueToExternalValue(); 2911cdf0e10cSrcweir return getControlValue(); 2912cdf0e10cSrcweir } 2913cdf0e10cSrcweir 2914cdf0e10cSrcweir //------------------------------------------------------------------------------ 2915cdf0e10cSrcweir Any OBoundControlModel::getControlValue( ) const 2916cdf0e10cSrcweir { 2917cdf0e10cSrcweir OSL_PRECOND( m_xAggregateFastSet.is() && m_xAggregateSet.is(), 2918cdf0e10cSrcweir "OBoundControlModel::getControlValue: invalid aggregate !" ); 2919cdf0e10cSrcweir OSL_PRECOND( m_sValuePropertyName.getLength() || ( m_nValuePropertyAggregateHandle != -1 ), 2920cdf0e10cSrcweir "OBoundControlModel::getControlValue: please override if you have own value property handling!" ); 2921cdf0e10cSrcweir 2922cdf0e10cSrcweir // determine the current control value 2923cdf0e10cSrcweir Any aControlValue; 2924cdf0e10cSrcweir if ( ( m_nValuePropertyAggregateHandle != -1 ) && m_xAggregateFastSet.is() ) 2925cdf0e10cSrcweir { 2926cdf0e10cSrcweir aControlValue = m_xAggregateFastSet->getFastPropertyValue( m_nValuePropertyAggregateHandle ); 2927cdf0e10cSrcweir } 2928cdf0e10cSrcweir else if ( m_sValuePropertyName.getLength() && m_xAggregateSet.is() ) 2929cdf0e10cSrcweir { 2930cdf0e10cSrcweir aControlValue = m_xAggregateSet->getPropertyValue( m_sValuePropertyName ); 2931cdf0e10cSrcweir } 2932cdf0e10cSrcweir 2933cdf0e10cSrcweir return aControlValue; 2934cdf0e10cSrcweir } 2935cdf0e10cSrcweir 2936cdf0e10cSrcweir //-------------------------------------------------------------------- 2937cdf0e10cSrcweir void OBoundControlModel::connectValidator( const Reference< XValidator >& _rxValidator ) 2938cdf0e10cSrcweir { 2939cdf0e10cSrcweir OSL_PRECOND( _rxValidator.is(), "OBoundControlModel::connectValidator: invalid validator instance!" ); 2940cdf0e10cSrcweir OSL_PRECOND( !hasValidator( ), "OBoundControlModel::connectValidator: precond not met (have a validator currently)!" ); 2941cdf0e10cSrcweir 2942cdf0e10cSrcweir m_xValidator = _rxValidator; 2943cdf0e10cSrcweir 2944cdf0e10cSrcweir // add as value listener so we get notified when the value changes 2945cdf0e10cSrcweir if ( m_xValidator.is() ) 2946cdf0e10cSrcweir { 2947cdf0e10cSrcweir try 2948cdf0e10cSrcweir { 2949cdf0e10cSrcweir m_xValidator->addValidityConstraintListener( this ); 2950cdf0e10cSrcweir } 2951cdf0e10cSrcweir catch( const RuntimeException& ) 2952cdf0e10cSrcweir { 2953cdf0e10cSrcweir } 2954cdf0e10cSrcweir } 2955cdf0e10cSrcweir 2956cdf0e10cSrcweir onConnectedValidator( ); 2957cdf0e10cSrcweir } 2958cdf0e10cSrcweir 2959cdf0e10cSrcweir //-------------------------------------------------------------------- 2960cdf0e10cSrcweir void OBoundControlModel::disconnectValidator( ) 2961cdf0e10cSrcweir { 2962cdf0e10cSrcweir OSL_PRECOND( hasValidator( ), "OBoundControlModel::connectValidator: precond not met (don't have a validator currently)!" ); 2963cdf0e10cSrcweir 2964cdf0e10cSrcweir // add as value listener so we get notified when the value changes 2965cdf0e10cSrcweir if ( m_xValidator.is() ) 2966cdf0e10cSrcweir { 2967cdf0e10cSrcweir try 2968cdf0e10cSrcweir { 2969cdf0e10cSrcweir m_xValidator->removeValidityConstraintListener( this ); 2970cdf0e10cSrcweir } 2971cdf0e10cSrcweir catch( const RuntimeException& ) 2972cdf0e10cSrcweir { 2973cdf0e10cSrcweir } 2974cdf0e10cSrcweir } 2975cdf0e10cSrcweir 2976cdf0e10cSrcweir m_xValidator.clear(); 2977cdf0e10cSrcweir 2978cdf0e10cSrcweir onDisconnectedValidator( ); 2979cdf0e10cSrcweir } 2980cdf0e10cSrcweir 2981cdf0e10cSrcweir //-------------------------------------------------------------------- 2982cdf0e10cSrcweir void SAL_CALL OBoundControlModel::setValidator( const Reference< XValidator >& _rxValidator ) throw (VetoException,RuntimeException) 2983cdf0e10cSrcweir { 2984cdf0e10cSrcweir ::osl::ClearableMutexGuard aGuard( m_aMutex ); 2985cdf0e10cSrcweir OSL_PRECOND( m_bSupportsValidation, "OBoundControlModel::setValidator: How did you reach this method?" ); 2986cdf0e10cSrcweir // the interface for this method should not have been exposed if we do not 2987cdf0e10cSrcweir // support validation 2988cdf0e10cSrcweir 2989cdf0e10cSrcweir // early out if the validator does not change 2990cdf0e10cSrcweir if( _rxValidator == m_xValidator ) 2991cdf0e10cSrcweir return; 2992cdf0e10cSrcweir 2993cdf0e10cSrcweir if ( m_xValidator.is() && ( m_xValidator == m_xExternalBinding ) ) 2994cdf0e10cSrcweir throw VetoException( 2995cdf0e10cSrcweir FRM_RES_STRING( RID_STR_INVALID_VALIDATOR ), 2996cdf0e10cSrcweir *this 2997cdf0e10cSrcweir ); 2998cdf0e10cSrcweir 2999cdf0e10cSrcweir // disconnect from the old validator 3000cdf0e10cSrcweir if ( hasValidator() ) 3001cdf0e10cSrcweir disconnectValidator( ); 3002cdf0e10cSrcweir 3003cdf0e10cSrcweir // connect to the new validator 3004cdf0e10cSrcweir if ( _rxValidator.is() ) 3005cdf0e10cSrcweir connectValidator( _rxValidator ); 3006cdf0e10cSrcweir } 3007cdf0e10cSrcweir 3008cdf0e10cSrcweir //-------------------------------------------------------------------- 3009cdf0e10cSrcweir Reference< XValidator > SAL_CALL OBoundControlModel::getValidator( ) throw (RuntimeException) 3010cdf0e10cSrcweir { 3011cdf0e10cSrcweir ::osl::MutexGuard aGuard( m_aMutex ); 3012cdf0e10cSrcweir OSL_PRECOND( m_bSupportsValidation, "OBoundControlModel::getValidator: How did you reach this method?" ); 3013cdf0e10cSrcweir // the interface for this method should not have been exposed if we do not 3014cdf0e10cSrcweir // support validation 3015cdf0e10cSrcweir 3016cdf0e10cSrcweir return m_xValidator; 3017cdf0e10cSrcweir } 3018cdf0e10cSrcweir 3019cdf0e10cSrcweir //-------------------------------------------------------------------- 3020cdf0e10cSrcweir void SAL_CALL OBoundControlModel::validityConstraintChanged( const EventObject& /*Source*/ ) throw (RuntimeException) 3021cdf0e10cSrcweir { 3022cdf0e10cSrcweir ::osl::ClearableMutexGuard aGuard( m_aMutex ); 3023cdf0e10cSrcweir OSL_PRECOND( m_bSupportsValidation, "OBoundControlModel::validityConstraintChanged: How did you reach this method?" ); 3024cdf0e10cSrcweir // the interface for this method should not have been exposed if we do not 3025cdf0e10cSrcweir // support validation 3026cdf0e10cSrcweir 3027cdf0e10cSrcweir recheckValidity( false ); 3028cdf0e10cSrcweir } 3029cdf0e10cSrcweir 3030cdf0e10cSrcweir //-------------------------------------------------------------------- 3031cdf0e10cSrcweir sal_Bool SAL_CALL OBoundControlModel::isValid( ) throw (RuntimeException) 3032cdf0e10cSrcweir { 3033cdf0e10cSrcweir return m_bIsCurrentValueValid; 3034cdf0e10cSrcweir } 3035cdf0e10cSrcweir 3036cdf0e10cSrcweir //-------------------------------------------------------------------- 3037cdf0e10cSrcweir ::com::sun::star::uno::Any OBoundControlModel::getCurrentFormComponentValue() const 3038cdf0e10cSrcweir { 3039cdf0e10cSrcweir if ( hasValidator() ) 3040cdf0e10cSrcweir return translateControlValueToValidatableValue(); 3041cdf0e10cSrcweir return getControlValue(); 3042cdf0e10cSrcweir } 3043cdf0e10cSrcweir 3044cdf0e10cSrcweir //-------------------------------------------------------------------- 3045cdf0e10cSrcweir Any SAL_CALL OBoundControlModel::getCurrentValue( ) throw (RuntimeException) 3046cdf0e10cSrcweir { 3047cdf0e10cSrcweir ::osl::MutexGuard aGuard( m_aMutex ); 3048cdf0e10cSrcweir return getCurrentFormComponentValue(); 3049cdf0e10cSrcweir } 3050cdf0e10cSrcweir 3051cdf0e10cSrcweir //-------------------------------------------------------------------- 3052cdf0e10cSrcweir void SAL_CALL OBoundControlModel::addFormComponentValidityListener( const Reference< validation::XFormComponentValidityListener >& Listener ) throw (NullPointerException, RuntimeException) 3053cdf0e10cSrcweir { 3054cdf0e10cSrcweir if ( Listener.is() ) 3055cdf0e10cSrcweir m_aFormComponentListeners.addInterface( Listener ); 3056cdf0e10cSrcweir } 3057cdf0e10cSrcweir 3058cdf0e10cSrcweir //-------------------------------------------------------------------- 3059cdf0e10cSrcweir void SAL_CALL OBoundControlModel::removeFormComponentValidityListener( const Reference< validation::XFormComponentValidityListener >& Listener ) throw (NullPointerException, RuntimeException) 3060cdf0e10cSrcweir { 3061cdf0e10cSrcweir if ( Listener.is() ) 3062cdf0e10cSrcweir m_aFormComponentListeners.removeInterface( Listener ); 3063cdf0e10cSrcweir } 3064cdf0e10cSrcweir 3065cdf0e10cSrcweir //-------------------------------------------------------------------- 3066cdf0e10cSrcweir void OBoundControlModel::recheckValidity( bool _bForceNotification ) 3067cdf0e10cSrcweir { 3068cdf0e10cSrcweir try 3069cdf0e10cSrcweir { 3070cdf0e10cSrcweir sal_Bool bIsCurrentlyValid = sal_True; 3071cdf0e10cSrcweir if ( hasValidator() ) 3072cdf0e10cSrcweir bIsCurrentlyValid = m_xValidator->isValid( translateControlValueToValidatableValue() ); 3073cdf0e10cSrcweir 3074cdf0e10cSrcweir if ( ( bIsCurrentlyValid != m_bIsCurrentValueValid ) || _bForceNotification ) 3075cdf0e10cSrcweir { 3076cdf0e10cSrcweir m_bIsCurrentValueValid = bIsCurrentlyValid; 3077cdf0e10cSrcweir 3078cdf0e10cSrcweir // release our mutex for the notifications 3079cdf0e10cSrcweir MutexRelease aRelease( m_aMutex ); 3080cdf0e10cSrcweir m_aFormComponentListeners.notifyEach( &validation::XFormComponentValidityListener::componentValidityChanged, EventObject( *this ) ); 3081cdf0e10cSrcweir } 3082cdf0e10cSrcweir } 3083cdf0e10cSrcweir catch( const Exception& ) 3084cdf0e10cSrcweir { 3085cdf0e10cSrcweir OSL_ENSURE( sal_False, "OBoundControlModel::recheckValidity: caught an exception!" ); 3086cdf0e10cSrcweir } 3087cdf0e10cSrcweir } 3088cdf0e10cSrcweir 3089cdf0e10cSrcweir //------------------------------------------------------------------------------ 3090cdf0e10cSrcweir void OBoundControlModel::describeFixedProperties( Sequence< Property >& _rProps ) const 3091cdf0e10cSrcweir { 3092cdf0e10cSrcweir BEGIN_DESCRIBE_PROPERTIES( 5, OControlModel ) 3093cdf0e10cSrcweir DECL_PROP1 ( CONTROLSOURCE, ::rtl::OUString, BOUND ); 3094cdf0e10cSrcweir DECL_IFACE_PROP3( BOUNDFIELD, XPropertySet, BOUND, READONLY, TRANSIENT ); 3095cdf0e10cSrcweir DECL_IFACE_PROP2( CONTROLLABEL, XPropertySet, BOUND, MAYBEVOID ); 3096cdf0e10cSrcweir DECL_PROP2 ( CONTROLSOURCEPROPERTY, ::rtl::OUString, READONLY, TRANSIENT ); 3097cdf0e10cSrcweir DECL_BOOL_PROP1 ( INPUT_REQUIRED, BOUND ); 3098cdf0e10cSrcweir END_DESCRIBE_PROPERTIES() 3099cdf0e10cSrcweir } 3100cdf0e10cSrcweir 3101cdf0e10cSrcweir // ----------------------------------------------------------------------------- 3102cdf0e10cSrcweir 3103cdf0e10cSrcweir //......................................................................... 3104cdf0e10cSrcweir } 3105cdf0e10cSrcweir //... namespace frm ....................................................... 3106cdf0e10cSrcweir 3107