3 // File: VISU_Convertor_impl.cxx
4 // Created: Fri Jan 10 11:44:54 2003
5 // Author: Alexey PETROV
6 // <apo@ivanox.nnov.matra-dtv.fr>
9 #include "VISU_Convertor_impl.hxx"
11 #include <vtkUnstructuredGridReader.h>
13 #include <qfileinfo.h>
14 #include <vtkCellType.h>
20 static int MYDEBUG = 1;
21 static int MYDEBUGWITHFILES = 0;
23 static int MYDEBUG = 0;
24 static int MYDEBUGWITHFILES = 0;
26 static int PRECISION = 7;
28 #define MED2VTK(MEDTYPE,VTKTYPE,VTKNBNODES) \
29 {MEDTYPE,#MEDTYPE,getNbMedNodes(MEDTYPE),VTKTYPE,#VTKTYPE,VTKNBNODES}
30 Med2vtk med2vtk[MED_NBR_GEOMETRIE_MAILLE] = {
31 MED2VTK(MED_POINT1,VTK_VERTEX,1),
32 MED2VTK(MED_SEG2,VTK_LINE,2),
33 MED2VTK(MED_SEG3,VTK_LINE,2),
34 MED2VTK(MED_TRIA3,VTK_TRIANGLE,3),
35 MED2VTK(MED_TRIA6,VTK_TRIANGLE,3),
36 MED2VTK(MED_QUAD4,VTK_QUAD,4),
37 MED2VTK(MED_QUAD8,VTK_QUAD,4),
38 MED2VTK(MED_TETRA4,VTK_TETRA,4),
39 MED2VTK(MED_TETRA10,VTK_TETRA,4),
40 MED2VTK(MED_HEXA8,VTK_HEXAHEDRON,8),
41 MED2VTK(MED_HEXA20,VTK_HEXAHEDRON,8),
42 MED2VTK(MED_PENTA6,VTK_WEDGE,6),
43 MED2VTK(MED_PENTA15,VTK_WEDGE,6),
44 MED2VTK(MED_PYRA5,VTK_PYRAMID,5),
45 MED2VTK(MED_PYRA13,VTK_PYRAMID,5)
50 VISU_Convertor* CreateConvertor(const string& theFileName) throw(std::runtime_error&){
51 if(QFileInfo(theFileName.c_str()).extension(false) == "med")
52 return CreateMedConvertor(theFileName);
54 return CreateDatConvertor(theFileName);
57 int getNbMedConnect(int theMedType, int theMedEntity, int theMeshDim){
58 int anElemDim = theMedType / 100, nsup = 0;
59 if(theMedEntity == VISU::CELL_ENTITY && anElemDim < theMeshDim) nsup = 1;
60 return nsup + theMedType % 100;
63 int getNbMedNodes(int geom){
67 int getIdMedType(int medType){
68 for(int i = 0; i < MED_NBR_GEOMETRIE_MAILLE; i++)
69 if(med2vtk[i].medType == medType) return i;
74 int VISU_Convertor_impl::ToFile(const string& theFileName) throw(std::runtime_error&){
75 if(QFileInfo(theFileName.c_str()).extension(false) == "med")
76 return ToMedFile(theFileName);
78 return ToDatFile(theFileName);
81 VISU_Convertor_impl::VISU_Convertor_impl() : myIsDone(false) {}
83 VISU_Convertor_impl::~VISU_Convertor_impl() {}
85 VISU_Convertor::OutputType* VISU_Convertor_impl::GetMeshOnEntity(const string& theMeshName,
86 const VISU::TEntity& theEntity,
87 const string& theFamilyName)
88 throw (std::runtime_error&)
91 MESSAGE("GetMeshOnEntity - theMeshName = '"<<theMeshName<<
92 "'; theEntity = "<<theEntity<<"; theFamilyName = '"<<theFamilyName<<"'");
93 //Cheching possibility do the query
94 if(myMeshMap.find(theMeshName) == myMeshMap.end())
95 throw std::runtime_error("MeshOnEntityToString >> There is no mesh with the name!!!");
96 VISU::TMesh& aMesh = myMeshMap[theMeshName];
97 VISU::TMeshOnEntityMap& aMeshOnEntityMap = aMesh.myMeshOnEntityMap;
98 if(aMeshOnEntityMap.find(theEntity) == aMeshOnEntityMap.end())
99 throw std::runtime_error("MeshOnEntityToString >> There is no mesh on the entity!!!");
100 VISU::TMeshOnEntity& aMeshOnEntity = aMeshOnEntityMap[theEntity];
101 VISU::TFamily* pFamily = VISU::GetFamily(aMeshOnEntity,theFamilyName);
102 VISU::TVTKReader* pReader;
104 pReader = &(pFamily->myStorage);
106 pReader = &(aMeshOnEntity.myStorage);
107 VISU::TVTKReader& aReader = *pReader;
109 if(aReader.get() == NULL){
110 LoadMeshOnEntity(aMeshOnEntity,theFamilyName);
112 strOut<<GetHead(theMeshName + dtos("-%d-",theEntity) + theFamilyName);
113 strOut<<GetPoints(aMesh);
114 pair<int,int> aCellsDim = aMeshOnEntity.GetCellsDims(theFamilyName);
115 int aNbCells = aCellsDim.first, aCellsSize = aCellsDim.second;
116 ostrstream strCellsOut, strTypesOut;
117 GetCells(strCellsOut,strTypesOut,aMeshOnEntity,theFamilyName);
120 strOut<<"CELLS "<<aNbCells<<"\t"<<aCellsSize<<endl;
121 strOut<<strCellsOut.str()<<endl;
122 strOut<<"CELL_TYPES "<<aNbCells<<endl;
123 strOut<<strTypesOut.str()<<endl;
125 aReader.reset(OutputType::New());
126 //aReader = OutputType::New();
127 //aReader->DebugOn();
128 aReader->ReadFromInputStringOn();
129 aReader->SetInputString(strOut.str());
131 //aReader->Print(cout);
132 if(MYDEBUGWITHFILES){
133 string aMeshName = QString(theMeshName.c_str()).simplifyWhiteSpace().latin1();
134 string aFamilyName = QString(theFamilyName.c_str()).simplifyWhiteSpace().latin1();
135 string aFileName = string("/users/")+getenv("USER")+"/"+getenv("USER")+"-";
136 aFileName += aMeshName + dtos("-%d-",theEntity) + aFamilyName + "-Conv.vtk";
137 ofstream stmOut(aFileName.c_str(),ios::out);
138 stmOut<<strOut.str();
141 return aReader.get();
145 VISU_Convertor::OutputType* VISU_Convertor_impl::GetMeshOnGroup(const string& theMeshName,
146 const string& theGroupName)
147 throw(std::runtime_error&)
149 if(MYDEBUG) MESSAGE("GetMeshOnGroup - theMeshName = '"<<theMeshName<<
150 "'; theGroupName = '"<<theGroupName<<"'");
151 //Cheching possibility do the query
152 if(myMeshMap.find(theMeshName) == myMeshMap.end())
153 throw std::runtime_error("GetMeshOnGroup >> There is no mesh with the name!!!");
154 VISU::TMesh& aMesh = myMeshMap[theMeshName];
155 VISU::TGroupMap& aGroupMap = aMesh.myGroupMap;
156 VISU::TGroupMap::iterator aGroupMapIter = aGroupMap.find(theGroupName);
157 if(aGroupMapIter == aGroupMap.end())
158 throw std::runtime_error("GetMeshOnGroup >> There is no the group in the mesh!!!");
159 VISU::TGroup& aGroup = aGroupMapIter->second;
160 const VISU::TFamilyAndEntitySet& aFamilyAndEntitySet = aGroup.myFamilyAndEntitySet;
161 VISU::TVTKReader& aReader = aGroup.myStorage;
162 if(aReader.get() == NULL){
163 LoadMeshOnGroup(aMesh,aFamilyAndEntitySet);
165 strOut<<GetHead(theMeshName + "-" + theGroupName);
166 strOut<<GetPoints(aMesh);
167 VISU::TFamilyAndEntitySet::const_iterator aFamilyAndEntitySetIter = aFamilyAndEntitySet.begin();
168 int aNbCells = 0, aCellsSize = 0;
169 ostrstream strCellsOut, strTypesOut;
170 for(; aFamilyAndEntitySetIter != aFamilyAndEntitySet.end(); aFamilyAndEntitySetIter++){
171 const VISU::TFamilyAndEntity& aFamilyAndEntity = *aFamilyAndEntitySetIter;
172 const string& aFamilyName = aFamilyAndEntity.first;
173 const VISU::TEntity& anEntity = aFamilyAndEntity.second;
174 VISU::TMeshOnEntity& aMeshOnEntity = aMesh.myMeshOnEntityMap[anEntity];
175 pair<int,int> aCellsDim = aMeshOnEntity.GetCellsDims(aFamilyName);
176 aNbCells += aCellsDim.first;
177 aCellsSize += aCellsDim.second;
178 GetCells(strCellsOut,strTypesOut,aMeshOnEntity,aFamilyName);
182 strOut<<"CELLS "<<aNbCells<<"\t"<<aCellsSize<<endl;
183 strOut<<strCellsOut.str()<<endl;
184 strOut<<"CELL_TYPES "<<aNbCells<<endl;
185 strOut<<strTypesOut.str()<<endl;
187 aReader.reset(OutputType::New());
188 //aReader = OutputType::New();
189 aReader->ReadFromInputStringOn();
190 aReader->SetInputString(strOut.str());
191 if(MYDEBUGWITHFILES){
192 string aMeshName = QString(theMeshName.c_str()).simplifyWhiteSpace().latin1();
193 string aGroupName = QString(theGroupName.c_str()).simplifyWhiteSpace().latin1();
194 string aFileName = string("/users/")+getenv("USER")+"/"+getenv("USER")+"-";
195 aFileName += aMeshName + "-" + aGroupName + "-Conv.vtk";
196 ofstream stmOut(aFileName.c_str(),ios::out);
197 stmOut<<strOut.str();
200 return aReader.get();
204 VISU_Convertor::OutputType* VISU_Convertor_impl::GetFieldOnMesh(const string& theMeshName,
205 const VISU::TEntity& theEntity,
206 const string& theFieldName,
208 throw(std::runtime_error&)
211 MESSAGE("GetFieldOnMesh - theMeshName = '"<<theMeshName<<"; theEntity = "<<theEntity);
212 MESSAGE("GetFieldOnMesh - theFieldName = '"<<theFieldName<<"'; theStampsNum = "<<theStampsNum);
214 //Cheching possibility do the query
215 if(myMeshMap.find(theMeshName) == myMeshMap.end())
216 throw std::runtime_error("GetFieldOnMesh >> There is no mesh with the name!!!");
217 VISU::TMesh& aMesh = myMeshMap[theMeshName];
218 VISU::TMeshOnEntityMap& aMeshOnEntityMap = aMesh.myMeshOnEntityMap;
219 if(aMeshOnEntityMap.find(theEntity) == aMeshOnEntityMap.end())
220 throw std::runtime_error("GetFieldOnMesh >> There is no mesh on the entity!!!");
221 VISU::TMeshOnEntity& aMeshOnEntity = aMeshOnEntityMap[theEntity];
222 VISU::TMeshOnEntity* pVtkMeshOnEntity = &aMeshOnEntity;
223 if(theEntity == VISU::NODE_ENTITY){
224 if(aMeshOnEntityMap.find(VISU::CELL_ENTITY) == aMeshOnEntityMap.end())
225 throw std::runtime_error("GetFieldOnMesh >> There is no mesh on CELL_ENTITY!!!");
226 pVtkMeshOnEntity = &aMeshOnEntityMap[VISU::CELL_ENTITY];
228 VISU::TMeshOnEntity& aVtkMeshOnEntity = *pVtkMeshOnEntity;
229 VISU::TFieldMap& aFieldMap = aMeshOnEntity.myFieldMap;
230 if(aFieldMap.find(theFieldName) == aFieldMap.end())
231 throw std::runtime_error("GetFieldOnMesh >> There is no field on the mesh!!!");
232 VISU::TField& aField = aFieldMap[theFieldName];
233 VISU::TField::TValField& aValField = aField.myValField;
234 if(aValField.find(theStampsNum) == aValField.end())
235 throw std::runtime_error("GetFieldOnMesh >> There is no field with the timestamp!!!");
236 VISU::TField::TValForTime& aValForTime = aValField[theStampsNum];
237 VISU::TVTKReader& aReader = aValForTime.myStorage;
239 if(aReader.get() == NULL){
240 LoadMeshOnEntity(aVtkMeshOnEntity);
241 LoadFieldOnMesh(aMesh,aMeshOnEntity,aField,aValForTime);
243 strOut<<GetHead(theMeshName + dtos("-%d-",theEntity) + theFieldName + dtos("-%d",theStampsNum));
244 strOut<<GetPoints(aMesh);
245 pair<int,int> aCellsDim = aVtkMeshOnEntity.GetCellsDims();
246 int aNbCells = aCellsDim.first, aCellsSize = aCellsDim.second;
247 ostrstream strCellsOut, strTypesOut;
248 GetCells(strCellsOut,strTypesOut,aVtkMeshOnEntity);
251 strOut<<"CELLS "<<aNbCells<<"\t"<<aCellsSize<<endl;
252 strOut<<strCellsOut.str()<<endl;
253 strOut<<"CELL_TYPES "<<aNbCells<<endl;
254 strOut<<strTypesOut.str()<<endl;
255 int aNbPoints = aMesh.myPointsCoord.size()/aMesh.myDim;
256 strOut<<GetField(aField,aValForTime,aMesh.myDim,aNbPoints,aNbCells);
257 aReader.reset(OutputType::New());
258 //aReader = OutputType::New();
259 aReader->ReadFromInputStringOn();
260 aReader->SetInputString(strOut.str());
261 if(MYDEBUGWITHFILES){
262 string aMeshName = QString(theMeshName.c_str()).simplifyWhiteSpace().latin1();
263 string aFieldName = QString(theFieldName.c_str()).simplifyWhiteSpace().latin1();
264 string aFileName = string("/users/")+getenv("USER")+"/"+getenv("USER")+"-";
265 aFileName += aMeshName + dtos("-%d-",theEntity) + aFieldName + dtos("-%d",theStampsNum) + "-Conv.vtk";
266 ofstream stmOut(aFileName.c_str(),ios::out);
267 stmOut<<strOut.str();
270 return aReader.get();
274 inline void PrintCells(ostrstream& strCellsOut, const VISU::TMeshOnEntity::TConnect& theVector,
275 ostrstream& strTypesOut, const int theVtkType)
277 strTypesOut<<theVtkType<<"\n";
278 int kEnd = theVector.size();
279 strCellsOut<<kEnd<<"\t";
280 for(int k = 0; k < kEnd; k++)
281 strCellsOut<<theVector[k]<<"\t";
285 int VISU_Convertor_impl::GetCells(ostrstream& strCellsOut, ostrstream& strTypesOut,
286 const VISU::TMeshOnEntity& theMeshOnEntity,
287 const string& theFamilyName) const
288 throw (std::runtime_error&)
290 //Check on existing family
291 const VISU::TFamily* pFamily = VISU::GetFamily(theMeshOnEntity,theFamilyName);
292 bool isFamilyPresent = (pFamily != NULL);
293 const VISU::TFamily& aFamily = *pFamily;
295 if(MYDEBUG) MESSAGE("GetCells - isFamilyPresent = "<<isFamilyPresent);
296 const VISU::TMeshOnEntity::TCellsConn &aCellsConn = theMeshOnEntity.myCellsConn;
297 VISU::TMeshOnEntity::TCellsConn::const_iterator aCellsConnIter = aCellsConn.begin();
298 for(; aCellsConnIter != aCellsConn.end(); aCellsConnIter++){
299 const VISU::TMeshOnEntity::TConnForCellType& anArray = aCellsConnIter->second;
300 if(MYDEBUG) MESSAGE("GetCells - anArray.size() = "<<anArray.size());
301 int aVtkType = aCellsConnIter->first;
303 for(int j = 0, jEnd = anArray.size(); j < jEnd; j++)
304 PrintCells(strCellsOut,anArray[j],strTypesOut,aVtkType);
306 const VISU::TFamily::TSubMesh& aSubMesh = aFamily.mySubMesh;
307 VISU::TFamily::TSubMesh::const_iterator aSubMeshIter = aSubMesh.find(aVtkType);
308 const VISU::TFamily::TSubMeshOnCellType& aSubMeshOnCellType = aSubMeshIter->second;
309 VISU::TFamily::TSubMeshOnCellType::const_iterator aSubMeshOnCellTypeIter = aSubMeshOnCellType.begin();
310 for(; aSubMeshOnCellTypeIter != aSubMeshOnCellType.end(); aSubMeshOnCellTypeIter++)
311 PrintCells(strCellsOut,anArray[*aSubMeshOnCellTypeIter],strTypesOut,aVtkType);
317 string VISU_Convertor_impl::GetHead(const string& theMeshName) const throw (std::runtime_error&){
319 strOut<<"# vtk DataFile Version 3.2\n";
320 strOut<<theMeshName<<endl;
322 strOut<<"DATASET UNSTRUCTURED_GRID\n";
327 string VISU_Convertor_impl::GetPoints(const VISU::TMesh& theMesh) const
328 throw (std::runtime_error&)
331 strOut.setf(ios::scientific,ios::floatfield); strOut.precision(PRECISION);
332 const VISU::TMesh::TPointsCoord& anArray = theMesh.myPointsCoord;
333 int iEnd = theMesh.myPointsCoord.size();
334 int aNbPoints = iEnd/theMesh.myDim;
335 strOut<<"POINTS "<<aNbPoints<<" float\n";
337 MESSAGE("GetPoints - aNbPoints = "<<aNbPoints<<"; myDim = "<<theMesh.myDim);
338 switch(theMesh.myDim) {
340 for (int i = 0; i < iEnd;)
341 strOut<<anArray[i++]<<"\n";
344 for (int i = 0; i < iEnd;){
345 strOut<<anArray[i++]<<"\t";
346 strOut<<anArray[i++]<<"\t";
351 for (int i = 0; i < iEnd;){
352 strOut<<anArray[i++]<<"\t";
353 strOut<<anArray[i++]<<"\t";
354 strOut<<anArray[i++]<<"\n";
362 string VISU_Convertor_impl::GetField(const VISU::TField& theField,
363 const VISU::TField::TValForTime& theValForTime,
364 int theDim, int theNbPoints, int theNbCells) const
365 throw (std::runtime_error&)
368 strOut.setf(ios::scientific,ios::floatfield); strOut.precision(PRECISION);
369 string aName = GenerateName(theField.myName,theValForTime.myId);
370 if(MYDEBUG) MESSAGE("GetField - aTime = "<<theValForTime.myId<<"; aName = "<<aName);
371 switch(theField.myEntity) {
372 case VISU::NODE_ENTITY :
373 strOut<<"POINT_DATA "<<theNbPoints<<"\n";
376 strOut<<"CELL_DATA "<<theNbCells<<"\n";
378 switch(theField.myNbComp) {
380 strOut<<"SCALARS "<<aName<<" float\n";
381 strOut<<"LOOKUP_TABLE default\n";
384 strOut<<"VECTORS "<<aName<<" float\n";
387 const VISU::TField::TValForCells& aValForCells = theValForTime.myValForCells;
388 VISU::TField::TValForCells::const_iterator aValForCellsIter = aValForCells.begin();
389 for(; aValForCellsIter != aValForCells.end(); aValForCellsIter++) {
390 const VISU::TField::TValForCellsWithType& anArray = aValForCellsIter->second;
391 int iEnd = anArray.size()/theField.myNbComp;
392 int aVtkType = aValForCellsIter->first;
393 if(MYDEBUG) MESSAGE("GetField - iEnd = "<<iEnd<<"; aVtkType = "<<aVtkType<<"; theDim = "<<theDim);
394 if(theField.myNbComp == 1){
395 for (int i = 0; i < iEnd;) strOut<<anArray[i++]<<"\n";
396 }else if(theDim == 2){
397 for (int i = 0, ji = 0; i < iEnd; ji = (++i)*theField.myNbComp){
398 strOut<<anArray[ji++]<<"\t";
399 strOut<<anArray[ji++]<<"\t";
402 }else if(theDim == 3){
403 for (int i = 0, ji = 0; i < iEnd; ji = (++i)*theField.myNbComp){
404 strOut<<anArray[ji++]<<"\t";
405 strOut<<anArray[ji++]<<"\t";
406 strOut<<anArray[ji++]<<"\n";
409 throw std::runtime_error("GetField - There is algorithm for representation the field !!!");