LCOV - code coverage report
Current view: top level - usr/local/src/libreoffice/forms/source/component - Button.cxx (source / functions) Hit Total Coverage
Test: libreoffice_filtered.info Lines: 190 314 60.5 %
Date: 2013-07-09 Functions: 42 57 73.7 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2             : /*
       3             :  * This file is part of the LibreOffice project.
       4             :  *
       5             :  * This Source Code Form is subject to the terms of the Mozilla Public
       6             :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       7             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       8             :  *
       9             :  * This file incorporates work covered by the following license notice:
      10             :  *
      11             :  *   Licensed to the Apache Software Foundation (ASF) under one or more
      12             :  *   contributor license agreements. See the NOTICE file distributed
      13             :  *   with this work for additional information regarding copyright
      14             :  *   ownership. The ASF licenses this file to you under the Apache
      15             :  *   License, Version 2.0 (the "License"); you may not use this file
      16             :  *   except in compliance with the License. You may obtain a copy of
      17             :  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
      18             :  */
      19             : 
      20             : 
      21             : #include "Button.hxx"
      22             : 
      23             : #include <com/sun/star/awt/XVclWindowPeer.hpp>
      24             : 
      25             : #include <comphelper/streamsection.hxx>
      26             : #include <comphelper/basicio.hxx>
      27             : #include <comphelper/processfactory.hxx>
      28             : #include <tools/diagnose_ex.h>
      29             : #include <tools/debug.hxx>
      30             : #include <tools/urlobj.hxx>
      31             : #include <vcl/svapp.hxx>
      32             : #include <osl/mutex.hxx>
      33             : 
      34             : //.........................................................................
      35             : namespace frm
      36             : {
      37             : //.........................................................................
      38             : 
      39             : using namespace ::com::sun::star::uno;
      40             : using namespace ::com::sun::star::sdb;
      41             : using namespace ::com::sun::star::sdbc;
      42             : using namespace ::com::sun::star::sdbcx;
      43             : using namespace ::com::sun::star::beans;
      44             : using namespace ::com::sun::star::container;
      45             : using namespace ::com::sun::star::form;
      46             : using namespace ::com::sun::star::awt;
      47             : using namespace ::com::sun::star::io;
      48             : using namespace ::com::sun::star::lang;
      49             : using namespace ::com::sun::star::util;
      50             : using ::com::sun::star::frame::XDispatchProviderInterceptor;
      51             : 
      52             : //==================================================================
      53             : //= OButtonModel
      54             : //==================================================================
      55             : DBG_NAME(OButtonModel)
      56             : //------------------------------------------------------------------
      57          48 : InterfaceRef SAL_CALL OButtonModel_CreateInstance(const Reference<XMultiServiceFactory>& _rxFactory)
      58             : {
      59          48 :     return *(new OButtonModel( comphelper::getComponentContext(_rxFactory) ));
      60             : }
      61             : 
      62             : //------------------------------------------------------------------
      63          48 : OButtonModel::OButtonModel(const Reference<XComponentContext>& _rxFactory)
      64             :     :OClickableImageBaseModel( _rxFactory, VCL_CONTROLMODEL_COMMANDBUTTON, FRM_SUN_CONTROL_COMMANDBUTTON )
      65             :                                     // use the old control name for compatibility reasons
      66             :     ,m_aResetHelper( *this, m_aMutex )
      67          48 :     ,m_eDefaultState( STATE_NOCHECK )
      68             : {
      69             :     DBG_CTOR( OButtonModel, NULL );
      70          48 :     m_nClassId = FormComponentType::COMMANDBUTTON;
      71          48 : }
      72             : 
      73             : //------------------------------------------------------------------
      74        9072 : Any SAL_CALL OButtonModel::queryAggregation( const Type& _type ) throw(RuntimeException)
      75             : {
      76        9072 :     Any aReturn = OClickableImageBaseModel::queryAggregation( _type );
      77        9072 :     if ( !aReturn.hasValue() )
      78         697 :         aReturn = OButtonModel_Base::queryInterface( _type );
      79        9072 :     return aReturn;
      80             : }
      81             : 
      82             : //------------------------------------------------------------------
      83          20 : Sequence< Type > OButtonModel::_getTypes()
      84             : {
      85             :     return ::comphelper::concatSequences(
      86             :         OClickableImageBaseModel::_getTypes(),
      87             :         OButtonModel_Base::getTypes()
      88          20 :     );
      89             : }
      90             : 
      91             : //------------------------------------------------------------------
      92           0 : OButtonModel::OButtonModel( const OButtonModel* _pOriginal, const Reference<XComponentContext>& _rxFactory )
      93             :     :OClickableImageBaseModel( _pOriginal, _rxFactory )
      94             :     ,m_aResetHelper( *this, m_aMutex )
      95           0 :     ,m_eDefaultState( _pOriginal->m_eDefaultState )
      96             : {
      97             :     DBG_CTOR( OButtonModel, NULL );
      98           0 :     m_nClassId = FormComponentType::COMMANDBUTTON;
      99             : 
     100           0 :     implInitializeImageURL();
     101           0 : }
     102             : 
     103             : //------------------------------------------------------------------------------
     104          90 : OButtonModel::~OButtonModel()
     105             : {
     106             :     DBG_DTOR(OButtonModel, NULL);
     107          90 : }
     108             : 
     109             : //------------------------------------------------------------------------------
     110          46 : void OButtonModel::describeFixedProperties( Sequence< Property >& _rProps ) const
     111             : {
     112          46 :     BEGIN_DESCRIBE_PROPERTIES( 6, OClickableImageBaseModel )
     113          46 :         DECL_PROP1( BUTTONTYPE,             FormButtonType,             BOUND );
     114          46 :         DECL_PROP1( DEFAULT_STATE,          sal_Int16,                  BOUND );
     115          46 :         DECL_PROP1( DISPATCHURLINTERNAL,    sal_Bool,                   BOUND );
     116          46 :         DECL_PROP1( TARGET_URL,             OUString,            BOUND );
     117          46 :         DECL_PROP1( TARGET_FRAME,           OUString,            BOUND );
     118          46 :         DECL_PROP1( TABINDEX,               sal_Int16,                  BOUND );
     119             :     END_DESCRIBE_PROPERTIES();
     120          46 : }
     121             : 
     122             : //------------------------------------------------------------------------------
     123           0 : IMPLEMENT_DEFAULT_CLONING( OButtonModel )
     124             : 
     125             : // XServiceInfo
     126             : //------------------------------------------------------------------------------
     127           0 : StringSequence  OButtonModel::getSupportedServiceNames() throw()
     128             : {
     129           0 :     StringSequence aSupported = OClickableImageBaseModel::getSupportedServiceNames();
     130           0 :     aSupported.realloc( aSupported.getLength() + 1 );
     131             : 
     132           0 :     OUString* pArray = aSupported.getArray();
     133           0 :     pArray[ aSupported.getLength() - 1 ] = FRM_SUN_COMPONENT_COMMANDBUTTON;
     134             : 
     135           0 :     return aSupported;
     136             : }
     137             : 
     138             : //------------------------------------------------------------------------------
     139           0 : OUString OButtonModel::getServiceName() throw ( ::com::sun::star::uno::RuntimeException)
     140             : {
     141           0 :     return OUString(FRM_COMPONENT_COMMANDBUTTON); // old (non-sun) name for compatibility !
     142             : }
     143             : 
     144             : //------------------------------------------------------------------------------
     145           0 : void OButtonModel::write(const Reference<XObjectOutputStream>& _rxOutStream) throw (::com::sun::star::io::IOException, ::com::sun::star::uno::RuntimeException)
     146             : {
     147           0 :     OClickableImageBaseModel::write(_rxOutStream);
     148             : 
     149           0 :     _rxOutStream->writeShort(0x0003);   // Version
     150             : 
     151             :     {
     152           0 :         OStreamSection aSection( _rxOutStream.get() );
     153             :             // this will allow readers to skip unknown bytes in their dtor
     154             : 
     155           0 :         _rxOutStream->writeShort( (sal_uInt16)m_eButtonType );
     156             : 
     157           0 :         OUString sTmp = INetURLObject::decode( m_sTargetURL, '%', INetURLObject::DECODE_UNAMBIGUOUS);
     158           0 :         _rxOutStream << sTmp;
     159           0 :         _rxOutStream << m_sTargetFrame;
     160           0 :         writeHelpTextCompatibly(_rxOutStream);
     161           0 :         _rxOutStream << isDispatchUrlInternal();
     162             :     }
     163           0 : }
     164             : 
     165             : //------------------------------------------------------------------------------
     166           0 : void OButtonModel::read(const Reference<XObjectInputStream>& _rxInStream) throw (::com::sun::star::io::IOException, ::com::sun::star::uno::RuntimeException)
     167             : {
     168           0 :     OClickableImageBaseModel::read(_rxInStream);
     169             : 
     170           0 :     sal_uInt16 nVersion = _rxInStream->readShort();     // Version
     171           0 :     switch (nVersion)
     172             :     {
     173             :         case 0x0001:
     174             :         {
     175           0 :             m_eButtonType = (FormButtonType)_rxInStream->readShort();
     176             : 
     177           0 :             _rxInStream >> m_sTargetURL;
     178           0 :             _rxInStream >> m_sTargetFrame;
     179             :         }
     180           0 :         break;
     181             : 
     182             :         case 0x0002:
     183             :         {
     184           0 :             m_eButtonType = (FormButtonType)_rxInStream->readShort();
     185             : 
     186           0 :             _rxInStream >> m_sTargetURL;
     187           0 :             _rxInStream >> m_sTargetFrame;
     188           0 :             readHelpTextCompatibly(_rxInStream);
     189             :         }
     190           0 :         break;
     191             : 
     192             :         case 0x0003:
     193             :         {
     194           0 :             OStreamSection aSection( _rxInStream.get() );
     195             :                 // this will skip any unknown bytes in it's dtor
     196             : 
     197             :             // button type
     198           0 :             m_eButtonType = (FormButtonType)_rxInStream->readShort();
     199             : 
     200             :             // URL
     201           0 :             _rxInStream >> m_sTargetURL;
     202             : 
     203             :             // target frame
     204           0 :             _rxInStream >> m_sTargetFrame;
     205             : 
     206             :             // help text
     207           0 :             readHelpTextCompatibly(_rxInStream);
     208             : 
     209             :             // DispatchInternal
     210             :             sal_Bool bDispath;
     211           0 :             _rxInStream >> bDispath;
     212           0 :             setDispatchUrlInternal(bDispath);
     213             :         }
     214           0 :         break;
     215             : 
     216             :         default:
     217             :             OSL_FAIL("OButtonModel::read : unknown version !");
     218           0 :             m_eButtonType = FormButtonType_PUSH;
     219           0 :             m_sTargetURL = OUString();
     220           0 :             m_sTargetFrame = OUString();
     221           0 :             break;
     222             :     }
     223           0 : }
     224             : 
     225             : //--------------------------------------------------------------------
     226          45 : void SAL_CALL OButtonModel::disposing()
     227             : {
     228          45 :     m_aResetHelper.disposing();
     229          45 :     OClickableImageBaseModel::disposing();
     230          45 : }
     231             : 
     232             : //--------------------------------------------------------------------
     233           0 : void SAL_CALL OButtonModel::reset() throw (RuntimeException)
     234             : {
     235           0 :     if ( !m_aResetHelper.approveReset() )
     236           0 :         return;
     237             : 
     238           0 :     impl_resetNoBroadcast_nothrow();
     239             : 
     240           0 :     m_aResetHelper.notifyResetted();
     241             : }
     242             : 
     243             : //--------------------------------------------------------------------
     244          31 : void SAL_CALL OButtonModel::addResetListener( const Reference< XResetListener >& _listener ) throw (RuntimeException)
     245             : {
     246          31 :     m_aResetHelper.addResetListener( _listener );
     247          31 : }
     248             : 
     249             : //--------------------------------------------------------------------
     250          31 : void SAL_CALL OButtonModel::removeResetListener( const Reference< XResetListener >& _listener ) throw (RuntimeException)
     251             : {
     252          31 :     m_aResetHelper.removeResetListener( _listener );
     253          31 : }
     254             : 
     255             : //--------------------------------------------------------------------
     256        3533 : void SAL_CALL OButtonModel::getFastPropertyValue( Any& _rValue, sal_Int32 _nHandle ) const
     257             : {
     258        3533 :     switch ( _nHandle )
     259             :     {
     260             :     case PROPERTY_ID_DEFAULT_STATE:
     261          47 :         _rValue <<= (sal_Int16)m_eDefaultState;
     262          47 :         break;
     263             : 
     264             :     default:
     265        3486 :         OClickableImageBaseModel::getFastPropertyValue( _rValue, _nHandle );
     266        3486 :         break;
     267             :     }
     268        3533 : }
     269             : 
     270             : //--------------------------------------------------------------------
     271         135 : void SAL_CALL OButtonModel::setFastPropertyValue_NoBroadcast( sal_Int32 _nHandle, const Any& _rValue ) throw (Exception)
     272             : {
     273         135 :     switch ( _nHandle )
     274             :     {
     275             :     case PROPERTY_ID_DEFAULT_STATE:
     276             :     {
     277           0 :         sal_Int16 nDefaultState( (sal_Int16)STATE_NOCHECK );
     278           0 :         OSL_VERIFY( _rValue >>= nDefaultState );
     279           0 :         m_eDefaultState = (ToggleState)nDefaultState;
     280           0 :         impl_resetNoBroadcast_nothrow();
     281             :     }
     282           0 :     break;
     283             : 
     284             :     default:
     285         135 :         OClickableImageBaseModel::setFastPropertyValue_NoBroadcast( _nHandle, _rValue );
     286         135 :         break;
     287             :     }
     288         135 : }
     289             : 
     290             : //--------------------------------------------------------------------
     291         182 : sal_Bool SAL_CALL OButtonModel::convertFastPropertyValue( Any& _rConvertedValue, Any& _rOldValue, sal_Int32 _nHandle, const Any& _rValue ) throw (IllegalArgumentException)
     292             : {
     293         182 :     sal_Bool bModified = sal_False;
     294         182 :     switch ( _nHandle )
     295             :     {
     296             :     case PROPERTY_ID_DEFAULT_STATE:
     297           1 :         bModified = tryPropertyValue( _rConvertedValue, _rOldValue, _rValue, (sal_Int16)m_eDefaultState );
     298           1 :         break;
     299             : 
     300             :     default:
     301         181 :         bModified = OClickableImageBaseModel::convertFastPropertyValue( _rConvertedValue, _rOldValue, _nHandle, _rValue );
     302         181 :         break;
     303             :     }
     304         182 :     return bModified;
     305             : }
     306             : 
     307             : //--------------------------------------------------------------------
     308           0 : Any OButtonModel::getPropertyDefaultByHandle( sal_Int32 _nHandle ) const
     309             : {
     310           0 :     Any aDefault;
     311           0 :     switch ( _nHandle )
     312             :     {
     313             :     case PROPERTY_ID_DEFAULT_STATE:
     314           0 :         aDefault <<= (sal_Int16)STATE_NOCHECK;
     315           0 :         break;
     316             : 
     317             :     default:
     318           0 :         aDefault = OClickableImageBaseModel::getPropertyDefaultByHandle( _nHandle );
     319           0 :         break;
     320             :     }
     321           0 :     return aDefault;
     322             : }
     323             : 
     324             : //--------------------------------------------------------------------
     325           0 : void OButtonModel::impl_resetNoBroadcast_nothrow()
     326             : {
     327             :     try
     328             :     {
     329           0 :         setPropertyValue( PROPERTY_STATE, getPropertyValue( PROPERTY_DEFAULT_STATE ) );
     330             :     }
     331           0 :     catch( const Exception& )
     332             :     {
     333             :         DBG_UNHANDLED_EXCEPTION();
     334             :     }
     335           0 : }
     336             : 
     337             : //==================================================================
     338             : // OButtonControl
     339             : //==================================================================
     340             : //------------------------------------------------------------------
     341         119 : InterfaceRef SAL_CALL OButtonControl_CreateInstance(const Reference<XMultiServiceFactory>& _rxFactory)
     342             : {
     343         119 :     return *(new OButtonControl( comphelper::getComponentContext(_rxFactory) ));
     344             : }
     345             : 
     346             : //------------------------------------------------------------------------------
     347          58 : Sequence<Type> OButtonControl::_getTypes()
     348             : {
     349             :     return ::comphelper::concatSequences(
     350             :         OButtonControl_BASE::getTypes(),
     351             :         OClickableImageBaseControl::_getTypes(),
     352             :         OFormNavigationHelper::getTypes()
     353          58 :     );
     354             : }
     355             : 
     356             : //------------------------------------------------------------------------------
     357           0 : StringSequence  OButtonControl::getSupportedServiceNames() throw()
     358             : {
     359           0 :     StringSequence aSupported = OClickableImageBaseControl::getSupportedServiceNames();
     360           0 :     aSupported.realloc(aSupported.getLength() + 1);
     361             : 
     362           0 :     OUString*pArray = aSupported.getArray();
     363           0 :     pArray[aSupported.getLength()-1] = FRM_SUN_CONTROL_COMMANDBUTTON;
     364           0 :     return aSupported;
     365             : }
     366             : 
     367             : //------------------------------------------------------------------------------
     368         119 : OButtonControl::OButtonControl(const Reference<XComponentContext>& _rxFactory)
     369             :                  :OClickableImageBaseControl(_rxFactory, VCL_CONTROL_COMMANDBUTTON)
     370             :                  ,OFormNavigationHelper( _rxFactory )
     371             :                  ,m_nClickEvent( 0 )
     372             :                  ,m_nTargetUrlFeatureId( -1 )
     373         119 :                  ,m_bEnabledByPropertyValue( sal_False )
     374             : {
     375         119 :     increment(m_refCount);
     376             :     {
     377             :         // Register as ActionListener
     378         119 :         Reference<XButton>  xButton;
     379         119 :         query_aggregation( m_xAggregate, xButton);
     380         119 :         if (xButton.is())
     381         119 :             xButton->addActionListener(this);
     382             :     }
     383             :     // For Listener: refcount at one
     384         119 :     decrement(m_refCount);
     385         119 : }
     386             : 
     387             : //------------------------------------------------------------------------------
     388         333 : OButtonControl::~OButtonControl()
     389             : {
     390         111 :     if (m_nClickEvent)
     391           0 :         Application::RemoveUserEvent(m_nClickEvent);
     392         222 : }
     393             : 
     394             : // UNO binding
     395             : //------------------------------------------------------------------------------
     396        3102 : Any SAL_CALL OButtonControl::queryAggregation(const Type& _rType) throw (RuntimeException)
     397             : {
     398             :     // if asked for the XTypeProvider, don't let OButtonControl_BASE do this
     399        3102 :     Any aReturn;
     400        3102 :     if ( !_rType.equals( ::getCppuType( static_cast< Reference< XTypeProvider >* >( NULL ) ) ) )
     401        3073 :         aReturn = OButtonControl_BASE::queryInterface( _rType );
     402             : 
     403        3102 :     if ( !aReturn.hasValue() )
     404        1558 :         aReturn = OClickableImageBaseControl::queryAggregation( _rType );
     405             : 
     406        3102 :     if ( !aReturn.hasValue() )
     407         158 :         aReturn = OFormNavigationHelper::queryInterface( _rType );
     408             : 
     409        3102 :     return aReturn;
     410             : }
     411             : 
     412             : //------------------------------------------------------------------------------
     413         111 : void SAL_CALL OButtonControl::disposing()
     414             : {
     415         111 :     startOrStopModelPropertyListening( false );
     416             : 
     417         111 :     OClickableImageBaseControl::disposing();
     418         111 :     OFormNavigationHelper::dispose();
     419         111 : }
     420             : 
     421             : //------------------------------------------------------------------------------
     422         425 : void SAL_CALL OButtonControl::disposing( const EventObject& _rSource ) throw( RuntimeException )
     423             : {
     424         425 :     OControl::disposing( _rSource );
     425         425 :     OFormNavigationHelper::disposing( _rSource );
     426         425 : }
     427             : 
     428             : // ActionListener
     429             : //------------------------------------------------------------------------------
     430           1 : void OButtonControl::actionPerformed(const ActionEvent& /*rEvent*/) throw ( ::com::sun::star::uno::RuntimeException)
     431             : {
     432             :     // Asynchronous for starutil::URL-Button
     433           1 :     sal_uLong n = Application::PostUserEvent( LINK(this, OButtonControl,OnClick) );
     434             :     {
     435           1 :         ::osl::MutexGuard aGuard( m_aMutex );
     436           1 :         m_nClickEvent = n;
     437             :     }
     438           1 : }
     439             : 
     440             : //------------------------------------------------------------------------------
     441           2 : IMPL_LINK_NOARG(OButtonControl, OnClick)
     442             : {
     443           1 :     ::osl::ClearableMutexGuard aGuard( m_aMutex );
     444           1 :     m_nClickEvent = 0;
     445             : 
     446           1 :     if (m_aApproveActionListeners.getLength())
     447             :     {
     448             :         // if there are listeners, start the action in an own thread, to not allow
     449             :         // them to block us here (we're in the application's main thread)
     450           0 :         getImageProducerThread()->addEvent();
     451             :     }
     452             :     else
     453             :     {
     454             :         // Else, don't. We then must not notify the Listeners in any case,
     455             :         // not even if added later on.
     456           1 :         aGuard.clear();
     457             : 
     458             :         // recognize the button type
     459           1 :         Reference<XPropertySet>  xSet(getModel(), UNO_QUERY);
     460           1 :         if (!xSet.is())
     461           0 :             return 0L;
     462             : 
     463           1 :         if (FormButtonType_PUSH == *(FormButtonType*)xSet->getPropertyValue(PROPERTY_BUTTONTYPE).getValue())
     464             :         {
     465             :             // notify the action listeners for a push button
     466           1 :             ::cppu::OInterfaceIteratorHelper aIter(m_aActionListeners);
     467           2 :             ActionEvent aEvt(static_cast<XWeak*>(this), m_aActionCommand);
     468           3 :             while(aIter.hasMoreElements() )
     469             :             {
     470             :                 // catch exceptions
     471             :                 // and catch them on a per-listener basis - if one listener fails, the others still need
     472             :                 // to get notified
     473             :                 try
     474             :                 {
     475           1 :                     static_cast< XActionListener* >( aIter.next() )->actionPerformed(aEvt);
     476             :                 }
     477             : #ifdef DBG_UTIL
     478             :                 catch( const RuntimeException& )
     479             :                 {
     480             :                     // silence this
     481             :                 }
     482             : #endif
     483           0 :                 catch( const Exception& )
     484             :                 {
     485             :                     OSL_FAIL( "OButtonControl::OnClick: caught a exception other than RuntimeException!" );
     486             :                 }
     487           1 :             }
     488             :         }
     489             :         else
     490           0 :             actionPerformed_Impl( sal_False, ::com::sun::star::awt::MouseEvent() );
     491             :     }
     492           1 :     return 0L;
     493             : }
     494             : 
     495             : //------------------------------------------------------------------------------
     496           0 : void OButtonControl::actionPerformed_Impl( sal_Bool _bNotifyListener, const ::com::sun::star::awt::MouseEvent& _rEvt )
     497             : {
     498             :     {
     499           0 :         sal_Int16 nFeatureId = -1;
     500             :         {
     501           0 :             ::osl::MutexGuard aGuard( m_aMutex );
     502           0 :             nFeatureId = m_nTargetUrlFeatureId;
     503             :         }
     504             : 
     505           0 :         if ( nFeatureId != -1 )
     506             :         {
     507           0 :             if ( !approveAction() )
     508           0 :                 return;
     509             : 
     510           0 :             SolarMutexGuard aGuard;
     511           0 :             dispatch( nFeatureId );
     512           0 :             return;
     513             :         }
     514             :     }
     515             : 
     516           0 :     OClickableImageBaseControl::actionPerformed_Impl( _bNotifyListener, _rEvt );
     517             : }
     518             : 
     519             : // XButton
     520             : //------------------------------------------------------------------------------
     521           1 : void OButtonControl::setLabel(const OUString& Label) throw( RuntimeException )
     522             : {
     523           1 :     Reference<XButton>  xButton;
     524           1 :     query_aggregation( m_xAggregate, xButton );
     525           1 :     if (xButton.is())
     526           1 :         xButton->setLabel(Label);
     527           1 : }
     528             : 
     529             : //------------------------------------------------------------------------------
     530           1 : void SAL_CALL OButtonControl::setActionCommand(const OUString& _rCommand) throw( RuntimeException )
     531             : {
     532             :     {
     533           1 :         ::osl::MutexGuard aGuard( m_aMutex );
     534           1 :         m_aActionCommand = _rCommand;
     535             :     }
     536             : 
     537           1 :     Reference<XButton>  xButton;
     538           1 :     query_aggregation( m_xAggregate, xButton);
     539           1 :     if (xButton.is())
     540           1 :         xButton->setActionCommand(_rCommand);
     541           1 : }
     542             : 
     543             : //------------------------------------------------------------------------------
     544           7 : void SAL_CALL OButtonControl::addActionListener(const Reference<XActionListener>& _rxListener) throw( RuntimeException )
     545             : {
     546           7 :     m_aActionListeners.addInterface(_rxListener);
     547           7 : }
     548             : 
     549             : //------------------------------------------------------------------------------
     550           7 : void SAL_CALL OButtonControl::removeActionListener(const Reference<XActionListener>& _rxListener) throw( RuntimeException )
     551             : {
     552           7 :     m_aActionListeners.removeInterface(_rxListener);
     553           7 : }
     554             : 
     555             : //------------------------------------------------------------------------------
     556         335 : class DoPropertyListening
     557             : {
     558             : private:
     559             :     Reference< XPropertySet >               m_xProps;
     560             :     Reference< XPropertyChangeListener >    m_xListener;
     561             :     bool                                    m_bStartListening;
     562             : 
     563             : public:
     564             :     DoPropertyListening(
     565             :         const Reference< XInterface >& _rxComponent,
     566             :         const Reference< XPropertyChangeListener >& _rxListener,
     567             :         bool _bStart
     568             :     );
     569             : 
     570             :     void    handleListening( const OUString& _rPropertyName );
     571             : };
     572             : 
     573             : //..............................................................................
     574         335 : DoPropertyListening::DoPropertyListening(
     575             :         const Reference< XInterface >& _rxComponent, const Reference< XPropertyChangeListener >& _rxListener,
     576             :         bool _bStart )
     577             :     :m_xProps( _rxComponent, UNO_QUERY )
     578             :     ,m_xListener( _rxListener )
     579         335 :     ,m_bStartListening( _bStart )
     580             : {
     581             :     DBG_ASSERT( m_xProps.is() || !_rxComponent.is(), "DoPropertyListening::DoPropertyListening: valid component, but no property set!" );
     582             :     DBG_ASSERT( m_xListener.is(), "DoPropertyListening::DoPropertyListening: invalid listener!" );
     583         335 : }
     584             : 
     585             : //..............................................................................
     586        1005 : void DoPropertyListening::handleListening( const OUString& _rPropertyName )
     587             : {
     588        1005 :     if ( m_xProps.is() )
     589             :     {
     590         471 :         if ( m_bStartListening )
     591         336 :             m_xProps->addPropertyChangeListener( _rPropertyName, m_xListener );
     592             :         else
     593         135 :             m_xProps->removePropertyChangeListener( _rPropertyName, m_xListener );
     594             :     }
     595        1005 : }
     596             : 
     597             : //------------------------------------------------------------------------------
     598         335 : void OButtonControl::startOrStopModelPropertyListening( bool _bStart )
     599             : {
     600         335 :     DoPropertyListening aListeningHandler( getModel(), this, _bStart );
     601         335 :     aListeningHandler.handleListening( PROPERTY_TARGET_URL );
     602         335 :     aListeningHandler.handleListening( PROPERTY_BUTTONTYPE );
     603         335 :     aListeningHandler.handleListening( PROPERTY_ENABLED );
     604         335 : }
     605             : 
     606             : //------------------------------------------------------------------------------
     607         112 : sal_Bool SAL_CALL OButtonControl::setModel( const Reference< XControlModel >& _rxModel ) throw ( RuntimeException )
     608             : {
     609         112 :     startOrStopModelPropertyListening( false );
     610         112 :     sal_Bool bResult = OClickableImageBaseControl::setModel( _rxModel );
     611         112 :     startOrStopModelPropertyListening( true );
     612             : 
     613         112 :     m_bEnabledByPropertyValue = sal_True;
     614         112 :     Reference< XPropertySet > xModelProps( _rxModel, UNO_QUERY );
     615         112 :     if ( xModelProps.is() )
     616         112 :         xModelProps->getPropertyValue( PROPERTY_ENABLED ) >>= m_bEnabledByPropertyValue;
     617             : 
     618         112 :     modelFeatureUrlPotentiallyChanged( );
     619             : 
     620         112 :     return bResult;
     621             : }
     622             : 
     623             : //------------------------------------------------------------------------------
     624         112 : void OButtonControl::modelFeatureUrlPotentiallyChanged( )
     625             : {
     626         112 :     sal_Int16 nOldUrlFeatureId = m_nTargetUrlFeatureId;
     627             : 
     628             :     // doe we have another TargetURL now? If so, we need to update our dispatches
     629         112 :     m_nTargetUrlFeatureId = getModelUrlFeatureId( );
     630         112 :     if ( nOldUrlFeatureId != m_nTargetUrlFeatureId )
     631             :     {
     632           0 :         invalidateSupportedFeaturesSet();
     633           0 :         if ( !isDesignMode() )
     634           0 :             updateDispatches( );
     635             :     }
     636         112 : }
     637             : 
     638             : //------------------------------------------------------------------------------
     639           0 : void SAL_CALL OButtonControl::propertyChange( const PropertyChangeEvent& _rEvent ) throw ( RuntimeException )
     640             : {
     641           0 :     if  (   _rEvent.PropertyName.equals( PROPERTY_TARGET_URL )
     642           0 :         ||  _rEvent.PropertyName.equals( PROPERTY_BUTTONTYPE )
     643             :         )
     644             :     {
     645           0 :         modelFeatureUrlPotentiallyChanged( );
     646             :     }
     647           0 :     else if ( _rEvent.PropertyName.equals( PROPERTY_ENABLED ) )
     648             :     {
     649           0 :         _rEvent.NewValue >>= m_bEnabledByPropertyValue;
     650             :     }
     651           0 : }
     652             : 
     653             : //------------------------------------------------------------------------------
     654             : namespace
     655             : {
     656           0 :     bool isFormControllerURL( const OUString& _rURL )
     657             :     {
     658           0 :         return  ( _rURL.getLength() > RTL_CONSTASCII_LENGTH( ".uno:FormController/" ) )
     659           0 :             &&  ( _rURL.startsWith( ".uno:FormController/" ) );
     660             :     }
     661             : }
     662             : 
     663             : //------------------------------------------------------------------------------
     664         112 : sal_Int16 OButtonControl::getModelUrlFeatureId( ) const
     665             : {
     666         112 :     sal_Int16 nFeatureId = -1;
     667             : 
     668             :     // some URL related properties of the model
     669         112 :     OUString sUrl;
     670         112 :     FormButtonType eButtonType = FormButtonType_PUSH;
     671             : 
     672         224 :     Reference< XPropertySet > xModelProps( const_cast< OButtonControl* >( this )->getModel(), UNO_QUERY );
     673         112 :     if ( xModelProps.is() )
     674             :     {
     675         112 :         xModelProps->getPropertyValue( PROPERTY_TARGET_URL ) >>= sUrl;
     676         112 :         xModelProps->getPropertyValue( PROPERTY_BUTTONTYPE ) >>= eButtonType;
     677             :     }
     678             : 
     679             :     // are we a URL button?
     680         112 :     if ( eButtonType == FormButtonType_URL )
     681             :     {
     682             :         // is it a feature URL?
     683           0 :         if ( isFormControllerURL( sUrl ) )
     684             :         {
     685           0 :             OFormNavigationMapper aMapper( m_xContext );
     686           0 :             nFeatureId = aMapper.getFeatureId( sUrl );
     687             :         }
     688             :     }
     689             : 
     690         224 :     return nFeatureId;
     691             : }
     692             : 
     693             : //------------------------------------------------------------------
     694          46 : void SAL_CALL OButtonControl::setDesignMode( sal_Bool _bOn ) throw( RuntimeException )
     695             : {
     696          46 :     OClickableImageBaseControl::setDesignMode( _bOn  );
     697             : 
     698          46 :     if ( _bOn )
     699          14 :         disconnectDispatchers();
     700             :     else
     701          32 :         connectDispatchers();
     702             :         // this will connect if not already connected and just update else
     703          46 : }
     704             : 
     705             : //------------------------------------------------------------------------------
     706          94 : void OButtonControl::getSupportedFeatures( ::std::vector< sal_Int16 >& /* [out] */ _rFeatureIds )
     707             : {
     708          94 :     if ( -1 != m_nTargetUrlFeatureId )
     709           0 :         _rFeatureIds.push_back( m_nTargetUrlFeatureId );
     710          94 : }
     711             : 
     712             : //------------------------------------------------------------------
     713           0 : void OButtonControl::featureStateChanged( sal_Int16 _nFeatureId, sal_Bool _bEnabled )
     714             : {
     715           0 :     if ( _nFeatureId == m_nTargetUrlFeatureId )
     716             :     {
     717             :         // enable or disable our peer, according to the new state
     718           0 :         Reference< XVclWindowPeer > xPeer( getPeer(), UNO_QUERY );
     719           0 :         if ( xPeer.is() )
     720           0 :             xPeer->setProperty( PROPERTY_ENABLED, makeAny( m_bEnabledByPropertyValue ? _bEnabled : sal_False ) );
     721             :             // if we're disabled according to our model's property, then
     722             :             // we don't care for the feature state, but *are* disabled.
     723             :             // If the model's property states that we're enabled, then we *do*
     724             :             // care for the feature state
     725             :     }
     726             : 
     727             :     // base class
     728           0 :     OFormNavigationHelper::featureStateChanged( _nFeatureId, _bEnabled );
     729           0 : }
     730             : 
     731             : //------------------------------------------------------------------
     732         219 : void OButtonControl::allFeatureStatesChanged( )
     733             : {
     734         219 :     if ( -1 != m_nTargetUrlFeatureId )
     735             :         // we have only one supported feature, so simulate it has changed ...
     736           0 :         featureStateChanged( m_nTargetUrlFeatureId, isEnabled( m_nTargetUrlFeatureId ) );
     737             : 
     738             :     // base class
     739         219 :     OFormNavigationHelper::allFeatureStatesChanged( );
     740         219 : }
     741             : 
     742             : //------------------------------------------------------------------
     743           0 : bool OButtonControl::isEnabled( sal_Int16 _nFeatureId ) const
     744             : {
     745           0 :     if ( const_cast< OButtonControl* >( this )->isDesignMode() )
     746             :         // TODO: the model property?
     747           0 :        return true;
     748             : 
     749           0 :     return OFormNavigationHelper::isEnabled( _nFeatureId );
     750             : }
     751             : 
     752             : //--------------------------------------------------------------------
     753          31 : void SAL_CALL OButtonControl::registerDispatchProviderInterceptor( const Reference< XDispatchProviderInterceptor >& _rxInterceptor ) throw (RuntimeException)
     754             : {
     755          31 :     OClickableImageBaseControl::registerDispatchProviderInterceptor( _rxInterceptor );
     756          31 :     OFormNavigationHelper::registerDispatchProviderInterceptor( _rxInterceptor );
     757          31 : }
     758             : 
     759             : //--------------------------------------------------------------------
     760          31 : void SAL_CALL OButtonControl::releaseDispatchProviderInterceptor( const Reference< XDispatchProviderInterceptor >& _rxInterceptor ) throw (RuntimeException)
     761             : {
     762          31 :     OClickableImageBaseControl::releaseDispatchProviderInterceptor( _rxInterceptor );
     763          31 :     OFormNavigationHelper::releaseDispatchProviderInterceptor( _rxInterceptor );
     764          31 : }
     765             : 
     766             : //.........................................................................
     767          72 : }   // namespace frm
     768             : //.........................................................................
     769             : 
     770             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10