00001
00002 #ifndef _cairo_REFPTR_H
00003 #define _cairo_REFPTR_H
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026 namespace Cairo
00027 {
00028
00041 template <class T_CppObject>
00042 class RefPtr
00043 {
00044 public:
00049 inline RefPtr();
00050
00052 inline ~RefPtr();
00053
00065 explicit inline RefPtr(T_CppObject* pCppObject);
00066
00068 explicit inline RefPtr(T_CppObject* pCppObject, int* refcount);
00069
00074 inline RefPtr(const RefPtr<T_CppObject>& src);
00075
00080 template <class T_CastFrom>
00081 inline RefPtr(const RefPtr<T_CastFrom>& src);
00082
00088 inline void swap(RefPtr<T_CppObject>& other);
00089
00091 inline RefPtr<T_CppObject>& operator=(const RefPtr<T_CppObject>& src);
00092
00097 template <class T_CastFrom>
00098 inline RefPtr<T_CppObject>& operator=(const RefPtr<T_CastFrom>& src);
00099
00101 inline bool operator==(const RefPtr<T_CppObject>& src) const;
00102
00104 inline bool operator!=(const RefPtr<T_CppObject>& src) const;
00105
00111 inline T_CppObject* operator->() const;
00112
00121 inline operator bool() const;
00122
00124 inline void clear();
00125
00126
00134 template <class T_CastFrom>
00135 static inline RefPtr<T_CppObject> cast_dynamic(const RefPtr<T_CastFrom>& src);
00136
00144 template <class T_CastFrom>
00145 static inline RefPtr<T_CppObject> cast_static(const RefPtr<T_CastFrom>& src);
00146
00154 template <class T_CastFrom>
00155 static inline RefPtr<T_CppObject> cast_const(const RefPtr<T_CastFrom>& src);
00156
00157
00158 #ifndef DOXYGEN_IGNORE_THIS
00159
00160
00161
00162 inline int* refcount_() const { return pCppRefcount_; }
00163
00164 #endif // DOXYGEN_IGNORE_THIS
00165
00166 private:
00167 void unref();
00168
00169 T_CppObject* pCppObject_;
00170 mutable int* pCppRefcount_;
00171 };
00172
00173
00174 #ifndef DOXYGEN_IGNORE_THIS
00175
00176
00177
00178
00179 template <class T_CppObject> inline
00180 T_CppObject* RefPtr<T_CppObject>::operator->() const
00181 {
00182 return pCppObject_;
00183 }
00184
00185 template <class T_CppObject> inline
00186 RefPtr<T_CppObject>::RefPtr()
00187 :
00188 pCppObject_(0),
00189 pCppRefcount_(0)
00190 {}
00191
00192 template <class T_CppObject> inline
00193 RefPtr<T_CppObject>::~RefPtr()
00194 {
00195 unref();
00196 }
00197
00198 template <class T_CppObject> inline
00199 void RefPtr<T_CppObject>::unref()
00200 {
00201 if(pCppRefcount_)
00202 {
00203 --(*pCppRefcount_);
00204
00205 if(*pCppRefcount_ == 0)
00206 {
00207 if(pCppObject_)
00208 {
00209 delete pCppObject_;
00210 pCppObject_ = 0;
00211 }
00212
00213 delete pCppRefcount_;
00214 pCppRefcount_ = 0;
00215 }
00216 }
00217 }
00218
00219
00220 template <class T_CppObject> inline
00221 RefPtr<T_CppObject>::RefPtr(T_CppObject* pCppObject)
00222 :
00223 pCppObject_(pCppObject),
00224 pCppRefcount_(0)
00225 {
00226 if(pCppObject)
00227 {
00228 pCppRefcount_ = new int;
00229 *pCppRefcount_ = 1;
00230 }
00231 }
00232
00233
00234 template <class T_CppObject> inline
00235 RefPtr<T_CppObject>::RefPtr(T_CppObject* pCppObject, int* refcount)
00236 :
00237 pCppObject_(pCppObject),
00238 pCppRefcount_(refcount)
00239 {
00240 if(pCppObject_ && pCppRefcount_)
00241 ++(*pCppRefcount_);
00242 }
00243
00244 template <class T_CppObject> inline
00245 RefPtr<T_CppObject>::RefPtr(const RefPtr<T_CppObject>& src)
00246 :
00247 pCppObject_ (src.pCppObject_),
00248 pCppRefcount_(src.pCppRefcount_)
00249 {
00250 if(pCppObject_ && pCppRefcount_)
00251 ++(*pCppRefcount_);
00252 }
00253
00254
00255
00256
00257 template <class T_CppObject>
00258 template <class T_CastFrom>
00259 inline
00260 RefPtr<T_CppObject>::RefPtr(const RefPtr<T_CastFrom>& src)
00261 :
00262
00263
00264
00265 pCppObject_ (src.operator->()),
00266 pCppRefcount_(src.refcount_())
00267 {
00268 if(pCppObject_ && pCppRefcount_)
00269 ++(*pCppRefcount_);
00270 }
00271
00272 template <class T_CppObject> inline
00273 void RefPtr<T_CppObject>::swap(RefPtr<T_CppObject>& other)
00274 {
00275 T_CppObject *const temp = pCppObject_;
00276 int* temp_count = pCppRefcount_;
00277
00278 pCppObject_ = other.pCppObject_;
00279 pCppRefcount_ = other.pCppRefcount_;
00280
00281 other.pCppObject_ = temp;
00282 other.pCppRefcount_ = temp_count;
00283 }
00284
00285 template <class T_CppObject> inline
00286 RefPtr<T_CppObject>& RefPtr<T_CppObject>::operator=(const RefPtr<T_CppObject>& src)
00287 {
00288
00289
00290
00291
00292
00293
00294
00295
00296
00297
00298
00299
00300
00301
00302
00303
00304
00305
00306
00307
00308
00309
00310
00311
00312 RefPtr<T_CppObject> temp (src);
00313 this->swap(temp);
00314 return *this;
00315 }
00316
00317 template <class T_CppObject>
00318 template <class T_CastFrom>
00319 inline
00320 RefPtr<T_CppObject>& RefPtr<T_CppObject>::operator=(const RefPtr<T_CastFrom>& src)
00321 {
00322 RefPtr<T_CppObject> temp (src);
00323 this->swap(temp);
00324 return *this;
00325 }
00326
00327 template <class T_CppObject> inline
00328 bool RefPtr<T_CppObject>::operator==(const RefPtr<T_CppObject>& src) const
00329 {
00330 return (pCppObject_ == src.pCppObject_);
00331 }
00332
00333 template <class T_CppObject> inline
00334 bool RefPtr<T_CppObject>::operator!=(const RefPtr<T_CppObject>& src) const
00335 {
00336 return (pCppObject_ != src.pCppObject_);
00337 }
00338
00339 template <class T_CppObject> inline
00340 RefPtr<T_CppObject>::operator bool() const
00341 {
00342 return (pCppObject_ != 0);
00343 }
00344
00345 template <class T_CppObject> inline
00346 void RefPtr<T_CppObject>::clear()
00347 {
00348 RefPtr<T_CppObject> temp;
00349 this->swap(temp);
00350 }
00351
00352 template <class T_CppObject>
00353 template <class T_CastFrom>
00354 inline
00355 RefPtr<T_CppObject> RefPtr<T_CppObject>::cast_dynamic(const RefPtr<T_CastFrom>& src)
00356 {
00357 T_CppObject *const pCppObject = dynamic_cast<T_CppObject*>(src.operator->());
00358
00359 if(pCppObject)
00360 return RefPtr<T_CppObject>(pCppObject, src.refcount_());
00361 else
00362 return RefPtr<T_CppObject>();
00363 }
00364
00365 template <class T_CppObject>
00366 template <class T_CastFrom>
00367 inline
00368 RefPtr<T_CppObject> RefPtr<T_CppObject>::cast_static(const RefPtr<T_CastFrom>& src)
00369 {
00370 T_CppObject *const pCppObject = static_cast<T_CppObject*>(src.operator->());
00371
00372 return RefPtr<T_CppObject>(pCppObject, src.refcount_());
00373 }
00374
00375 template <class T_CppObject>
00376 template <class T_CastFrom>
00377 inline
00378 RefPtr<T_CppObject> RefPtr<T_CppObject>::cast_const(const RefPtr<T_CastFrom>& src)
00379 {
00380 T_CppObject *const pCppObject = const_cast<T_CppObject*>(src.operator->());
00381
00382 return RefPtr<T_CppObject>(pCppObject, src.refcount_());
00383 }
00384
00385 #endif
00386
00388 template <class T_CppObject> inline
00389 void swap(RefPtr<T_CppObject>& lhs, RefPtr<T_CppObject>& rhs)
00390 {
00391 lhs.swap(rhs);
00392 }
00393
00394 }
00395
00396
00397 #endif
00398
00399