Rapicorn - Experimental UI Toolkit - Source Code 10.08.1
utilities.hh
Go to the documentation of this file.
00001 /* Rapicorn
00002  * Copyright (C) 2005 Tim Janik
00003  *
00004  * This library is free software; you can redistribute it and/or
00005  * modify it under the terms of the GNU Lesser General Public
00006  * License as published by the Free Software Foundation; either
00007  * version 2.1 of the License, or (at your option) any later version.
00008  *
00009  * This library is distributed in the hope that it will be useful,
00010  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00011  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00012  * Lesser General Public License for more details.
00013  *
00014  * A copy of the GNU Lesser General Public License should ship along
00015  * with this library; if not, see http://www.gnu.org/copyleft/.
00016  */
00017 #ifndef __RAPICORN_UTILITIES_HH__
00018 #define __RAPICORN_UTILITIES_HH__
00019 
00020 #include <rapicorn-core.hh>
00021 #include <typeinfo>
00022 
00023 #if !defined __RAPICORN_CLIENTAPI_HH_ && !defined __RAPICORN_UITHREAD_HH__ && !defined __RAPICORN_BUILD__
00024 #error Only <rapicorn.hh> can be included directly.
00025 #endif
00026 
00027 /* --- internally used macros --- */
00028 #ifdef __RAPICORN_BUILD__
00029 /* convenience macros */
00030 #define MakeProperty                    RAPICORN_MakeProperty
00031 #define MakeNamedCommand                RAPICORN_MakeNamedCommand
00032 #define MakeSimpleCommand               RAPICORN_MakeSimpleCommand
00033 #endif
00034 
00035 namespace Rapicorn {
00036 
00037 /* --- init stuff --- */
00038 void          rapicorn_thread_enter     ();
00039 bool          rapicorn_thread_try_enter ();
00040 bool          rapicorn_thread_entered   ();
00041 void          rapicorn_thread_leave     ();
00042 
00043 /* --- standard utlities --- */
00044 //template<typename T> inline const T& min   (const T &a, const T &b) { return ::std::min<T> (a, b); }
00045 //template<typename T> inline const T& max   (const T &a, const T &b) { return ::std::min<T> (a, b); }
00046 using ::std::min;
00047 using ::std::max;
00048 inline double min     (double a, int64  b) { return min<double> (a, b); }
00049 inline double min     (int64  a, double b) { return min<double> (a, b); }
00050 inline double max     (double a, int64  b) { return max<double> (a, b); }
00051 inline double max     (int64  a, double b) { return max<double> (a, b); }
00052 
00053 // === IDL Helpers === // FIXME: remove
00054 template<class O>
00055 O*      connection_id2object (uint64 oid) { return dynamic_cast<O*> (reinterpret_cast<BaseObject*> (oid)); }
00056 inline uint64  connection_object2id (const BaseObject *obj) { return reinterpret_cast<ptrdiff_t> (obj); }
00057 inline uint64  connection_object2id (const BaseObject &obj) { return connection_object2id (&obj); }
00058 
00059 /* --- exceptions --- */
00060 struct Exception : std::exception {
00061 public:
00062   // BROKEN(g++-3.3,g++-3.4): Exception  (const char *reason_format, ...) RAPICORN_PRINTF (2, 3);
00063   explicit            Exception  (const String &s1, const String &s2 = String(), const String &s3 = String(), const String &s4 = String(),
00064                                   const String &s5 = String(), const String &s6 = String(), const String &s7 = String(), const String &s8 = String());
00065   void                set        (const String &s);
00066   virtual const char* what       () const throw() { return reason ? reason : "out of memory"; }
00067   /*Copy*/            Exception  (const Exception &e);
00068   /*Des*/             ~Exception () throw();
00069 private:
00070   Exception&          operator=  (const Exception&);
00071   char *reason;
00072 };
00073 struct NullPointer : std::exception {};
00074 /* allow 'dothrow' as function argument analogous to 'nothrow' */
00075 extern const std::nothrow_t dothrow; /* indicate "with exception" semantics */
00076 using std::nothrow_t;
00077 using std::nothrow;
00078 
00079 /* --- derivation assertions --- */
00080 template<class Derived, class Base>
00081 struct EnforceDerivedFrom {
00082   EnforceDerivedFrom (Derived *derived = 0,
00083                       Base    *base = 0)
00084   { base = derived; }
00085 };
00086 template<class Derived, class Base>
00087 struct EnforceDerivedFrom<Derived*,Base*> {
00088   EnforceDerivedFrom (Derived *derived = 0,
00089                       Base    *base = 0)
00090   { base = derived; }
00091 };
00092 template<class Derived, class Base> void        // ex: assert_derived_from<Child, Base>();
00093 assert_derived_from (void)
00094 {
00095   EnforceDerivedFrom<Derived, Base> assertion;
00096 }
00097 
00098 /* --- derivation checks --- */
00099 template<class Child, class Base>
00100 class CheckDerivedFrom {
00101   static bool is_derived (void*) { return false; }
00102   static bool is_derived (Base*) { return true; }
00103 public:
00104   static bool is_derived () { return is_derived ((Child*) (0)); }
00105 };
00106 template<class Child, class Base>
00107 struct CheckDerivedFrom<Child*,Base*> : CheckDerivedFrom<Child,Base> {};
00108 template<class Derived, class Base> bool
00109 is_derived ()                                   // ex: if (is_derived<Child, Base>()) ...; */
00110 {
00111   return CheckDerivedFrom<Derived,Base>::is_derived();
00112 }
00113 
00114 /* --- type dereferencing --- */
00115 template<typename Type> struct Dereference;
00116 template<typename Type> struct Dereference<Type*> {
00117   typedef Type* Pointer;
00118   typedef Type  Value;
00119 };
00120 template<typename Type> struct Dereference<Type*const> {
00121   typedef Type* Pointer;
00122   typedef Type  Value;
00123 };
00124 template<typename Type> struct Dereference<const Type*> {
00125   typedef const Type* Pointer;
00126   typedef const Type  Value;
00127 };
00128 template<typename Type> struct Dereference<const Type*const> {
00129   typedef const Type* Pointer;
00130   typedef const Type  Value;
00131 };
00132 
00133 /* --- PointerIterator - iterator object from pointer --- */
00134 template<typename Value>
00135 class PointerIterator {
00136 protected:
00137   Value *current;
00138 public:
00139   typedef std::random_access_iterator_tag       iterator_category;
00140   typedef Value                                 value_type;
00141   typedef ptrdiff_t                             difference_type;
00142   typedef Value*                                pointer;
00143   typedef Value&                                reference;
00144 public:
00145   explicit          PointerIterator ()                          : current() {}
00146   explicit          PointerIterator (value_type *v)             : current (v) {}
00147   /*Copy*/          PointerIterator (const PointerIterator &x)  : current (x.current) {}
00148   Value*            base()                              const   { return current; }
00149   reference         operator*       ()                  const   { return *current; }
00150   pointer           operator->      ()                  const   { return &(operator*()); }
00151   PointerIterator&  operator++      ()                          { ++current; return *this; }
00152   PointerIterator   operator++      (int)                       { PointerIterator tmp = *this; ++current; return tmp; }
00153   PointerIterator&  operator--      ()                          { --current; return *this; }
00154   PointerIterator   operator--      (int)                       { PointerIterator tmp = *this; --current; return tmp; }
00155   PointerIterator   operator+       (difference_type n) const   { return PointerIterator (current + n); }
00156   PointerIterator&  operator+=      (difference_type n)         { current += n; return *this; }
00157   PointerIterator   operator-       (difference_type n) const   { return PointerIterator (current - n); }
00158   PointerIterator&  operator-=      (difference_type n)         { current -= n; return *this; }
00159   reference         operator[]      (difference_type n) const   { return *(*this + n); }
00160 };
00161 template<typename Value> PointerIterator<Value>
00162 pointer_iterator (Value * const val)
00163 { return PointerIterator<Value> (val); }
00164 template<typename Value> inline bool
00165 operator== (const PointerIterator<Value> &x, const PointerIterator<Value> &y)
00166 { return x.base() == y.base(); }
00167 template<typename Value> inline bool
00168 operator!= (const PointerIterator<Value> &x, const PointerIterator<Value> &y)
00169 { return x.base() != y.base(); }
00170 template<typename Value> inline bool
00171 operator< (const PointerIterator<Value> &x, const PointerIterator<Value> &y)
00172 { return x.base() < y.base(); }
00173 template<typename Value> inline bool
00174 operator<= (const PointerIterator<Value> &x, const PointerIterator<Value> &y)
00175 { return x.base() <= y.base(); }
00176 template<typename Value> inline bool
00177 operator> (const PointerIterator<Value> &x, const PointerIterator<Value> &y)
00178 { return x.base() > y.base(); }
00179 template<typename Value> inline bool
00180 operator>= (const PointerIterator<Value> &x, const PointerIterator<Value> &y)
00181 { return x.base() >= y.base(); }
00182 template<typename Value> inline typename PointerIterator<Value>::difference_type
00183 operator- (const PointerIterator<Value> &x, const PointerIterator<Value> &y)
00184 { return x.base() - y.base(); }
00185 template<typename Value> inline PointerIterator<Value>
00186 operator+ (typename PointerIterator<Value>::difference_type n, const PointerIterator<Value> &x)
00187 { return x.operator+ (n); }
00188 
00189 /* --- ValueIterator - dereferencing iterator --- */
00190 template<class Iterator> struct ValueIterator : public Iterator {
00191   typedef Iterator                              iterator_type;
00192   typedef typename Iterator::iterator_category  iterator_category;
00193   typedef typename Iterator::difference_type    difference_type;
00194   typedef typename Iterator::value_type         pointer;
00195   typedef typename Dereference<pointer>::Value  value_type;
00196   typedef value_type&                           reference;
00197   Iterator       base          () const { return *this; }
00198   reference      operator*     () const { return *Iterator::operator*(); }
00199   pointer        operator->    () const { return *Iterator::operator->(); }
00200   ValueIterator& operator=     (const Iterator &it) { Iterator::operator= (it); return *this; }
00201   explicit       ValueIterator (Iterator it) : Iterator (it) {}
00202   /*Copy*/       ValueIterator (const ValueIterator &dup) : Iterator (dup.base()) {}
00203   /*Con*/        ValueIterator () : Iterator() {}
00204   template<typename Iter>
00205   /*Con*/        ValueIterator (const ValueIterator<Iter> &src) : Iterator (src.base()) {}
00206 };
00207 template<class Iterator> ValueIterator<Iterator>
00208 value_iterator (const Iterator &iter)
00209 { return ValueIterator<Iterator> (iter); }
00210 template<class Iterator> inline bool
00211 operator== (const ValueIterator<Iterator> &x, const ValueIterator<Iterator> &y)
00212 { return x.base() == y.base(); }
00213 template<class Iterator> inline bool
00214 operator!= (const ValueIterator<Iterator> &x, const ValueIterator<Iterator> &y)
00215 { return x.base() != y.base(); }
00216 template<class Iterator> inline bool
00217 operator< (const ValueIterator<Iterator> &x, const ValueIterator<Iterator> &y)
00218 { return x.base() < y.base(); }
00219 template<class Iterator> inline bool
00220 operator<= (const ValueIterator<Iterator> &x, const ValueIterator<Iterator> &y)
00221 { return x.base() <= y.base(); }
00222 template<class Iterator> inline bool
00223 operator> (const ValueIterator<Iterator> &x, const ValueIterator<Iterator> &y)
00224 { return x.base() > y.base(); }
00225 template<class Iterator> inline bool
00226 operator>= (const ValueIterator<Iterator> &x, const ValueIterator<Iterator> &y)
00227 { return x.base() >= y.base(); }
00228 template<class Iterator> inline typename ValueIterator<Iterator>::difference_type
00229 operator- (const ValueIterator<Iterator> &x, const ValueIterator<Iterator> &y)
00230 { return x.base() - y.base(); }
00231 template<class Iterator> inline ValueIterator<Iterator>
00232 operator+ (typename ValueIterator<Iterator>::difference_type n, const ValueIterator<Iterator> &x)
00233 { return x.operator+ (n); }
00234 
00235 /* --- IteratorRange (iterator range wrappers) --- */
00236 template<class Iterator> class IteratorRange {
00237   Iterator ibegin, iend;
00238 public:
00239   typedef Iterator                              iterator;
00240   typedef typename Iterator::iterator_category  iterator_category;
00241   typedef typename Iterator::value_type         value_type;
00242   typedef typename Iterator::difference_type    difference_type;
00243   typedef typename Iterator::reference          reference;
00244   typedef typename Iterator::pointer            pointer;
00245   explicit IteratorRange (const Iterator &cbegin, const Iterator &cend) :
00246     ibegin (cbegin), iend (cend)
00247   {}
00248   explicit IteratorRange()
00249   {}
00250   iterator       begin()       const { return ibegin; }
00251   iterator       end()         const { return iend; }
00252   bool           done()        const { return ibegin == iend; }
00253   bool           has_next()    const { return ibegin != iend; }
00254   reference      operator* ()  const { return ibegin.operator*(); }
00255   pointer        operator-> () const { return ibegin.operator->(); }
00256   IteratorRange& operator++ ()       { ibegin.operator++(); return *this; }
00257   IteratorRange  operator++ (int)    { IteratorRange dup (*this); ibegin.operator++(); return dup; }
00258   bool           operator== (const IteratorRange &w) const
00259   {
00260     return ibegin == w.begin && iend == w.end;
00261   }
00262   bool        operator!= (const IteratorRange &w) const
00263   {
00264     return ibegin != w.begin || iend != w.end;
00265   }
00266 };
00267 template<class Iterator> IteratorRange<Iterator>
00268 iterator_range (const Iterator &begin, const Iterator &end)
00269 {
00270   return IteratorRange<Iterator> (begin, end);
00271 }
00272 
00273 /* --- ValueIteratorRange (iterator range wrappers) --- */
00274 template<class Iterator> class ValueIteratorRange {
00275   Iterator ibegin, iend;
00276 public:
00277   typedef Iterator                              iterator;
00278   typedef typename Iterator::iterator_category  iterator_category;
00279   typedef typename Iterator::value_type         pointer;
00280   // typedef typeof (*(pointer) 0)              value_type;
00281   typedef typename Dereference<pointer>::Value  value_type;
00282   typedef typename Iterator::difference_type    difference_type;
00283   typedef value_type&                           reference;
00284   explicit ValueIteratorRange (const Iterator &cbegin, const Iterator &cend) :
00285     ibegin (cbegin), iend (cend)
00286   {}
00287   explicit ValueIteratorRange()
00288   {}
00289   iterator            begin()       const { return ibegin; }
00290   iterator            end()         const { return iend; }
00291   bool                done()        const { return ibegin == iend; }
00292   bool                has_next()    const { return ibegin != iend; }
00293   reference           operator* ()  const { return *ibegin.operator*(); }
00294   pointer             operator-> () const { return ibegin.operator*(); }
00295   ValueIteratorRange& operator++ ()       { ibegin.operator++(); return *this; }
00296   ValueIteratorRange  operator++ (int)    { ValueIteratorRange dup (*this); ibegin.operator++(); return dup; }
00297   bool                operator== (const ValueIteratorRange &w) const
00298   {
00299     return ibegin == w.begin && iend == w.end;
00300   }
00301   bool                operator!= (const ValueIteratorRange &w) const
00302   {
00303     return ibegin != w.begin || iend != w.end;
00304   }
00305 };
00306 template<class Iterator> ValueIteratorRange<Iterator>
00307 value_iterator_range (const Iterator &begin, const Iterator &end)
00308 {
00309   return ValueIteratorRange<Iterator> (begin, end);
00310 }
00311 
00312 /* --- Walker (easy to use iterator_range (begin(), end()) substitute) --- */
00313 template<typename Value> class Walker {
00314   /* auxillary Walker classes */
00315   struct AdapterBase {
00316     virtual bool         done    () = 0;
00317     virtual void         inc     () = 0;
00318     virtual AdapterBase* clone   () const = 0;
00319     virtual void*        element () const = 0;
00320     virtual bool         equals  (const AdapterBase &eb) const = 0;
00321   };
00322   AdapterBase *adapter;
00323 public:
00324   template<class Iterator> class Adapter : public AdapterBase {
00325     Iterator ibegin, iend;
00326   public:
00327     explicit Adapter (const Iterator &cbegin, const Iterator &cend) :
00328       ibegin (cbegin), iend (cend)
00329     {}
00330     virtual bool         done    ()              { return ibegin == iend; }
00331     virtual void         inc     ()              { ibegin.operator++(); }
00332     virtual AdapterBase* clone   () const        { return new Adapter (ibegin, iend); }
00333     virtual void*        element () const        { return (void*) ibegin.operator->(); }
00334     virtual bool         equals  (const AdapterBase &eb) const
00335     {
00336       const Adapter *we = dynamic_cast<const Adapter*> (&eb);
00337       return we && ibegin == we->ibegin && iend == we->iend;
00338     }
00339   };
00340   /* Walker API */
00341   typedef Value       value_type;
00342   typedef value_type& reference;
00343   typedef value_type* pointer;
00344   Walker&   operator= (const Walker &w)         { adapter = w.adapter ? w.adapter->clone() : NULL; return *this; }
00345   bool      done       () const                 { return !adapter || adapter->done(); }
00346   bool      has_next   () const                 { return !done(); }
00347   pointer   operator-> () const                 { return reinterpret_cast<pointer> (adapter ? adapter->element() : NULL); }
00348   reference operator*  () const                 { return *operator->(); }
00349   Walker&   operator++ ()                       { if (adapter) adapter->inc(); return *this; }
00350   Walker    operator++ (int)                    { Walker dup (*this); if (adapter) adapter->inc(); return dup; }
00351   bool      operator== (const Walker &w) const  { return w.adapter == adapter || (adapter && w.adapter && adapter->equals (*w.adapter)); }
00352   bool      operator!= (const Walker &w) const  { return !operator== (w); }
00353   ~Walker()                                     { if (adapter) delete adapter; adapter = NULL; }
00354   Walker (const Walker &w)                      : adapter (w.adapter ? w.adapter->clone() : NULL) {}
00355   Walker (AdapterBase *cadapter = NULL)         : adapter (cadapter) {}
00356 };
00357 template<class Container> Walker<const typename Container::const_iterator::value_type>
00358 walker (const Container &container)
00359 {
00360   typedef typename Container::const_iterator          Iterator;
00361   typedef Walker<const typename Iterator::value_type> Walker;
00362   typedef typename Walker::template Adapter<Iterator> Adapter;
00363   return Walker (new Adapter (container.begin(), container.end()));
00364 }
00365 template<class Container> Walker<typename Container::iterator::value_type>
00366 walker (Container &container)
00367 {
00368   typedef typename Container::iterator                Iterator;
00369   typedef Walker<typename Iterator::value_type>       Walker;
00370   typedef typename Walker::template Adapter<Iterator> Adapter;
00371   return Walker (new Adapter (container.begin(), container.end()));
00372 }
00373 template<class Container> Walker<typename Dereference<const typename Container::const_iterator::value_type>::Value>
00374 value_walker (const Container &container)
00375 {
00376   typedef typename Container::const_iterator                               Iterator;
00377   typedef typename Dereference<const typename Iterator::value_type>::Value Value;
00378   typedef Walker<Value>                                                    Walker;
00379   typedef ValueIterator<Iterator>                                          VIterator;
00380   typedef typename Walker::template Adapter<VIterator>                     Adapter;
00381   return Walker (new Adapter (VIterator (container.begin()), VIterator (container.end())));
00382 }
00383 template<class Container> Walker<typename Dereference<typename Container::iterator::value_type>::Value>
00384 value_walker (Container &container)
00385 {
00386   typedef typename Container::iterator                               Iterator;
00387   typedef typename Dereference<typename Iterator::value_type>::Value Value;
00388   typedef Walker<Value>                                              Walker;
00389   typedef ValueIterator<Iterator>                                    VIterator;
00390   typedef typename Walker::template Adapter<VIterator>               Adapter;
00391   return Walker (new Adapter (VIterator (container.begin()), VIterator (container.end())));
00392 }
00393 template<class Iterator> Walker<typename Iterator::value_type>
00394 walker (const Iterator &begin, const Iterator &end)
00395 {
00396   typedef Walker<typename Iterator::value_type>       Walker;
00397   typedef typename Walker::template Adapter<Iterator> Adapter;
00398   return Walker (new Adapter (begin, end));
00399 }
00400 template<class Iterator> Walker<typename Dereference<typename Iterator::value_type>::Value>
00401 value_walker (const Iterator &begin, const Iterator &end)
00402 {
00403   typedef typename Dereference<typename Iterator::value_type>::Value Value;
00404   typedef Walker<Value>                                              Walker;
00405   typedef ValueIterator<Iterator>                                    VIterator;
00406   typedef typename Walker::template Adapter<VIterator>               Adapter;
00407   return Walker (new Adapter (VIterator (begin), VIterator (end)));
00408 }
00409 
00410 } // Rapicorn
00411 
00412 #endif  /* __RAPICORN_UTILITIES_HH__ */
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Defines