Itk::FEMObject

From KitwarePublic
Jump to navigationJump to search

Return to Refactoring itk::FEM_framework - V4

We are proposing to develop a new ITK object (itk::FEMObject) that will hold the finite element model and will have a parallel spatial object (itk::FEMSpatialObject). This will match the current implementation for itk::Mesh and itk::MeshSpatialObject.


Proposed itk::FEMObject Class

<source lang="cpp"> template <unsigned int VDimension = 3> class ITK_EXPORT FEMObject : public DataObject { public:

 /** Standard class typedefs. */
 typedef PointSet                  Self;
 typedef DataObject                Superclass;
 typedef SmartPointer<Self>        Pointer;
 typedef SmartPointer<const Self>  ConstPointer;
   
 /** Method for creation through the object factory. */
 itkNewMacro(Self);
 /** Standard part of every itk Object. */
 itkTypeMacro(FEMObject, DataObject);
 itkStaticConstMacro(FEMDimension, unsigned int, VPointDimension);
 itkStaticConstMacro(MaxDimensions, unsigned int, 3);
 typedef unsigned long ElementIdentifier;
 typedef unsigned long NodeIdentifier;
 typedef unsigned long LoadIdentifier;
 typedef unsigned long MaterialIdentifier;
 typedef VectorContainer< ElementIdentifier, Element >   ElementContainer;
 typedef VectorContainer< NodeIdentifier, Node >         NodeContainer;
 typedef VectorContainer< LoadIdentifier, Load >         LoadContainer;
 typedef VectorContainer< MaterialIdentifier, Material > MaterialContainer;
 /** Create types that are pointers to each of the container types. */
 typedef typename ElementContainer::Pointer             ElementContainerPointer;
 typedef typename ElementContainer::ConstPointer        ElementContainerConstPointer;
 typedef typename NodeContainer::Pointer                NodeContainerPointer;
 typedef typename NodeContainer::ConstPointer           NodeContainerConstPointer;
 typedef typename LoadContainer::Pointer                LoadContainerPointer;
 typedef typename LoadContainer::ConstPointer           LoadContainerConstPointer;
 typedef typename MaterialContainer::Pointer            MaterialContainerPointer;
 typedef typename MaterialContainer::ConstPointer       MaterialContainerConstPointer;


 /** Create types that are iterators for each of the container types. */
 typedef typename
         ElementContainerPointer::ConstIterator         ElementContainerConstIterator;
 typedef typename
         ElementContainerPointer::Iterator              ElementContainerIterator;
 typedef typename
         NodeContainerPointer::ConstIterator            NodeContainerConstIterator;
 typedef typename
         NodeContainerPointer::Iterator                 NodeContainerIterator;
 typedef typename
         LoadContainerPointer::ConstIterator            LoadContainerConstIterator;
 typedef typename
         LoadContainerPointer::Iterator                 LoadContainerIterator;
 typedef typename
         MaterialContainerPointer::ConstIterator        MaterialContainerConstIterator;
 typedef typename
         MaterialContainerPointer::Iterator             MaterialContainerIterator;
 /* ADD OTHER Public Methods */

protected:

 /** Constructor for use by New() method. */
 FEMObject();
 ~FEMObject();
 void PrintSelf(std::ostream& os, Indent indent) const;


private:

 FEMObject(const Self&); //purposely not implemented
 void operator=(const Self&); //purposely not implemented
 ElementContainerPointer   m_ElementContainer;
 NodeContainerPointer      m_NodeContainer;
 LoadContainerPointer      m_LoadContainer;
 MaterialContainerPointer  m_MaterialContainer;

}; // End Class: FEMObject


</source>


Proposed itk::FEMSpatialObject Class

<source lang="cpp"> template <class TFEM = FEMObject<int> > class ITK_EXPORT FEMSpatialObject

public SpatialObject< ::itk::GetMeshDimension<TFEM>::FEMDimension >

{

public:

 typedef double ScalarType; 
 typedef FEMSpatialObject< TMesh>                  Self;
  
 itkStaticConstMacro(Dimension, unsigned int,TMesh::PointDimension);
 typedef SpatialObject< itkGetStaticConstMacro(Dimension) > Superclass;
 typedef SmartPointer< Self >                       Pointer;
 typedef SmartPointer< const Self >                 ConstPointer;
 typedef TFEM                                       FEMObjectType;
 typedef typename FEMObjectType::Pointer            FEMObjectPointer;
 typedef typename Superclass::TransformType         TransformType;
 typedef typename Superclass::PointType             PointType;
 typedef typename Superclass::BoundingBoxType       BoundingBoxType;
 typedef VectorContainer< unsigned long, PointType> PointContainerType;
 typedef typename PointContainerType::Pointer       PointContainerPointer;
 /** Method for creation through the object factory. */
 itkNewMacro( Self );
 /** Run-time type information (and related methods). */
 itkTypeMacro( FEMSpatialObject, SpatialObject );
 /** Set the Mesh. */
 void SetFEMObject( FEMObjectType * Mesh );
 /** Get a pointer to the Mesh currently attached to the object. */
 FEMObjectType * GetMesh( void );
 /** Return true if the object is evaluable at the requested point, 
  *  and else otherwise. */
 bool IsEvaluableAt( const PointType & point, 
                     unsigned int depth=0, char *name=NULL) const;
 /**Should this be retained ??? */
 /** Returns the value of the Mesh at the requested point. 
  *  If the point is not inside the object, then an exception is thrown.
  * \sa ExceptionObject */
 //bool ValueAt( const PointType & point, double & value, 
 //              unsigned int depth=0, char *name=NULL) const;
 
 /** Returns true if the point is inside, false otherwise. */
 bool IsInside( const PointType & point,
                unsigned int depth, char *name) const;
 /** Test whether a point is inside or outside the object 
  *  For computational speed purposes, it is faster if the method does not
  *  check the name of the class and the current depth */ 
 virtual bool IsInside( const PointType & point) const;

 /** Compute the boundaries of the spatial object. */
 bool ComputeLocalBoundingBox() const;
 /** Returns the latest modified time of the object and its component. */
 unsigned long GetMTime( void ) const;
 /** Set/Get the precision for the IsInside function. 
  *  This is used when the cell is a triangle, in this case, it's more likely 
  *  that the given point will not be falling exactly on the triangle surface.
  *  If the distance from the point to the surface is <= to 
  *  m_IsInsidePrecision the point is considered inside the mesh. 
  *  The default value is 1. */
 itkSetMacro(IsInsidePrecision, double);
 itkGetMacro(IsInsidePrecision, double);

protected:

 FEMObjectPointer m_FEMObject;
 double      m_IsInsidePrecision;
 FEMSpatialObject();
 virtual ~FEMSpatialObject();
 void PrintSelf( std::ostream& os, Indent indent ) const;

}; </source>


Proposed I/O Support

Use Spatial Object Framework for supporting input/output. Use original FEM I/O format to encode the actual model information. We will used the format previously provided by the Read() and Write() methods in each class deriving from itk::fem::FEMLightObject. This functionality will be moved to the MetaIO. Here is an outline of these changes.

  1. Create Utilities/MetaIO/metaFEM.cxx and Utilities/MetaIO/metaFEM.h - Take functionality from the classes that derive from FEMLightObject. Add support for binary point data.
  2. Create SpatialObject/itkMetaFEMConverter.h and SpatialObject/itkMetaFEMConverter.txx
  3. Update to SpatialObject/itkMetaSceneConverter.txx
    1. Include itkMetaFEMConverter.h
    2. Include itkFEMSpatialObject.h
    3. In CreateSpatialObjectScene() - add type comparison between lines 155 and 294
    4. In CreateMetaScene() - add type comparison between lines 344 and 584


itk::MetaFEMConverter

<source lang="cpp"> template <unsigned int NDimensions> class ITK_EXPORT MetaFEMConverter {

public:

 MetaFEMConverter();
 ~MetaFEMConverter() {};
 typedef itk::FEMObject<NDimensions>             FEMObjectType;
 typedef itk::FEMSpatialObject<MeshType>         SpatialObjectType;
 typedef typename SpatialObjectType::TransformType TransformType;
 typedef typename SpatialObjectType::Pointer SpatialObjectPointer;
 SpatialObjectPointer ReadMeta(const char* name);
 bool WriteMeta(SpatialObjectType* spatialObject,const char* name);
 SpatialObjectPointer MetaFEMToFEMSpatialObject(MetaFEM * FEM);
 MetaFEM* FEMSpatialObjectToMetaFEM(SpatialObjectType * spatialObject);

};

</source>

MetaFEM

Similar to metaMesh but with additions for the FEM specific information.