00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00026
00028 #ifndef __REFCOUNTSFIELD_H__
00029 #define __REFCOUNTSFIELD_H__
00030
00031 #include "AutoRef.h"
00032 #include "RefCountedClass.h"
00033 #include "Field.h"
00034
00035 namespace H3D {
00036
00041 template< class RefClass, class BaseField = H3D::Field >
00042 class RefCountSField: public BaseField {
00043 public:
00047 typedef RefClass typed_class_type;
00051 typedef RefClass * typed_value_type;
00053 typedef RefClass class_type;
00055 typedef RefClass * value_type;
00056
00058 RefCountSField(): value( NULL ) {
00059 value.rc_field = this;
00060 };
00061
00063 RefCountSField( RefClass *_value ) : value( _value ) {
00064 value.rc_field = this;
00065 }
00066
00068 inline virtual void setValue( const AutoRef< RefClass > &n, int id = 0 );
00069
00071 inline virtual void setValue( RefClass *n, int id = 0 );
00072
00074 inline virtual RefClass *getValue( int id = 0 );
00075
00076 protected:
00078 inline virtual void update();
00079
00080 virtual RefClass *preOnAdd( RefClass *n ) {
00081 return n;
00082 }
00083
00084 virtual RefClass *preOnRemove( RefClass *n ) {
00085 return n;
00086 }
00087
00093 class RefCountSFieldAutoRef: public AutoRef< RefClass > {
00094 public :
00095
00097 explicit RefCountSFieldAutoRef( RefClass* n = 0) throw() :
00098 AutoRef< RefClass >( n ) {
00099
00100 }
00101
00103 RefCountSFieldAutoRef& operator=(RefClass* n) throw() {
00104 this->reset( n );
00105 return *this;
00106 }
00107
00109 template< class RefClassClass >
00110 RefCountSFieldAutoRef& operator=(const AutoRef<RefClassClass> &n)
00111 throw() {
00112 this->reset( n.get() );
00113 return *this;
00114 }
00115
00117 ~RefCountSFieldAutoRef() throw() {
00118 this->reset( NULL );
00119 }
00120
00128 inline virtual void ref( RefClass *n ) {
00129 if( rc_field && n ) {
00130 AutoRef< RefClass >::ref( n );
00131 rc_field->onAdd( rc_field->preOnAdd( n ) );
00132 }
00133 }
00134
00141 inline virtual void unref( RefClass *n ) {
00142 if( rc_field && n ) {
00143 rc_field->onRemove( rc_field->preOnRemove( n ) );
00144 AutoRef< RefClass >::unref( n );
00145 }
00146 }
00148 RefCountSField *rc_field;
00149 };
00150
00151 friend class RefCountSFieldAutoRefVector;
00152
00159 virtual void onAdd( RefClass *n ) {
00160 #ifdef REF_COUNT_DEBUG
00161 Console(1) << "RefCountSField: Add node" << endl;
00162 #endif
00163 }
00164
00171 virtual void onRemove( RefClass *n ) {
00172 #ifdef REF_COUNT_DEBUG
00173 Console(1) << "RefCountSField: Remove node" << endl;
00174 #endif
00175 }
00176
00178 RefCountSFieldAutoRef value;
00179 };
00180
00181 template< class RefClass, class BaseField >
00182 void RefCountSField< RefClass, BaseField >::update() {
00183 #ifdef REF_COUNT_DEBUG
00184 Console(1) << "RefCountSField(" << name << ")::update() event_ptr = "
00185 << event.ptr << endl;
00186 #endif
00187 value = static_cast< RefCountSField* >(this->event.ptr)->getValue();
00188
00189 }
00190
00191 template< class RefClass, class BaseField >
00192 inline void RefCountSField< RefClass, BaseField >::setValue( RefClass *n,
00193 int id ) {
00194 this->checkAccessTypeSet( id );
00195 #ifdef REF_COUNT_DEBUG
00196 Console(1) << "RefCountSField(" << name << ")::setValue()" << endl;
00197 #endif
00198 value = n;
00199
00200 this->startEvent();
00201 }
00202
00203 template< class RefClass, class BaseField >
00204 void RefCountSField< RefClass, BaseField >::setValue(
00205 const AutoRef< RefClass > &n,
00206 int id ) {
00207 this->setValue( n.get(), id );
00208 }
00209
00210 template< class RefClass, class BaseField >
00211 RefClass *RefCountSField< RefClass, BaseField >::getValue( int id ) {
00212 #ifdef REF_COUNT_DEBUG
00213 Console(1) << "RefCountSField(" << name << ")::getValue()" << endl;
00214 #endif
00215 this->checkAccessTypeGet( id );
00216
00217 this->upToDate();
00218 return value.get();
00219 }
00220
00221 }
00222
00223 #endif