UDK 3.2.7 C/C++ API Reference
|
00001 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ 00002 /************************************************************************* 00003 * 00004 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 00005 * 00006 * Copyright 2000, 2010 Oracle and/or its affiliates. 00007 * 00008 * OpenOffice.org - a multi-platform office productivity suite 00009 * 00010 * This file is part of OpenOffice.org. 00011 * 00012 * OpenOffice.org is free software: you can redistribute it and/or modify 00013 * it under the terms of the GNU Lesser General Public License version 3 00014 * only, as published by the Free Software Foundation. 00015 * 00016 * OpenOffice.org is distributed in the hope that it will be useful, 00017 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00018 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00019 * GNU Lesser General Public License version 3 for more details 00020 * (a copy is included in the LICENSE file that accompanied this code). 00021 * 00022 * You should have received a copy of the GNU Lesser General Public License 00023 * version 3 along with OpenOffice.org. If not, see 00024 * <http://www.openoffice.org/license.html> 00025 * for a copy of the LGPLv3 License. 00026 * 00027 ************************************************************************/ 00028 #ifndef _CPPUHELPER_INTERFACECONTAINER_H_ 00029 #define _CPPUHELPER_INTERFACECONTAINER_H_ 00030 00031 #include <vector> 00032 #include <osl/mutex.hxx> 00033 #include <rtl/alloc.h> 00034 #include <com/sun/star/uno/Sequence.hxx> 00035 #include <com/sun/star/uno/XInterface.hpp> 00036 #ifndef _COM_SUN_STAR_LANG_EVENTOBJECT_HXX_ 00037 #include <com/sun/star/lang/EventObject.hpp> 00038 #endif 00039 00040 #ifndef _COM_SUN_STAR_LANG_DISPOSEDEXCEPTION_HXX_ 00041 #include "com/sun/star/lang/DisposedException.hpp" 00042 #endif 00043 #include "cppuhelperdllapi.h" 00044 //for docpp 00046 namespace cppu 00047 { 00048 00049 namespace detail { 00050 00051 union element_alias 00052 { 00053 ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > > *pAsSequence; 00054 ::com::sun::star::uno::XInterface * pAsInterface; 00055 element_alias() : pAsInterface(0) {} 00056 }; 00057 00058 } 00059 00060 //=================================================================== 00061 class OInterfaceContainerHelper; 00069 class CPPUHELPER_DLLPUBLIC OInterfaceIteratorHelper 00070 { 00071 public: 00085 OInterfaceIteratorHelper( OInterfaceContainerHelper & rCont ) SAL_THROW(()); 00086 00090 ~OInterfaceIteratorHelper() SAL_THROW(()); 00091 00093 sal_Bool SAL_CALL hasMoreElements() const SAL_THROW(()) 00094 { return nRemain != 0; } 00099 ::com::sun::star::uno::XInterface * SAL_CALL next() SAL_THROW(()); 00100 00106 void SAL_CALL remove() SAL_THROW(()); 00107 00108 private: 00109 OInterfaceContainerHelper & rCont; 00110 sal_Bool bIsList; 00111 00112 detail::element_alias aData; 00113 00114 sal_Int32 nRemain; 00115 00116 OInterfaceIteratorHelper( const OInterfaceIteratorHelper & ) SAL_THROW(()); 00117 OInterfaceIteratorHelper & operator = ( const OInterfaceIteratorHelper & ) SAL_THROW(()); 00118 }; 00119 00120 //=================================================================== 00127 class CPPUHELPER_DLLPUBLIC OInterfaceContainerHelper 00128 { 00129 public: 00130 // these are here to force memory de/allocation to sal lib. 00131 inline static void * SAL_CALL operator new( size_t nSize ) SAL_THROW(()) 00132 { return ::rtl_allocateMemory( nSize ); } 00133 inline static void SAL_CALL operator delete( void * pMem ) SAL_THROW(()) 00134 { ::rtl_freeMemory( pMem ); } 00135 inline static void * SAL_CALL operator new( size_t, void * pMem ) SAL_THROW(()) 00136 { return pMem; } 00137 inline static void SAL_CALL operator delete( void *, void * ) SAL_THROW(()) 00138 {} 00139 00147 OInterfaceContainerHelper( ::osl::Mutex & rMutex ) SAL_THROW(()); 00152 ~OInterfaceContainerHelper() SAL_THROW(()); 00157 sal_Int32 SAL_CALL getLength() const SAL_THROW(()); 00158 00162 ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > > SAL_CALL getElements() const SAL_THROW(()); 00163 00180 sal_Int32 SAL_CALL addInterface( const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > & rxIFace ) SAL_THROW(()); 00188 sal_Int32 SAL_CALL removeInterface( const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > & rxIFace ) SAL_THROW(()); 00193 void SAL_CALL disposeAndClear( const ::com::sun::star::lang::EventObject & rEvt ) SAL_THROW(()); 00197 void SAL_CALL clear() SAL_THROW(()); 00198 00210 template <typename ListenerT, typename FuncT> 00211 inline void forEach( FuncT const& func ); 00212 00234 template< typename ListenerT, typename EventT > 00235 inline void notifyEach( void ( SAL_CALL ListenerT::*NotificationMethod )( const EventT& ), const EventT& Event ); 00236 00237 private: 00238 friend class OInterfaceIteratorHelper; 00243 detail::element_alias aData; 00244 ::osl::Mutex & rMutex; 00246 sal_Bool bInUse; 00248 sal_Bool bIsList; 00249 00250 OInterfaceContainerHelper( const OInterfaceContainerHelper & ) SAL_THROW(()); 00251 OInterfaceContainerHelper & operator = ( const OInterfaceContainerHelper & ) SAL_THROW(()); 00252 00253 /* 00254 Dulicate content of the conaitner and release the old one without destroying. 00255 The mutex must be locked and the memberbInUse must be true. 00256 */ 00257 void copyAndResetInUse() SAL_THROW(()); 00258 00259 private: 00260 template< typename ListenerT, typename EventT > 00261 class NotifySingleListener 00262 { 00263 private: 00264 typedef void ( SAL_CALL ListenerT::*NotificationMethod )( const EventT& ); 00265 NotificationMethod m_pMethod; 00266 const EventT& m_rEvent; 00267 public: 00268 NotifySingleListener( NotificationMethod method, const EventT& event ) : m_pMethod( method ), m_rEvent( event ) { } 00269 00270 void operator()( const ::com::sun::star::uno::Reference<ListenerT>& listener ) const 00271 { 00272 (listener.get()->*m_pMethod)( m_rEvent ); 00273 } 00274 }; 00275 }; 00276 00277 template <typename ListenerT, typename FuncT> 00278 inline void OInterfaceContainerHelper::forEach( FuncT const& func ) 00279 { 00280 OInterfaceIteratorHelper iter( *this ); 00281 while (iter.hasMoreElements()) { 00282 ::com::sun::star::uno::Reference<ListenerT> const xListener( 00283 iter.next(), ::com::sun::star::uno::UNO_QUERY ); 00284 if (xListener.is()) { 00285 #if defined(EXCEPTIONS_OFF) 00286 func( xListener ); 00287 #else 00288 try { 00289 func( xListener ); 00290 } 00291 catch (::com::sun::star::lang::DisposedException const& exc) { 00292 if (exc.Context == xListener) 00293 iter.remove(); 00294 } 00295 #endif 00296 } 00297 } 00298 } 00299 00300 template< typename ListenerT, typename EventT > 00301 inline void OInterfaceContainerHelper::notifyEach( void ( SAL_CALL ListenerT::*NotificationMethod )( const EventT& ), const EventT& Event ) 00302 { 00303 forEach< ListenerT, NotifySingleListener< ListenerT, EventT > >( NotifySingleListener< ListenerT, EventT >( NotificationMethod, Event ) ); 00304 } 00305 00306 //=================================================================== 00313 template< class key , class hashImpl , class equalImpl > 00314 class OMultiTypeInterfaceContainerHelperVar 00315 { 00316 public: 00317 // these are here to force memory de/allocation to sal lib. 00318 inline static void * SAL_CALL operator new( size_t nSize ) SAL_THROW(()) 00319 { return ::rtl_allocateMemory( nSize ); } 00320 inline static void SAL_CALL operator delete( void * pMem ) SAL_THROW(()) 00321 { ::rtl_freeMemory( pMem ); } 00322 inline static void * SAL_CALL operator new( size_t, void * pMem ) SAL_THROW(()) 00323 { return pMem; } 00324 inline static void SAL_CALL operator delete( void *, void * ) SAL_THROW(()) 00325 {} 00326 00334 inline OMultiTypeInterfaceContainerHelperVar( ::osl::Mutex & rMutex ) SAL_THROW(()); 00338 inline ~OMultiTypeInterfaceContainerHelperVar() SAL_THROW(()); 00339 00343 inline ::com::sun::star::uno::Sequence< key > SAL_CALL getContainedTypes() const SAL_THROW(()); 00344 00351 inline OInterfaceContainerHelper * SAL_CALL getContainer( const key & ) const SAL_THROW(()); 00352 00371 inline sal_Int32 SAL_CALL addInterface( 00372 const key & rKey, 00373 const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > & r ) 00374 SAL_THROW(()); 00375 00386 inline sal_Int32 SAL_CALL removeInterface( 00387 const key & rKey, 00388 const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > & rxIFace ) 00389 SAL_THROW(()); 00390 00396 inline void SAL_CALL disposeAndClear( const ::com::sun::star::lang::EventObject & rEvt ) SAL_THROW(()); 00400 inline void SAL_CALL clear() SAL_THROW(()); 00401 00402 typedef key keyType; 00403 private: 00404 typedef ::std::vector< std::pair < key , void* > > InterfaceMap; 00405 InterfaceMap *m_pMap; 00406 ::osl::Mutex & rMutex; 00407 00408 inline typename InterfaceMap::iterator find(const key &rKey) const 00409 { 00410 typename InterfaceMap::iterator iter = m_pMap->begin(); 00411 typename InterfaceMap::iterator end = m_pMap->end(); 00412 00413 while( iter != end ) 00414 { 00415 equalImpl equal; 00416 if( equal( iter->first, rKey ) ) 00417 break; 00418 iter++; 00419 } 00420 return iter; 00421 } 00422 00423 inline OMultiTypeInterfaceContainerHelperVar( const OMultiTypeInterfaceContainerHelperVar & ) SAL_THROW(()); 00424 inline OMultiTypeInterfaceContainerHelperVar & operator = ( const OMultiTypeInterfaceContainerHelperVar & ) SAL_THROW(()); 00425 }; 00426 00427 00428 00429 00439 template < class container , class keyType > 00440 struct OBroadcastHelperVar 00441 { 00443 ::osl::Mutex & rMutex; 00445 container aLC; 00447 sal_Bool bDisposed; 00449 sal_Bool bInDispose; 00450 00455 OBroadcastHelperVar( ::osl::Mutex & rMutex_ ) SAL_THROW(()) 00456 : rMutex( rMutex_ ) 00457 , aLC( rMutex_ ) 00458 , bDisposed( sal_False ) 00459 , bInDispose( sal_False ) 00460 {} 00461 00465 inline void addListener( 00466 const keyType &key, 00467 const ::com::sun::star::uno::Reference < ::com::sun::star::uno::XInterface > &r ) 00468 SAL_THROW(()) 00469 { 00470 ::osl::MutexGuard guard( rMutex ); 00471 OSL_ENSURE( !bInDispose, "do not add listeners in the dispose call" ); 00472 OSL_ENSURE( !bDisposed, "object is disposed" ); 00473 if( ! bInDispose && ! bDisposed ) 00474 aLC.addInterface( key , r ); 00475 } 00476 00480 inline void removeListener( 00481 const keyType &key, 00482 const ::com::sun::star::uno::Reference < ::com::sun::star::uno::XInterface > & r ) 00483 SAL_THROW(()) 00484 { 00485 ::osl::MutexGuard guard( rMutex ); 00486 OSL_ENSURE( !bDisposed, "object is disposed" ); 00487 if( ! bInDispose && ! bDisposed ) 00488 aLC.removeInterface( key , r ); 00489 } 00490 00497 inline OInterfaceContainerHelper * SAL_CALL getContainer( const keyType &key ) const SAL_THROW(()) 00498 { return aLC.getContainer( key ); } 00499 }; 00500 00501 /*------------------------------------------ 00502 * 00503 * In general, the above templates are used with a Type as key. 00504 * Therefore a default declaration is given ( OMultiTypeInterfaceContainerHelper and OBroadcastHelper ) 00505 * 00506 *------------------------------------------*/ 00507 00508 // helper function call class 00509 struct hashType_Impl 00510 { 00511 size_t operator()(const ::com::sun::star::uno::Type & s) const SAL_THROW(()) 00512 { return (size_t) s.getTypeName().hashCode(); } 00513 }; 00514 00515 00519 class CPPUHELPER_DLLPUBLIC OMultiTypeInterfaceContainerHelper 00520 { 00521 public: 00522 // these are here to force memory de/allocation to sal lib. 00523 inline static void * SAL_CALL operator new( size_t nSize ) SAL_THROW(()) 00524 { return ::rtl_allocateMemory( nSize ); } 00525 inline static void SAL_CALL operator delete( void * pMem ) SAL_THROW(()) 00526 { ::rtl_freeMemory( pMem ); } 00527 inline static void * SAL_CALL operator new( size_t, void * pMem ) SAL_THROW(()) 00528 { return pMem; } 00529 inline static void SAL_CALL operator delete( void *, void * ) SAL_THROW(()) 00530 {} 00531 00539 OMultiTypeInterfaceContainerHelper( ::osl::Mutex & rMutex ) SAL_THROW(()); 00543 ~OMultiTypeInterfaceContainerHelper() SAL_THROW(()); 00544 00548 ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Type > SAL_CALL getContainedTypes() const SAL_THROW(()); 00549 00555 OInterfaceContainerHelper * SAL_CALL getContainer( const ::com::sun::star::uno::Type & rKey ) const SAL_THROW(()); 00556 00575 sal_Int32 SAL_CALL addInterface( 00576 const ::com::sun::star::uno::Type & rKey, 00577 const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > & r ) 00578 SAL_THROW(()); 00579 00590 sal_Int32 SAL_CALL removeInterface( 00591 const ::com::sun::star::uno::Type & rKey, 00592 const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > & rxIFace ) 00593 SAL_THROW(()); 00594 00599 void SAL_CALL disposeAndClear( const ::com::sun::star::lang::EventObject & rEvt ) SAL_THROW(()); 00603 void SAL_CALL clear() SAL_THROW(()); 00604 00605 typedef ::com::sun::star::uno::Type keyType; 00606 private: 00607 void *m_pMap; 00608 ::osl::Mutex & rMutex; 00609 00610 inline OMultiTypeInterfaceContainerHelper( const OMultiTypeInterfaceContainerHelper & ) SAL_THROW(()); 00611 inline OMultiTypeInterfaceContainerHelper & operator = ( const OMultiTypeInterfaceContainerHelper & ) SAL_THROW(()); 00612 }; 00613 00614 typedef OBroadcastHelperVar< OMultiTypeInterfaceContainerHelper , OMultiTypeInterfaceContainerHelper::keyType > OBroadcastHelper; 00615 00616 } 00617 00618 #endif 00619 00620 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */