1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: eventsupplier.cxx,v $
10 * $Revision: 1.36.12.5 $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_sfx2.hxx"
34 //--------------------------------------------------------------------------------------------------------
35 #include <com/sun/star/beans/PropertyValue.hpp>
37 #ifndef _COM_SUN_STAR_UTL_URL_HPP_
38 #include <com/sun/star/util/URL.hpp>
41 #ifndef _COM_SUN_STAR_UTL_XURLTRANSFORMER_HPP_
42 #include <com/sun/star/util/XURLTransformer.hpp>
44 #include <tools/urlobj.hxx>
45 #include <svtools/macitem.hxx>
46 #include <sfx2/appuno.hxx>
47 #include <sfx2/objsh.hxx>
48 #include <sfx2/sfxbasemodel.hxx>
49 #include <sfx2/evntconf.hxx>
50 #include <svtools/eventcfg.hxx>
52 #include <svtools/securityoptions.hxx>
53 #include <comphelper/processfactory.hxx>
54 #include "eventsupplier.hxx"
56 #include <sfx2/app.hxx>
57 #include "sfxresid.hxx"
59 #include <sfx2/sfxsids.hrc>
60 #include "sfxlocal.hrc"
61 #include <sfx2/docfile.hxx>
62 #include <sfx2/viewfrm.hxx>
63 #include <sfx2/frame.hxx>
65 //--------------------------------------------------------------------------------------------------------
67 #define MACRO_PRFIX "macro://"
68 #define MACRO_POSTFIX "()"
70 //--------------------------------------------------------------------------------------------------------
72 #define PROPERTYVALUE ::com::sun::star::beans::PropertyValue
73 #define UNO_QUERY ::com::sun::star::uno::UNO_QUERY
75 namespace css
= ::com::sun::star
;
76 using ::com::sun::star::uno::Sequence
;
77 using ::com::sun::star::beans::PropertyValue
;
79 //--------------------------------------------------------------------------------------------------------
80 // --- XNameReplace ---
81 //--------------------------------------------------------------------------------------------------------
82 void SAL_CALL
SfxEvents_Impl::replaceByName( const OUSTRING
& aName
, const ANY
& rElement
)
83 throw( ILLEGALARGUMENTEXCEPTION
, NOSUCHELEMENTEXCEPTION
,
84 WRAPPEDTARGETEXCEPTION
, RUNTIMEEXCEPTION
)
86 ::osl::MutexGuard
aGuard( maMutex
);
88 // find the event in the list and replace the data
89 long nCount
= maEventNames
.getLength();
90 for ( long i
=0; i
<nCount
; i
++ )
92 if ( maEventNames
[i
] == aName
)
94 Sequence
< PropertyValue
> aProperties
;
95 // check for correct type of the element
96 if ( rElement
.hasValue() && !( rElement
>>= aProperties
) )
97 throw ILLEGALARGUMENTEXCEPTION();
99 // create Configuration at first, creation might call this method also and that would overwrite everything
100 // we might have stored before!
101 USHORT nID
= (USHORT
) SfxEventConfiguration::GetEventId_Impl( aName
);
102 OSL_ENSURE( nID
, "SfxEvents_Impl::replaceByName: no ID for the given event!" );
107 if ( mpObjShell
&& !mpObjShell
->IsLoading() )
108 mpObjShell
->SetModified( TRUE
);
110 if ( aProperties
.getLength() )
112 // "normalize" the macro descriptor
114 BlowUpMacro( rElement
, aValue
, mpObjShell
);
115 aValue
>>= aProperties
;
117 ::rtl::OUString sType
;
118 if ( ( aProperties
.getLength() == 1 )
119 && ( aProperties
[0].Name
.compareToAscii( PROP_EVENT_TYPE
) == 0 )
120 && ( aProperties
[0].Value
>>= sType
)
121 && ( sType
.getLength() == 0 )
124 // An empty event type means no binding. Therefore reset data
125 // to reflect that state.
126 // (that's for compatibility only. Nowadays, the Tools/Customize dialog should
127 // set an empty sequence to indicate the request for resetting the assignment.)
128 aProperties
.realloc( 0 );
132 if ( aProperties
.getLength() )
134 maEventData
[i
] = makeAny( aProperties
);
138 maEventData
[i
].clear();
144 throw NOSUCHELEMENTEXCEPTION();
147 //--------------------------------------------------------------------------------------------------------
148 // --- XNameAccess ---
149 //--------------------------------------------------------------------------------------------------------
150 ANY SAL_CALL
SfxEvents_Impl::getByName( const OUSTRING
& aName
)
151 throw( NOSUCHELEMENTEXCEPTION
, WRAPPEDTARGETEXCEPTION
,
154 ::osl::MutexGuard
aGuard( maMutex
);
156 // find the event in the list and return the data
158 long nCount
= maEventNames
.getLength();
160 for ( long i
=0; i
<nCount
; i
++ )
162 if ( maEventNames
[i
] == aName
)
163 return maEventData
[i
];
166 throw NOSUCHELEMENTEXCEPTION();
169 //--------------------------------------------------------------------------------------------------------
170 SEQUENCE
< OUSTRING
> SAL_CALL
SfxEvents_Impl::getElementNames() throw ( RUNTIMEEXCEPTION
)
175 //--------------------------------------------------------------------------------------------------------
176 sal_Bool SAL_CALL
SfxEvents_Impl::hasByName( const OUSTRING
& aName
) throw ( RUNTIMEEXCEPTION
)
178 ::osl::MutexGuard
aGuard( maMutex
);
180 // find the event in the list and return the data
182 long nCount
= maEventNames
.getLength();
184 for ( long i
=0; i
<nCount
; i
++ )
186 if ( maEventNames
[i
] == aName
)
193 //--------------------------------------------------------------------------------------------------------
194 // --- XElementAccess ( parent of XNameAccess ) ---
195 //--------------------------------------------------------------------------------------------------------
196 UNOTYPE SAL_CALL
SfxEvents_Impl::getElementType() throw ( RUNTIMEEXCEPTION
)
198 UNOTYPE aElementType
= ::getCppuType( (const SEQUENCE
< PROPERTYVALUE
> *)0 );
202 //--------------------------------------------------------------------------------------------------------
203 sal_Bool SAL_CALL
SfxEvents_Impl::hasElements() throw ( RUNTIMEEXCEPTION
)
205 ::osl::MutexGuard
aGuard( maMutex
);
207 if ( maEventNames
.getLength() )
213 static void Execute( ANY
& aEventData
, const css::document::DocumentEvent
& aTrigger
, SfxObjectShell
* pDoc
)
215 SEQUENCE
< PROPERTYVALUE
> aProperties
;
216 if ( aEventData
>>= aProperties
)
218 OUSTRING aPrefix
= OUSTRING( RTL_CONSTASCII_USTRINGPARAM( MACRO_PRFIX
) );
224 sal_Int32 nCount
= aProperties
.getLength();
229 sal_Int32 nIndex
= 0;
230 while ( nIndex
< nCount
)
232 if ( aProperties
[ nIndex
].Name
.compareToAscii( PROP_EVENT_TYPE
) == 0 )
233 aProperties
[ nIndex
].Value
>>= aType
;
234 else if ( aProperties
[ nIndex
].Name
.compareToAscii( PROP_SCRIPT
) == 0 )
235 aProperties
[ nIndex
].Value
>>= aScript
;
236 else if ( aProperties
[ nIndex
].Name
.compareToAscii( PROP_LIBRARY
) == 0 )
237 aProperties
[ nIndex
].Value
>>= aLibrary
;
238 else if ( aProperties
[ nIndex
].Name
.compareToAscii( PROP_MACRO_NAME
) == 0 )
239 aProperties
[ nIndex
].Value
>>= aMacroName
;
241 DBG_ERROR("Unknown property value!");
246 if ( aType
.compareToAscii( STAR_BASIC
) == 0 && aScript
.getLength() )
248 com::sun::star::uno::Any aAny
;
249 SfxMacroLoader::loadMacro( aScript
, aAny
, pDoc
);
251 else if ( aType
.compareToAscii( "Service" ) == 0 ||
252 aType
.compareToAscii( "Script" ) == 0 )
254 if ( aScript
.getLength() )
256 SfxViewFrame
* pView
= pDoc
?
257 SfxViewFrame::GetFirst( pDoc
) :
258 SfxViewFrame::Current();
260 ::com::sun::star::uno::Reference
261 < ::com::sun::star::util::XURLTransformer
> xTrans(
262 ::comphelper::getProcessServiceFactory()->createInstance(
263 rtl::OUString::createFromAscii(
264 "com.sun.star.util.URLTransformer" ) ),
267 ::com::sun::star::util::URL aURL
;
268 aURL
.Complete
= aScript
;
269 xTrans
->parseStrict( aURL
);
271 ::com::sun::star::uno::Reference
272 < ::com::sun::star::frame::XDispatchProvider
> xProv
;
276 xProv
= ::com::sun::star::uno::Reference
277 < ::com::sun::star::frame::XDispatchProvider
> (
278 pView
->GetFrame()->GetFrameInterface(), UNO_QUERY
);
282 xProv
= ::com::sun::star::uno::Reference
283 < ::com::sun::star::frame::XDispatchProvider
> (
284 ::comphelper::getProcessServiceFactory()->createInstance(
285 rtl::OUString::createFromAscii(
286 "com.sun.star.frame.Desktop" ) ),
290 ::com::sun::star::uno::Reference
< ::com::sun::star::frame::XDispatch
> xDisp
;
292 xDisp
= xProv
->queryDispatch( aURL
, ::rtl::OUString(), 0 );
296 //::com::sun::star::uno::Sequence < ::com::sun::star::beans::PropertyValue > aArgs(1);
297 //aArgs[0].Name = rtl::OUString::createFromAscii("Referer");
298 //aArs[0].Value <<= ::rtl::OUString( pDoc->GetMedium()->GetName() );
299 //xDisp->dispatch( aURL, aArgs );
301 css::beans::PropertyValue aEventParam
;
302 aEventParam
.Value
<<= aTrigger
;
303 css::uno::Sequence
< css::beans::PropertyValue
> aDispatchArgs( &aEventParam
, 1 );
304 xDisp
->dispatch( aURL
, aDispatchArgs
);
308 else if ( aType
.getLength() == 0 )
310 // Empty type means no active binding for the event. Just ignore do nothing.
314 DBG_ERRORFILE( "notifyEvent(): Unsupported event type" );
319 //--------------------------------------------------------------------------------------------------------
320 // --- ::document::XEventListener ---
321 //--------------------------------------------------------------------------------------------------------
322 void SAL_CALL
SfxEvents_Impl::notifyEvent( const DOCEVENTOBJECT
& aEvent
) throw( RUNTIMEEXCEPTION
)
324 ::osl::ClearableMutexGuard
aGuard( maMutex
);
326 // get the event name, find the coresponding data, execute the data
328 OUSTRING aName
= aEvent
.EventName
;
329 long nCount
= maEventNames
.getLength();
331 sal_Bool bFound
= sal_False
;
333 while ( !bFound
&& ( nIndex
< nCount
) )
335 if ( maEventNames
[nIndex
] == aName
)
344 ANY aEventData
= maEventData
[ nIndex
];
346 Execute( aEventData
, css::document::DocumentEvent(aEvent
.Source
, aEvent
.EventName
, NULL
, css::uno::Any()), mpObjShell
);
349 //--------------------------------------------------------------------------------------------------------
350 // --- ::lang::XEventListener ---
351 //--------------------------------------------------------------------------------------------------------
352 void SAL_CALL
SfxEvents_Impl::disposing( const EVENTOBJECT
& /*Source*/ ) throw( RUNTIMEEXCEPTION
)
354 ::osl::MutexGuard
aGuard( maMutex
);
356 if ( mxBroadcaster
.is() )
358 mxBroadcaster
->removeEventListener( this );
359 mxBroadcaster
= NULL
;
363 //--------------------------------------------------------------------------------------------------------
365 //--------------------------------------------------------------------------------------------------------
366 SfxEvents_Impl::SfxEvents_Impl( SfxObjectShell
* pShell
,
367 REFERENCE
< XEVENTBROADCASTER
> xBroadcaster
)
369 // get the list of supported events and store it
371 maEventNames
= pShell
->GetEventNames();
373 maEventNames
= SfxObjectShell::GetEventNames_Impl();
375 maEventData
= SEQUENCE
< ANY
> ( maEventNames
.getLength() );
378 mxBroadcaster
= xBroadcaster
;
380 if ( mxBroadcaster
.is() )
381 mxBroadcaster
->addEventListener( this );
384 //--------------------------------------------------------------------------------------------------------
385 SfxEvents_Impl::~SfxEvents_Impl()
389 //--------------------------------------------------------------------------------------------------------
390 SvxMacro
* SfxEvents_Impl::ConvertToMacro( const ANY
& rElement
, SfxObjectShell
* pObjShell
, BOOL bBlowUp
)
392 SvxMacro
* pMacro
= NULL
;
393 SEQUENCE
< PROPERTYVALUE
> aProperties
;
396 BlowUpMacro( rElement
, aAny
, pObjShell
);
400 if ( aAny
>>= aProperties
)
407 long nCount
= aProperties
.getLength();
413 while ( nIndex
< nCount
)
415 if ( aProperties
[ nIndex
].Name
.compareToAscii( PROP_EVENT_TYPE
) == 0 )
416 aProperties
[ nIndex
].Value
>>= aType
;
417 else if ( aProperties
[ nIndex
].Name
.compareToAscii( PROP_SCRIPT
) == 0 )
418 aProperties
[ nIndex
].Value
>>= aScriptURL
;
419 else if ( aProperties
[ nIndex
].Name
.compareToAscii( PROP_LIBRARY
) == 0 )
420 aProperties
[ nIndex
].Value
>>= aLibrary
;
421 else if ( aProperties
[ nIndex
].Name
.compareToAscii( PROP_MACRO_NAME
) == 0 )
422 aProperties
[ nIndex
].Value
>>= aMacroName
;
424 DBG_ERROR("Unknown propery value!");
430 ScriptType
eType( STARBASIC
);
431 if ( aType
.compareToAscii( STAR_BASIC
) == COMPARE_EQUAL
)
433 else if ( aType
.compareToAscii( "Script" ) == COMPARE_EQUAL
&& aScriptURL
.getLength() )
434 eType
= EXTENDED_STYPE
;
435 else if ( aType
.compareToAscii( SVX_MACRO_LANGUAGE_JAVASCRIPT
) == COMPARE_EQUAL
)
438 DBG_ERRORFILE( "ConvertToMacro: Unknown macro type" );
441 if ( aMacroName
.getLength() )
443 if ( aLibrary
.compareToAscii("application") == 0 )
444 aLibrary
= SFX_APP()->GetName();
446 aLibrary
= ::rtl::OUString();
447 pMacro
= new SvxMacro( aMacroName
, aLibrary
, eType
);
449 else if ( eType
== EXTENDED_STYPE
)
450 pMacro
= new SvxMacro( aScriptURL
, aType
);
456 void SfxEvents_Impl::BlowUpMacro( const ANY
& rEvent
, ANY
& rRet
, SfxObjectShell
* pDoc
)
459 pDoc
= SfxObjectShell::Current();
461 SEQUENCE
< PROPERTYVALUE
> aInProps
;
462 SEQUENCE
< PROPERTYVALUE
> aOutProps(2);
464 if ( !( rEvent
>>= aInProps
) )
467 sal_Int32 nCount
= aInProps
.getLength();
477 sal_Int32 nIndex
= 0;
479 while ( nIndex
< nCount
)
481 if ( aInProps
[ nIndex
].Name
.compareToAscii( PROP_EVENT_TYPE
) == 0 )
483 aInProps
[nIndex
].Value
>>= aType
;
484 aOutProps
[0] = aInProps
[nIndex
];
486 else if ( aInProps
[ nIndex
].Name
.compareToAscii( PROP_SCRIPT
) == 0 )
488 aInProps
[nIndex
].Value
>>= aScript
;
489 aOutProps
[1] = aInProps
[nIndex
];
491 else if ( aInProps
[ nIndex
].Name
.compareToAscii( PROP_LIBRARY
) == 0 )
493 aInProps
[ nIndex
].Value
>>= aLibrary
;
495 else if ( aInProps
[ nIndex
].Name
.compareToAscii( PROP_MACRO_NAME
) == 0 )
497 aInProps
[ nIndex
].Value
>>= aMacroName
;
502 if ( aType
.compareToAscii( STAR_BASIC
) == 0 )
504 aOutProps
.realloc(4);
505 if ( aScript
.getLength() )
507 if( ! aMacroName
.getLength() || ! aLibrary
.getLength() )
509 sal_Int32 nHashPos
= aScript
.indexOf( '/', 8 );
510 sal_Int32 nArgsPos
= aScript
.indexOf( '(' );
511 if ( ( nHashPos
!= STRING_NOTFOUND
) && ( nHashPos
< nArgsPos
) )
513 OUSTRING
aBasMgrName( INetURLObject::decode( aScript
.copy( 8, nHashPos
-8 ), INET_HEX_ESCAPE
, INetURLObject::DECODE_WITH_CHARSET
) );
514 if ( aBasMgrName
.compareToAscii(".") == 0 )
515 aLibrary
= pDoc
->GetTitle();
517 else if ( aBasMgrName.getLength() )
518 aLibrary = aBasMgrName;
521 aLibrary
= SFX_APP()->GetName();
523 // Get the macro name
524 aMacroName
= aScript
.copy( nHashPos
+1, nArgsPos
- nHashPos
- 1 );
528 DBG_ERRORFILE( "ConvertToMacro: Unknown macro url format" );
532 else if ( aMacroName
.getLength() )
534 aScript
= OUSTRING( RTL_CONSTASCII_USTRINGPARAM( MACRO_PRFIX
) );
535 if ( aLibrary
.compareTo( SFX_APP()->GetName() ) != 0 && aLibrary
.compareToAscii("StarDesktop") != 0 && aLibrary
.compareToAscii("application") != 0 )
536 aScript
+= String('.');
538 aScript
+= String('/');
539 aScript
+= aMacroName
;
540 aScript
+= OUSTRING( RTL_CONSTASCII_USTRINGPARAM( MACRO_POSTFIX
) );
546 if ( aLibrary
.compareToAscii("document") != 0 )
548 if ( !aLibrary
.getLength() || (pDoc
&& ( String(aLibrary
) == pDoc
->GetTitle( SFX_TITLE_APINAME
) || String(aLibrary
) == pDoc
->GetTitle() )) )
549 aLibrary
= String::CreateFromAscii("document");
551 aLibrary
= String::CreateFromAscii("application");
554 aOutProps
[1].Name
= OUSTRING::createFromAscii( PROP_SCRIPT
);
555 aOutProps
[1].Value
<<= aScript
;
556 aOutProps
[2].Name
= OUSTRING::createFromAscii( PROP_LIBRARY
);
557 aOutProps
[2].Value
<<= aLibrary
;
558 aOutProps
[3].Name
= OUSTRING::createFromAscii( PROP_MACRO_NAME
);
559 aOutProps
[3].Value
<<= aMacroName
;
562 else if ( aType
.compareToAscii( SVX_MACRO_LANGUAGE_JAVASCRIPT
) == 0 )
564 aOutProps
[1] = aInProps
[1];
573 ModelCollectionEnumeration::ModelCollectionEnumeration(const css::uno::Reference
< css::lang::XMultiServiceFactory
>& xSMGR
)
574 : ModelCollectionMutexBase( )
576 , m_pEnumerationIt (m_lModels
.begin())
580 ModelCollectionEnumeration::~ModelCollectionEnumeration()
584 void ModelCollectionEnumeration::setModelList(const TModelList
& rList
)
587 ::osl::ResettableMutexGuard
aLock(m_aLock
);
589 m_pEnumerationIt
= m_lModels
.begin();
594 sal_Bool SAL_CALL
ModelCollectionEnumeration::hasMoreElements()
595 throw(css::uno::RuntimeException
)
598 ::osl::ResettableMutexGuard
aLock(m_aLock
);
599 return (m_pEnumerationIt
!= m_lModels
.end());
603 css::uno::Any SAL_CALL
ModelCollectionEnumeration::nextElement()
604 throw(css::container::NoSuchElementException
,
605 css::lang::WrappedTargetException
,
606 css::uno::RuntimeException
)
609 ::osl::ResettableMutexGuard
aLock(m_aLock
);
610 if (m_pEnumerationIt
== m_lModels
.end())
611 throw css::container::NoSuchElementException(
612 ::rtl::OUString::createFromAscii("End of model enumeration reached."),
613 static_cast< css::container::XEnumeration
* >(this));
614 css::uno::Reference
< css::frame::XModel
> xModel(*m_pEnumerationIt
, UNO_QUERY
);
619 return css::uno::makeAny(xModel
);
622 SFX_IMPL_XSERVICEINFO( SfxGlobalEvents_Impl
, "com.sun.star.frame.GlobalEventBroadcaster", "com.sun.star.comp.sfx2.GlobalEventBroadcaster" )
623 SFX_IMPL_ONEINSTANCEFACTORY( SfxGlobalEvents_Impl
);
625 //-----------------------------------------------------------------------------
626 SfxGlobalEvents_Impl::SfxGlobalEvents_Impl( const com::sun::star::uno::Reference
< ::com::sun::star::lang::XMultiServiceFactory
>& xSMGR
)
627 : ModelCollectionMutexBase( )
629 , m_aLegacyListeners (m_aLock
)
630 , m_aDocumentListeners (m_aLock
)
635 pImp
= new GlobalEventConfig();
637 m_xJobExecutorListener
= css::uno::Reference
< css::document::XEventListener
>(
638 xSMGR
->createInstance(::rtl::OUString::createFromAscii("com.sun.star.task.JobExecutor")),
643 //-----------------------------------------------------------------------------
644 SfxGlobalEvents_Impl::~SfxGlobalEvents_Impl()
648 //-----------------------------------------------------------------------------
649 void SfxGlobalEvents_Impl::Notify( SfxBroadcaster
& /*aBC*/, const SfxHint
& aHint
)
651 SfxEventHint
* pNamedHint
= PTR_CAST(SfxEventHint
, &aHint
);
655 css::uno::Reference
< css::document::XEventsSupplier
> xSup
;
657 ::rtl::OUString sName
= SfxEventConfiguration::GetEventName_Impl(pNamedHint
->GetEventId());
658 SfxObjectShell
* pShell
= pNamedHint
->GetObjShell();
660 xSup
= css::uno::Reference
< css::document::XEventsSupplier
>(pShell
->GetModel(), UNO_QUERY
);
662 css::document::EventObject
aEvent(xSup
, sName
);
666 //-----------------------------------------------------------------------------
667 css::uno::Reference
< css::container::XNameReplace
> SAL_CALL
SfxGlobalEvents_Impl::getEvents()
668 throw(css::uno::RuntimeException
)
671 ::osl::ResettableMutexGuard
aLock(m_aLock
);
676 //-----------------------------------------------------------------------------
677 void SAL_CALL
SfxGlobalEvents_Impl::addEventListener(const css::uno::Reference
< css::document::XEventListener
>& xListener
)
678 throw(css::uno::RuntimeException
)
680 // container is threadsafe
681 m_aLegacyListeners
.addInterface(xListener
);
684 //-----------------------------------------------------------------------------
685 void SAL_CALL
SfxGlobalEvents_Impl::removeEventListener(const css::uno::Reference
< css::document::XEventListener
>& xListener
)
686 throw(css::uno::RuntimeException
)
688 // container is threadsafe
689 m_aLegacyListeners
.removeInterface(xListener
);
692 //-----------------------------------------------------------------------------
693 void SAL_CALL
SfxGlobalEvents_Impl::addDocumentEventListener( const css::uno::Reference
< css::document::XDocumentEventListener
>& _Listener
)
694 throw(css::uno::RuntimeException
)
696 m_aDocumentListeners
.addInterface( _Listener
);
699 //-----------------------------------------------------------------------------
700 void SAL_CALL
SfxGlobalEvents_Impl::removeDocumentEventListener( const css::uno::Reference
< css::document::XDocumentEventListener
>& _Listener
)
701 throw(css::uno::RuntimeException
)
703 m_aDocumentListeners
.removeInterface( _Listener
);
706 //-----------------------------------------------------------------------------
707 void SAL_CALL
SfxGlobalEvents_Impl::notifyDocumentEvent( const ::rtl::OUString
& /*_EventName*/,
708 const css::uno::Reference
< css::frame::XController2
>& /*_ViewController*/, const css::uno::Any
& /*_Supplement*/ )
709 throw (css::lang::IllegalArgumentException
, css::lang::NoSupportException
, css::uno::RuntimeException
)
711 // we're a multiplexer only, no change to generate artifical events here
712 throw css::lang::NoSupportException(::rtl::OUString(), *this);
715 //-----------------------------------------------------------------------------
716 void SAL_CALL
SfxGlobalEvents_Impl::notifyEvent(const css::document::EventObject
& aEvent
)
717 throw(css::uno::RuntimeException
)
719 css::document::DocumentEvent
aDocEvent(aEvent
.Source
, aEvent
.EventName
, NULL
, css::uno::Any());
720 implts_notifyJobExecution(aEvent
);
721 implts_checkAndExecuteEventBindings(aDocEvent
);
722 implts_notifyListener(aDocEvent
);
725 //-----------------------------------------------------------------------------
726 void SAL_CALL
SfxGlobalEvents_Impl::documentEventOccured( const ::css::document::DocumentEvent
& _Event
)
727 throw (::css::uno::RuntimeException
)
729 implts_notifyJobExecution(css::document::EventObject(_Event
.Source
, _Event
.EventName
));
730 implts_checkAndExecuteEventBindings(_Event
);
731 implts_notifyListener(_Event
);
734 //-----------------------------------------------------------------------------
735 void SAL_CALL
SfxGlobalEvents_Impl::disposing(const css::lang::EventObject
& aEvent
)
736 throw(css::uno::RuntimeException
)
738 css::uno::Reference
< css::frame::XModel
> xDoc(aEvent
.Source
, UNO_QUERY
);
741 ::osl::ResettableMutexGuard
aLock(m_aLock
);
742 TModelList::iterator pIt
= impl_searchDoc(xDoc
);
743 if (pIt
!= m_lModels
.end())
744 m_lModels
.erase(pIt
);
749 //-----------------------------------------------------------------------------
750 sal_Bool SAL_CALL
SfxGlobalEvents_Impl::has(const css::uno::Any
& aElement
)
751 throw (css::uno::RuntimeException
)
753 css::uno::Reference
< css::frame::XModel
> xDoc
;
756 sal_Bool bHas
= sal_False
;
759 ::osl::ResettableMutexGuard
aLock(m_aLock
);
760 TModelList::iterator pIt
= impl_searchDoc(xDoc
);
761 if (pIt
!= m_lModels
.end())
769 //-----------------------------------------------------------------------------
770 void SAL_CALL
SfxGlobalEvents_Impl::insert( const css::uno::Any
& aElement
)
771 throw (css::lang::IllegalArgumentException
,
772 css::container::ElementExistException
,
773 css::uno::RuntimeException
)
775 css::uno::Reference
< css::frame::XModel
> xDoc
;
778 throw css::lang::IllegalArgumentException(
779 ::rtl::OUString::createFromAscii("Cant locate at least the model parameter."),
780 static_cast< css::container::XSet
* >(this),
784 ::osl::ResettableMutexGuard
aLock(m_aLock
);
785 TModelList::iterator pIt
= impl_searchDoc(xDoc
);
786 if (pIt
!= m_lModels
.end())
787 throw css::container::ElementExistException(
789 static_cast< css::container::XSet
* >(this));
790 m_lModels
.push_back(xDoc
);
794 css::uno::Reference
< css::document::XDocumentEventBroadcaster
> xDocBroadcaster(xDoc
, UNO_QUERY
);
795 if (xDocBroadcaster
.is())
796 xDocBroadcaster
->addDocumentEventListener(this);
799 // try the "legacy version" of XDocumentEventBroadcaster, which is XEventBroadcaster
800 css::uno::Reference
< css::document::XEventBroadcaster
> xBroadcaster(xDoc
, UNO_QUERY
);
801 if (xBroadcaster
.is())
802 xBroadcaster
->addEventListener(static_cast< css::document::XEventListener
* >(this));
806 //-----------------------------------------------------------------------------
807 void SAL_CALL
SfxGlobalEvents_Impl::remove( const css::uno::Any
& aElement
)
808 throw (css::lang::IllegalArgumentException
,
809 css::container::NoSuchElementException
,
810 css::uno::RuntimeException
)
812 css::uno::Reference
< css::frame::XModel
> xDoc
;
815 throw css::lang::IllegalArgumentException(
816 ::rtl::OUString::createFromAscii("Cant locate at least the model parameter."),
817 static_cast< css::container::XSet
* >(this),
821 ::osl::ResettableMutexGuard
aLock(m_aLock
);
822 TModelList::iterator pIt
= impl_searchDoc(xDoc
);
823 if (pIt
== m_lModels
.end())
824 throw css::container::NoSuchElementException(
826 static_cast< css::container::XSet
* >(this));
827 m_lModels
.erase(pIt
);
831 css::uno::Reference
< css::document::XDocumentEventBroadcaster
> xDocBroadcaster(xDoc
, UNO_QUERY
);
832 if (xDocBroadcaster
.is())
833 xDocBroadcaster
->removeDocumentEventListener(this);
836 // try the "legacy version" of XDocumentEventBroadcaster, which is XEventBroadcaster
837 css::uno::Reference
< css::document::XEventBroadcaster
> xBroadcaster(xDoc
, UNO_QUERY
);
838 if (xBroadcaster
.is())
839 xBroadcaster
->removeEventListener(static_cast< css::document::XEventListener
* >(this));
843 //-----------------------------------------------------------------------------
844 css::uno::Reference
< css::container::XEnumeration
> SAL_CALL
SfxGlobalEvents_Impl::createEnumeration()
845 throw (css::uno::RuntimeException
)
848 ::osl::ResettableMutexGuard
aLock(m_aLock
);
849 ModelCollectionEnumeration
* pEnum
= new ModelCollectionEnumeration(m_xSMGR
);
850 pEnum
->setModelList(m_lModels
);
851 css::uno::Reference
< css::container::XEnumeration
> xEnum(
852 static_cast< css::container::XEnumeration
* >(pEnum
),
860 //-----------------------------------------------------------------------------
861 css::uno::Type SAL_CALL
SfxGlobalEvents_Impl::getElementType()
862 throw (css::uno::RuntimeException
)
864 return ::getCppuType(static_cast< css::uno::Reference
< css::frame::XModel
>* >(NULL
));
867 //-----------------------------------------------------------------------------
868 sal_Bool SAL_CALL
SfxGlobalEvents_Impl::hasElements()
869 throw (css::uno::RuntimeException
)
872 ::osl::ResettableMutexGuard
aLock(m_aLock
);
873 return (m_lModels
.size()>0);
877 //-----------------------------------------------------------------------------
878 void SfxGlobalEvents_Impl::implts_notifyJobExecution(const css::document::EventObject
& aEvent
)
883 ::osl::ResettableMutexGuard
aLock(m_aLock
);
884 css::uno::Reference
< css::document::XEventListener
> xJobExecutor(m_xJobExecutorListener
);
887 if (xJobExecutor
.is())
888 xJobExecutor
->notifyEvent(aEvent
);
890 catch(const css::uno::RuntimeException
& exRun
)
892 catch(const css::uno::Exception
&)
896 //-----------------------------------------------------------------------------
897 void SfxGlobalEvents_Impl::implts_checkAndExecuteEventBindings(const css::document::DocumentEvent
& aEvent
)
902 ::osl::ResettableMutexGuard
aLock(m_aLock
);
903 css::uno::Reference
< css::container::XNameReplace
> xEvents
= m_xEvents
;
909 aAny
= xEvents
->getByName(aEvent
.EventName
);
910 Execute(aAny
, aEvent
, 0);
912 catch(const css::uno::RuntimeException
& exRun
)
914 catch(const css::uno::Exception
&)
918 //-----------------------------------------------------------------------------
919 void SfxGlobalEvents_Impl::implts_notifyListener(const css::document::DocumentEvent
& aEvent
)
921 // containers are threadsafe
922 css::document::EventObject
aLegacyEvent(aEvent
.Source
, aEvent
.EventName
);
923 m_aLegacyListeners
.notifyEach( &css::document::XEventListener::notifyEvent
, aLegacyEvent
);
925 m_aDocumentListeners
.notifyEach( &css::document::XDocumentEventListener::documentEventOccured
, aEvent
);
928 //-----------------------------------------------------------------------------
929 // not threadsafe ... must be locked from outside!
930 TModelList::iterator
SfxGlobalEvents_Impl::impl_searchDoc(const css::uno::Reference
< css::frame::XModel
>& xModel
)
933 return m_lModels
.end();
935 TModelList::iterator pIt
;
936 for ( pIt
= m_lModels
.begin();
937 pIt
!= m_lModels
.end() ;
940 css::uno::Reference
< css::frame::XModel
> xContainerDoc(*pIt
, UNO_QUERY
);
941 if (xContainerDoc
== xModel
)