1 // Copyright (C) 2007-2008 CEA/DEN, EDF R&D, OPEN CASCADE
3 // Copyright (C) 2003-2007 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
6 // This library is free software; you can redistribute it and/or
7 // modify it under the terms of the GNU Lesser General Public
8 // License as published by the Free Software Foundation; either
9 // version 2.1 of the License.
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 // Lesser General Public License for more details.
16 // You should have received a copy of the GNU Lesser General Public
17 // License along with this library; if not, write to the Free Software
18 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
32 #include "MEDMEM_Utilities.hxx"
33 #include "MEDMEM_STRING.hxx"
34 #include "MEDMEM_Exception.hxx"
35 #include "MEDMEM_define.hxx"
36 #include "MEDMEM_Coordinate.hxx"
37 #include "MEDMEM_Connectivity.hxx"
38 #include "MEDMEM_GenDriver.hxx"
39 #include "MEDMEM_RCBase.hxx"
40 #include "MEDMEM_FieldForward.hxx"
50 MEDMEM_EXPORT ostream & operator<<(ostream &os, const MESH &my);
52 /*! This class contains all the informations related with a MESH :
60 NOTE: A Family is only on one type of entity (MED_CELL, MED_FACE, MED_EDGE, MED_NODE).
61 You can't have a family on MED_CELL and MED_FACE
65 class MEDMEM_EXPORT MESH : public RCBASE
67 //-----------------------//
69 //-----------------------//
73 string _name; // A POSITIONNER EN FCT DES IOS ?
76 mutable COORDINATE * _coordinate;
77 mutable CONNECTIVITY * _connectivity;
84 //////////////////////////////////////////////////////////////////////////////////////
85 /// Modification pour prise en compte de la numérotation optionnelle des noeuds ///
86 //////////////////////////////////////////////////////////////////////////////////////
88 /// La map suivante donne le lien numérotation optionnelle => numérotation cannonique
89 /// Elle sera calculée apres l'appel de MEDnumLire(...)
90 /// Et sera utilisée avant chaque appel a MEDconnLire(...) pour renuméroter toutes les mailles de façon canonique [1...n]
91 /// _coordinate->NodeNumber sera utilisé avant chaque appel à MEDconnEcri pour démunéroter les mailles en leur numérotation originelle
92 /// Ce traitement devrait prévenir tout plantage du aux numérotations optionnelles DES NOEUDS
93 /// Et ne ralentira que tres peu les traitements sans numéros optionnels
95 int _arePresentOptionnalNodesNumbers;
96 map<int,int> _optionnalToCanonicNodesNumbers;
98 vector<FAMILY*> _familyNode;
99 vector<FAMILY*> _familyCell;
100 vector<FAMILY*> _familyFace;
101 vector<FAMILY*> _familyEdge;
103 vector<GROUP*> _groupNode;
104 vector<GROUP*> _groupCell;
105 vector<GROUP*> _groupFace;
106 vector<GROUP*> _groupEdge;
109 vector<GENDRIVER *> _drivers; // Storage of the drivers currently in use
111 bool _isAGrid; // am I a GRID or not
113 map<MED_EN::medEntityMesh,SUPPORT*> _entitySupport;
115 //-----------------------//
117 //-----------------------//
119 // inline void checkGridFillCoords() const;
120 // inline void checkGridFillConnectivity() const;
121 bool isEmpty() const;
122 // if this->_isAGrid, assure that _coordinate and _connectivity are filled
125 // Add your personnal driver line (step 2)
126 friend class IMED_MESH_RDONLY_DRIVER;
127 friend class IMED_MESH_WRONLY_DRIVER;
128 friend class MED_MESH_RDONLY_DRIVER21;
129 friend class MED_MESH_WRONLY_DRIVER21;
130 friend class MED_MESH_RDONLY_DRIVER22;
131 friend class MED_MESH_WRONLY_DRIVER22;
133 friend class MED_MED_RDONLY_DRIVER21;
134 friend class MED_MED_WRONLY_DRIVER21;
135 friend class MED_MED_RDWR_DRIVER21;
136 friend class MED_MED_RDONLY_DRIVER22;
137 friend class MED_MED_WRONLY_DRIVER22;
138 friend class MED_MED_RDWR_DRIVER22;
140 friend class GIBI_MESH_RDONLY_DRIVER;
141 friend class GIBI_MESH_WRONLY_DRIVER;
142 friend class GIBI_MESH_RDWR_DRIVER;
144 friend class PORFLOW_MESH_RDONLY_DRIVER;
145 friend class PORFLOW_MESH_WRONLY_DRIVER;
146 friend class PORFLOW_MESH_RDWR_DRIVER;
148 friend class VTK_MESH_DRIVER;
150 friend class ENSIGHT_MESH_RDONLY_DRIVER;
155 MESH & operator=(const MESH &m);
156 virtual bool operator==(const MESH& other) const;
157 virtual bool deepCompare(const MESH& other) const;
158 MESH( driverTypes driverType, const string & fileName="",
159 const string & meshName="") throw (MEDEXCEPTION);
161 friend ostream & operator<<(ostream &os, const MESH &my);
162 virtual void printMySelf(ostream &os) const;
164 int addDriver(driverTypes driverType,
165 const string & fileName ="Default File Name.med",
166 const string & driverName="Default Mesh Name",
167 MED_EN::med_mode_acces access=MED_EN::RDWR);
168 int addDriver(GENDRIVER & driver);
169 void rmDriver(int index=0);
171 virtual void read(int index=0);
172 inline void read(const GENDRIVER & genDriver);
173 //inline void write(int index=0, const string & driverName = "");
174 virtual void write(int index=0, const string & driverName = "");
175 inline void write(const GENDRIVER & genDriver);
177 inline void setName(string name);
178 inline void setDescription(string description);
179 inline void setMeshDimension(int dim);
180 inline string getName() const;
181 inline string getDescription() const;
182 inline int getSpaceDimension() const;
183 inline int getMeshDimension() const;
184 inline bool getIsAGrid();
186 inline int getNumberOfNodes() const;
187 virtual inline const COORDINATE * getCoordinateptr() const;
188 inline string getCoordinatesSystem() const;
189 virtual inline const double * getCoordinates(MED_EN::medModeSwitch Mode) const;
190 virtual inline const double getCoordinate(int Number,int Axis) const;
191 inline const string * getCoordinatesNames() const;
192 inline const string * getCoordinatesUnits() const;
193 //inline int * getNodesNumbers();
195 virtual inline int getNumberOfTypes(MED_EN::medEntityMesh Entity) const;
196 virtual int getNumberOfTypesWithPoly(MED_EN::medEntityMesh Entity) const;
197 virtual inline const MED_EN::medGeometryElement * getTypes(MED_EN::medEntityMesh Entity) const;
198 virtual MED_EN::medGeometryElement * getTypesWithPoly(MED_EN::medEntityMesh Entity) const;
199 virtual inline const CELLMODEL * getCellsTypes(MED_EN::medEntityMesh Entity) const;
200 virtual inline string * getCellTypeNames(MED_EN::medEntityMesh Entity) const;
201 virtual const int * getGlobalNumberingIndex(MED_EN::medEntityMesh Entity) const;
202 virtual inline int getNumberOfElements(MED_EN::medEntityMesh Entity,
203 MED_EN::medGeometryElement Type) const;
204 virtual int getNumberOfElementsWithPoly(MED_EN::medEntityMesh Entity,
205 MED_EN::medGeometryElement Type) const;
206 virtual inline bool existConnectivity(MED_EN::medConnectivity ConnectivityType,
207 MED_EN::medEntityMesh Entity) const;
208 virtual bool existConnectivityWithPoly(MED_EN::medConnectivity ConnectivityType,
209 MED_EN::medEntityMesh Entity) const;
210 inline bool existPolygonsConnectivity(MED_EN::medConnectivity ConnectivityType,
211 MED_EN::medEntityMesh Entity) const;
212 inline bool existPolyhedronConnectivity(MED_EN::medConnectivity ConnectivityType,
213 MED_EN::medEntityMesh Entity) const;
215 virtual inline MED_EN::medGeometryElement getElementType(MED_EN::medEntityMesh Entity,
217 virtual inline MED_EN::medGeometryElement getElementTypeWithPoly(MED_EN::medEntityMesh Entity,
219 virtual inline void calculateConnectivity(MED_EN::medModeSwitch Mode,
220 MED_EN::medConnectivity ConnectivityType,
221 MED_EN::medEntityMesh Entity) const ;
222 virtual inline int getConnectivityLength(MED_EN::medModeSwitch Mode,
223 MED_EN::medConnectivity ConnectivityType,
224 MED_EN::medEntityMesh Entity,
225 MED_EN::medGeometryElement Type) const;
226 virtual inline const int * getConnectivity(MED_EN::medModeSwitch Mode,
227 MED_EN::medConnectivity ConnectivityType,
228 MED_EN::medEntityMesh Entity,
229 MED_EN::medGeometryElement Type) const;
230 virtual inline const int * getConnectivityIndex(MED_EN::medConnectivity ConnectivityType,
231 MED_EN::medEntityMesh Entity) const;
233 inline int getPolygonsConnectivityLength(MED_EN::medConnectivity ConnectivityType,
234 MED_EN::medEntityMesh Entity) const;
235 inline const int * getPolygonsConnectivity(MED_EN::medConnectivity ConnectivityType,
236 MED_EN::medEntityMesh Entity) const;
237 inline const int * getPolygonsConnectivityIndex(MED_EN::medConnectivity ConnectivityType,
238 MED_EN::medEntityMesh Entity) const;
239 inline int getNumberOfPolygons(MED_EN::medEntityMesh Entity=MED_EN::MED_ALL_ENTITIES) const;
240 inline int getPolyhedronConnectivityLength(MED_EN::medConnectivity ConnectivityType) const;
241 inline const int * getPolyhedronConnectivity(MED_EN::medConnectivity ConnectivityType) const;
242 inline const int * getPolyhedronFacesIndex() const;
243 inline const int * getPolyhedronIndex(MED_EN::medConnectivity ConnectivityType) const;
244 inline int getNumberOfPolyhedronFaces() const;
245 inline int getNumberOfPolyhedron() const;
247 virtual int getElementNumber(MED_EN::medConnectivity ConnectivityType,
248 MED_EN::medEntityMesh Entity,
249 MED_EN::medGeometryElement Type,
250 int * connectivity) const;
251 virtual inline int getReverseConnectivityLength(MED_EN::medConnectivity ConnectivityType,
252 MED_EN::medEntityMesh Entity=MED_EN::MED_CELL) const;
253 virtual inline const int * getReverseConnectivity(MED_EN::medConnectivity ConnectivityType,
254 MED_EN::medEntityMesh Entity=MED_EN::MED_CELL) const;
255 virtual inline int getReverseConnectivityIndexLength(MED_EN::medConnectivity ConnectivityType,
256 MED_EN::medEntityMesh Entity=MED_EN::MED_CELL) const;
257 virtual inline const int * getReverseConnectivityIndex(MED_EN::medConnectivity ConnectivityType,
258 MED_EN::medEntityMesh Entity=MED_EN::MED_CELL) const;
260 virtual int getNumberOfFamilies(MED_EN::medEntityMesh Entity) const;
261 virtual inline const vector<FAMILY*> getFamilies(MED_EN::medEntityMesh Entity) const;
262 virtual inline const FAMILY* getFamily(MED_EN::medEntityMesh Entity,int i) const;
263 virtual int getNumberOfGroups(MED_EN::medEntityMesh Entity) const;
264 virtual const vector<GROUP*> getGroups(MED_EN::medEntityMesh Entity) const;
265 virtual const GROUP* getGroup(MED_EN::medEntityMesh Entity,int i) const;
266 virtual const GROUP* getGroup(const string& name) const throw (MEDEXCEPTION);
267 virtual inline const CONNECTIVITY* getConnectivityptr() const;
268 inline void setConnectivityptr(CONNECTIVITY*);
269 virtual SUPPORT * getBoundaryElements(MED_EN::medEntityMesh Entity)
270 throw (MEDEXCEPTION);
271 virtual SUPPORT * getSupportOnAll(MED_EN::medEntityMesh Entity)
272 throw (MEDEXCEPTION);
273 // problème avec le maillage dans le support :
274 // le pointeur n'est pas const, mais sa valeur oui. A voir !!! PG
276 SUPPORT * getSkin(const SUPPORT * Support3D)
277 throw (MEDEXCEPTION);
279 // Node DonneBarycentre(const Cell &m) const;
280 virtual FIELD<double>* getVolume (const SUPPORT * Support) const
281 throw (MEDEXCEPTION);
282 // Support must be on 3D elements
283 virtual FIELD<double>* getArea (const SUPPORT * Support) const
284 throw (MEDEXCEPTION);
285 // Support must be on 2D elements
286 virtual FIELD<double>* getLength (const SUPPORT * Support) const
287 throw (MEDEXCEPTION);
288 // Support must be on 1D elements
289 virtual FIELD<double>* getNormal (const SUPPORT * Support) const
290 throw (MEDEXCEPTION);
291 // Support must be on 2D elements
292 virtual FIELD<double>* getBarycenter (const SUPPORT * Support) const
293 throw (MEDEXCEPTION);
294 // FIELD<int>* getNeighbourhood(SUPPORT * Support) const
295 // throw (MEDEXCEPTION); // Il faut preciser !
298 returns a SUPPORT pointer on the union of all SUPPORTs in Supports.
299 You should delete this pointer after use to avois memory leaks.
301 static SUPPORT * mergeSupports(const vector<SUPPORT *> Supports) throw (MEDEXCEPTION) ;
304 returns a SUPPORT pointer on the intersection of all SUPPORTs in Supports.
305 The (SUPPORT *) NULL pointer is returned if the intersection is empty.
306 You should delete this pointer after use to avois memory leaks.
308 static SUPPORT * intersectSupports(const vector<SUPPORT *> Supports) throw (MEDEXCEPTION) ;
311 * Create families from groups.
312 * This function is automaticaly called whenever we ask for families that are not up-to-date.
313 * (The creation of families is delayed to the need of user.)
314 * If a new created family hapen to already exist, we keep the old one.
315 * (There is no way to know which family has change.)
317 void createFamilies();
319 SUPPORT *buildSupportOnNodeFromElementList(const list<int>& listOfElt, MED_EN::medEntityMesh entity) const throw (MEDEXCEPTION);
320 void fillSupportOnNodeFromElementList(const list<int>& listOfElt, SUPPORT *supportToFill) const throw (MEDEXCEPTION);
321 SUPPORT *buildSupportOnElementsFromElementList(const list<int>& listOfElt, MED_EN::medEntityMesh entity) const throw (MEDEXCEPTION);
322 int getElementContainingPoint(const double *coord);
323 // vector< vector<double> > MESH::getBoundingBox() const;
324 vector< vector<double> > getBoundingBox() const;
325 template<class T> static
326 FIELD<T> * mergeFields(const vector< FIELD<T> * > & others, bool meshCompare=false);
327 void convertToPoly();
330 *For ref counter. Only for client
332 virtual void addReference() const;
333 virtual void removeReference() const;
336 // ---------------------------------------
338 // ---------------------------------------
340 inline const CONNECTIVITY* MESH::getConnectivityptr() const
342 // checkGridFillConnectivity();
343 return _connectivity;
346 inline void MESH::setConnectivityptr(CONNECTIVITY* conn)
350 // This method is MED specific : don't use it
352 inline void MESH::write(const GENDRIVER & genDriver)
354 const char* LOC = "MESH::write(const MED_MED_DRIVER & genDriver): ";
357 for (unsigned int index=0; index < _drivers.size(); index++ )
358 if ( *_drivers[index] == genDriver ) {
360 // EAP for MEDMEMTest_Med.cxx:305 :
361 // CPPUNIT_ASSERT_MED_NO_THROW(myMed->writeFrom(idMedV21_from));
362 // CPPUNIT_ASSERT_MED(access(filenameout21_from.data(), F_OK) != 0);
363 string myDrvName = _drivers[index]->getFileName();
364 string otherName = genDriver.getFileName();
365 if ( !otherName.empty() )
366 _drivers[index]->setFileName( otherName );
367 // end EAP for MEDMEMTest_Med.cxx:305
369 _drivers[index]->open();
370 _drivers[index]->write();
371 _drivers[index]->close();
373 _drivers[index]->setFileName( myDrvName );// EAP for MEDMEMTest_Med.cxx:305
374 // ? FINALEMENT PAS BESOIN DE L'EXCEPTION ?
381 // This method is MED specific : don't use it
383 inline void MESH::read(const GENDRIVER & genDriver)
385 const char* LOC = "MESH::read(const MED_MED_DRIVER & genDriver): ";
388 for (unsigned int index=0; index < _drivers.size(); index++ )
389 if ( *_drivers[index] == genDriver ) {
390 _drivers[index]->open();
391 _drivers[index]->read();
392 _drivers[index]->close();
393 // ? FINALEMENT PAS BESOIN DE L'EXCEPTION ?
400 /*! Sets the MESH name. Name should not exceed MED_TAILLE_NOM
401 length defined in Med (i.e. 32 characters).*/
402 inline void MESH::setName(string name)
404 _name=name; //NOM interne à la classe
408 \addtogroup MESH_general
414 Gets the MESH name.*/
415 inline string MESH::getName() const
420 inline void MESH::setMeshDimension(int dim)
425 /*! Set the MESH description */
427 Sets the MESH description. Description should not exceed MED_TAILLE_DESC length defined in Med (i.e. 200 characters).
429 inline void MESH::setDescription(string description)
431 _description=description; //NOM interne à la classe
434 /*! Gets the MESH description. The string returned contains
435 a short description of the mesh, which is stored for
436 information purposes only.*/
437 inline string MESH::getDescription() const
442 /*! Gets the dimension of the space in which the
443 mesh is described (2 for planar meshes, 3 for volumes and
445 inline int MESH::getSpaceDimension() const
447 return _spaceDimension;
450 /*! Gets the dimension of the mesh (2 for 2D- and 3D-surfaces, 3 for volumes). */
451 inline int MESH::getMeshDimension() const
453 return _meshDimension;
457 The retrieval of general information about a mesh is illustrated in the following C++ example. Its Python equivalent can be found in \a MESHgeneral.py.
458 This example illustrates how to retrieve the name, description, mesh and space dimensions.
460 \example MESHgeneral.cxx
465 \addtogroup MESH_nodes
469 /*! Gets the number of nodes used in the mesh. */
470 inline int MESH::getNumberOfNodes() const
472 return _numberOfNodes;
476 Gets the COORDINATES object. Use it only if you need COORDINATES informations not provided by the MESH class.
479 inline const COORDINATE * MESH::getCoordinateptr() const
481 // checkGridFillCoords();
485 /*! Retrieves the system in which coordinates are given (CARTESIAN,CYLINDRICAL,SPHERICAL). */
486 inline string MESH::getCoordinatesSystem() const
488 return _coordinate->getCoordinatesSystem();
491 /*! Gets the whole coordinates array in a given interlacing mode. The interlacing mode are :
492 - MED_NO_INTERLACE : X1 X2 Y1 Y2 Z1 Z2
493 - MED_FULL_INTERLACE : X1 Y1 Z1 X2 Y2 Z2
495 inline const double * MESH::getCoordinates(MED_EN::medModeSwitch Mode) const
497 // checkGridFillCoords();
498 return _coordinate->getCoordinates(Mode);
501 /*! Gets the coordinate number \a number on axis \a axis.*/
502 inline const double MESH::getCoordinate(int number, int axis) const
504 // checkGridFillCoords();
505 return _coordinate->getCoordinate(number,axis);
508 /*! Gets a pointer to the coordinate names array.
510 inline const string * MESH::getCoordinatesNames() const
512 return _coordinate->getCoordinatesNames();
515 /*! Gets a pointer to the coordinate units array.
517 inline const string * MESH::getCoordinatesUnits() const
519 return _coordinate->getCoordinatesUnits();
523 Here is a small C++ example program for which the
524 Python version may be found in
525 \a MESHcoordinates.py.
527 \example MESHcoordinates.cxx
533 // int * MESH::getNodesNumbers() const
535 // return nodesNumbers;
539 \addtogroup MESH_connectivity
544 /*! Gets the number of different geometric types for a given entity type.
546 For example getNumberOfTypes(MED_CELL) would return 3 if the MESH
547 have some MED_TETRA4, MED_PYRA5 and MED_HEXA8 in it.
548 If entity is not defined, returns 0.
549 If there is no connectivity, returns an exception.
551 \param entity entity type (MED_CELL, MED_FACE, MED_EDGE, MED_NODE, MED_ALL_ENTITIES)
555 inline int MESH::getNumberOfTypes(MED_EN::medEntityMesh entity) const
557 MESSAGE_MED("MESH::getNumberOfTypes(medEntityMesh entity) : "<<entity);
558 if (entity == MED_EN::MED_NODE)
560 // checkGridFillConnectivity();
561 if (_connectivity != NULL)
562 return _connectivity->getNumberOfTypes(entity);
563 throw MEDEXCEPTION(LOCALIZED("MESH::getNumberOfTypes( medEntityMesh ) : Connectivity not defined !"));
567 Gets the list of geometric types used by a given entity.
568 If entity is not defined, it returns an exception.
569 \param entity Entity type must be MED_CELL, MED_FACE, MED_EDGE or MED_ALL_ENTITIES.
570 Passing MED_NODE as an entity type will throw an exception.
572 inline const MED_EN::medGeometryElement * MESH::getTypes(MED_EN::medEntityMesh entity) const
574 if (entity == MED_EN::MED_NODE)
575 throw MEDEXCEPTION(LOCALIZED("MESH::getTypes( medEntityMesh ) : No medGeometryElement with MED_NODE entity !"));
576 // return un tableau de taille 1 contenant MED_NONE, comme les supports pour etre coherent avec getNumberOfTypes ???? PG
578 // checkGridFillConnectivity();
579 if (_connectivity != NULL)
580 return _connectivity->getGeometricTypes(entity);
581 throw MEDEXCEPTION(LOCALIZED("MESH::getTypes( medEntityMesh ) : Connectivity not defined !"));
583 /*! \if MEDMEM_ug @} \endif */
586 Get the whole list of CELLMODEL used by cells of given type (medEntityMesh).
587 Passing MED_NODE as an entity type will throw an exception.
589 inline const CELLMODEL * MESH::getCellsTypes(MED_EN::medEntityMesh Entity) const
591 // checkGridFillConnectivity();
592 if (_connectivity != NULL)
593 return _connectivity->getCellsTypes(Entity);
594 throw MEDEXCEPTION(LOCALIZED("MESH::getCellsTypes( medEntityMesh ) : Connectivity not defined !"));
598 Get an array (it should deleted after use) of the whole list of CELLMODEL
599 Name of a given type (medEntityMesh).
601 REMARK : Don't use MED_NODE as medEntityMesh
603 inline string * MESH::getCellTypeNames(MED_EN::medEntityMesh Entity) const
605 // checkGridFillConnectivity();
606 if (_connectivity != NULL)
607 return _connectivity->getCellTypeNames(Entity);
608 throw MEDEXCEPTION(LOCALIZED("MESH::getCellTypesName( medEntityMesh ) : Connectivity not defined !"));
611 \addtogroup MESH_connectivity
616 /*! Returns an array of size NumberOfTypes+1 which contains, for each
617 geometric type of the given entity, the first global element number
620 For exemple, if we have a mesh with 5 triangles and 4 quadrangle :
621 - size of GlobalNumberingIndex is 3
622 - GlobalNumberingIndex[0]=1 (the first type)
623 - GlobalNumberingIndex[1]=6 (the second type)
624 - GlobalNumberingIndex[2]=10
626 inline const int * MESH::getGlobalNumberingIndex(MED_EN::medEntityMesh entity) const
628 // checkGridFillConnectivity();
629 if (_connectivity != NULL)
630 return _connectivity->getGlobalNumberingIndex(entity);
631 throw MEDEXCEPTION(LOCALIZED("MESH::getNumberOfTypes( medEntityMesh ) : Connectivity not defined !"));
634 Returns the number of elements of given geometric type of given entity. Returns 0 if query is not defined.
637 - getNumberOfElements(MED_NODE,MED_NONE) : number of nodes
638 - getNumberOfElements(MED_NODE,MED_TRIA3) : returns 0 (not defined)
639 - getNumberOfElements(MED_FACE,MED_TRIA3) : returns number of triangle
640 elements defined in face entity (0 if not defined)
641 - getNumberOfElements(MED_CELL,MED_ALL_ELEMENTS) : returns total number
642 of elements defined in cell entity
644 inline int MESH::getNumberOfElements(MED_EN::medEntityMesh entity, MED_EN::medGeometryElement Type) const
646 if (entity==MED_EN::MED_NODE)
647 if ((Type==MED_EN::MED_NONE)|(Type==MED_EN::MED_ALL_ELEMENTS))
648 return _numberOfNodes;
651 //throw MEDEXCEPTION(LOCALIZED(STRING(LOC)<<"wrong medGeometryElement with MED_NODE"));
654 // checkGridFillConnectivity();
655 if (_connectivity != (CONNECTIVITY*)NULL)
656 return _connectivity->getNumberOf(entity,Type);
659 //throw MEDEXCEPTION(LOCALIZED(STRING(LOC)<<"connectivity not defined !"));
664 This example shows the use of connectivity retrieval methods on a mesh which
665 corresponds to the four-element mesh given in figure ??. Note
666 the use of connectivity and connnectivity index tables, and the
667 offsets used to convert Fortran-style numbering to C arrays.
669 The output of this program reads :
678 Element 1 : 4 6 5 10 11 9
681 \example read_example.cxx
683 A more complete example involving descending connectivities
684 can be found in \c MESHconnectivities.cxx and \c MESHconnectivities.py.
690 Returns true if the wanted connectivity exist, else returns false
691 (to use before a getSomething method).
693 inline bool MESH::existConnectivity(MED_EN::medConnectivity connectivityType, MED_EN::medEntityMesh entity) const
695 // checkGridFillConnectivity();
696 if (_connectivity==(CONNECTIVITY*)NULL)
697 throw MEDEXCEPTION("MESH::existConnectivity(medConnectivity,medEntityMesh) : no connectivity defined !");
698 return _connectivity->existConnectivity(connectivityType,entity);
701 Returns true if the wanted polygons connectivity exist, else returns false
703 inline bool MESH::existPolygonsConnectivity(MED_EN::medConnectivity connectivityType, MED_EN::medEntityMesh entity) const
705 if (_connectivity == (CONNECTIVITY*) NULL)
706 throw MEDEXCEPTION("MESH::existPolygonsConnectivity(medConnectivity,medEntityMesh) : no connectivity defined !");
707 return _connectivity->existPolygonsConnectivity(connectivityType,entity);
710 Returns true if the wanted polyhedron connectivity exist, else returns false
712 inline bool MESH::existPolyhedronConnectivity(MED_EN::medConnectivity connectivityType, MED_EN::medEntityMesh entity) const
714 if (_connectivity == (CONNECTIVITY*) NULL)
715 throw MEDEXCEPTION("MESH::existPolyhedronConnectivity(medConnectivity,medEntityMesh) : no connectivity defined !");
716 return _connectivity->existPolyhedronConnectivity(connectivityType,entity);
720 \addtogroup MESH_connectivity
726 Returns the geometric type of global element number \a Number of entity \a Entity.
728 Throw an exception if \a Entity is not defined or if \a Numberis wrong.
730 inline MED_EN::medGeometryElement MESH::getElementType(MED_EN::medEntityMesh Entity,int Number) const
732 // checkGridFillConnectivity();
733 if (_connectivity==(CONNECTIVITY*)NULL)
734 throw MEDEXCEPTION("MESH::getElementType(medEntityMesh,int) : no connectivity defined !");
735 return _connectivity->getElementType(Entity,Number);
744 \addtogroup MESH_poly
750 Method equivalent to getElementType except that it includes not only classical Types but polygons/polyhedra also.
752 MED_EN::medGeometryElement MESH::getElementTypeWithPoly(MED_EN::medEntityMesh Entity, int Number) const
754 if (_connectivity==(CONNECTIVITY*)NULL)
755 throw MEDEXCEPTION("MESH::getElementType(medEntityMesh,int) : no connectivity defined !");
756 return _connectivity->getElementTypeWithPoly(Entity,Number);
766 Calculates the required connectivity. Returns an exception if this could not be
767 done. Do nothing if connectivity already exist.
770 inline void MESH::calculateConnectivity(MED_EN::medModeSwitch Mode,MED_EN::medConnectivity ConnectivityType,MED_EN::medEntityMesh entity) const
772 // checkGridFillConnectivity();
773 if (Mode==MED_EN::MED_FULL_INTERLACE)
774 _connectivity->calculateConnectivity(ConnectivityType,entity);
776 throw MEDEXCEPTION(LOCALIZED("MESH::calculateConnectivity : only for MED_FULL_INTERLACE mode"));
779 Returns the corresponding length of the array returned by MESH::getConnectivity with exactly the same arguments.
780 Used particulary for wrapping CORBA and python.
782 inline int MESH::getConnectivityLength(MED_EN::medModeSwitch Mode,MED_EN::medConnectivity ConnectivityType,MED_EN::medEntityMesh entity, MED_EN::medGeometryElement Type) const
784 int nbOfElm = getNumberOfElements(entity,Type);
787 if (Type == MED_EN::MED_ALL_ELEMENTS)
789 size = getConnectivityIndex(ConnectivityType,entity)[nbOfElm]-1;
793 if ( ConnectivityType==MED_EN::MED_NODAL )
794 size = nbOfElm*(((int) Type)%100);
796 size = _connectivity->getConnectivityLength(ConnectivityType,entity,Type); // issue 19983
802 \addtogroup MESH_connectivity
808 Returns the required connectivity in mode \a Mode for the
809 geometric type \a Type of the entity type \a entity.
810 \a ConnectivityType specifies descending or nodal connectivity.
812 To get connectivity for all geometric type, use \a Mode=MED_FULL_INTERLACE
813 and \a Type=MED_ALL_ELEMENTS.
814 You must also get the corresponding index array.
816 inline const int * MESH::getConnectivity(MED_EN::medModeSwitch Mode,MED_EN::medConnectivity ConnectivityType,MED_EN::medEntityMesh entity, MED_EN::medGeometryElement Type) const
818 // checkGridFillConnectivity();
819 if (Mode==MED_EN::MED_FULL_INTERLACE)
820 return _connectivity->getConnectivity(ConnectivityType,entity,Type);
821 throw MEDEXCEPTION(LOCALIZED("MESH::getConnectivity : only for MED_FULL_INTERLACE mode"));
824 Returns the required index array for a connectivity received in
825 MED_FULL_INTERLACE mode and MED_ALL_ELEMENTS type.
827 This array allows to find connectivity of each element.
829 Example : Connectivity of i-th element (1<=i<=NumberOfElement) begins
830 at index ConnectivityIndex[i-1] and ends at index ConnectivityIndex[i]-1
831 in Connectivity array (Connectivity[ConnectivityIndex[i-1]-1] is the
832 first node of the element)
834 inline const int * MESH::getConnectivityIndex(MED_EN::medConnectivity ConnectivityType,MED_EN::medEntityMesh entity) const
836 // checkGridFillConnectivity();
837 return _connectivity->getConnectivityIndex(ConnectivityType, entity);
840 /*!\if MEDMEM_ug @} \endif */
846 Returns the corresponding length of the array returned by MESH::getPolygonsConnectivity.
847 Used particulary for wrapping CORBA and python.
849 inline int MESH::getPolygonsConnectivityLength(MED_EN::medConnectivity ConnectivityType,
850 MED_EN::medEntityMesh Entity) const
852 return getPolygonsConnectivityIndex (ConnectivityType,Entity)[ getNumberOfPolygons(Entity) ] - 1;
856 \addtogroup MESH_poly
861 Return the required connectivity of polygons for the given entity.
862 You must also get the corresponding index array.
864 inline const int * MESH::getPolygonsConnectivity(MED_EN::medConnectivity ConnectivityType,
865 MED_EN::medEntityMesh Entity) const
867 return _connectivity->getPolygonsConnectivity(ConnectivityType,Entity);
870 Return the required index array for polygons connectivity.
872 inline const int * MESH::getPolygonsConnectivityIndex(MED_EN::medConnectivity ConnectivityType,
873 MED_EN::medEntityMesh Entity) const
875 return _connectivity->getPolygonsConnectivityIndex(ConnectivityType,Entity);
878 Return the number of polygons.
880 inline int MESH::getNumberOfPolygons(MED_EN::medEntityMesh Entity) const
882 return _connectivity->getNumberOfPolygons(Entity);
884 /*! \if MEDMEM_ug @} \endif */
887 Returns the corresponding length of the array returned by MESH::getPolyhedronConnectivity with exactly the same arguments.
888 Used particulary for wrapping CORBA and python.
890 inline int MESH::getPolyhedronConnectivityLength(MED_EN::medConnectivity ConnectivityType) const
892 if ( ConnectivityType == MED_EN::MED_DESCENDING )
893 return getPolyhedronIndex (ConnectivityType) [ getNumberOfPolyhedron() ] - 1;
895 return getPolyhedronFacesIndex()[ getNumberOfPolyhedronFaces() ] - 1;
899 \addtogroup MESH_poly
903 Returns the required connectivity of polyhedron :
904 - in nodal mode, it gives you the polyhedron faces nodal connectivity.
905 - in descending mode, it gives you the polyhedron faces list.
907 - faces index and polyhedron index arrays in nodal mode.
908 - polyhedron index array in descending mode.
910 inline const int * MESH::getPolyhedronConnectivity(MED_EN::medConnectivity ConnectivityType) const
912 return _connectivity->getPolyhedronConnectivity(ConnectivityType);
915 Returns the index array of polyhedron faces in nodal mode.
916 You must also get the polyhedron index array.
918 inline const int * MESH::getPolyhedronFacesIndex() const
920 return _connectivity->getPolyhedronFacesIndex();
923 Returns the required polyhedron index array.
925 inline const int * MESH::getPolyhedronIndex(MED_EN::medConnectivity ConnectivityType) const
927 return _connectivity->getPolyhedronIndex(ConnectivityType);
930 Returns the number of polyhedron faces.
932 inline int MESH::getNumberOfPolyhedronFaces() const
934 return _connectivity->getNumberOfPolyhedronFaces();
937 Returns the number of polyhedron.
939 inline int MESH::getNumberOfPolyhedron() const
941 return _connectivity->getNumberOfPolyhedron();
950 Returns the corresponding length of the array returned by MESH::getReverseConnectivity with exactly the same arguments.
951 Used particulary for wrapping CORBA and python.
954 inline int MESH::getReverseConnectivityLength(MED_EN::medConnectivity ConnectivityType,
955 MED_EN::medEntityMesh Entity) const
957 int spaceDim = getSpaceDimension();
960 if (ConnectivityType == MED_EN::MED_NODAL)
962 nb = getNumberOfNodes();
967 nb = getNumberOfElements(MED_EN::MED_EDGE,
968 MED_EN::MED_ALL_ELEMENTS);
969 else if (spaceDim == 3)
970 nb = getNumberOfElements(MED_EN::MED_FACE,
971 MED_EN::MED_ALL_ELEMENTS);
973 return getReverseConnectivityIndex(ConnectivityType,Entity)[nb]-1;
976 Returns the reverse connectivity required by ConnectivityType :
977 - If ConnectivityType=MED_NODAL : returns connectivity node-cell
978 - If ConnectivityType=MED_DESCENDING : returns connectivity face-cell
980 You must get ReverseConnectivityIndex array to use it.
983 inline const int * MESH::getReverseConnectivity(MED_EN::medConnectivity ConnectivityType,MED_EN::medEntityMesh Entity/*=MED_CELL*/) const
985 // checkGridFillConnectivity();
986 if (NULL==_connectivity)
987 throw MEDEXCEPTION("MESH::getReverseConnectivity : no connectivity defined in MESH !");
989 return _connectivity->getReverseConnectivity(ConnectivityType,Entity);
992 Returns the corresponding length of the array returned by MESH::getReverseConnectivityIndex with exactly the same arguments.
993 Used particulary for wrapping CORBA and python.
995 inline int MESH::getReverseConnectivityIndexLength(MED_EN::medConnectivity ConnectivityType,
996 MED_EN::medEntityMesh Entity) const
998 int spaceDim = getSpaceDimension();
1000 if (ConnectivityType == MED_EN::MED_NODAL)
1002 return getNumberOfNodes()+1;
1007 return getNumberOfElements(MED_EN::MED_EDGE,MED_EN::MED_ALL_ELEMENTS)+1;
1008 else if (spaceDim == 3)
1009 return getNumberOfElements(MED_EN::MED_FACE,MED_EN::MED_ALL_ELEMENTS)+1;
1011 throw MEDEXCEPTION("Invalid dimension");
1015 Returns the index array required by ConnectivityType.
1017 This array allow to find reverse connectivity of each elements.
1019 Example : Reverse connectivity of i^{th} elements (1<=i<=NumberOfElement)
1020 begin at index ReverseConnectivityIndex[i-1] and end at index
1021 ReverseConnectivityIndex[i]-1
1022 in ReverseConnectivity array (
1023 ReverseConnectivity[ReverseConnectivityIndex[i-1]-1]
1026 inline const int * MESH::getReverseConnectivityIndex(MED_EN::medConnectivity ConnectivityType,MED_EN::medEntityMesh Entity/*=MED_CELL*/) const
1028 // checkGridFillConnectivity();
1029 if (NULL==_connectivity)
1030 throw MEDEXCEPTION("MESH::getReverseConnectivityIndex : no connectivity defined in MESH !");
1032 return _connectivity->getReverseConnectivityIndex(ConnectivityType,Entity);
1037 Retrieves the number of families in the mesh for entity type \a entity
1039 inline int MESH::getNumberOfFamilies (MED_EN::medEntityMesh entity) const
1042 case MED_EN::MED_NODE :
1043 return _familyNode.size();
1044 case MED_EN::MED_CELL :
1045 return _familyCell.size();
1046 case MED_EN::MED_FACE :
1047 return _familyFace.size();
1048 case MED_EN::MED_EDGE :
1049 return _familyEdge.size();
1051 throw MEDEXCEPTION("MESH::getNumberOfFamilies : Unknown entity");
1055 /*! Retrieves the number of groups in the mesh for entity type \a entity
1058 inline int MESH::getNumberOfGroups (MED_EN::medEntityMesh entity) const
1061 case MED_EN::MED_NODE :
1062 return _groupNode.size();
1063 case MED_EN::MED_CELL :
1064 return _groupCell.size();
1065 case MED_EN::MED_FACE :
1066 return _groupFace.size();
1067 case MED_EN::MED_EDGE :
1068 return _groupEdge.size();
1070 throw MEDEXCEPTION("MESH::getNumberOfGroups : Unknown entity");
1073 /*! Returns the families of type \a entity present in the mesh as a vector of pointers */
1074 const vector<MEDMEM::FAMILY*> MESH::getFamilies(MED_EN::medEntityMesh entity) const
1077 case MED_EN::MED_NODE :
1079 case MED_EN::MED_CELL :
1081 case MED_EN::MED_FACE :
1083 case MED_EN::MED_EDGE :
1086 throw MEDEXCEPTION("MESH::getFamilies : Unknown entity");
1092 const MEDMEM::FAMILY* MESH::getFamily(MED_EN::medEntityMesh entity, int i) const
1095 throw MEDEXCEPTION("MESH::getFamily(i) : argument i must be > 0");
1096 vector<FAMILY*> Family;
1098 case MED_EN::MED_NODE : {
1099 Family = _familyNode;
1102 case MED_EN::MED_CELL : {
1103 Family = _familyCell;
1106 case MED_EN::MED_FACE : {
1107 Family = _familyFace;
1110 case MED_EN::MED_EDGE : {
1111 Family = _familyEdge;
1115 throw MEDEXCEPTION("MESH::getFamilies : Unknown entity");
1117 if (i>(int)Family.size())
1118 throw MEDEXCEPTION("MESH::getFamily(entity,i) : argument i must be <= _numberOfFamilies");
1127 //inline void MESH::write(const string & driverName) {
1128 // write(0,driverName);
1131 inline bool MESH::getIsAGrid()
1133 SCRUTE_MED(_isAGrid);
1140 #include "MEDMEM_Support.hxx"
1144 //Create a new FIELD that should be deallocated based on a SUPPORT that should be deallocated too.
1146 FIELD<T, FullInterlace> * MESH::mergeFields(const vector< FIELD<T, FullInterlace> * > & others,
1149 const char * LOC = "MESH::mergeFields(const vector< FIELD<T>* >& others,bool meshCompare): ";
1152 if(others.size()==0)
1154 vector<SUPPORT *> sup;
1155 typename vector< FIELD<T, FullInterlace>* >::const_iterator iter;
1156 iter = others.begin();
1157 MED_EN::med_type_champ valueType = (*iter)->getValueType();
1158 for(iter=others.begin();iter!=others.end();iter++)
1160 MED_EN::med_type_champ valueTypeIter = (*iter)->getValueType();
1161 if (valueTypeIter != valueType)
1162 throw MEDEXCEPTION(LOCALIZED(STRING(LOC)<<" Fields vector have not the same value type"));
1164 sup.push_back((SUPPORT *)(*iter)->getSupport());
1166 iter=others.begin();
1167 SUPPORT *retSup=mergeSupports(sup);
1168 int retNumberOfComponents=(*iter)->getNumberOfComponents();
1169 FIELD<T, FullInterlace> *ret=new FIELD<T, FullInterlace>(retSup, retNumberOfComponents);
1170 T* valuesToSet=(T*)ret->getValue();
1171 int nbOfEltsRetSup=retSup->getNumberOfElements(MED_EN::MED_ALL_ELEMENTS);
1172 T* tempValues=new T[retNumberOfComponents];
1173 if(retSup->isOnAllElements())
1175 for(i=0;i<nbOfEltsRetSup;i++)
1178 for(iter=others.begin();iter!=others.end() && !found;iter++)
1180 found=(*iter)->getValueOnElement(i+1,tempValues);
1182 for(j=0;j<retNumberOfComponents;j++)
1183 valuesToSet[i*retNumberOfComponents+j]=tempValues[j];
1189 const int *eltsRetSup=retSup->getNumber(MED_EN::MED_ALL_ELEMENTS);
1190 for(i=0;i<nbOfEltsRetSup;i++)
1193 for(iter=others.begin();iter!=others.end() && !found;iter++)
1195 found=(*iter)->getValueOnElement(eltsRetSup[i],tempValues);
1197 for(j=0;j<retNumberOfComponents;j++)
1198 valuesToSet[i*retNumberOfComponents+j]=tempValues[j];
1201 throw MEDEXCEPTION(LOCALIZED(STRING(LOC)<<" Merging error due to an error in merging support"));
1204 delete [] tempValues;
1211 #endif /* MESH_HXX */