1 // File : MEDMEM_Grid.hxx
2 // Created : Wed Dec 18 08:35:26 2002
3 // Descr : class containing structured mesh data
5 // Author : Edward AGAPOV (eap)
6 // Project : SALOME Pro
8 // Copyright : Open CASCADE
11 #ifndef MEDMEM_Grid_HeaderFile
12 #define MEDMEM_Grid_HeaderFile
14 #include "MEDMEM_Mesh.hxx"
16 // class containing structured mesh data
19 class GRID: public MESH
22 //-----------------------//
24 //-----------------------//
26 // 1. grid type: MED_CARTESIAN, MED_POLAR, MED_BODY_FITTED
27 // med_grid_type _gridType;
29 // 1. grid type MED_GRILLE_CARTESIENNE, MED_GRILLE_POLAIRE,
30 // MED_GRILLE_STANDARD
31 med_type_grille _gridType;
33 // 2. node coordinates
34 // For MED_BODY_FITTED MESH::_coordinate is used
36 // 2.1. i component array: X for MED_CARTESIAN, R for MED_POLAR
39 // 2.2. j component array: Y for MED_CARTESIAN, Theta for MED_POLAR
42 // 2.3. k component array: Z for both MED_CARTESIAN and MED_POLAR
46 // 3. flags to know that _coordinates and _connectivity of MESH are filled
47 bool _is_coordinates_filled;
48 bool _is_connectivity_filled;
50 //-----------------------//
52 //-----------------------//
54 CONNECTIVITY * makeConnectivity (const medEntityMesh Entity,
55 const medGeometryElement Geometry,
56 const int NbEntities, const int NbNodes,
57 int * NodeNumbers) const ;
58 // creates nodal connectivity
61 // Suppose a READ Driver to do the following except filling _[ijk]Array's
62 // 1) fill MESH fields:
66 // * _numberOfNodesFamilies, _numberOfCellsFamilies, ect
67 // * _familyNode, _familyCell, etc
68 // * _numberOfNodesGroups, _numberOfCellsGroups, etc
69 // * _groupNode, _groupCell, etc
71 // 2) create MESH::_coordinate without setting _coordinate->_coordinate and set:
72 // * _coordinate->_coordinateSystem
73 // * _coordinate->_coordinateName
74 // * _coordinate->_coordinateUnit
78 //-----------------------//
80 //-----------------------//
83 // GRID(const med_grid_type type);
84 GRID(const med_type_grille type);
86 GRID( driverTypes driverType, const string & fileName="",const string & meshName="");
87 GRID & operator=(const GRID &m);
91 void fillCoordinates() const ;
92 void fillConnectivity() const ;
93 // fill _coordinates and _connectivity of MESH if not yet done
95 inline void makeUnstructured();
96 // fill both coordinates and connectivity of MESH
98 void fillMeshAfterRead();
99 // fill some fields (_numberOfNodes, etc.) after reading
101 void writeUnstructured(int index=0, const string & driverName = "");
102 // write a Grid as an Unstructured mesh
104 void read(int index=0);
106 // API Methods returning fields of MESH that are filled while reading.
107 // So they need not to be redefined
109 // string getName() const;
110 // int getSpaceDimension();
111 // int getMeshDimension();
112 // string getCoordinatesSystem();
113 // int getNumberOfNodes();
114 // string * getCoordinatesNames();
115 // string * getCoordinatesUnits();
116 // int getNumberOfFamilies(medEntityMesh Entity);
117 // vector<FAMILY*> getFamilies(medEntityMesh Entity);
118 // FAMILY* getFamily(medEntityMesh Entity,int i);
119 // int getNumberOfGroups(medEntityMesh Entity);
120 // vector<GROUP*> getGroups(medEntityMesh Entity);
121 // GROUP* getGroup(medEntityMesh Entity,int i);
124 // Since a MESH itself knows if it is a GRID, it calls fillConnectivity()
125 // or fillCoordinates() whenever needed. So no redifinition of the following methods
127 // const double * getCoordinates(medModeSwitch Mode);
128 // COORDINATE * getCoordinateptr();
129 // const double getCoordinate(int Number,int Axis);
130 // int getNumberOfTypes(medEntityMesh Entity);
131 // medGeometryElement * getTypes(medEntityMesh Entity);
132 // CELLMODEL * getCellsTypes(medEntityMesh Entity);
133 // medGeometryElement getElementType(medEntityMesh Entity,int Number) ;
134 // int getNumberOfElements(medEntityMesh Entity,medGeometryElement Type);
135 // int getElementNumber(medConnectivity ConnectivityType, medEntityMesh Entity, medGeometryElement Type, int * connectivity) ;
136 // int * getGlobalNumberingIndex(medEntityMesh Entity);
137 // int * getConnectivity(medModeSwitch Mode,medConnectivity ConnectivityType,medEntityMesh Entity, medGeometryElement Type);
138 // int * getConnectivityIndex(medConnectivity ConnectivityType,medEntityMesh Entity);
139 // int * getReverseConnectivity(medConnectivity ConnectivityType);
140 // int * getReverseConnectivityIndex(medConnectivity ConnectivityType);
141 // bool existConnectivity(medConnectivity ConnectivityType,medEntityMesh Entity);
142 // void calculateConnectivity(medModeSwitch Mode,medConnectivity ConnectivityType,medEntityMesh Entity);
143 // FIELD<double>* getVolume(const SUPPORT * Support) throw (MEDEXCEPTION) ;
144 // FIELD<double>* getArea(const SUPPORT * Support) throw (MEDEXCEPTION) ;
145 // FIELD<double>* getLength(const SUPPORT * Support) throw (MEDEXCEPTION) ;
146 // FIELD<double>* getNormal(const SUPPORT * Support) throw (MEDEXCEPTION) ;
147 // FIELD<double>* getBarycenter(const SUPPORT * Support) throw (MEDEXCEPTION) ;
150 // Specific GRID methods
152 inline int getNodeNumber(const int i, const int j=0, const int k=0) const;
153 // return a NODE number by its position in the grid.
154 // WARNING: be carefull, there is no check that i,j,k are within a good range
155 // A good range is: 0 <= X < getArrayLength( X_Axis )
156 inline int getCellNumber(const int i, const int j=0, const int k=0) const ;
157 // return a CELL number by its position in the grid.
158 // WARNING: be carefull, there is no check that i,j,k are within a good range
159 // A good range is: 0 <= X < (getArrayLength( X_Axis )-1)
161 int getEdgeNumber(const int Axis, const int i, const int j=0, const int k=0) const throw (MEDEXCEPTION) ;
162 // return an EDGE number by its position in the grid.
163 // Axis [1,2,3] means one of directions: along i, j or k.
164 // It selects an edge of ones having same (i,j,k):
165 // * an EDGE going along given Axis.
166 // Exception for Axis out of range or when there is no edges in the grid (1D)
167 // WARNING: be carefull, there is no check that i,j,k are within a good range
169 // 0 <= X < (getArrayLength( X_Axis )-1)
170 // 0 <= X < getArrayLength( NOT_X_Axis )
172 int getFaceNumber(const int Axis, const int i, const int j=0, const int k=0) const throw (MEDEXCEPTION) ;
173 // return a FACE number by its position in the grid.
174 // Axis [1,2,3] means one of directions: along i, j or k.
175 // It selects a face of ones having same (i,j,k):
176 // * a FACE which is normal to given Axis
177 // Exception for Axis out of range or when there is no faces in the grid (1,2D)
178 // WARNING: be carefull, there is no check that i,j,k are within a good range
180 // 0 <= X < (getArrayLength( NOT_X_Axis )-1)
181 // 0 <= X < getArrayLength( X_Axis )
184 void getNodePosition(const int Number, int& i, int& j, int& k) const throw (MEDEXCEPTION) ;
185 void getCellPosition(const int Number, int& i, int& j, int& k) const throw (MEDEXCEPTION) ;
186 void getEdgePosition(const int Number, int& Axis, int& i, int& j, int& k) const throw (MEDEXCEPTION) ;
187 void getFacePosition(const int Number, int& Axis, int& i, int& j, int& k) const throw (MEDEXCEPTION) ;
188 // return position (i,j,k) of an entity #Number
189 // Axis: [1,2,3], see get*Number for details
190 // Exception for Number out of range
195 // inline med_grid_type getGridType() const;
196 // return MED_CARTESIAN, MED_POLAR or MED_BODY_FITTED
198 inline med_type_grille getGridType() const;
199 // returns MED_GRILLE_CARTESIENNE, MED_GRILLE_POLAIRE, MED_GRILLE_STANDARD
201 int getArrayLength( const int Axis ) const throw (MEDEXCEPTION);
202 // return array length. Axis = [1,2,3] meaning [i,j,k],
203 // exception if Axis out of [1-3] range
205 const double getArrayValue (const int Axis, const int i) const throw (MEDEXCEPTION) ;
206 // return i-th array component. Axis = [1,2,3] meaning [i,j,k],
207 // exception if Axis out of [1 - 3] range
208 // exception if i is out of range [0 - (getArrayLength(Axis)-1)];
210 inline const COORDINATE * getCoordinateptr() const;
212 inline const double * getCoordinates(medModeSwitch Mode) const;
214 inline const double getCoordinate(int Number,int Axis) const;
216 inline int getNumberOfTypes(medEntityMesh Entity) const;
218 inline const medGeometryElement * getTypes(medEntityMesh Entity) const;
220 inline const CELLMODEL * getCellsTypes(medEntityMesh Entity) const;
222 const int * getGlobalNumberingIndex(medEntityMesh Entity) const;
224 inline int getNumberOfElements(medEntityMesh Entity,
225 medGeometryElement Type) const;
227 inline bool existConnectivity(medConnectivity ConnectivityType,
228 medEntityMesh Entity) const;
230 inline medGeometryElement getElementType(medEntityMesh Entity,
233 inline void calculateConnectivity(medModeSwitch Mode,
234 medConnectivity ConnectivityType,
235 medEntityMesh Entity) const ;
237 inline const CONNECTIVITY* getConnectivityptr() const;
239 inline const int * getConnectivity(medModeSwitch Mode,
240 medConnectivity ConnectivityType,
241 medEntityMesh Entity,
242 medGeometryElement Type) const;
244 inline const int * getConnectivityIndex(medConnectivity ConnectivityType,
245 medEntityMesh Entity) const;
247 inline const int * getReverseConnectivity(medConnectivity ConnectivityType,
248 medEntityMesh Entity=MED_CELL) const;
250 inline const int * getReverseConnectivityIndex(medConnectivity ConnectivityType,
251 medEntityMesh Entity=MED_CELL) const;
255 // inline void setGridType(med_grid_type gridType);
256 inline void setGridType(med_type_grille gridType);
258 friend class MED_MESH_RDONLY_DRIVER;
259 friend class MED_MESH_WRONLY_DRIVER;
263 using namespace MEDMEM;
266 //----------------------------------//
267 // Inline Methods Implementation
268 //----------------------------------//
270 // inline med_grid_type GRID::getGridType() const
275 inline med_type_grille GRID::getGridType() const
279 //=======================================================================
280 //function : getNodeNumber
282 //=======================================================================
284 inline int GRID::getNodeNumber(const int i, const int j, const int k) const
286 return 1 + i + _iArrayLength * j + _iArrayLength * _jArrayLength * k;
289 //=======================================================================
290 //function : getCellNumber
292 //=======================================================================
294 inline int GRID::getCellNumber(const int i, const int j, const int k) const
296 return 1 + i + (_iArrayLength-1) * j + (_iArrayLength-1) * (_jArrayLength-1) * k;
299 //=======================================================================
300 //function : makeUnstructured
301 //purpose : fill coordinates and connectivity of MESH
302 //=======================================================================
304 inline void GRID::makeUnstructured()
310 //=======================================================================
311 //function : setGridType
312 //purpose : set the _gridType field od the class GRID
313 //=======================================================================
315 // inline void GRID::setGridType(med_grid_type gridType)
317 // _gridType = gridType;
320 inline void GRID::setGridType(med_type_grille gridType)
322 _gridType = gridType;
325 /*! Get the COORDINATES object. Use it only if you need COORDINATES informations not provided by the GRID class via the MESH class.*/
326 inline const COORDINATE * GRID::getCoordinateptr() const
332 /*! Get the whole coordinates array in a given interlacing mode. The interlacing mode are :
333 - MED_NO_INTERLACE : X1 X2 Y1 Y2 Z1 Z2
334 - MED_FULL_INTERLACE : X1 Y1 Z1 X2 Y2 Z2
336 inline const double * GRID::getCoordinates(medModeSwitch Mode) const
339 return _coordinate->getCoordinates(Mode);
342 /*! Get the coordinate n° number on axis n°axis*/
343 inline const double GRID::getCoordinate(int number, int axis) const
346 return _coordinate->getCoordinate(number,axis);
349 /*! Get the number of different geometric types for a given entity type.
351 medEntityMesh entity : MED_CELL, MED_FACE, MED_EDGE, MED_NODE,
354 If entity is not defined, return 0.
356 If there is no connectivity, return an exception.
358 inline int GRID::getNumberOfTypes(medEntityMesh entity) const
360 MESSAGE("GRID::getNumberOfTypes(medEntityMesh entity) : "<<entity);
361 if (entity == MED_NODE)
366 if (_connectivity != NULL)
367 return _connectivity->getNumberOfTypes(entity);
368 throw MEDEXCEPTION(LOCALIZED("GRID::getNumberOfTypes( medEntityMesh ) : Connectivity not defined !"));
372 Get the list of geometric types used by a given entity.
373 medEntityMesh entity : MED_CELL, MED_FACE, MED_EDGE, MED_ALL_ENTITIES
375 REM : Don't use MED_NODE
377 If entity is not defined, return an exception.
379 inline const medGeometryElement * GRID::getTypes(medEntityMesh entity) const
381 if (entity == MED_NODE)
382 throw MEDEXCEPTION(LOCALIZED("GRID::getTypes( medEntityMesh ) : No medGeometryElement with MED_NODE entity !"));
383 // return un tableau de taille 1 contenant MED_NONE, comme les supports pour etre coherent avec getNumberOfTypes ???? PG
387 if (_connectivity != NULL)
388 return _connectivity->getGeometricTypes(entity);
389 throw MEDEXCEPTION(LOCALIZED("GRID::getTypes( medEntityMesh ) : Connectivity not defined !"));
393 Get the whole list of CELLMODEL used by cells of given type (medEntityMesh).
395 REMARK : Don't use MED_NODE as medEntityMesh
397 inline const CELLMODEL * GRID::getCellsTypes(medEntityMesh Entity) const
401 if (_connectivity != NULL)
402 return _connectivity->getCellsTypes(Entity);
403 throw MEDEXCEPTION(LOCALIZED("GRID::getCellsTypes( medEntityMesh ) : Connectivity not defined !"));
406 /*! Return an array of size NumbreOfTypes+1 which contains, for each
407 geometric type of the given entity, the first global element number
410 For exemple, if we have a mesh with 5 triangles and 4 quadrangle :
411 - size of GlobalNumberingIndex is 3
412 - GlobalNumberingIndex[0]=1 (the first type)
413 - GlobalNumberingIndex[1]=6 (the second type)
414 - GlobalNumberingIndex[2]=10
416 inline const int * GRID::getGlobalNumberingIndex(medEntityMesh entity) const
420 if (_connectivity != NULL)
421 return _connectivity->getGlobalNumberingIndex(entity);
422 throw MEDEXCEPTION(LOCALIZED("GRID::getNumberOfTypes( medEntityMesh ) : Connectivity not defined !"));
426 Return the number of element of given geometric type of given entity. Return 0 if query is not defined.
429 - getNumberOfElements(MED_NODE,MED_NONE) : number of node
430 - getNumberOfElements(MED_NODE,MED_TRIA3) : return 0 (not defined)
431 - getNumberOfElements(MED_FACE,MED_TRIA3) : return number of triangles
432 elements defined in face entity (0 if not defined)
433 - getNumberOfElements(MED_CELL,MED_ALL_ELEMENTS) : return total number
434 of elements defined in cell entity
436 inline int GRID::getNumberOfElements(medEntityMesh entity, medGeometryElement Type) const
438 // const char * LOC = "MESH::getNumberOfElements(medEntityMesh,medGeometryElement) : ";
439 if (entity==MED_NODE)
440 if ((Type==MED_NONE)|(Type==MED_ALL_ELEMENTS))
441 return _numberOfNodes;
444 //throw MEDEXCEPTION(LOCALIZED(STRING(LOC)<<"wrong medGeometryElement with MED_NODE"));
449 if (_connectivity != (CONNECTIVITY*)NULL)
450 return _connectivity->getNumberOf(entity,Type);
453 //throw MEDEXCEPTION(LOCALIZED(STRING(LOC)<<"connectivity not defined !"));
458 Return true if the wanted connectivity exist, else return false
459 (to use before a getSomething method).
461 inline bool GRID::existConnectivity(medConnectivity connectivityType, medEntityMesh entity) const
465 if (_connectivity==(CONNECTIVITY*)NULL)
466 throw MEDEXCEPTION("GRID::existConnectivity(medConnectivity,medEntityMesh) : no connectivity defined !");
467 return _connectivity->existConnectivity(connectivityType,entity);
471 Return the geometric type of global element Number of entity Entity.
473 Throw an exception if Entity is not defined or Number are wrong (too big).
475 inline medGeometryElement GRID::getElementType(medEntityMesh Entity,int Number) const
479 if (_connectivity==(CONNECTIVITY*)NULL)
480 throw MEDEXCEPTION("GRID::getElementType(medEntityMesh,int) : no connectivity defined !");
481 return _connectivity->getElementType(Entity,Number);
485 Calculate the ask connectivity. Return an exception if this could not be
486 done. Do nothing if connectivity already exist.
489 inline void GRID::calculateConnectivity(medModeSwitch Mode,medConnectivity ConnectivityType,medEntityMesh entity) const
493 if (Mode==MED_FULL_INTERLACE)
494 _connectivity->calculateConnectivity(ConnectivityType,entity);
496 throw MEDEXCEPTION(LOCALIZED("GRID::calculateConnectivity : only for MED_FULL_INTERLACE mode"));
499 inline const CONNECTIVITY* GRID::getConnectivityptr() const
503 return _connectivity;
507 Return the required connectivity in the right mode for the given
508 geometric type of the given entity.
510 To get connectivity for all geometric type, use Mode=MED_FULL_INTERLACE
511 and Type=MED_ALL_ELEMENTS.
512 You must also get the corresponding index array.
514 inline const int * GRID::getConnectivity(medModeSwitch Mode,medConnectivity ConnectivityType,medEntityMesh entity, medGeometryElement Type) const
518 if (Mode==MED_FULL_INTERLACE)
519 return _connectivity->getConnectivity(ConnectivityType,entity,Type);
520 throw MEDEXCEPTION(LOCALIZED("GRID::getConnectivity : only for MED_FULL_INTERLACE mode"));
524 Return the required index array for a connectivity received in
525 MED_FULL_ENTERLACE mode and MED_ALL_ELEMENTS type.
527 This array allow to find connectivity of each elements.
529 Example : Connectivity of i^{th} elements (1<=i<=NumberOfElement) begin
530 at index ConnectivityIndex[i-1] and end at index ConnectivityIndex[i]-1
531 in Connectivity array (Connectivity[ConnectivityIndex[i-1]-1] is the
534 inline const int * GRID::getConnectivityIndex(medConnectivity ConnectivityType,medEntityMesh entity) const
538 return _connectivity->getConnectivityIndex(ConnectivityType, entity);
542 Return the reverse connectivity required by ConnectivityType :
543 - If ConnectivityType=MED_NODAL : return connectivity node-cell
544 - If ConnectivityType=MED_DESCENDING : return connectivity face-cell
546 You must get ReverseConnectivityIndex array to use it.
548 inline const int * GRID::getReverseConnectivity(medConnectivity ConnectivityType,medEntityMesh Entity/*=MED_CELL*/) const
552 if (NULL==_connectivity)
553 throw MEDEXCEPTION("GRID::getReverseConnectivity : no connectivity defined in MESH !");
555 return _connectivity->getReverseConnectivity(ConnectivityType,Entity);
559 Return the index array required by ConnectivityType.
561 This array allow to find reverse connectivity of each elements.
563 Example : Reverse connectivity of i^{th} elements (1<=i<=NumberOfElement)
564 begin at index ReverseConnectivityIndex[i-1] and end at index
565 ReverseConnectivityIndex[i]-1
566 in ReverseConnectivity array (
567 ReverseConnectivity[ReverseConnectivityIndex[i-1]-1]
570 inline const int * GRID::getReverseConnectivityIndex(medConnectivity ConnectivityType,medEntityMesh Entity/*=MED_CELL*/) const
574 if (NULL==_connectivity)
575 throw MEDEXCEPTION("GRID::getReverseConnectivityIndex : no connectivity defined in MESH !");
577 return _connectivity->getReverseConnectivityIndex(ConnectivityType,Entity);