My Project
UDK 3.2.7 C/C++ API Reference
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
interfacecontainer.h
Go to the documentation of this file.
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 #ifndef _CPPUHELPER_INTERFACECONTAINER_H_
20 #define _CPPUHELPER_INTERFACECONTAINER_H_
21 
22 #include <vector>
23 #include <osl/mutex.hxx>
24 #include <rtl/alloc.h>
26 #include <com/sun/star/uno/XInterface.hpp>
27 #ifndef _COM_SUN_STAR_LANG_EVENTOBJECT_HXX_
28 #include <com/sun/star/lang/EventObject.hpp>
29 #endif
30 
31 #ifndef _COM_SUN_STAR_LANG_DISPOSEDEXCEPTION_HXX_
32 #include "com/sun/star/lang/DisposedException.hpp"
33 #endif
34 #include "cppuhelperdllapi.h"
35  //for docpp
37 namespace cppu
38 {
39 
40 namespace detail {
41 
43  {
45  ::com::sun::star::uno::XInterface * pAsInterface;
47  };
48 
49 }
50 
51 //===================================================================
52 class OInterfaceContainerHelper;
61 {
62 public:
77 
82 
84  sal_Bool SAL_CALL hasMoreElements() const SAL_THROW(())
85  { return nRemain != 0; }
90  ::com::sun::star::uno::XInterface * SAL_CALL next() SAL_THROW(());
91 
97  void SAL_CALL remove() SAL_THROW(());
98 
99 private:
101  sal_Bool bIsList;
102 
103  detail::element_alias aData;
104 
105  sal_Int32 nRemain;
106 
107  OInterfaceIteratorHelper( const OInterfaceIteratorHelper & ) SAL_THROW(());
108  OInterfaceIteratorHelper & operator = ( const OInterfaceIteratorHelper & ) SAL_THROW(());
109 };
110 
111 //===================================================================
119 {
120 public:
121  // these are here to force memory de/allocation to sal lib.
122  inline static void * SAL_CALL operator new( size_t nSize ) SAL_THROW(())
123  { return ::rtl_allocateMemory( nSize ); }
124  inline static void SAL_CALL operator delete( void * pMem ) SAL_THROW(())
125  { ::rtl_freeMemory( pMem ); }
126  inline static void * SAL_CALL operator new( size_t, void * pMem ) SAL_THROW(())
127  { return pMem; }
128  inline static void SAL_CALL operator delete( void *, void * ) SAL_THROW(())
129  {}
130 
138  OInterfaceContainerHelper( ::osl::Mutex & rMutex ) SAL_THROW(());
143  ~OInterfaceContainerHelper() SAL_THROW(());
148  sal_Int32 SAL_CALL getLength() const SAL_THROW(());
149 
153  ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > > SAL_CALL getElements() const SAL_THROW(());
154 
171  sal_Int32 SAL_CALL addInterface( const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > & rxIFace ) SAL_THROW(());
179  sal_Int32 SAL_CALL removeInterface( const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > & rxIFace ) SAL_THROW(());
184  void SAL_CALL disposeAndClear( const ::com::sun::star::lang::EventObject & rEvt ) SAL_THROW(());
188  void SAL_CALL clear() SAL_THROW(());
189 
201  template <typename ListenerT, typename FuncT>
202  inline void forEach( FuncT const& func );
203 
225  template< typename ListenerT, typename EventT >
226  inline void notifyEach( void ( SAL_CALL ListenerT::*NotificationMethod )( const EventT& ), const EventT& Event );
227 
228 private:
234  detail::element_alias aData;
235  ::osl::Mutex & rMutex;
237  sal_Bool bInUse;
239  sal_Bool bIsList;
240 
241  OInterfaceContainerHelper( const OInterfaceContainerHelper & ) SAL_THROW(());
242  OInterfaceContainerHelper & operator = ( const OInterfaceContainerHelper & ) SAL_THROW(());
243 
244  /*
245  Dulicate content of the conaitner and release the old one without destroying.
246  The mutex must be locked and the memberbInUse must be true.
247  */
248  void copyAndResetInUse() SAL_THROW(());
249 
250 private:
251  template< typename ListenerT, typename EventT >
252  class NotifySingleListener
253  {
254  private:
255  typedef void ( SAL_CALL ListenerT::*NotificationMethod )( const EventT& );
256  NotificationMethod m_pMethod;
257  const EventT& m_rEvent;
258  public:
259  NotifySingleListener( NotificationMethod method, const EventT& event ) : m_pMethod( method ), m_rEvent( event ) { }
260 
261  void operator()( const ::com::sun::star::uno::Reference<ListenerT>& listener ) const
262  {
263  (listener.get()->*m_pMethod)( m_rEvent );
264  }
265  };
266 };
267 
268 template <typename ListenerT, typename FuncT>
269 inline void OInterfaceContainerHelper::forEach( FuncT const& func )
270 {
271  OInterfaceIteratorHelper iter( *this );
272  while (iter.hasMoreElements()) {
275  if (xListener.is()) {
276 #if defined(EXCEPTIONS_OFF)
277  func( xListener );
278 #else
279  try {
280  func( xListener );
281  }
282  catch (::com::sun::star::lang::DisposedException const& exc) {
283  if (exc.Context == xListener)
284  iter.remove();
285  }
286 #endif
287  }
288  }
289 }
290 
291 template< typename ListenerT, typename EventT >
292 inline void OInterfaceContainerHelper::notifyEach( void ( SAL_CALL ListenerT::*NotificationMethod )( const EventT& ), const EventT& Event )
293 {
294  forEach< ListenerT, NotifySingleListener< ListenerT, EventT > >( NotifySingleListener< ListenerT, EventT >( NotificationMethod, Event ) );
295 }
296 
297 //===================================================================
304 template< class key , class hashImpl , class equalImpl >
306 {
307 public:
308  // these are here to force memory de/allocation to sal lib.
309  inline static void * SAL_CALL operator new( size_t nSize ) SAL_THROW(())
310  { return ::rtl_allocateMemory( nSize ); }
311  inline static void SAL_CALL operator delete( void * pMem ) SAL_THROW(())
312  { ::rtl_freeMemory( pMem ); }
313  inline static void * SAL_CALL operator new( size_t, void * pMem ) SAL_THROW(())
314  { return pMem; }
315  inline static void SAL_CALL operator delete( void *, void * ) SAL_THROW(())
316  {}
317 
329  inline ~OMultiTypeInterfaceContainerHelperVar() SAL_THROW(());
330 
334  inline ::com::sun::star::uno::Sequence< key > SAL_CALL getContainedTypes() const SAL_THROW(());
335 
342  inline OInterfaceContainerHelper * SAL_CALL getContainer( const key & ) const SAL_THROW(());
343 
362  inline sal_Int32 SAL_CALL addInterface(
363  const key & rKey,
364  const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > & r )
365  SAL_THROW(());
366 
377  inline sal_Int32 SAL_CALL removeInterface(
378  const key & rKey,
379  const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > & rxIFace )
380  SAL_THROW(());
381 
387  inline void SAL_CALL disposeAndClear( const ::com::sun::star::lang::EventObject & rEvt ) SAL_THROW(());
391  inline void SAL_CALL clear() SAL_THROW(());
392 
393  typedef key keyType;
394 private:
395  typedef ::std::vector< std::pair < key , void* > > InterfaceMap;
396  InterfaceMap *m_pMap;
397  ::osl::Mutex & rMutex;
398 
399  inline typename InterfaceMap::iterator find(const key &rKey) const
400  {
401  typename InterfaceMap::iterator iter = m_pMap->begin();
402  typename InterfaceMap::iterator end = m_pMap->end();
403 
404  while( iter != end )
405  {
406  equalImpl equal;
407  if( equal( iter->first, rKey ) )
408  break;
409  iter++;
410  }
411  return iter;
412  }
413 
415  inline OMultiTypeInterfaceContainerHelperVar & operator = ( const OMultiTypeInterfaceContainerHelperVar & ) SAL_THROW(());
416 };
417 
418 
419 
420 
430 template < class container , class keyType >
432 {
436  container aLC;
441 
446  OBroadcastHelperVar( ::osl::Mutex & rMutex_ ) SAL_THROW(())
447  : rMutex( rMutex_ )
448  , aLC( rMutex_ )
449  , bDisposed( sal_False )
450  , bInDispose( sal_False )
451  {}
452 
456  inline void addListener(
457  const keyType &key,
458  const ::com::sun::star::uno::Reference < ::com::sun::star::uno::XInterface > &r )
459  SAL_THROW(())
460  {
461  ::osl::MutexGuard guard( rMutex );
462  OSL_ENSURE( !bInDispose, "do not add listeners in the dispose call" );
463  OSL_ENSURE( !bDisposed, "object is disposed" );
464  if( ! bInDispose && ! bDisposed )
465  aLC.addInterface( key , r );
466  }
467 
471  inline void removeListener(
472  const keyType &key,
473  const ::com::sun::star::uno::Reference < ::com::sun::star::uno::XInterface > & r )
474  SAL_THROW(())
475  {
476  ::osl::MutexGuard guard( rMutex );
477  OSL_ENSURE( !bDisposed, "object is disposed" );
478  if( ! bInDispose && ! bDisposed )
479  aLC.removeInterface( key , r );
480  }
481 
488  inline OInterfaceContainerHelper * SAL_CALL getContainer( const keyType &key ) const SAL_THROW(())
489  { return aLC.getContainer( key ); }
490 };
491 
492 /*------------------------------------------
493 *
494 * In general, the above templates are used with a Type as key.
495 * Therefore a default declaration is given ( OMultiTypeInterfaceContainerHelper and OBroadcastHelper )
496 *
497 *------------------------------------------*/
498 
499 // helper function call class
501 {
502  size_t operator()(const ::com::sun::star::uno::Type & s) const SAL_THROW(())
503  { return (size_t) s.getTypeName().hashCode(); }
504 };
505 
506 
511 {
512 public:
513  // these are here to force memory de/allocation to sal lib.
514  inline static void * SAL_CALL operator new( size_t nSize ) SAL_THROW(())
515  { return ::rtl_allocateMemory( nSize ); }
516  inline static void SAL_CALL operator delete( void * pMem ) SAL_THROW(())
517  { ::rtl_freeMemory( pMem ); }
518  inline static void * SAL_CALL operator new( size_t, void * pMem ) SAL_THROW(())
519  { return pMem; }
520  inline static void SAL_CALL operator delete( void *, void * ) SAL_THROW(())
521  {}
522 
534  ~OMultiTypeInterfaceContainerHelper() SAL_THROW(());
535 
539  ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Type > SAL_CALL getContainedTypes() const SAL_THROW(());
540 
546  OInterfaceContainerHelper * SAL_CALL getContainer( const ::com::sun::star::uno::Type & rKey ) const SAL_THROW(());
547 
566  sal_Int32 SAL_CALL addInterface(
567  const ::com::sun::star::uno::Type & rKey,
568  const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > & r )
569  SAL_THROW(());
570 
581  sal_Int32 SAL_CALL removeInterface(
582  const ::com::sun::star::uno::Type & rKey,
583  const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > & rxIFace )
584  SAL_THROW(());
585 
590  void SAL_CALL disposeAndClear( const ::com::sun::star::lang::EventObject & rEvt ) SAL_THROW(());
594  void SAL_CALL clear() SAL_THROW(());
595 
596  typedef ::com::sun::star::uno::Type keyType;
597 private:
598  void *m_pMap;
599  ::osl::Mutex & rMutex;
600 
602  inline OMultiTypeInterfaceContainerHelper & operator = ( const OMultiTypeInterfaceContainerHelper & ) SAL_THROW(());
603 };
604 
605 typedef OBroadcastHelperVar< OMultiTypeInterfaceContainerHelper , OMultiTypeInterfaceContainerHelper::keyType > OBroadcastHelper;
606 
607 }
608 
609 #endif
610 
611 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */