contrib/gel/vtol/vtol_topology_object.h
Go to the documentation of this file.
00001 // This is gel/vtol/vtol_topology_object.h
00002 #ifndef topology_object_h_
00003 #define topology_object_h_
00004 //:
00005 // \file
00006 // \brief base class for topology objects
00007 // \author Patricia A. Vrobel.
00008 
00009 #include <vtol/vtol_topology_object_sptr.h>
00010 #include <vsol/vsol_spatial_object_2d.h> // parent class
00011 #include <vcl_vector.h>
00012 #include <vcl_list.h>
00013 #include <vcl_iosfwd.h>
00014 #include <vtol/vtol_vertex_sptr.h>
00015 #include <vtol/vtol_zero_chain_sptr.h>
00016 #include <vtol/vtol_edge_sptr.h>
00017 #include <vtol/vtol_one_chain_sptr.h>
00018 #include <vtol/vtol_face_sptr.h>
00019 #include <vtol/vtol_two_chain_sptr.h>
00020 #include <vtol/vtol_block_sptr.h>
00021 #include <vtol/vtol_chain_sptr.h>
00022 class vtol_topology_cache;
00023 
00024 // Useful typedefs
00025 typedef vcl_vector<vtol_topology_object_sptr> topology_list;
00026 typedef vcl_vector<vtol_vertex_sptr>          vertex_list;
00027 typedef vcl_vector<vtol_zero_chain_sptr>      zero_chain_list;
00028 typedef vcl_vector<vtol_edge_sptr>            edge_list;
00029 typedef vcl_vector<vtol_one_chain_sptr>       one_chain_list;
00030 typedef vcl_vector<vtol_face_sptr>            face_list;
00031 typedef vcl_vector<vtol_two_chain_sptr>       two_chain_list;
00032 typedef vcl_vector<vtol_block_sptr>           block_list;
00033 typedef vcl_vector<vtol_chain_sptr>           chain_list;
00034 
00035 //*****************************************************************************
00036 // ALL THE DERIVED AND NON-ABSTRACT CLASSES OF THIS CLASS MUST CALL
00037 // unlink_all_inferiors() IN THEIR DESTRUCTOR
00038 // unlink_all_inferiors() CANT BE CALLED DIRECTLY IN THIS CLASS, OTHERWISE
00039 // BAD VERSIONS OF METHODS SHOULD BE CALLED (C++ IS STUPID !)
00040 //*****************************************************************************
00041 
00042 //: Base class for topology objects
00043 // The vtol_topology_object class is the interface base class for all
00044 // topological entities. There are only access methods in this class.
00045 // vtol_topology_object inherits from vtol_spatial_object, which is
00046 // the base class for all topology and geometry.
00047 //
00048 // The topology class hierarchy:
00049 // \verbatim
00050 //                             vtol_topology_object
00051 //                                   |
00052 //             ---------------------------------------------------
00053 //             |        |       |       |       |       |        |
00054 //         vertex  zero_chain  edge  one_chain  face  two_chain  block
00055 //             |                |               |
00056 //        vertex_2d           edge_2d          face_2d
00057 // \endverbatim
00058 //
00059 // (Actually, one_chain and two_chain share a common parent class vtol_chain,
00060 //  but that's just a matter of convenience; conceptually, the scheme is this.)
00061 //
00062 // \verbatim
00063 // Incidence of:
00064 //       (vsol_point)      (vsol_curve)     (vsol_surface)    (vsol_volume)
00065 // Directed
00066 // Sequence of:       vertex           edge             face
00067 //
00068 // \endverbatim
00069 //
00070 // The vertex, edge and face entities account for incidence between
00071 // points, curves and surfaces, respectively. For example, two vtol_edge(s)
00072 // are incident at exactly one vtol_vertex.  That is, an edge does not
00073 // intersect itself or another edge, except possibly at a vertex.
00074 // The chain entities are directed sequences which define composite
00075 // structures. Each element of the chain has a sign associated with
00076 // with it denoting the "direction" of use in a boundary traversal.
00077 // For example, a closed vtol_one_chain (a 1-cycle) forms the boundary of
00078 // a surface region. Two adjacent surface regions (vtol_face(s)) use an
00079 // edge in the opposite sense in their bounding 1-chains.
00080 //
00081 // The data member "inferiors_" stores a list of all topology objects of
00082 // the type "below" the current one, which form the boundary of this one.
00083 // All these objects should have the current object listed in their "superiors_"
00084 // list.  It is the responsibility of the superior to break the link with its
00085 // inferior, not vice versa, hence conceptually the "superiors_" entries are
00086 // under control of the referred superior object.  Otherwise said, an object
00087 // cannot live without its inferiors (and will disappear when its inferiors
00088 // disappear), while an object can live without its superiors (and is just
00089 // notified of their appearance and disappearance by the entries listed in
00090 // its superiors_ list).
00091 //
00092 // As a consequence, the "inferior" does not obtain a new time stamp when its
00093 // superiors change (hence its "superiors_" list is mutable).
00094 // This also explains why the "superiors_" list consists of ordinary pointers,
00095 // not smart pointers:  the refcount toggling is done from superior to
00096 // inferior (which requires its inferiors to be kept alive), not from inferior
00097 // to superior (which need not bother about its superiors' existence).
00098 //
00099 // \author
00100 //    Patricia A. Vrobel.
00101 // \verbatim
00102 //  Modifications
00103 //   ported to vxl by Luis E. Galup
00104 //   JLM November 2002 - added a local bounding box method
00105 //   dec.2002 -Peter Vanroose- added chain_list (typedef) and cast_to_chain()
00106 //   dec.2002 -Peter Vanroose- link_inferior() now takes smart pointer argument
00107 //   sep.2004 -Peter Vanroose- made methods returning the inf_sup cache "const"
00108 // \endverbatim
00109 
00110 class vtol_topology_object : public vsol_spatial_object_2d
00111 {
00112   //***************************************************************************
00113   // Data members
00114   //***************************************************************************
00115 
00116   //---------------------------------------------------------------------------
00117   // Description: cache system
00118   //---------------------------------------------------------------------------
00119   mutable vtol_topology_cache *inf_sup_cache_;
00120 
00121  protected:
00122 
00123   //---------------------------------------------------------------------------
00124   // Description: array of superiors
00125   //---------------------------------------------------------------------------
00126   vcl_list<vtol_topology_object*> superiors_;
00127 
00128   //---------------------------------------------------------------------------
00129   // Description: array of inferiors
00130   //---------------------------------------------------------------------------
00131   topology_list inferiors_;
00132 
00133   enum vtol_topology_object_type
00134   { TOPOLOGY_NO_TYPE=0,
00135     VERTEX,
00136     ZEROCHAIN,
00137     EDGE,
00138     ONECHAIN,
00139     FACE,
00140     TRIFACE,
00141     INTENSITYFACE,
00142     INTENSITYFACE3D,
00143     DDBINTENSITYFACE,
00144     TWOCHAIN,
00145     TRIMESHTWOCHAIN,
00146     BLOCK,
00147     NUM_TOPOLOGYOBJECT_TYPES
00148   };
00149  private: // has been superseded by is_a()
00150   //: Return the topology type
00151   // To be overridden by all subclasses
00152   virtual vtol_topology_object_type topology_type() const { return TOPOLOGY_NO_TYPE; }
00153 
00154  public:
00155   //***************************************************************************
00156   // Initialization
00157   //***************************************************************************
00158 
00159   //---------------------------------------------------------------------------
00160   //: Default constructor
00161   //---------------------------------------------------------------------------
00162   vtol_topology_object();
00163 
00164   //---------------------------------------------------------------------------
00165   //: Constructor with given sizes for arrays of inferiors and superiors
00166   //---------------------------------------------------------------------------
00167   vtol_topology_object(int num_inferiors, int num_superiors);
00168 
00169  protected:
00170   //---------------------------------------------------------------------------
00171   //: Destructor
00172   //---------------------------------------------------------------------------
00173   virtual ~vtol_topology_object();
00174 
00175  public:
00176   //***************************************************************************
00177   // Replaces dynamic_cast<T>
00178   //***************************************************************************
00179   virtual vtol_topology_object *cast_to_topology_object() { return this; }
00180   virtual const vtol_topology_object*cast_to_topology_object()const{return this;}
00181 
00182   //---------------------------------------------------------------------------
00183   //: Return `this' if `this' is a vertex, 0 otherwise
00184   //---------------------------------------------------------------------------
00185   virtual const vtol_vertex *cast_to_vertex() const { return 0; }
00186 
00187   //---------------------------------------------------------------------------
00188   //: Return `this' if `this' is a vertex, 0 otherwise
00189   //---------------------------------------------------------------------------
00190   virtual vtol_vertex *cast_to_vertex() { return 0; }
00191 
00192   //---------------------------------------------------------------------------
00193   //: Return `this' if `this' is a zero_chain, 0 otherwise
00194   //---------------------------------------------------------------------------
00195   virtual const vtol_zero_chain *cast_to_zero_chain() const { return 0; }
00196 
00197   //---------------------------------------------------------------------------
00198   //: Return `this' if `this' is a zero_chain, 0 otherwise
00199   //---------------------------------------------------------------------------
00200   virtual vtol_zero_chain *cast_to_zero_chain() { return 0; }
00201 
00202   //---------------------------------------------------------------------------
00203   //: Return `this' if `this' is an edge, 0 otherwise
00204   //---------------------------------------------------------------------------
00205   virtual const vtol_edge *cast_to_edge() const { return 0; }
00206 
00207   //---------------------------------------------------------------------------
00208   //: Return `this' if `this' is an edge, 0 otherwise
00209   //---------------------------------------------------------------------------
00210   virtual vtol_edge *cast_to_edge() { return 0; }
00211 
00212   //---------------------------------------------------------------------------
00213   //: Return `this' if `this' is a chain, 0 otherwise
00214   //---------------------------------------------------------------------------
00215   virtual const vtol_chain *cast_to_chain() const { return 0; }
00216 
00217   //---------------------------------------------------------------------------
00218   //: Return `this' if `this' is a chain, 0 otherwise
00219   //---------------------------------------------------------------------------
00220   virtual vtol_chain *cast_to_chain() { return 0; }
00221 
00222   //---------------------------------------------------------------------------
00223   //: Return `this' if `this' is a one_chain, 0 otherwise
00224   //---------------------------------------------------------------------------
00225   virtual const vtol_one_chain *cast_to_one_chain() const { return 0; }
00226 
00227   //---------------------------------------------------------------------------
00228   //: Return `this' if `this' is a one_chain, 0 otherwise
00229   //---------------------------------------------------------------------------
00230   virtual vtol_one_chain *cast_to_one_chain() { return 0; }
00231 
00232   //---------------------------------------------------------------------------
00233   //: Return `this' if `this' is a face, 0 otherwise
00234   //---------------------------------------------------------------------------
00235   virtual const vtol_face *cast_to_face() const { return 0; }
00236 
00237   //---------------------------------------------------------------------------
00238   //: Return `this' if `this' is a face, 0 otherwise
00239   //---------------------------------------------------------------------------
00240   virtual vtol_face *cast_to_face() { return 0; }
00241 
00242   //---------------------------------------------------------------------------
00243   //: Return `this' if `this' is a two_chain, 0 otherwise
00244   //---------------------------------------------------------------------------
00245   virtual const vtol_two_chain *cast_to_two_chain() const { return 0; }
00246 
00247   //---------------------------------------------------------------------------
00248   //: Return `this' if `this' is a two_chain, 0 otherwise
00249   //---------------------------------------------------------------------------
00250   virtual vtol_two_chain *cast_to_two_chain() { return 0; }
00251 
00252   //---------------------------------------------------------------------------
00253   //: Return `this' if `this' is a block, 0 otherwise
00254   //---------------------------------------------------------------------------
00255   virtual const vtol_block *cast_to_block() const { return 0; }
00256 
00257   //---------------------------------------------------------------------------
00258   //: Return `this' if `this' is a block, 0 otherwise
00259   //---------------------------------------------------------------------------
00260   virtual vtol_block *cast_to_block() { return 0; }
00261 
00262   //***************************************************************************
00263   // Status report
00264   //***************************************************************************
00265 
00266   //---------------------------------------------------------------------------
00267   //: Is `inferior' type valid for `this' ?
00268   //---------------------------------------------------------------------------
00269   virtual bool valid_inferior_type(vtol_topology_object const* inf) const = 0;
00270 
00271   //---------------------------------------------------------------------------
00272   //: Is `superior' type valid for `this' ?
00273   //---------------------------------------------------------------------------
00274   inline bool valid_superior_type(vtol_topology_object const* sup) const
00275   { return sup->valid_inferior_type(this); }
00276 
00277   //---------------------------------------------------------------------------
00278   //: Is `inferior' already an inferior of `this' ?
00279   //---------------------------------------------------------------------------
00280   bool is_inferior(vtol_topology_object_sptr inferior) const;
00281 
00282   //---------------------------------------------------------------------------
00283   //: Is `superior' already a superior of `this' ?
00284   //---------------------------------------------------------------------------
00285   bool is_superior(vtol_topology_object* const& superior) const;
00286 
00287   //---------------------------------------------------------------------------
00288   //: Number of inferiors
00289   //---------------------------------------------------------------------------
00290   int numinf() const { return inferiors()->size(); }
00291 
00292   //---------------------------------------------------------------------------
00293   //: Number of superiors
00294   //---------------------------------------------------------------------------
00295   int numsup() const { return superiors_.size(); }
00296 
00297   //---------------------------------------------------------------------------
00298   //: Return the superiors list (must be deallocated after use)
00299   //---------------------------------------------------------------------------
00300  private:
00301   const topology_list *superiors() const;
00302  public:
00303   const vcl_list<vtol_topology_object*> *superiors_list() const {return &superiors_;}
00304 
00305   //---------------------------------------------------------------------------
00306   //: Return the inferiors list
00307   //---------------------------------------------------------------------------
00308         topology_list *inferiors() { return &inferiors_; }
00309   const topology_list *inferiors() const { return &inferiors_; }
00310 
00311   //---------------------------------------------------------------------------
00312   //: Return the spatial type
00313   //---------------------------------------------------------------------------
00314   virtual vsol_spatial_object_2d_type spatial_type()const{return TOPOLOGYOBJECT;}
00315 
00316   //***************************************************************************
00317   // Basic operations
00318   //***************************************************************************
00319 
00320   //---------------------------------------------------------------------------
00321   //: Link `this' with an inferior `inferior'
00322   //  REQUIRE: valid_inferior_type(inferior) and !is_inferior(inferior)
00323   //---------------------------------------------------------------------------
00324   void link_inferior(vtol_topology_object_sptr inferior);
00325 
00326   //---------------------------------------------------------------------------
00327   //: Unlink `this' from the inferior `inferior'
00328   //  REQUIRE: valid_inferior_type(inferior) and is_inferior(inferior)
00329   //---------------------------------------------------------------------------
00330   void unlink_inferior(vtol_topology_object_sptr inferior);
00331 
00332   //---------------------------------------------------------------------------
00333   //: Unlink `this' from all its inferiors
00334   //---------------------------------------------------------------------------
00335   void unlink_all_inferiors();
00336 
00337   //---------------------------------------------------------------------------
00338   //: Unlink `this' of the network
00339   //---------------------------------------------------------------------------
00340   void unlink();
00341 
00342   //: Get list of vertices
00343   void vertices(vertex_list &list) const;
00344   //: Get list of zero chains
00345   void zero_chains(zero_chain_list &list) const;
00346   //: Get list of edges
00347   void edges(edge_list &list) const;
00348   //: Get list of one chains
00349   void one_chains(one_chain_list &list) const;
00350   //: Get list of faces
00351   void faces(face_list &list) const;
00352   //: Get list of two chains
00353   void two_chains(two_chain_list &list) const;
00354   //: Get list of blocks
00355   void blocks(block_list &list) const;
00356  private:
00357   //---------------------------------------------------------------------------
00358   //: Get list of vertices
00359   // returned list must be deleted after use.
00360   // \deprecated - use vertices(list) instead
00361   //---------------------------------------------------------------------------
00362   vertex_list *vertices() const;
00363 
00364   //---------------------------------------------------------------------------
00365   //: Get list of zero chains
00366   // returned list must be deleted after use.
00367   // \deprecated - use zero_chains(list) instead
00368   //---------------------------------------------------------------------------
00369   zero_chain_list *zero_chains() const;
00370 
00371   //---------------------------------------------------------------------------
00372   //: Get list of edges
00373   // returned list must be deleted after use.
00374   // \deprecated - use edges(list) instead
00375   //---------------------------------------------------------------------------
00376   edge_list *edges() const;
00377 
00378   //---------------------------------------------------------------------------
00379   //: Get list of one chains
00380   // returned list must be deleted after use.
00381   // \deprecated - use one_chains(list) instead
00382   //---------------------------------------------------------------------------
00383   one_chain_list *one_chains() const;
00384 
00385   //---------------------------------------------------------------------------
00386   //: Get list of faces
00387   // returned list must be deleted after use.
00388   // \deprecated - use faces(list) instead
00389   //---------------------------------------------------------------------------
00390   face_list *faces() const;
00391 
00392   //---------------------------------------------------------------------------
00393   //: Get list of two chains
00394   // returned list must be deleted after use.
00395   // \deprecated - use two_chains(list) instead
00396   //---------------------------------------------------------------------------
00397   two_chain_list *two_chains() const;
00398 
00399   //---------------------------------------------------------------------------
00400   //: Get list of blocks
00401   // returned list must be deleted after use.
00402   // \deprecated - use blocks(list) instead
00403   //---------------------------------------------------------------------------
00404   block_list *blocks() const;
00405  public:
00406   //---------------------------------------------------------------------------
00407   //: print and describe the objects
00408   //---------------------------------------------------------------------------
00409   virtual void print(vcl_ostream &strm=vcl_cout) const;
00410   void describe_inferiors(vcl_ostream &strm=vcl_cout, int blanking=0) const;
00411   void describe_superiors(vcl_ostream &strm=vcl_cout, int blanking=0) const;
00412   virtual void describe(vcl_ostream &strm=vcl_cout, int blanking=0) const;
00413 
00414   virtual void compute_bounding_box() const; //A local implementation
00415 
00416   //---------------------------------------------------------------------------
00417   //: compute lists of vertices
00418   // \warning should not be used by clients
00419   //---------------------------------------------------------------------------
00420   virtual vcl_vector<vtol_vertex*> *compute_vertices();
00421 
00422   //---------------------------------------------------------------------------
00423   //: compute lists of zero chains
00424   // \warning should not be used by clients
00425   //---------------------------------------------------------------------------
00426   virtual vcl_vector<vtol_zero_chain*> *compute_zero_chains();
00427 
00428   //---------------------------------------------------------------------------
00429   //: compute lists of edges
00430   // \warning should not be used by clients
00431   //---------------------------------------------------------------------------
00432   virtual vcl_vector<vtol_edge*> *compute_edges();
00433 
00434   //---------------------------------------------------------------------------
00435   //: compute lists of one chains
00436   // \warning should not be used by clients
00437   //---------------------------------------------------------------------------
00438   virtual vcl_vector<vtol_one_chain*> *compute_one_chains();
00439 
00440   //---------------------------------------------------------------------------
00441   //: compute lists of faces
00442   // \warning should not be used by clients
00443   //---------------------------------------------------------------------------
00444   virtual vcl_vector<vtol_face*> *compute_faces();
00445 
00446   //---------------------------------------------------------------------------
00447   //: compute lists of two chains
00448   // \warning should not be used by clients
00449   //---------------------------------------------------------------------------
00450   virtual vcl_vector<vtol_two_chain*> *compute_two_chains();
00451 
00452   //---------------------------------------------------------------------------
00453   //: compute lists of blocks
00454   // \warning should not be used by clients
00455   //---------------------------------------------------------------------------
00456   virtual vcl_vector<vtol_block*> *compute_blocks();
00457 
00458  private:
00459   // declare a friend class
00460   friend class vtol_topology_cache;
00461 };
00462 
00463 #endif // topology_object_h_