• Skip to content
  • Skip to link menu
  • KDE API Reference
  • kdepimlibs-4.10.5 API Reference
  • KDE Home
  • Contact Us
 

akonadi

  • akonadi
itempayloadinternals_p.h
1 /*
2  Copyright (c) 2007 Till Adam <adam@kde.org>
3 
4  This library is free software; you can redistribute it and/or modify it
5  under the terms of the GNU Library General Public License as published by
6  the Free Software Foundation; either version 2 of the License, or (at your
7  option) any later version.
8 
9  This library is distributed in the hope that it will be useful, but WITHOUT
10  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11  FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public
12  License for more details.
13 
14  You should have received a copy of the GNU Library General Public License
15  along with this library; see the file COPYING.LIB. If not, write to the
16  Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
17  02110-1301, USA.
18 */
19 
20 #ifndef ITEMPAYLOADINTERNALS_P_H
21 #define ITEMPAYLOADINTERNALS_P_H
22 
23 #include <kpimutils/supertrait.h>
24 
25 #include <QtCore/QtGlobal>
26 #include <QtCore/QSharedPointer>
27 #include <QtCore/QMetaType>
28 
29 #include <boost/shared_ptr.hpp>
30 #include <boost/type_traits/is_same.hpp>
31 #include <boost/mpl/eval_if.hpp>
32 #include <boost/mpl/identity.hpp>
33 #include <boost/utility/enable_if.hpp>
34 
35 #include <typeinfo>
36 
37 #include "exception.h"
38 
39 //@cond PRIVATE Doxygen 1.7.1 hangs processing this file. so skip it.
40 //for more info, see https://bugzilla.gnome.org/show_bug.cgi?id=531637
41 
42 /* WARNING
43  * The below is an implementation detail of the Item class. It is not to be
44  * considered public API, and subject to change without notice
45  */
46 
47 namespace Akonadi {
48 namespace Internal {
49 
50 template <typename T>
51 struct has_clone_method {
52 private:
53  template <typename S, S * (S::*)() const> struct sfinae {};
54  struct No {};
55  struct Yes { No no[2]; };
56  template <typename S> static No test( ... );
57  template <typename S> static Yes test( sfinae<S,&S::clone> * );
58 public:
59  static const bool value = sizeof( test<T>(0) ) == sizeof( Yes ) ;
60 };
61 
62 template <typename T, bool b>
63 struct clone_traits_helper {
64  // runtime error (commented in) or compiletime error (commented out)?
65  // ### runtime error, until we check has_clone_method in the
66  // ### Item::payload<T> impl directly...
67  template <typename U>
68  static T * clone( U ) { return 0; }
69 };
70 
71 template <typename T>
72 struct clone_traits_helper<T,true> {
73  static T * clone( T * t ) { return t ? t->clone() : 0 ; }
74 };
75 
76 template <typename T>
77 struct clone_traits : clone_traits_helper<T, has_clone_method<T>::value> {};
78 
79 template <typename T>
80 struct shared_pointer_traits {
81  static const bool defined = false;
82 };
83 
84 template <typename T>
85 struct shared_pointer_traits< boost::shared_ptr<T> > {
86  static const bool defined = true;
87  typedef T element_type;
88  template <typename S>
89  struct make { typedef boost::shared_ptr<S> type; };
90  typedef QSharedPointer<T> next_shared_ptr;
91 };
92 
93 template <typename T>
94 struct shared_pointer_traits< QSharedPointer<T> > {
95  static const bool defined = true;
96  typedef T element_type;
97  template <typename S>
98  struct make { typedef QSharedPointer<S> type; };
99  typedef boost::shared_ptr<T> next_shared_ptr;
100 };
101 
102 template <typename T>
103 struct is_shared_pointer {
104  static const bool value = shared_pointer_traits<T>::defined;
105 };
106 
107 template <typename T>
108 struct get_hierarchy_root;
109 
110 template <typename T, typename S>
111 struct get_hierarchy_root_recurse
112  : get_hierarchy_root<S> {};
113 
114 template <typename T>
115 struct get_hierarchy_root_recurse<T,T>
116  : boost::mpl::identity<T> {};
117 
118 template <typename T>
119 struct get_hierarchy_root
120  : get_hierarchy_root_recurse< T, typename ::KPIMUtils::SuperClass<T>::Type > {};
121 
122 template <typename T>
123 struct get_hierarchy_root< boost::shared_ptr<T> > {
124  typedef boost::shared_ptr< typename get_hierarchy_root<T>::type > type;
125 };
126 
127 template <typename T>
128 struct get_hierarchy_root< QSharedPointer<T> > {
129  typedef QSharedPointer< typename get_hierarchy_root<T>::type > type;
130 };
131 
132 
139 template <typename T> struct PayloadTrait
140 {
142  typedef T ElementType;
143  // the metatype id for the element type, or for pointer-to-element
144  // type, if in a shared pointer
145  static int elementMetaTypeId() { return qMetaTypeId<T>(); }
148  typedef typename KPIMUtils::SuperClass<T>::Type SuperElementType;
150  typedef T Type;
154  typedef typename KPIMUtils::SuperClass<T>::Type SuperType;
157  static const bool isPolymorphic = false;
159  static inline bool isNull( const Type & ) { return true; }
162  template <typename U> static inline Type castFrom( const U& )
163  {
164  throw PayloadException( "you should never get here" );
165  }
167  template <typename U> static inline bool canCastFrom( const U& )
168  {
169  return false;
170  }
172  template <typename U> static inline U castTo( const Type& )
173  {
174  throw PayloadException( "you should never get here" );
175  }
176  template <typename U> static T clone( const U & )
177  {
178  throw PayloadException( "clone: you should never get here" );
179  }
181  static const unsigned int sharedPointerId = 0;
182 };
183 
189 template <typename T> struct PayloadTrait<boost::shared_ptr<T> >
190 {
191  typedef T ElementType;
192  static int elementMetaTypeId() { return qMetaTypeId<T*>(); }
193  typedef typename KPIMUtils::SuperClass<T>::Type SuperElementType;
194  typedef boost::shared_ptr<ElementType> Type;
195  typedef boost::shared_ptr<SuperElementType> SuperType;
196  static const bool isPolymorphic = !boost::is_same<ElementType, SuperElementType>::value;
197  static inline bool isNull( const Type &p ) { return p.get() == 0; }
198  template <typename U> static inline Type castFrom( const boost::shared_ptr<U> &p )
199  {
200  const Type sp = boost::dynamic_pointer_cast<T,U>( p );
201  if ( sp.get() != 0 || p.get() == 0 )
202  return sp;
203  throw PayloadException( "boost::dynamic_pointer_cast failed" );
204  }
205  template <typename U> static inline bool canCastFrom( const boost::shared_ptr<U> &p )
206  {
207  const Type sp = boost::dynamic_pointer_cast<T,U>( p );
208  return sp.get() != 0 || p.get() == 0;
209  }
210  template <typename U> static inline boost::shared_ptr<U> castTo( const Type &p )
211  {
212  const boost::shared_ptr<U> sp = boost::dynamic_pointer_cast<U>( p );
213  return sp;
214  }
215  static boost::shared_ptr<T> clone( const QSharedPointer<T> & t ) {
216  if ( T * nt = clone_traits<T>::clone( t.data() ) )
217  return boost::shared_ptr<T>( nt );
218  else
219  return boost::shared_ptr<T>();
220  }
221  static const unsigned int sharedPointerId = 1;
222 };
223 
229 template <typename T> struct PayloadTrait<QSharedPointer<T> >
230 {
231  typedef T ElementType;
232  static int elementMetaTypeId() { return qMetaTypeId<T*>(); }
233  typedef typename KPIMUtils::SuperClass<T>::Type SuperElementType;
234  typedef QSharedPointer<T> Type;
235  typedef QSharedPointer<SuperElementType> SuperType;
236  static const bool isPolymorphic = !boost::is_same<ElementType, SuperElementType>::value;
237  static inline bool isNull( const Type &p ) { return p.isNull(); }
238  template <typename U> static inline Type castFrom( const QSharedPointer<U> &p )
239  {
240  const Type sp = qSharedPointerDynamicCast<T,U>( p );
241  if ( !sp.isNull() || p.isNull() )
242  return sp;
243  throw PayloadException( "qSharedPointerDynamicCast failed" );
244  }
245  template <typename U> static inline bool canCastFrom( const QSharedPointer<U> &p )
246  {
247  const Type sp = qSharedPointerDynamicCast<T,U>( p );
248  return !sp.isNull() || p.isNull();
249  }
250  template <typename U> static inline QSharedPointer<U> castTo( const Type &p )
251  {
252  const QSharedPointer<U> sp = qSharedPointerDynamicCast<U,T>( p );
253  return sp;
254  }
255  static QSharedPointer<T> clone( const boost::shared_ptr<T> & t ) {
256  if ( T * nt = clone_traits<T>::clone( t.get() ) )
257  return QSharedPointer<T>( nt );
258  else
259  return QSharedPointer<T>();
260  }
261  static const unsigned int sharedPointerId = 2;
262 };
263 
264 
265 }
266 
272 struct PayloadBase
273 {
274  virtual ~PayloadBase() { }
275  virtual PayloadBase * clone() const = 0;
276  virtual const char* typeName() const = 0;
277 };
278 
284 template <typename T>
285 struct Payload : public PayloadBase
286 {
287  Payload() {};
288  Payload( const T& p ) : payload( p ) {}
289 
290  PayloadBase * clone() const
291  {
292  return new Payload<T>( const_cast<Payload<T>* >(this)->payload);
293  }
294 
295  const char* typeName() const
296  {
297  return typeid(const_cast<Payload<T>*> (this)).name();
298  }
299 
300  T payload;
301 };
302 
307 template <typename T>
308 struct Payload<T*> : public PayloadBase
309 {
310 };
311 
312 namespace Internal {
313 
318 template <typename T> inline Payload<T>* payload_cast( PayloadBase* payloadBase )
319 {
320  Payload<T> *p = dynamic_cast<Payload<T>*>( payloadBase );
321  // try harder to cast, workaround for some gcc issue with template instances in multiple DSO's
322  if ( !p && payloadBase && strcmp( payloadBase->typeName(), typeid(p).name() ) == 0 ) {
323  p = static_cast<Payload<T>*>( payloadBase );
324  }
325  return p;
326 }
327 
328 }
329 
330 }
331 //@endcond
332 
333 #endif
334 
This file is part of the KDE documentation.
Documentation copyright © 1996-2013 The KDE developers.
Generated on Sat Jul 13 2013 01:27:38 by doxygen 1.8.3.1 written by Dimitri van Heesch, © 1997-2006

KDE's Doxygen guidelines are available online.

akonadi

Skip menu "akonadi"
  • Main Page
  • Namespace List
  • Namespace Members
  • Alphabetical List
  • Class List
  • Class Hierarchy
  • Class Members
  • File List
  • Modules
  • Related Pages

kdepimlibs-4.10.5 API Reference

Skip menu "kdepimlibs-4.10.5 API Reference"
  • akonadi
  •   contact
  •   kmime
  •   socialutils
  • kabc
  • kalarmcal
  • kblog
  • kcal
  • kcalcore
  • kcalutils
  • kholidays
  • kimap
  • kioslave
  •   imap4
  •   mbox
  •   nntp
  • kldap
  • kmbox
  • kmime
  • kontactinterface
  • kpimidentities
  • kpimtextedit
  • kpimutils
  • kresources
  • ktnef
  • kxmlrpcclient
  • mailtransport
  • microblog
  • qgpgme
  • syndication
  •   atom
  •   rdf
  •   rss2
Report problems with this website to our bug tracking system.
Contact the specific authors with questions and comments about the page contents.

KDE® and the K Desktop Environment® logo are registered trademarks of KDE e.V. | Legal