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: propertysethelper.cxx,v $
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_framework.hxx"
34 //_________________________________________________________________________________________________________________
37 #include <classes/propertysethelper.hxx>
38 #include <threadhelp/transactionguard.hxx>
39 #include <threadhelp/readguard.hxx>
40 #include <threadhelp/writeguard.hxx>
42 //_________________________________________________________________________________________________________________
45 //_________________________________________________________________________________________________________________
48 //_________________________________________________________________________________________________________________
53 //_________________________________________________________________________________________________________________
54 // non exported definitions
56 //-----------------------------------------------------------------------------
57 PropertySetHelper::PropertySetHelper(const css::uno::Reference
< css::lang::XMultiServiceFactory
>& xSMGR
,
58 LockHelper
* pExternalLock
,
59 TransactionManager
* pExternalTransactionManager
,
60 sal_Bool bReleaseLockOnCall
)
62 , m_lSimpleChangeListener(pExternalLock
->getShareableOslMutex())
63 , m_lVetoChangeListener (pExternalLock
->getShareableOslMutex())
64 , m_bReleaseLockOnCall (bReleaseLockOnCall
)
65 , m_rLock (*pExternalLock
)
66 , m_rTransactionManager (*pExternalTransactionManager
)
70 //-----------------------------------------------------------------------------
71 PropertySetHelper::~PropertySetHelper()
75 //-----------------------------------------------------------------------------
76 void PropertySetHelper::impl_setPropertyChangeBroadcaster(const css::uno::Reference
< css::uno::XInterface
>& xBroadcaster
)
78 TransactionGuard
aTransaction(m_rTransactionManager
, E_SOFTEXCEPTIONS
);
81 WriteGuard
aWriteLock(m_rLock
);
82 m_xBroadcaster
= xBroadcaster
;
87 //-----------------------------------------------------------------------------
88 void SAL_CALL
PropertySetHelper::impl_addPropertyInfo(const css::beans::Property
& aProperty
)
89 throw(css::beans::PropertyExistException
,
92 TransactionGuard
aTransaction(m_rTransactionManager
, E_SOFTEXCEPTIONS
);
95 WriteGuard
aWriteLock(m_rLock
);
97 PropertySetHelper::TPropInfoHash::const_iterator pIt
= m_lProps
.find(aProperty
.Name
);
98 if (pIt
!= m_lProps
.end())
99 throw css::beans::PropertyExistException();
101 m_lProps
[aProperty
.Name
] = aProperty
;
105 //-----------------------------------------------------------------------------
106 void SAL_CALL
PropertySetHelper::impl_removePropertyInfo(const ::rtl::OUString
& sProperty
)
107 throw(css::beans::UnknownPropertyException
,
108 css::uno::Exception
)
110 TransactionGuard
aTransaction(m_rTransactionManager
, E_SOFTEXCEPTIONS
);
113 WriteGuard
aWriteLock(m_rLock
);
115 PropertySetHelper::TPropInfoHash::iterator pIt
= m_lProps
.find(sProperty
);
116 if (pIt
== m_lProps
.end())
117 throw css::beans::UnknownPropertyException();
123 //-----------------------------------------------------------------------------
124 void SAL_CALL
PropertySetHelper::impl_enablePropertySet()
128 //-----------------------------------------------------------------------------
129 void SAL_CALL
PropertySetHelper::impl_disablePropertySet()
131 TransactionGuard
aTransaction(m_rTransactionManager
, E_SOFTEXCEPTIONS
);
134 WriteGuard
aWriteLock(m_rLock
);
136 css::uno::Reference
< css::uno::XInterface
> xThis(static_cast< css::beans::XPropertySet
* >(this), css::uno::UNO_QUERY
);
137 css::lang::EventObject
aEvent(xThis
);
139 m_lSimpleChangeListener
.disposeAndClear(aEvent
);
140 m_lVetoChangeListener
.disposeAndClear(aEvent
);
147 //-----------------------------------------------------------------------------
148 sal_Bool
PropertySetHelper::impl_existsVeto(const css::beans::PropertyChangeEvent
& aEvent
)
150 /* Dont use the lock here!
151 The used helper is threadsafe and it lives for the whole lifetime of
154 ::cppu::OInterfaceContainerHelper
* pVetoListener
= m_lVetoChangeListener
.getContainer(aEvent
.PropertyName
);
158 ::cppu::OInterfaceIteratorHelper
pListener(*pVetoListener
);
159 while (pListener
.hasMoreElements())
163 css::uno::Reference
< css::beans::XVetoableChangeListener
> xListener(
164 ((css::beans::XVetoableChangeListener
*)pListener
.next()),
165 css::uno::UNO_QUERY_THROW
);
166 xListener
->vetoableChange(aEvent
);
168 catch(const css::uno::RuntimeException
&)
169 { pListener
.remove(); }
170 catch(const css::beans::PropertyVetoException
&)
177 //-----------------------------------------------------------------------------
178 void PropertySetHelper::impl_notifyChangeListener(const css::beans::PropertyChangeEvent
& aEvent
)
180 /* Dont use the lock here!
181 The used helper is threadsafe and it lives for the whole lifetime of
184 ::cppu::OInterfaceContainerHelper
* pSimpleListener
= m_lSimpleChangeListener
.getContainer(aEvent
.PropertyName
);
185 if (! pSimpleListener
)
188 ::cppu::OInterfaceIteratorHelper
pListener(*pSimpleListener
);
189 while (pListener
.hasMoreElements())
193 css::uno::Reference
< css::beans::XPropertyChangeListener
> xListener(
194 ((css::beans::XVetoableChangeListener
*)pListener
.next()),
195 css::uno::UNO_QUERY_THROW
);
196 xListener
->propertyChange(aEvent
);
198 catch(const css::uno::RuntimeException
&)
199 { pListener
.remove(); }
203 //-----------------------------------------------------------------------------
204 css::uno::Reference
< css::beans::XPropertySetInfo
> SAL_CALL
PropertySetHelper::getPropertySetInfo()
205 throw(css::uno::RuntimeException
)
207 TransactionGuard
aTransaction(m_rTransactionManager
, E_HARDEXCEPTIONS
);
209 css::uno::Reference
< css::beans::XPropertySetInfo
> xInfo(static_cast< css::beans::XPropertySetInfo
* >(this), css::uno::UNO_QUERY_THROW
);
213 //-----------------------------------------------------------------------------
214 void SAL_CALL
PropertySetHelper::setPropertyValue(const ::rtl::OUString
& sProperty
,
215 const css::uno::Any
& aValue
)
216 throw(css::beans::UnknownPropertyException
,
217 css::beans::PropertyVetoException
,
218 css::lang::IllegalArgumentException
,
219 css::lang::WrappedTargetException
,
220 css::uno::RuntimeException
)
222 // TODO look for e.g. readonly props and reject setProp() call!
224 TransactionGuard
aTransaction(m_rTransactionManager
, E_HARDEXCEPTIONS
);
227 WriteGuard
aWriteLock(m_rLock
);
229 PropertySetHelper::TPropInfoHash::const_iterator pIt
= m_lProps
.find(sProperty
);
230 if (pIt
== m_lProps
.end())
231 throw css::beans::UnknownPropertyException();
233 css::beans::Property aPropInfo
= pIt
->second
;
235 sal_Bool bLocked
= sal_True
;
236 if (m_bReleaseLockOnCall
)
243 css::uno::Any aCurrentValue
= impl_getPropertyValue(aPropInfo
.Name
, aPropInfo
.Handle
);
252 sal_Bool bWillBeChanged
= (aCurrentValue
!= aValue
);
253 if (! bWillBeChanged
)
256 css::beans::PropertyChangeEvent aEvent
;
257 aEvent
.PropertyName
= aPropInfo
.Name
;
258 aEvent
.Further
= sal_False
;
259 aEvent
.PropertyHandle
= aPropInfo
.Handle
;
260 aEvent
.OldValue
= aCurrentValue
;
261 aEvent
.NewValue
= aValue
;
262 aEvent
.Source
= css::uno::Reference
< css::uno::XInterface
>(m_xBroadcaster
.get(), css::uno::UNO_QUERY
);
264 if (m_bReleaseLockOnCall
)
271 if (impl_existsVeto(aEvent
))
272 throw css::beans::PropertyVetoException();
274 impl_setPropertyValue(aPropInfo
.Name
, aPropInfo
.Handle
, aValue
);
276 impl_notifyChangeListener(aEvent
);
279 //-----------------------------------------------------------------------------
280 css::uno::Any SAL_CALL
PropertySetHelper::getPropertyValue(const ::rtl::OUString
& sProperty
)
281 throw(css::beans::UnknownPropertyException
,
282 css::lang::WrappedTargetException
,
283 css::uno::RuntimeException
)
285 TransactionGuard
aTransaction(m_rTransactionManager
, E_HARDEXCEPTIONS
);
288 ReadGuard
aReadLock(m_rLock
);
290 PropertySetHelper::TPropInfoHash::const_iterator pIt
= m_lProps
.find(sProperty
);
291 if (pIt
== m_lProps
.end())
292 throw css::beans::UnknownPropertyException();
294 css::beans::Property aPropInfo
= pIt
->second
;
296 sal_Bool bLocked
= sal_True
;
297 if (m_bReleaseLockOnCall
)
304 return impl_getPropertyValue(aPropInfo
.Name
, aPropInfo
.Handle
);
307 //-----------------------------------------------------------------------------
308 void SAL_CALL
PropertySetHelper::addPropertyChangeListener(const ::rtl::OUString
& sProperty
,
309 const css::uno::Reference
< css::beans::XPropertyChangeListener
>& xListener
)
310 throw(css::beans::UnknownPropertyException
,
311 css::lang::WrappedTargetException
,
312 css::uno::RuntimeException
)
314 TransactionGuard
aTransaction(m_rTransactionManager
, E_HARDEXCEPTIONS
);
317 ReadGuard
aReadLock(m_rLock
);
319 PropertySetHelper::TPropInfoHash::const_iterator pIt
= m_lProps
.find(sProperty
);
320 if (pIt
== m_lProps
.end())
321 throw css::beans::UnknownPropertyException();
326 m_lSimpleChangeListener
.addInterface(sProperty
, xListener
);
329 //-----------------------------------------------------------------------------
330 void SAL_CALL
PropertySetHelper::removePropertyChangeListener(const ::rtl::OUString
& sProperty
,
331 const css::uno::Reference
< css::beans::XPropertyChangeListener
>& xListener
)
332 throw(css::beans::UnknownPropertyException
,
333 css::lang::WrappedTargetException
,
334 css::uno::RuntimeException
)
336 TransactionGuard
aTransaction(m_rTransactionManager
, E_SOFTEXCEPTIONS
);
339 ReadGuard
aReadLock(m_rLock
);
341 PropertySetHelper::TPropInfoHash::const_iterator pIt
= m_lProps
.find(sProperty
);
342 if (pIt
== m_lProps
.end())
343 throw css::beans::UnknownPropertyException();
348 m_lSimpleChangeListener
.removeInterface(sProperty
, xListener
);
351 //-----------------------------------------------------------------------------
352 void SAL_CALL
PropertySetHelper::addVetoableChangeListener(const ::rtl::OUString
& sProperty
,
353 const css::uno::Reference
< css::beans::XVetoableChangeListener
>& xListener
)
354 throw(css::beans::UnknownPropertyException
,
355 css::lang::WrappedTargetException
,
356 css::uno::RuntimeException
)
358 TransactionGuard
aTransaction(m_rTransactionManager
, E_HARDEXCEPTIONS
);
361 ReadGuard
aReadLock(m_rLock
);
363 PropertySetHelper::TPropInfoHash::const_iterator pIt
= m_lProps
.find(sProperty
);
364 if (pIt
== m_lProps
.end())
365 throw css::beans::UnknownPropertyException();
370 m_lVetoChangeListener
.addInterface(sProperty
, xListener
);
373 //-----------------------------------------------------------------------------
374 void SAL_CALL
PropertySetHelper::removeVetoableChangeListener(const ::rtl::OUString
& sProperty
,
375 const css::uno::Reference
< css::beans::XVetoableChangeListener
>& xListener
)
376 throw(css::beans::UnknownPropertyException
,
377 css::lang::WrappedTargetException
,
378 css::uno::RuntimeException
)
380 TransactionGuard
aTransaction(m_rTransactionManager
, E_SOFTEXCEPTIONS
);
383 ReadGuard
aReadLock(m_rLock
);
385 PropertySetHelper::TPropInfoHash::const_iterator pIt
= m_lProps
.find(sProperty
);
386 if (pIt
== m_lProps
.end())
387 throw css::beans::UnknownPropertyException();
392 m_lVetoChangeListener
.removeInterface(sProperty
, xListener
);
395 //-----------------------------------------------------------------------------
396 css::uno::Sequence
< css::beans::Property
> SAL_CALL
PropertySetHelper::getProperties()
397 throw(css::uno::RuntimeException
)
399 TransactionGuard
aTransaction(m_rTransactionManager
, E_HARDEXCEPTIONS
);
402 ReadGuard
aReadLock(m_rLock
);
404 sal_Int32 c
= (sal_Int32
)m_lProps
.size();
405 css::uno::Sequence
< css::beans::Property
> lProps(c
);
406 PropertySetHelper::TPropInfoHash::const_iterator pIt
;
408 for ( pIt
= m_lProps
.begin();
409 pIt
!= m_lProps
.end() ;
412 lProps
[--c
] = pIt
->second
;
419 //-----------------------------------------------------------------------------
420 css::beans::Property SAL_CALL
PropertySetHelper::getPropertyByName(const ::rtl::OUString
& sName
)
421 throw(css::beans::UnknownPropertyException
,
422 css::uno::RuntimeException
)
424 TransactionGuard
aTransaction(m_rTransactionManager
, E_HARDEXCEPTIONS
);
427 ReadGuard
aReadLock(m_rLock
);
429 PropertySetHelper::TPropInfoHash::const_iterator pIt
= m_lProps
.find(sName
);
430 if (pIt
== m_lProps
.end())
431 throw css::beans::UnknownPropertyException();
437 //-----------------------------------------------------------------------------
438 sal_Bool SAL_CALL
PropertySetHelper::hasPropertyByName(const ::rtl::OUString
& sName
)
439 throw(css::uno::RuntimeException
)
441 TransactionGuard
aTransaction(m_rTransactionManager
, E_HARDEXCEPTIONS
);
444 ReadGuard
aReadLock(m_rLock
);
446 PropertySetHelper::TPropInfoHash::iterator pIt
= m_lProps
.find(sName
);
447 sal_Bool bExist
= (pIt
!= m_lProps
.end());
453 } // namespace framework