1 // Copyright (C) 2007-2012 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
24 File MEDMEM_Family.cxx
27 #include "MEDMEM_Mesh.hxx"
28 #include "MEDMEM_Family.hxx"
31 using namespace MEDMEM;
32 using namespace MED_EN;
35 Those defines are from the med File V2.1 and for this class they are fixed.
38 #define MED_TAILLE_DESC 200
39 #define MED_TAILLE_LNOM 80
41 FAMILY::FAMILY():_identifier(0), _numberOfAttribute(0), _numberOfGroup(0)
43 MESSAGE_MED("FAMILY::FAMILY()");
46 FAMILY::FAMILY(GMESH* Mesh, int Identifier, string Name, int NumberOfAttribute,
47 int *AttributeIdentifier, int *AttributeValue, string AttributeDescription,
48 int NumberOfGroup, string GroupName,
49 int * MEDArrayNodeFamily,
50 int ** MEDArrayCellFamily,
51 int ** MEDArrayFaceFamily,
52 int ** MEDArrayEdgeFamily
54 _identifier(Identifier),
55 _numberOfAttribute(NumberOfAttribute),
56 _numberOfGroup(NumberOfGroup)
58 MESSAGE_MED("FAMILY(int Identifier, string Name, int NumberOfAttribute,int *AttributeIdentifier,int *AttributeValue,string AttributeDescription,int NumberOfGroup,string GroupName, int ** Number) : "<<Identifier);
62 _isOnAllElts = false ;
63 SCRUTE_MED(_numberOfAttribute);
64 if (_numberOfAttribute > 0)
66 _attributeIdentifier.set(_numberOfAttribute,AttributeIdentifier);
67 _attributeValue.set(_numberOfAttribute,AttributeValue);
69 _attributeDescription.resize(_numberOfAttribute);
70 for (int i=0;i<NumberOfAttribute;i++) {
71 _attributeDescription[i].assign(AttributeDescription,i*MED_TAILLE_DESC,MED_TAILLE_DESC);
72 _attributeDescription[i].erase(strlen(_attributeDescription[i].c_str()));
77 _attributeIdentifier.set(_numberOfAttribute);
78 _attributeValue.set(_numberOfAttribute);
79 _attributeDescription.resize(_numberOfAttribute);
82 _groupName.resize(_numberOfGroup);
83 for (int i=0;i<NumberOfGroup;i++)
85 _groupName[i].assign(GroupName,i*MED_TAILLE_LNOM,MED_TAILLE_LNOM);
86 _groupName[i].erase(strlen(_groupName[i].c_str()));
89 // well, we must set SUPPORT attribut
90 _description = "FAMILY" ;
91 // on which geometric type :
95 // ************************ NODES RELATED PART *************************************************
96 // Scan every node family number <NodeFamilyNumber[i]> in order to create
97 // the list <tmp_NodesList> of node numbers <i+1> belonging to the family <_identifier>
98 int NumberOfNodes = _mesh->getNumberOfNodes();
99 int NumberOfNodesInFamily = 0 ;
100 int * tmp_NodesList = new int[NumberOfNodes] ; // Un peu brutal...., oui mais ce n'est qu'un tableau de travail !
101 for (int i=0; i<NumberOfNodes; i++)
102 if ( _identifier == MEDArrayNodeFamily[i] )
104 tmp_NodesList[NumberOfNodesInFamily]=i+1 ;
105 NumberOfNodesInFamily++;
108 SCRUTE_MED(NumberOfNodesInFamily);
110 // If we found nodes, set the family attributes adequatly
111 if (NumberOfNodesInFamily>0)
117 // family on all NODE
118 if (NumberOfNodesInFamily==NumberOfNodes)
120 _isOnAllElts = true ;
125 _numberOfGeometricType = 1 ;
127 _geometricType.set(1) ;
129 _geometricType[0]=MED_NONE ;
130 _isOnAllElts= false ;
132 _numberOfElements.set(1) ;
134 _numberOfElements[0]=NumberOfNodesInFamily ;
135 _totalNumberOfElements=NumberOfNodesInFamily;
137 int * NumberIndex = new int[2];
138 int * NumberValue = new int[NumberOfNodesInFamily];
140 NumberIndex[0]=1; //set the MEDSKYLINEARRAY Index table
141 NumberIndex[1]=1+NumberOfNodesInFamily; //set the MEDSKYLINEARRAY Index table
142 for(int i=0; i<NumberOfNodesInFamily; i++) // OH LA LA...
143 NumberValue[i]=tmp_NodesList[i] ; // RESIZE de tmp_NodesList serait plus efficace !!!!!!!!
144 setNumber( new MEDSKYLINEARRAY(1,NumberOfNodesInFamily,NumberIndex,NumberValue));
145 delete[] NumberIndex ;
146 delete[] NumberValue ;
149 delete[] tmp_NodesList ;
153 // ************************ CELLS RELATED PART *************************************************
154 // If we previously found nodes in our family don't scan the CELLS because a
155 // family contains different geometic types of only one entity type.
156 // ?? Scan every cell family number <NodeFamilyNumber[i]> in order to create
157 // ?? the list <tmp_NodesList> of node numbers <i+1> belonging to the family <_identifier>
160 Find = build(MED_CELL,MEDArrayCellFamily) ;
165 if ( _mesh->getNumberOfElements(MED_FACE, MED_ALL_ELEMENTS) > 0 )
166 Find = build(MED_FACE,MEDArrayFaceFamily) ;
172 if ( _mesh->getNumberOfElements(MED_EDGE, MED_ALL_ELEMENTS) > 0 )
173 Find = build(MED_EDGE,MEDArrayEdgeFamily) ;
177 // if not find : no entity in familly !!!
180 _numberOfGeometricType = 0 ;
181 _isOnAllElts = false ;
182 MESSAGE_MED ("FAMILY() : No entity found !") ;
185 MESSAGE_MED("Well now ??? :::");
187 MESSAGE_MED("Name : "<< getName());
188 MESSAGE_MED("Description : "<< getDescription());
189 MESSAGE_MED("Mesh name : " << getMesh()->getName());
190 MESSAGE_MED("Entity : "<< getEntity());
191 MESSAGE_MED("Entity list :");
192 if ( !isOnAllElements() )
194 MESSAGE_MED("NumberOfTypes : "<<getNumberOfTypes());
195 for (int j=0;j<getNumberOfTypes();j++)
197 MESSAGE_MED(" * Type "<<getTypes()[j]<<" : there is(are) "<<
198 getNumberOfElements(getTypes()[j])<<" element(s) : ");
199 SCRUTE_MED(getNumber(getTypes()[j]));
204 MESSAGE_MED("Is on all entities !");
208 FAMILY::FAMILY(const FAMILY & m):SUPPORT(m)
210 MESSAGE_MED("FAMILY::FAMILY(FAMILY & m)");
211 _identifier = m._identifier;
212 _numberOfAttribute = m._numberOfAttribute;
214 if (_numberOfAttribute)
216 _attributeIdentifier.set(_numberOfAttribute,m._attributeIdentifier);
217 _attributeValue.set(_numberOfAttribute,m._attributeValue);
220 _attributeDescription.resize(_numberOfAttribute);
221 for (int i=0;i<m._numberOfAttribute;i++)
222 _attributeDescription[i] = m._attributeDescription[i];
224 _numberOfGroup = m._numberOfGroup;
226 _groupName.resize(_numberOfGroup) ;
227 for (int i=0;i<m._numberOfGroup;i++)
228 _groupName[i]=m._groupName[i];
231 FAMILY::FAMILY(const SUPPORT & s):SUPPORT(s)
233 MESSAGE_MED("FAMILY::FAMILY(const SUPPORT & s)");
236 _numberOfAttribute = 0;
243 MESSAGE_MED("~FAMILY()");
246 FAMILY & FAMILY::operator=(const FAMILY &fam)
248 MESSAGE_MED("FAMILY::operator=");
249 if ( this == &fam ) return *this;
251 //Etant donné que l'opérateur d'affectation de la classe SUPPORT effectuait
252 //une recopie profonde j'ai mis en cohérence l'opérateur d'affectation
253 // de la classe FAMILY
254 SUPPORT::operator=(fam);
257 _identifier = fam._identifier;
258 _numberOfAttribute = fam._numberOfAttribute;
259 _attributeIdentifier.set(_numberOfAttribute, fam._attributeIdentifier) ;
260 _attributeValue.set(_numberOfAttribute, fam._attributeValue) ;
261 _attributeDescription.clear();
262 _attributeDescription = fam._attributeDescription;
263 _numberOfGroup = fam._numberOfGroup;
265 _groupName = fam._groupName;
269 ostream & MEDMEM::operator<<(ostream &os, FAMILY &myFamily)
271 // how do cast without duplicate ?
272 os << (SUPPORT&) myFamily;
274 os << " - Identifier : "<<myFamily.getIdentifier()<<endl;
275 int numberofattributes = myFamily.getNumberOfAttributes();
276 os << " - Attributes ("<<numberofattributes<<") :"<<endl;
277 for (int j=1;j<numberofattributes+1;j++)
278 os << " * "<<myFamily.getAttributeIdentifier(j)<<" : "<<myFamily.getAttributeValue(j)<<", "<<myFamily.getAttributeDescription(j).c_str()<<endl;
279 int numberofgroups = myFamily.getNumberOfGroups();
280 os << " - Groups ("<<numberofgroups<<") :"<<endl;
281 for (int j=1;j<numberofgroups+1;j++)
282 os << " * "<<myFamily.getGroupName(j).c_str()<<endl ;
287 ostream & MEDMEM::operator<<(ostream &os, const FAMILY &myFamily)
289 // how do cast without duplicate ?
290 os << (const SUPPORT&) myFamily;
292 os << " - Identifier : "<<myFamily.getIdentifier()<<endl;
293 int numberofattributes = myFamily.getNumberOfAttributes();
294 os << " - Attributes ("<<numberofattributes<<") :"<<endl;
295 for (int j=1;j<numberofattributes+1;j++)
296 os << " * "<<myFamily.getAttributeIdentifier(j)<<" : "<<myFamily.getAttributeValue(j)<<", "<<myFamily.getAttributeDescription(j).c_str()<<endl;
297 int numberofgroups = myFamily.getNumberOfGroups();
298 os << " - Groups ("<<numberofgroups<<") :"<<endl;
299 for (int j=1;j<numberofgroups+1;j++)
300 os << " * "<<myFamily.getGroupName(j).c_str()<<endl ;
305 bool FAMILY::build(medEntityMesh Entity,int **FamilyNumber /* from MED file */)
307 MESSAGE_MED("FAMILY::build(medEntityMesh Entity,int **FamilyNumber /* from MED file */)");
309 // Get types information from <_mesh>
310 int numberOfTypes = _mesh->getNumberOfTypes(Entity) ;
311 const medGeometryElement * types = _mesh->getTypes(Entity) ;
313 int * numberOfElementsInFamily = new int[numberOfTypes] ;
314 int numberOfElementTypesInFamily = 0 ;
316 medGeometryElement * tmp_Types = new medGeometryElement[numberOfTypes];
317 int ** tmp_ElementsLists = new int*[numberOfTypes] ;
318 int elementNumber = 1;
321 SCRUTE_MED(numberOfTypes);
323 // we search for all elements in this family
324 for (int TypeNumber=0; TypeNumber < numberOfTypes; TypeNumber++) {
326 int NumberOfElements = _mesh->getNumberOfElements(Entity,types[TypeNumber]) ;
327 int NumberOfElementsInThisFamily = 0 ;
328 int * ElementsOfThisFamilyNumber = FamilyNumber[TypeNumber];
329 int * tmp_ElementsList = new int[NumberOfElements];
331 for (int i=0; i<NumberOfElements; i++, elementNumber++)
333 if (_identifier == ElementsOfThisFamilyNumber[i]) {
334 tmp_ElementsList[NumberOfElementsInThisFamily]=elementNumber;
335 NumberOfElementsInThisFamily++;
339 if (NumberOfElementsInThisFamily>0) {// we have found some elements
340 numberOfElementsInFamily[numberOfElementTypesInFamily]=NumberOfElementsInThisFamily;
342 int * ElementsList = new int[NumberOfElementsInThisFamily] ;
343 memcpy(ElementsList,tmp_ElementsList,sizeof(int)*NumberOfElementsInThisFamily); // RESIZE de tmp_NodesList serait plus efficace !!!!!!!!
345 tmp_ElementsLists[numberOfElementTypesInFamily]=ElementsList ;
346 tmp_Types[numberOfElementTypesInFamily]=types[TypeNumber];
347 numberOfElementTypesInFamily++;
349 delete[] tmp_ElementsList;
352 // we define all attribut in SUPPORT :
353 if (numberOfElementTypesInFamily>0) // we have found elements
357 _numberOfGeometricType = numberOfElementTypesInFamily ;
358 _geometricType.set(numberOfElementTypesInFamily) ;
360 _isOnAllElts = false ;
362 _numberOfElements.set(numberOfElementTypesInFamily) ;
363 _totalNumberOfElements=0;
365 for (int i=0; i<numberOfElementTypesInFamily; i++)
367 _geometricType[i]=tmp_Types[i] ;
368 _numberOfElements[i]=numberOfElementsInFamily[i]; // plutot un resize !!
369 _totalNumberOfElements+=_numberOfElements[i];
372 // family on all ELEMENT ?
373 if (Entity == MED_EN::MED_CELL &&
374 _totalNumberOfElements ==_mesh->getNumberOfElements(Entity,MED_ALL_ELEMENTS))
376 _isOnAllElts = true ;
378 // all others attributs are rights !
379 for (int i=0; i<_numberOfGeometricType; i++)
380 delete[] tmp_ElementsLists[i];
384 int *NumberValue = new int[_totalNumberOfElements];
385 int *NumberIndex = new int[_numberOfGeometricType+1];
387 for (int i=0; i<_numberOfGeometricType; i++)
389 NumberIndex[i+1]=NumberIndex[i]+_numberOfElements[i];
390 for (int j=NumberIndex[i]; j<NumberIndex[i+1]; j++)
391 NumberValue[j-1]=tmp_ElementsLists[i][j-NumberIndex[i]];
392 delete[] tmp_ElementsLists[i];
394 setNumber( new MEDSKYLINEARRAY(_numberOfGeometricType, _totalNumberOfElements,
395 NumberIndex, NumberValue));
396 delete[] NumberIndex ;
397 delete[] NumberValue ;
401 delete[] numberOfElementsInFamily;
403 delete[] tmp_ElementsLists;