DependentNodeFields.h

00001 
00002 //    Copyright 2004, SenseGraphics AB
00003 //
00004 //    This file is part of H3D API.
00005 //
00006 //    H3D API is free software; you can redistribute it and/or modify
00007 //    it under the terms of the GNU General Public License as published by
00008 //    the Free Software Foundation; either version 2 of the License, or
00009 //    (at your option) any later version.
00010 //
00011 //    H3D API is distributed in the hope that it will be useful,
00012 //    but WITHOUT ANY WARRANTY; without even the implied warranty of
00013 //    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00014 //    GNU General Public License for more details.
00015 //
00016 //    You should have received a copy of the GNU General Public License
00017 //    along with H3D API; if not, write to the Free Software
00018 //    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00019 //
00020 //    A commercial license is also available. Please contact us at 
00021 //    www.sensegraphics.com for more information.
00022 //
00023 //
00024 // \file DependentNodeFields.h Contains the DependentSFNode and 
00026 //
00028 #ifndef __DEPENDENTNODEFIELDS_H__
00029 #define __DEPENDENTNODEFIELDS_H__
00030 
00031 #include "SFNode.h"
00032 #include "MFNode.h"
00033 
00034 namespace H3D {
00035 
00045   template< class NodeType, 
00046             class FieldType, 
00047             auto_ptr< FieldType > NodeType:: *member_ptr >
00048   class FieldRef {
00049   public:
00050     typedef NodeType node_type;
00051     typedef FieldType field_type;
00052     typedef auto_ptr< FieldType > NodeType:: * member_ptr_type;
00053     static Field *getField( NodeType *n ) {
00054       return (n->*member_ptr).get();
00055     }
00056     static member_ptr_type getMemberPtr() {
00057       return member_ptr;
00058     }
00059   };
00060 
00061   namespace FieldInternals {
00062     
00067     template< class FieldRefType >
00068     class DoRoutes {
00069     public:
00071       typedef typename FieldRefType::node_type node_type;
00072             
00077       static void route( node_type *n, Field *f ) {
00078         FieldRefType::getField( n )->route( f ); 
00079       }
00080 
00085       static void unroute( node_type *n, Field *f ) {
00086         FieldRefType::getField( n )->unroute( f ); 
00087       }
00088     };
00089         
00093     template< class FieldRefType, class FieldRefs >
00094     class DoRoutes< pair< FieldRefType, FieldRefs > > {
00095     public:
00097       typedef typename FieldRefType::node_type node_type;       
00098             
00103       static void route( node_type *n, Field *f ) {
00104         FieldRefType::getField( n )->route( f ); 
00105         DoRoutes< FieldRefs >::route( n , f );
00106       }
00107 
00112       static void unroute( node_type *n, Field *f ) {
00113         DoRoutes< FieldRefs >::unroute( n , f );
00114         FieldRefType::getField( n )->unroute( f ); 
00115       }
00116     };
00117 
00124     template< class BaseField, class FieldRefs >
00125     class DependentNodeFieldBase: public BaseField {
00126     public:
00127       typedef typename FieldRefs::node_type fr_node_type; 
00128             
00130       DependentNodeFieldBase() {
00131         event_field.reset( new EventField( this ) );
00132       }
00133             
00135       //            DependentNodeField( Node *_value ) : 
00136       //                BaseFieldType( _value ) {
00137       //                event_field.reset( new EventField( this ) );
00138       //                }
00139             
00140     protected:
00147       class EventField: public AutoUpdate< Field > {
00148       public:
00151         EventField( Field *f ):
00152           field( f ) {
00153           name = "EventField";
00154         }
00155 
00157         virtual void update() {
00158           field->touch();
00159         }
00161         Field *field;
00162       };
00163             
00166       auto_ptr< EventField > event_field;
00167     };
00168 
00175     template< class BaseField, class FieldRefs, bool DynamicCast = false >
00176     class DependentNodeField: public DependentNodeFieldBase< BaseField, FieldRefs > {
00177     protected:
00178       typedef typename FieldRefs::node_type fr_node_type;
00179 
00183       virtual void onAdd( Node *n ) {
00184         BaseField::onAdd( n );
00185         fr_node_type *node = static_cast< fr_node_type * >( n );
00186         if( node )
00187         DoRoutes< FieldRefs >::route( node,
00188                                       this->event_field.get() );
00189       }
00190             
00191             
00195       virtual void onRemove( Node *n ) {
00196         fr_node_type *node = static_cast< fr_node_type * >( n );
00197         if( node )
00198         DoRoutes< FieldRefs >::unroute( node, 
00199                                         this->event_field.get() );
00200         BaseField::onRemove( n );
00201       }
00202     };
00203 
00204     template< class BaseField, class FieldRefs >
00205     class DependentNodeField< BaseField, FieldRefs, true >: public DependentNodeFieldBase< BaseField, FieldRefs > {
00206     protected:
00207       typedef typename FieldRefs::node_type fr_node_type;
00208 
00212       virtual void onAdd( Node *n ) {
00213         BaseField::onAdd( n );
00214         fr_node_type *node = dynamic_cast< fr_node_type * >( n );
00215         if( node )
00216         DoRoutes< FieldRefs >::route( node,
00217                                       this->event_field.get() );
00218       }
00219             
00220             
00224       virtual void onRemove( Node *n ) {
00225         fr_node_type *node = dynamic_cast< fr_node_type * >( n );
00226         if( node )
00227         DoRoutes< FieldRefs >::unroute( node, 
00228                                         this->event_field.get() );
00229         BaseField::onRemove( n );
00230       }
00231     };
00232   }
00290   template< class NodeType, class FieldRefs = void, bool DynamicCast = false > 
00291   class DependentSFNode: 
00292     public FieldInternals::DependentNodeField< 
00293     TypedSFNode< NodeType >,
00294     FieldRefs, DynamicCast > {
00295   public:
00296         
00298     DependentSFNode(){}
00299 
00301     ~DependentSFNode(){
00302       this->value = NULL;
00303     }
00304 
00306     //        DependentSFNode( Node *_value ) : 
00307     //            FieldInternals::DependentNodeField< TypedSFNode< NodeType >,
00308     //                           FieldRefs >( _value ) {}
00309         
00310   };
00311 
00315   template< class FieldRefs, bool DynamicCast > 
00316   class DependentSFNode< FieldRefs, void, DynamicCast >: 
00317     public FieldInternals::DependentNodeField< 
00318     TypedSFNode< typename FieldInternals::DoRoutes< FieldRefs >::node_type >,
00319     FieldRefs, DynamicCast >  {
00320   public:
00321         
00323     DependentSFNode(){}
00324     ~DependentSFNode(){ 
00325       this->value = NULL;
00326     }
00327 
00329     //        DependentSFNode( Node *_value ) : 
00330     //            FieldInternals::DependentNodeField< 
00331     //            TypedSFNode< typename DoRoutes< FieldRefs >::node_type >,
00332     //            FieldRefs >( _value ) {}
00333         
00334   };
00335 
00342   template< class NodeType, class FieldRefs = void, bool DynamicCast = false > 
00343   class DependentMFNode: 
00344     public FieldInternals::DependentNodeField< 
00345     TypedMFNode< NodeType >,
00346     FieldRefs,
00347     DynamicCast > {
00348   public:
00349         
00351     DependentMFNode(){}
00352       
00354     ~DependentMFNode(){
00355       this->clear( this->ownerId() );
00356     }
00357 
00359     //        DependentMFNode( MFNode::size_type size ) : 
00360     //            FieldInternals::DependentNodeField< 
00361     //            TypedMFNode< typename DoRoutes< FieldRefs >::node_type >,
00362     //            FieldRefs >( size ){}
00363   };
00364     
00368   template< class FieldRefs, bool DynamicCast > 
00369   class DependentMFNode< FieldRefs, void, DynamicCast >: 
00370     public FieldInternals::DependentNodeField< 
00371     TypedMFNode< typename FieldInternals::DoRoutes< FieldRefs >::node_type >,
00372     FieldRefs,
00373     DynamicCast >  {
00374   public:
00375         
00377     DependentMFNode(){}
00378 
00380     ~DependentMFNode(){
00381       this->clear( this->ownerId() );
00382     }
00383         
00385     //        DependentMFNode( MFNode::size_type size ) : 
00386     //            FieldInternals::DependentNodeField< 
00387     //              TypedMFNode< typename FieldInternals::DoRoutes< FieldRefs >::node_type >,
00388     //            FieldRefs >( size ){}
00389         
00390   };
00391 }
00392 
00393 #endif

Generated on Thu Aug 24 12:38:32 2006 for H3D API by  doxygen 1.4.5