]> SALOME platform Git repositories - plugins/ghs3dplugin.git/blob - src/GHS3DPlugin/GHS3DPlugin_Hypothesis.cxx
Salome HOME
23307: [EDF 7315] Improvement of DISTENE meshing plugins
[plugins/ghs3dplugin.git] / src / GHS3DPlugin / GHS3DPlugin_Hypothesis.cxx
1 // Copyright (C) 2004-2016  CEA/DEN, EDF R&D
2 //
3 // This library is free software; you can redistribute it and/or
4 // modify it under the terms of the GNU Lesser General Public
5 // License as published by the Free Software Foundation; either
6 // version 2.1 of the License, or (at your option) any later version.
7 //
8 // This library is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
11 // Lesser General Public License for more details.
12 //
13 // You should have received a copy of the GNU Lesser General Public
14 // License along with this library; if not, write to the Free Software
15 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
16 //
17 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
18 //
19
20 //=============================================================================
21 // File      : GHS3DPlugin_Hypothesis.cxx
22 // Created   : Wed Apr  2 12:36:29 2008
23 // Author    : Edward AGAPOV (eap)
24 //=============================================================================
25 //
26 #include "GHS3DPlugin_Hypothesis.hxx"
27
28 #include <SMESHDS_Mesh.hxx>
29
30 #include <TCollection_AsciiString.hxx>
31
32 #ifdef WIN32
33 #include <process.h>
34 #define getpid _getpid
35 #endif
36
37 using namespace std;
38
39 //=======================================================================
40 //function : GHS3DPlugin_Hypothesis
41 //=======================================================================
42
43 GHS3DPlugin_Hypothesis::GHS3DPlugin_Hypothesis(int hypId, int studyId, SMESH_Gen * gen)
44   : SMESH_Hypothesis(hypId, studyId, gen),
45   myToMeshHoles(DefaultMeshHoles()),
46   myToMakeGroupsOfDomains(DefaultToMakeGroupsOfDomains()),
47   myMaximumMemory(-1),
48   myInitialMemory(-1),
49   myOptimizationLevel(DefaultOptimizationLevel()),
50   myKeepFiles(DefaultKeepFiles()),
51   myWorkingDirectory(DefaultWorkingDirectory()),
52   myVerboseLevel(DefaultVerboseLevel()),
53   myToCreateNewNodes(DefaultToCreateNewNodes()),
54   myToUseBoundaryRecoveryVersion(DefaultToUseBoundaryRecoveryVersion()),
55   myToUseFemCorrection(DefaultToUseFEMCorrection()),
56   myToRemoveCentralPoint(DefaultToRemoveCentralPoint()),
57   myLogInStandardOutput(DefaultStandardOutputLog()),
58   myGradation(DefaultGradation()),
59   _enfVertexList(DefaultGHS3DEnforcedVertexList()),
60   _enfVertexCoordsSizeList(DefaultGHS3DEnforcedVertexCoordsValues()),
61   _enfVertexEntrySizeList(DefaultGHS3DEnforcedVertexEntryValues()),
62   _coordsEnfVertexMap(DefaultCoordsGHS3DEnforcedVertexMap()),
63   _geomEntryEnfVertexMap(DefaultGeomEntryGHS3DEnforcedVertexMap()),
64   _enfMeshList(DefaultGHS3DEnforcedMeshList()),
65   _entryEnfMeshMap(DefaultEntryGHS3DEnforcedMeshListMap()),
66   _enfNodes(TIDSortedNodeGroupMap()),
67   _enfEdges(TIDSortedElemGroupMap()),
68   _enfTriangles(TIDSortedElemGroupMap()),
69   _nodeIDToSizeMap(DefaultID2SizeMap()),
70   _groupsToRemove(DefaultGroupsToRemove())
71 {
72   _name = GetHypType();
73   _param_algo_dim = 3;
74 }
75
76 //=======================================================================
77 //function : SetToMeshHoles
78 //=======================================================================
79
80 void GHS3DPlugin_Hypothesis::SetToMeshHoles(bool toMesh)
81 {
82   if ( myToMeshHoles != toMesh ) {
83     myToMeshHoles = toMesh;
84     NotifySubMeshesHypothesisModification();
85   }
86 }
87
88 //=======================================================================
89 //function : GetToMeshHoles
90 //=======================================================================
91
92 bool GHS3DPlugin_Hypothesis::GetToMeshHoles(bool checkFreeOption) const
93 {
94   if (checkFreeOption && !myTextOption.empty()) {
95     if ( myTextOption.find("--components all"))
96       return true;
97     if ( myTextOption.find("--components outside_components"))
98       return false;
99   }
100   return myToMeshHoles;
101 }
102
103 //=======================================================================
104 //function : SetToMakeGroupsOfDomains
105 //=======================================================================
106
107 void GHS3DPlugin_Hypothesis::SetToMakeGroupsOfDomains(bool toMakeGroups)
108 {
109   if ( myToMakeGroupsOfDomains != toMakeGroups ) {
110     myToMakeGroupsOfDomains = toMakeGroups;
111     NotifySubMeshesHypothesisModification();
112   }
113 }
114
115 //=======================================================================
116 //function : GetToMakeGroupsOfDomains
117 //=======================================================================
118
119 bool GHS3DPlugin_Hypothesis::GetToMakeGroupsOfDomains() const
120 {
121   return myToMakeGroupsOfDomains;
122 }
123
124 //=======================================================================
125 //function : GetToMakeGroupsOfDomains
126 //=======================================================================
127
128 bool GHS3DPlugin_Hypothesis::GetToMakeGroupsOfDomains(const GHS3DPlugin_Hypothesis* hyp)
129 {
130   bool res;
131   if ( hyp ) res = /*hyp->GetToMeshHoles(true) &&*/ hyp->GetToMakeGroupsOfDomains();
132   else       res = /*DefaultMeshHoles()        &&*/ DefaultToMakeGroupsOfDomains();
133   return res;
134 }
135
136 //=======================================================================
137 //function : SetMaximumMemory
138 //=======================================================================
139
140 void GHS3DPlugin_Hypothesis::SetMaximumMemory(long MB)
141 {
142   if ( myMaximumMemory != MB ) {
143     myMaximumMemory = MB;
144     NotifySubMeshesHypothesisModification();
145   }
146 }
147
148 //=======================================================================
149 //function : GetMaximumMemory
150 //           * automatic memory adjustment mode. Default is zero
151 //=======================================================================
152
153 long GHS3DPlugin_Hypothesis::GetMaximumMemory() const
154 {
155   return myMaximumMemory;
156 }
157
158 //=======================================================================
159 //function : SetInitialMemory
160 //=======================================================================
161
162 void GHS3DPlugin_Hypothesis::SetInitialMemory(long MB)
163 {
164   if ( myInitialMemory != MB ) {
165     myInitialMemory = MB;
166     NotifySubMeshesHypothesisModification();
167   }
168 }
169
170 //=======================================================================
171 //function : GetInitialMemory
172 //=======================================================================
173
174 long GHS3DPlugin_Hypothesis::GetInitialMemory() const
175 {
176   return myInitialMemory;
177 }
178
179 //=======================================================================
180 //function : SetOptimizationLevel
181 //=======================================================================
182
183 void GHS3DPlugin_Hypothesis::SetOptimizationLevel(OptimizationLevel level)
184 {
185   if ( myOptimizationLevel != level ) {
186     myOptimizationLevel = level;
187     NotifySubMeshesHypothesisModification();
188   }
189 }
190
191 //=======================================================================
192 //function : GetOptimizationLevel
193 //=======================================================================
194
195 GHS3DPlugin_Hypothesis::OptimizationLevel GHS3DPlugin_Hypothesis::GetOptimizationLevel() const
196 {
197   return (OptimizationLevel) myOptimizationLevel;
198 }
199
200 //=======================================================================
201 //function : SetWorkingDirectory
202 //=======================================================================
203
204 void GHS3DPlugin_Hypothesis::SetWorkingDirectory(const std::string& path)
205 {
206   if ( myWorkingDirectory != path ) {
207     myWorkingDirectory = path;
208     NotifySubMeshesHypothesisModification();
209   }
210 }
211
212 //=======================================================================
213 //function : GetWorkingDirectory
214 //=======================================================================
215
216 std::string GHS3DPlugin_Hypothesis::GetWorkingDirectory() const
217 {
218   return myWorkingDirectory;
219 }
220
221 //=======================================================================
222 //function : SetKeepFiles
223 //=======================================================================
224
225 void GHS3DPlugin_Hypothesis::SetKeepFiles(bool toKeep)
226 {
227   if ( myKeepFiles != toKeep ) {
228     myKeepFiles = toKeep;
229     NotifySubMeshesHypothesisModification();
230   }
231 }
232
233 //=======================================================================
234 //function : GetKeepFiles
235 //=======================================================================
236
237 bool GHS3DPlugin_Hypothesis::GetKeepFiles() const
238 {
239   return myKeepFiles;
240 }
241
242 //=======================================================================
243 //function : SetVerboseLevel
244 //=======================================================================
245
246 void GHS3DPlugin_Hypothesis::SetVerboseLevel(short level)
247 {
248   if ( myVerboseLevel != level ) {
249     myVerboseLevel = level;
250     NotifySubMeshesHypothesisModification();
251   }
252 }
253
254 //=======================================================================
255 //function : GetVerboseLevel
256 //=======================================================================
257
258 short GHS3DPlugin_Hypothesis::GetVerboseLevel() const
259 {
260   return myVerboseLevel;
261 }
262
263 //=======================================================================
264 //function : SetToCreateNewNodes
265 //=======================================================================
266
267 void GHS3DPlugin_Hypothesis::SetToCreateNewNodes(bool toCreate)
268 {
269   if ( myToCreateNewNodes != toCreate ) {
270     myToCreateNewNodes = toCreate;
271     NotifySubMeshesHypothesisModification();
272   }
273 }
274
275 //=======================================================================
276 //function : GetToCreateNewNodes
277 //=======================================================================
278
279 bool GHS3DPlugin_Hypothesis::GetToCreateNewNodes() const
280 {
281   return myToCreateNewNodes;
282 }
283
284 //=======================================================================
285 //function : SetToUseBoundaryRecoveryVersion
286 //=======================================================================
287
288 void GHS3DPlugin_Hypothesis::SetToUseBoundaryRecoveryVersion(bool toUse)
289 {
290   if ( myToUseBoundaryRecoveryVersion != toUse ) {
291     myToUseBoundaryRecoveryVersion = toUse;
292     NotifySubMeshesHypothesisModification();
293   }
294 }
295
296 //=======================================================================
297 //function : GetToUseBoundaryRecoveryVersion
298 //=======================================================================
299
300 bool GHS3DPlugin_Hypothesis::GetToUseBoundaryRecoveryVersion() const
301 {
302   return myToUseBoundaryRecoveryVersion;
303 }
304
305 //=======================================================================
306 //function : SetFEMCorrection
307 //=======================================================================
308
309 void GHS3DPlugin_Hypothesis::SetFEMCorrection(bool toUseFem)
310 {
311   if ( myToUseFemCorrection != toUseFem ) {
312     myToUseFemCorrection = toUseFem;
313     NotifySubMeshesHypothesisModification();
314   }
315 }
316
317 //=======================================================================
318 //function : GetFEMCorrection
319 //=======================================================================
320
321 bool GHS3DPlugin_Hypothesis::GetFEMCorrection() const
322 {
323   return myToUseFemCorrection;
324 }
325
326 //=======================================================================
327 //function : SetToRemoveCentralPoint
328 //=======================================================================
329
330 void GHS3DPlugin_Hypothesis::SetToRemoveCentralPoint(bool toRemove)
331 {
332   if ( myToRemoveCentralPoint != toRemove ) {
333     myToRemoveCentralPoint = toRemove;
334     NotifySubMeshesHypothesisModification();
335   }
336 }
337
338 //=======================================================================
339 //function : GetToRemoveCentralPoint
340 //=======================================================================
341
342 bool GHS3DPlugin_Hypothesis::GetToRemoveCentralPoint() const
343 {
344   return myToRemoveCentralPoint;
345 }
346
347 //=======================================================================
348 //function : SetAdvancedOption
349 //=======================================================================
350
351 void GHS3DPlugin_Hypothesis::SetAdvancedOption(const std::string& option)
352 {
353   if ( myTextOption != option ) {
354     myTextOption = option;
355     NotifySubMeshesHypothesisModification();
356   }
357 }
358
359 //=======================================================================
360 //function : GetAdvancedOption
361 //=======================================================================
362
363 std::string GHS3DPlugin_Hypothesis::GetAdvancedOption() const
364 {
365   return myTextOption;
366 }
367
368 //=======================================================================
369 //function : SetGradation
370 //=======================================================================
371
372 void GHS3DPlugin_Hypothesis::SetGradation(double gradation)
373 {
374   if ( myGradation != gradation ) {
375     myGradation = gradation;
376     NotifySubMeshesHypothesisModification();
377   }
378 }
379
380 //=======================================================================
381 //function : GetGradation
382 //=======================================================================
383
384 double GHS3DPlugin_Hypothesis::GetGradation() const
385 {
386   return myGradation;
387 }
388
389 //=======================================================================
390 //function : SetStandardOutputLog
391 //=======================================================================
392
393 void GHS3DPlugin_Hypothesis::SetStandardOutputLog(bool logInStandardOutput)
394 {
395   if ( myLogInStandardOutput != logInStandardOutput ) {
396     myLogInStandardOutput = logInStandardOutput;
397     NotifySubMeshesHypothesisModification();
398   }
399 }
400
401 //=======================================================================
402 //function : GetStandardOutputLog
403 //=======================================================================
404
405 bool GHS3DPlugin_Hypothesis::GetStandardOutputLog() const
406 {
407   return myLogInStandardOutput;
408 }
409
410 //=======================================================================
411 //function : SetRemoveLogOnSuccess
412 //=======================================================================
413
414 void GHS3DPlugin_Hypothesis::SetRemoveLogOnSuccess(bool removeLogOnSuccess)
415 {
416   if ( myRemoveLogOnSuccess != removeLogOnSuccess ) {
417     myRemoveLogOnSuccess = removeLogOnSuccess;
418     NotifySubMeshesHypothesisModification();
419   }
420 }
421
422 //=======================================================================
423 //function : GetRemoveLogOnSuccess
424 //=======================================================================
425
426 bool GHS3DPlugin_Hypothesis::GetRemoveLogOnSuccess() const
427 {
428   return myRemoveLogOnSuccess;
429 }
430
431 //=======================================================================
432 //function : SetEnforcedVertex
433 //=======================================================================
434
435 bool GHS3DPlugin_Hypothesis::SetEnforcedVertex(std::string theName, std::string theEntry, std::string theGroupName,
436                                                double size, double x, double y, double z, bool isCompound)
437 {
438   MESSAGE("GHS3DPlugin_Hypothesis::SetEnforcedVertex(\""<< theName << "\", \""<< theEntry << "\", \"" << theGroupName << "\", "
439                                                       << size << ", " << x << ", " << y << ", " << z  << ", "<< isCompound << ")");
440
441   bool toNotify = false;
442   bool toCreate = true;
443
444   TGHS3DEnforcedVertex *oldEnVertex;
445   TGHS3DEnforcedVertex *newEnfVertex = new TGHS3DEnforcedVertex();
446   newEnfVertex->name = theName;
447   newEnfVertex->geomEntry = theEntry;
448   newEnfVertex->coords.clear();
449   if (!isCompound) {
450     newEnfVertex->coords.push_back(x);
451     newEnfVertex->coords.push_back(y);
452     newEnfVertex->coords.push_back(z);
453   }
454   newEnfVertex->groupName = theGroupName;
455   newEnfVertex->size = size;
456   newEnfVertex->isCompound = isCompound;
457   
458   
459   // update _enfVertexList
460   TGHS3DEnforcedVertexList::iterator it = _enfVertexList.find(newEnfVertex);
461   if (it != _enfVertexList.end()) {
462     toCreate = false;
463     oldEnVertex = (*it);
464     MESSAGE("Enforced Vertex was found => Update");
465     if (oldEnVertex->name != theName) {
466       MESSAGE("Update name from \"" << oldEnVertex->name << "\" to \"" << theName << "\"");
467       oldEnVertex->name = theName;
468       toNotify = true;
469     }
470     if (oldEnVertex->groupName != theGroupName) {
471       MESSAGE("Update group name from \"" << oldEnVertex->groupName << "\" to \"" << theGroupName << "\"");
472       oldEnVertex->groupName = theGroupName;
473       toNotify = true;
474     }
475     if (oldEnVertex->size != size) {
476       MESSAGE("Update size from \"" << oldEnVertex->size << "\" to \"" << size << "\"");
477       oldEnVertex->size = size;
478       toNotify = true;
479     }
480     if (toNotify) {
481       // update map coords / enf vertex if needed
482       if (oldEnVertex->coords.size()) {
483         _coordsEnfVertexMap[oldEnVertex->coords] = oldEnVertex;
484         _enfVertexCoordsSizeList[oldEnVertex->coords] = size;
485       }
486
487       // update map geom entry / enf vertex if needed
488       if (oldEnVertex->geomEntry != "") {
489         _geomEntryEnfVertexMap[oldEnVertex->geomEntry] = oldEnVertex;
490         _enfVertexEntrySizeList[oldEnVertex->geomEntry] = size;
491       }
492     }
493   }
494
495 //   //////// CREATE ////////////
496   if (toCreate) {
497     toNotify = true;
498     MESSAGE("Creating new enforced vertex");
499     _enfVertexList.insert(newEnfVertex);
500     if (theEntry == "") {
501       _coordsEnfVertexMap[newEnfVertex->coords] = newEnfVertex;
502       _enfVertexCoordsSizeList[newEnfVertex->coords] = size;
503     }
504     else {
505       _geomEntryEnfVertexMap[newEnfVertex->geomEntry] = newEnfVertex;
506       _enfVertexEntrySizeList[newEnfVertex->geomEntry] = size;
507     }
508   }
509
510   if (toNotify)
511     NotifySubMeshesHypothesisModification();
512
513   MESSAGE("GHS3DPlugin_Hypothesis::SetEnforcedVertex END");
514   return toNotify;
515 }
516
517
518 //=======================================================================
519 //function : SetEnforcedMesh
520 //=======================================================================
521 bool GHS3DPlugin_Hypothesis::SetEnforcedMesh(SMESH_Mesh& theMesh, SMESH::ElementType elementType, std::string name, std::string entry, std::string groupName)
522 {
523   TIDSortedElemSet theElemSet;
524   SMDS_ElemIteratorPtr eIt = theMesh.GetMeshDS()->elementsIterator(SMDSAbs_ElementType(elementType));
525   while ( eIt->more() )
526     theElemSet.insert( eIt->next() );
527   MESSAGE("Add "<<theElemSet.size()<<" types["<<elementType<<"] from source mesh");
528   bool added = SetEnforcedElements( theElemSet, elementType, groupName);
529   if (added) {
530     TGHS3DEnforcedMesh* newEnfMesh = new TGHS3DEnforcedMesh();
531     newEnfMesh->persistID   = theMesh.GetMeshDS()->GetPersistentId();
532     newEnfMesh->name        = name;
533     newEnfMesh->entry       = entry;
534     newEnfMesh->elementType = elementType;
535     newEnfMesh->groupName   = groupName;
536     
537     TGHS3DEnforcedMeshList::iterator it = _enfMeshList.find(newEnfMesh);
538     if (it == _enfMeshList.end()) {
539       _entryEnfMeshMap[entry].insert(newEnfMesh);
540       _enfMeshList.insert(newEnfMesh);
541     }
542     else {
543       delete newEnfMesh;
544     }
545   }
546   return added;
547 }
548
549 //=======================================================================
550 //function : SetEnforcedGroup
551 //=======================================================================
552 bool GHS3DPlugin_Hypothesis::SetEnforcedGroup(const SMESHDS_Mesh* theMeshDS, SMESH::long_array_var theIDs, SMESH::ElementType elementType, std::string name, std::string entry, std::string groupName)
553 {
554   MESSAGE("GHS3DPlugin_Hypothesis::SetEnforcedGroup");
555   TIDSortedElemSet theElemSet;
556     if ( theIDs->length() == 0 ){MESSAGE("The source group is empty");}
557     for ( CORBA::ULong i=0; i < theIDs->length(); i++) {
558       CORBA::Long ind = theIDs[i];
559       if (elementType == SMESH::NODE)
560       {
561         const SMDS_MeshNode * node = theMeshDS->FindNode(ind);
562         if (node)
563           theElemSet.insert( node );
564       }
565       else
566       {
567         const SMDS_MeshElement * elem = theMeshDS->FindElement(ind);
568         if (elem)
569           theElemSet.insert( elem );
570       }
571     }
572
573 //   SMDS_ElemIteratorPtr it = theGroup->GetGroupDS()->GetElements();
574 //   while ( it->more() ) 
575 //     theElemSet.insert( it->next() );
576
577   MESSAGE("Add "<<theElemSet.size()<<" types["<<elementType<<"] from source group ");
578   bool added = SetEnforcedElements( theElemSet, elementType, groupName);
579   if (added) {
580     TGHS3DEnforcedMesh* newEnfMesh = new TGHS3DEnforcedMesh();
581     newEnfMesh->name = name;
582     newEnfMesh->entry = entry;
583     newEnfMesh->elementType = elementType;
584     newEnfMesh->groupName = groupName;
585     
586     TGHS3DEnforcedMeshList::iterator it = _enfMeshList.find(newEnfMesh);
587     if (it == _enfMeshList.end()) {
588       _entryEnfMeshMap[entry].insert(newEnfMesh);
589       _enfMeshList.insert(newEnfMesh);
590     }
591   }
592   return added;
593 }
594
595 //=======================================================================
596 //function : SetEnforcedElements
597 //=======================================================================
598 bool GHS3DPlugin_Hypothesis::SetEnforcedElements(TIDSortedElemSet theElemSet, SMESH::ElementType elementType, std::string groupName)
599 {
600   MESSAGE("GHS3DPlugin_Hypothesis::SetEnforcedElements");
601   TIDSortedElemSet::const_iterator it = theElemSet.begin();
602   const SMDS_MeshElement* elem;
603   const SMDS_MeshNode* node;
604   bool added = true;
605   pair<TIDSortedNodeGroupMap::iterator,bool> nodeRet;
606   pair<TIDSortedElemGroupMap::iterator,bool> elemRet;
607
608   for (;it != theElemSet.end();++it)
609   {
610     elem = (*it);
611     switch (elementType) {
612       case SMESH::NODE:
613         node = dynamic_cast<const SMDS_MeshNode*>(elem);
614         if (node) {
615           nodeRet = _enfNodes.insert(make_pair(node,groupName));
616           added = added && nodeRet.second;
617           string msg = added ? "yes":"no";
618           MESSAGE( "Node (" <<node->X()<<","<<node->Y()<<","<<node->Z()<< ") with ID " << node->GetID() <<" added ? " << msg);
619         }
620         else {
621           SMDS_ElemIteratorPtr nodeIt = elem->nodesIterator();
622           for (;nodeIt->more();) {
623             node = dynamic_cast<const SMDS_MeshNode*>(nodeIt->next());
624             nodeRet = _enfNodes.insert(make_pair(node,groupName));
625             added = added && nodeRet.second;
626           }
627 //          added = true;s
628         }
629         break;
630       case SMESH::EDGE:
631         if (elem->GetType() == SMDSAbs_Edge) {
632           elemRet = _enfEdges.insert(make_pair(elem,groupName));
633           added = added && elemRet.second;
634         }
635         else if (elem->GetType() > SMDSAbs_Edge) {
636           SMDS_ElemIteratorPtr it = elem->edgesIterator();
637           for (;it->more();) {
638             const SMDS_MeshElement* anEdge = it->next();
639             elemRet = _enfEdges.insert(make_pair(anEdge,groupName));
640             added = added && elemRet.second;
641           }
642         }
643         break;
644       case SMESH::FACE:
645         if (elem->GetType() == SMDSAbs_Face)
646         {
647           if (elem->NbCornerNodes() == 3) {
648             elemRet = _enfTriangles.insert(make_pair(elem,groupName));
649             added = added && elemRet.second;
650           }
651         }
652         else if (elem->GetType() > SMDSAbs_Face) { // Group of faces
653           SMDS_ElemIteratorPtr it = elem->facesIterator();
654           for (;it->more();) {
655             const SMDS_MeshElement* aFace = it->next();
656             if (aFace->NbCornerNodes() == 3) {
657               elemRet = _enfTriangles.insert(make_pair(aFace,groupName));
658               added = added && elemRet.second;
659             }
660           }
661         }
662         break;
663       default:
664         break;
665     };
666   }
667   if (added)
668     NotifySubMeshesHypothesisModification();
669   return added;
670 }
671
672
673 //=======================================================================
674 //function : GetEnforcedVertex
675 //=======================================================================
676
677 GHS3DPlugin_Hypothesis::TGHS3DEnforcedVertex* GHS3DPlugin_Hypothesis::GetEnforcedVertex(double x, double y, double z)
678   throw (std::invalid_argument)
679 {
680   std::vector<double> coord(3);
681   coord[0] = x;
682   coord[1] = y;
683   coord[2] = z;
684   if (_coordsEnfVertexMap.count(coord)>0)
685     return _coordsEnfVertexMap[coord];
686   std::ostringstream msg ;
687   msg << "No enforced vertex at " << x << ", " << y << ", " << z;
688   throw std::invalid_argument(msg.str());
689 }
690
691 GHS3DPlugin_Hypothesis::TGHS3DEnforcedVertex* GHS3DPlugin_Hypothesis::GetEnforcedVertex(const std::string theEntry)
692   throw (std::invalid_argument)
693 {
694   if (_geomEntryEnfVertexMap.count(theEntry)>0)
695     return _geomEntryEnfVertexMap[theEntry];
696   
697   std::ostringstream msg ;
698   msg << "No enforced vertex with entry " << theEntry;
699   throw std::invalid_argument(msg.str());
700 }
701
702 //=======================================================================
703 //function : RemoveEnforcedVertex
704 //=======================================================================
705
706 bool GHS3DPlugin_Hypothesis::RemoveEnforcedVertex(double x, double y, double z, const std::string theEntry)
707   throw (std::invalid_argument)
708 {
709   bool toNotify = false;
710   std::ostringstream msg;
711   TGHS3DEnforcedVertex *oldEnfVertex;
712   std::vector<double> coords(3);
713   coords[0] = x;
714   coords[1] = y;
715   coords[2] = z;
716   
717   // check that enf vertex with given enf vertex entry exists
718   TGeomEntryGHS3DEnforcedVertexMap::iterator it_enfVertexEntry = _geomEntryEnfVertexMap.find(theEntry);
719   if (it_enfVertexEntry != _geomEntryEnfVertexMap.end()) {
720     // Success
721     MESSAGE("Found enforced vertex with geom entry " << theEntry);
722     oldEnfVertex = it_enfVertexEntry->second;
723     _geomEntryEnfVertexMap.erase(it_enfVertexEntry);
724   } else {
725     // Fail
726     MESSAGE("Enforced vertex with geom entry " << theEntry << " not found");
727     // check that enf vertex with given coords exists
728     TCoordsGHS3DEnforcedVertexMap::iterator it_coords_enf = _coordsEnfVertexMap.find(coords);
729     if (it_coords_enf != _coordsEnfVertexMap.end()) {
730       // Success
731       MESSAGE("Found enforced vertex with coords " << x << ", " << y << ", " << z);
732       oldEnfVertex = it_coords_enf->second;
733       _coordsEnfVertexMap.erase(it_coords_enf);
734       _enfVertexCoordsSizeList.erase(_enfVertexCoordsSizeList.find(coords));
735     } else {
736       // Fail
737       MESSAGE("Enforced vertex with coords " << x << ", " << y << ", " << z << " not found");
738       throw std::invalid_argument(msg.str());
739     }
740   }
741
742   MESSAGE("Remove enf vertex from _enfVertexList");
743
744   // update _enfVertexList
745   TGHS3DEnforcedVertexList::iterator it = _enfVertexList.find(oldEnfVertex);
746   if (it != _enfVertexList.end()) {
747     if ((*it)->groupName != "")
748       _groupsToRemove.insert((*it)->groupName);
749     _enfVertexList.erase(it);
750     toNotify = true;
751     MESSAGE("Done");
752   }
753
754   if (toNotify)
755     NotifySubMeshesHypothesisModification();
756
757   return toNotify;
758 }
759
760 //=======================================================================
761 //function : ClearEnforcedVertices
762 //=======================================================================
763 void GHS3DPlugin_Hypothesis::ClearEnforcedVertices()
764 {
765   TGHS3DEnforcedVertexList::const_iterator it = _enfVertexList.begin();
766   for(;it != _enfVertexList.end();++it) {
767     if ((*it)->groupName != "")
768       _groupsToRemove.insert((*it)->groupName);
769   }
770   _enfVertexList.clear();
771   _coordsEnfVertexMap.clear();
772   _geomEntryEnfVertexMap.clear();
773   _enfVertexCoordsSizeList.clear();
774   _enfVertexEntrySizeList.clear();
775   NotifySubMeshesHypothesisModification();
776 }
777
778 //=======================================================================
779 //function : ClearEnforcedMeshes
780 //=======================================================================
781 void GHS3DPlugin_Hypothesis::ClearEnforcedMeshes()
782 {
783   TGHS3DEnforcedMeshList::const_iterator it = _enfMeshList.begin();
784   for(;it != _enfMeshList.end();++it) {
785     if ((*it)->groupName != "")
786       _groupsToRemove.insert((*it)->groupName);
787   }
788   _enfNodes.clear();
789   _enfEdges.clear();
790   _enfTriangles.clear();
791   _nodeIDToSizeMap.clear();
792   _enfMeshList.clear();
793   _entryEnfMeshMap.clear();
794   NotifySubMeshesHypothesisModification();
795 }
796
797 //================================================================================
798 /*!
799  * \brief At mesh loading, restore enforced elements by just loaded enforced meshes
800  */
801 //================================================================================
802
803 void GHS3DPlugin_Hypothesis::RestoreEnfElemsByMeshes()
804 {
805   TGHS3DEnforcedMeshList::const_iterator it = _enfMeshList.begin();
806   for(;it != _enfMeshList.end();++it) {
807     TGHS3DEnforcedMesh* enfMesh = *it;
808     if ( SMESH_Mesh* mesh = GetMeshByPersistentID( enfMesh->persistID ))
809       SetEnforcedMesh( *mesh,
810                        enfMesh->elementType,
811                        enfMesh->name,
812                        enfMesh->entry,
813                        enfMesh->groupName );
814     enfMesh->persistID = -1; // not to restore again
815   }
816 }
817
818 //=======================================================================
819 //function : SetGroupsToRemove
820 //=======================================================================
821
822 void GHS3DPlugin_Hypothesis::ClearGroupsToRemove()
823 {
824   _groupsToRemove.clear();
825 }
826
827
828 //=======================================================================
829 //function : DefaultMeshHoles
830 //=======================================================================
831
832 bool GHS3DPlugin_Hypothesis::DefaultMeshHoles()
833 {
834   return false; // PAL19680
835 }
836
837 //=======================================================================
838 //function : DefaultToMakeGroupsOfDomains
839 //=======================================================================
840
841 bool GHS3DPlugin_Hypothesis::DefaultToMakeGroupsOfDomains()
842 {
843   return false; // issue 0022172
844 }
845
846 //=======================================================================
847 //function : DefaultMaximumMemory
848 //=======================================================================
849
850 #ifndef WIN32
851 #include <sys/sysinfo.h>
852 #else
853 #include <windows.h>
854 #endif
855
856 long  GHS3DPlugin_Hypothesis::DefaultMaximumMemory()
857 {
858 #ifndef WIN32
859   struct sysinfo si;
860   long err = sysinfo( &si );
861   if ( err == 0 ) {
862     long ramMB = si.totalram * si.mem_unit / 1024 / 1024;
863     return ( 0.7 * ramMB );
864   }
865 #else
866   // See http://msdn.microsoft.com/en-us/library/aa366589.aspx
867   MEMORYSTATUSEX statex;
868   statex.dwLength = sizeof (statex);
869   long err = GlobalMemoryStatusEx (&statex);
870   if (err != 0) {
871     long totMB = 
872       statex.ullTotalPhys / 1024 / 1024 +
873       statex.ullTotalPageFile / 1024 / 1024 +
874       statex.ullTotalVirtual / 1024 / 1024;
875     return ( 0.7 * totMB );
876   }
877 #endif
878   return 1024;
879 }
880
881 //=======================================================================
882 //function : DefaultInitialMemory
883 //=======================================================================
884
885 long  GHS3DPlugin_Hypothesis::DefaultInitialMemory()
886 {
887   return DefaultMaximumMemory();
888 }
889
890 //=======================================================================
891 //function : DefaultOptimizationLevel
892 //=======================================================================
893
894 short  GHS3DPlugin_Hypothesis::DefaultOptimizationLevel()
895 {
896   return Medium;
897 }
898
899 //=======================================================================
900 //function : DefaultWorkingDirectory
901 //=======================================================================
902
903 std::string GHS3DPlugin_Hypothesis::DefaultWorkingDirectory()
904 {
905   TCollection_AsciiString aTmpDir;
906
907   char *Tmp_dir = getenv("SALOME_TMP_DIR");
908   if(Tmp_dir != NULL) {
909     aTmpDir = Tmp_dir;
910   }
911   else {
912 #ifdef WIN32
913     aTmpDir = TCollection_AsciiString("C:\\");
914 #else
915     aTmpDir = TCollection_AsciiString("/tmp/");
916 #endif
917   }
918   return aTmpDir.ToCString();
919 }
920
921 //=======================================================================
922 //function : DefaultKeepFiles
923 //=======================================================================
924
925 bool   GHS3DPlugin_Hypothesis::DefaultKeepFiles()
926 {
927   return false;
928 }
929
930 //=======================================================================
931 //function : DefaultRemoveLogOnSuccess
932 //=======================================================================
933
934 bool   GHS3DPlugin_Hypothesis::DefaultRemoveLogOnSuccess()
935 {
936   return false;
937 }
938
939
940 //=======================================================================
941 //function : DefaultVerboseLevel
942 //=======================================================================
943
944 short  GHS3DPlugin_Hypothesis::DefaultVerboseLevel()
945 {
946   return 10;
947 }
948
949 //=======================================================================
950 //function : DefaultToCreateNewNodes
951 //=======================================================================
952
953 bool GHS3DPlugin_Hypothesis::DefaultToCreateNewNodes()
954 {
955   return true;
956 }
957
958 //=======================================================================
959 //function : DefaultToUseBoundaryRecoveryVersion
960 //=======================================================================
961
962 bool GHS3DPlugin_Hypothesis::DefaultToUseBoundaryRecoveryVersion()
963 {
964   return false;
965 }
966
967 //=======================================================================
968 //function : DefaultToUseFEMCorrection
969 //=======================================================================
970
971 bool GHS3DPlugin_Hypothesis::DefaultToUseFEMCorrection()
972 {
973   return false;
974 }
975
976 //=======================================================================
977 //function : DefaultToRemoveCentralPoint
978 //=======================================================================
979
980 bool GHS3DPlugin_Hypothesis::DefaultToRemoveCentralPoint()
981 {
982   return false;
983 }
984
985 //=======================================================================
986 //function : DefaultGradation
987 //=======================================================================
988
989 double GHS3DPlugin_Hypothesis::DefaultGradation()
990 {
991   return 1.05;
992 }
993
994 //=======================================================================
995 //function : DefaultStandardOutputLog
996 //=======================================================================
997
998 bool GHS3DPlugin_Hypothesis::DefaultStandardOutputLog()
999 {
1000   return false;
1001 }
1002
1003 // //=======================================================================
1004 // //function : DefaultID2SizeMap
1005 // //=======================================================================
1006 // 
1007 // GHS3DPlugin_Hypothesis::TID2SizeMap GHS3DPlugin_Hypothesis::DefaultID2SizeMap()
1008 // {
1009 //   return GHS3DPlugin_Hypothesis::TID2SizeMap();
1010 // }
1011
1012
1013 //=======================================================================
1014 //function : SaveTo
1015 //=======================================================================
1016
1017 std::ostream & GHS3DPlugin_Hypothesis::SaveTo(std::ostream & save)
1018 {
1019   save << (int) myToMeshHoles                 << " ";
1020   save << myMaximumMemory                     << " ";
1021   save << myInitialMemory                     << " ";
1022   save << myOptimizationLevel                 << " ";
1023   save << myWorkingDirectory                  << " ";
1024   save << (int)myKeepFiles                    << " ";
1025   save << myVerboseLevel                      << " ";
1026   save << (int)myToCreateNewNodes             << " ";
1027   save << (int)myToUseBoundaryRecoveryVersion << " ";
1028   save << (int)myToUseFemCorrection           << " ";
1029   save << (int)myToRemoveCentralPoint         << " ";
1030   save << myGradation                         << " ";
1031   save << myToMakeGroupsOfDomains             << " ";
1032   if (!myTextOption.empty()) {
1033     save << "__OPTIONS_BEGIN__ ";
1034     save << myTextOption                      << " ";
1035     save << "__OPTIONS_END__ ";
1036   }
1037   
1038
1039   TGHS3DEnforcedVertexList::iterator it  = _enfVertexList.begin();
1040   if (it != _enfVertexList.end()) {
1041     save << " " << "__ENFORCED_VERTICES_BEGIN__ ";
1042     for ( ; it != _enfVertexList.end(); ++it ) {
1043       TGHS3DEnforcedVertex *enfVertex = (*it);
1044       save << " " << "__BEGIN_VERTEX__";
1045       if (!enfVertex->name.empty()) {
1046         save << " " << "__BEGIN_NAME__";
1047         save << " " << enfVertex->name;
1048         save << " " << "__END_NAME__";
1049       }
1050       if (!enfVertex->geomEntry.empty()) {
1051         save << " " << "__BEGIN_ENTRY__";
1052         save << " " << enfVertex->geomEntry;
1053         save << " " << enfVertex->isCompound;
1054         save << " " << "__END_ENTRY__";
1055       }
1056       if (!enfVertex->groupName.empty()) {
1057         save << " " << "__BEGIN_GROUP__";
1058         save << " " << enfVertex->groupName;
1059         save << " " << "__END_GROUP__";
1060       }
1061       if (enfVertex->coords.size()) {
1062         save << " " << "__BEGIN_COORDS__";
1063         for ( size_t i = 0; i < enfVertex->coords.size(); i++ )
1064           save << " " << enfVertex->coords[i];
1065         save << " " << "__END_COORDS__";
1066       }
1067       save << " " << "__BEGIN_SIZE__";
1068       save << " " << enfVertex->size;
1069       save << " " << "__END_SIZE__";
1070       save << " " << "__END_VERTEX__";
1071     }
1072     save << " " << "__ENFORCED_VERTICES_END__ ";
1073   }
1074
1075   TGHS3DEnforcedMeshList::iterator it_mesh  = _enfMeshList.begin();
1076   if (it_mesh != _enfMeshList.end()) {
1077     save << " " << "__ENFORCED_MESHES_BEGIN__ ";
1078     for ( ; it_mesh != _enfMeshList.end(); ++it_mesh ) {
1079       TGHS3DEnforcedMesh *enfMesh = (*it_mesh);
1080       save << " " << "__BEGIN_ENF_MESH__";
1081
1082       save << " " << "__BEGIN_NAME__";
1083       save << " " << enfMesh->name;
1084       save << " " << "__END_NAME__";
1085
1086       save << " " << "__BEGIN_ENTRY__";
1087       save << " " << enfMesh->entry;
1088       save << " " << "__END_ENTRY__";
1089
1090       save << " " << "__BEGIN_ELEM_TYPE__";
1091       save << " " << (int)enfMesh->elementType;
1092       save << " " << "__END_ELEM_TYPE__";
1093
1094       if (!enfMesh->groupName.empty()) {
1095         save << " " << "__BEGIN_GROUP__";
1096         save << " " << enfMesh->groupName;
1097         save << " " << "__END_GROUP__";
1098       }
1099       save << " " << "__PERSIST_ID__";
1100       save << " " << enfMesh->persistID;
1101       save << " " << "__END_ENF_MESH__";
1102       std::cout << "Saving of enforced mesh " << enfMesh->name.c_str() << " done" << std::endl;
1103     }
1104     save << " "  << "__ENFORCED_MESHES_END__ ";
1105   }
1106   return save;
1107 }
1108
1109 //=======================================================================
1110 //function : LoadFrom
1111 //=======================================================================
1112
1113 std::istream & GHS3DPlugin_Hypothesis::LoadFrom(std::istream & load)
1114 {
1115   bool isOK = true;
1116   int i;
1117   double d;
1118
1119   isOK = static_cast<bool>(load >> i);
1120   if (isOK)
1121     myToMeshHoles = i;
1122   else
1123     load.clear(ios::badbit | load.rdstate());
1124
1125   isOK = static_cast<bool>(load >> d);
1126   if (isOK)
1127     myMaximumMemory = d;
1128   else
1129     load.clear(ios::badbit | load.rdstate());
1130
1131   isOK = static_cast<bool>(load >> d);
1132   if (isOK)
1133     myInitialMemory = d;
1134   else
1135     load.clear(ios::badbit | load.rdstate());
1136
1137   isOK = static_cast<bool>(load >> i);
1138   if (isOK)
1139     myOptimizationLevel = i;
1140   else
1141     load.clear(ios::badbit | load.rdstate());
1142
1143   isOK = static_cast<bool>(load >> myWorkingDirectory);
1144   if (isOK) {
1145     if ( myWorkingDirectory == "0") { // myWorkingDirectory was empty
1146       myKeepFiles = false;
1147       myWorkingDirectory.clear();
1148     }
1149     else if ( myWorkingDirectory == "1" ) {
1150       myKeepFiles = true;
1151       myWorkingDirectory.clear();
1152     }
1153   }
1154   else
1155     load.clear(ios::badbit | load.rdstate());
1156
1157   if ( !myWorkingDirectory.empty() ) {
1158     isOK = static_cast<bool>(load >> i);
1159     if (isOK)
1160       myKeepFiles = i;
1161     else
1162       load.clear(ios::badbit | load.rdstate());
1163   }
1164
1165   isOK = static_cast<bool>(load >> i);
1166   if (isOK)
1167     myVerboseLevel = (short) i;
1168   else
1169     load.clear(ios::badbit | load.rdstate());
1170
1171   isOK = static_cast<bool>(load >> i);
1172   if (isOK)
1173     myToCreateNewNodes = (bool) i;
1174   else
1175     load.clear(ios::badbit | load.rdstate());
1176
1177   isOK = static_cast<bool>(load >> i);
1178   if (isOK)
1179     myToUseBoundaryRecoveryVersion = (bool) i;
1180   else
1181     load.clear(ios::badbit | load.rdstate());
1182
1183   isOK = static_cast<bool>(load >> i);
1184   if (isOK)
1185     myToUseFemCorrection = (bool) i;
1186   else
1187     load.clear(ios::badbit | load.rdstate());
1188
1189   isOK = static_cast<bool>(load >> i);
1190   if (isOK)
1191     myToRemoveCentralPoint = (bool) i;
1192   else
1193     load.clear(ios::badbit | load.rdstate());
1194
1195   isOK = static_cast<bool>(load >> d);
1196   if (isOK)
1197     myGradation = d;
1198   else
1199     load.clear(ios::badbit | load.rdstate());
1200
1201   std::string separator;
1202   bool hasOptions = false;
1203   bool hasEnforcedVertices = false;
1204   bool hasEnforcedMeshes = false;
1205   isOK = static_cast<bool>(load >> separator);
1206
1207   if ( isOK && ( separator == "0" || separator == "1" ))
1208   {
1209     myToMakeGroupsOfDomains = ( separator == "1" );
1210     isOK = static_cast<bool>(load >> separator);
1211   }
1212
1213   if (isOK) {
1214     if (separator == "__OPTIONS_BEGIN__")
1215       hasOptions = true;
1216     else if (separator == "__ENFORCED_VERTICES_BEGIN__")
1217       hasEnforcedVertices = true;
1218     else if (separator == "__ENFORCED_MESHES_BEGIN__")
1219       hasEnforcedMeshes = true;
1220   }
1221
1222   if (hasOptions) {
1223     std::string txt;
1224     while (isOK) {
1225       isOK = static_cast<bool>(load >> txt);
1226       if (isOK) {
1227         if (txt == "__OPTIONS_END__") {
1228           if (!myTextOption.empty()) {
1229             // Remove last space
1230             myTextOption.erase(myTextOption.end()-1);
1231           }
1232           isOK = false;
1233           break;
1234         }
1235         myTextOption += txt;
1236         myTextOption += " ";
1237       }
1238     }
1239   }
1240
1241   if (hasOptions) {
1242     isOK = static_cast<bool>(load >> separator);
1243     if (isOK && separator == "__ENFORCED_VERTICES_BEGIN__")
1244       hasEnforcedVertices = true;
1245     if (isOK && separator == "__ENFORCED_MESHES_BEGIN__")
1246       hasEnforcedMeshes = true;
1247   }
1248
1249   if (hasEnforcedVertices) {
1250     std::string txt, name, entry, groupName;
1251     double size, coords[3];
1252     bool isCompound;
1253     bool hasCoords = false;
1254     isOK = static_cast<bool>(load >> txt);  // __BEGIN_VERTEX__
1255     while (isOK) {
1256       if (txt == "__ENFORCED_VERTICES_END__") {
1257         //isOK = false;
1258         break;
1259       }
1260       
1261       TGHS3DEnforcedVertex *enfVertex = new TGHS3DEnforcedVertex();
1262       while (isOK) {
1263         isOK = static_cast<bool>(load >> txt);
1264         if (txt == "__END_VERTEX__") {
1265           enfVertex->name = name;
1266           enfVertex->geomEntry = entry;
1267           enfVertex->isCompound = isCompound;
1268           enfVertex->groupName = groupName;
1269           enfVertex->coords.clear();
1270           if (hasCoords)
1271             enfVertex->coords.assign(coords,coords+3);
1272
1273           _enfVertexList.insert(enfVertex);
1274
1275           if (enfVertex->coords.size())
1276             _coordsEnfVertexMap[enfVertex->coords] = enfVertex;
1277           if (!enfVertex->geomEntry.empty())
1278             _geomEntryEnfVertexMap[enfVertex->geomEntry] = enfVertex;
1279
1280           name.clear();
1281           entry.clear();
1282           groupName.clear();
1283           hasCoords = false;
1284           isOK = false;
1285         }
1286
1287         if (txt == "__BEGIN_NAME__") {  // __BEGIN_NAME__
1288           while (isOK && (txt != "__END_NAME__")) {
1289             isOK = static_cast<bool>(load >> txt);
1290             if (txt != "__END_NAME__") {
1291               if (!name.empty())
1292                 name += " ";
1293               name += txt;
1294             }
1295           }
1296           MESSAGE("name: " <<name);
1297         }
1298
1299         if (txt == "__BEGIN_ENTRY__") {  // __BEGIN_ENTRY__
1300           isOK = static_cast<bool>(load >> entry);
1301           isOK = static_cast<bool>(load >> isCompound);
1302           isOK = static_cast<bool>(load >> txt); // __END_ENTRY__
1303           if (txt != "__END_ENTRY__")
1304             throw std::exception();
1305           MESSAGE("entry: " << entry);
1306         }
1307
1308         if (txt == "__BEGIN_GROUP__") {  // __BEGIN_GROUP__
1309           while (isOK && (txt != "__END_GROUP__")) {
1310             isOK = static_cast<bool>(load >> txt);
1311             if (txt != "__END_GROUP__") {
1312               if (!groupName.empty())
1313                 groupName += " ";
1314               groupName += txt;
1315             }
1316           }
1317           MESSAGE("groupName: " << groupName);
1318         }
1319
1320         if (txt == "__BEGIN_COORDS__") {  // __BEGIN_COORDS__
1321           hasCoords = true;
1322           isOK = static_cast<bool>(load >> coords[0] >> coords[1] >> coords[2]);
1323           isOK = static_cast<bool>(load >> txt); // __END_COORDS__
1324           if (txt != "__END_COORDS__")
1325             throw std::exception();
1326           MESSAGE("coords: " << coords[0] <<","<< coords[1] <<","<< coords[2]);
1327         }
1328
1329         if (txt == "__BEGIN_SIZE__") {  // __BEGIN_ENTRY__
1330           isOK = static_cast<bool>(load >> size);
1331           isOK = static_cast<bool>(load >> txt); // __END_ENTRY__
1332           if (txt != "__END_SIZE__") {
1333             throw std::exception();
1334           }
1335           MESSAGE("size: " << size);
1336         }
1337       }
1338       isOK = static_cast<bool>(load >> txt);  // __BEGIN_VERTEX__
1339     }
1340   }
1341
1342   if (hasEnforcedVertices) {
1343     isOK = static_cast<bool>(load >> separator);
1344     if (isOK && separator == "__ENFORCED_MESHES_BEGIN__")
1345       hasEnforcedMeshes = true;
1346   }
1347
1348   if (hasEnforcedMeshes) {
1349     std::string txt, name, entry, groupName;
1350     int elementType = -1, persistID = -1;
1351     isOK = static_cast<bool>(load >> txt);  // __BEGIN_ENF_MESH__
1352     while (isOK) {
1353       //                if (isOK) {
1354       if (txt == "__ENFORCED_MESHES_END__")
1355         isOK = false;
1356
1357       TGHS3DEnforcedMesh *enfMesh = new TGHS3DEnforcedMesh();
1358       while (isOK) {
1359         isOK = static_cast<bool>(load >> txt);
1360         if (txt == "__END_ENF_MESH__") {
1361           enfMesh->name = name;
1362           enfMesh->entry = entry;
1363           enfMesh->elementType = (SMESH::ElementType)elementType;
1364           enfMesh->groupName = groupName;
1365           enfMesh->persistID = persistID;
1366
1367           _enfMeshList.insert(enfMesh);
1368           //std::cout << "Restoring of enforced mesh " <<name  << " done" << std::endl;
1369
1370           name.clear();
1371           entry.clear();
1372           elementType = -1;
1373           groupName.clear();
1374           persistID = -1;
1375           isOK = false;
1376         }
1377
1378         if (txt == "__BEGIN_NAME__") {  // __BEGIN_NAME__
1379           while (isOK && (txt != "__END_NAME__")) {
1380             isOK = static_cast<bool>(load >> txt);
1381             if (txt != "__END_NAME__") {
1382               if (!name.empty())
1383                 name += " ";
1384               name += txt;
1385             }
1386           }
1387           MESSAGE("name: " <<name);
1388         }
1389
1390         if (txt == "__BEGIN_ENTRY__") {  // __BEGIN_ENTRY__
1391           isOK = static_cast<bool>(load >> entry);
1392           isOK = static_cast<bool>(load >> txt); // __END_ENTRY__
1393           if (txt != "__END_ENTRY__")
1394             throw std::exception();
1395           MESSAGE("entry: " << entry);
1396         }
1397
1398         if (txt == "__BEGIN_ELEM_TYPE__") {  // __BEGIN_ELEM_TYPE__
1399           isOK = static_cast<bool>(load >> elementType);
1400           isOK = static_cast<bool>(load >> txt); // __END_ELEM_TYPE__
1401           if (txt != "__END_ELEM_TYPE__")
1402             throw std::exception();
1403           MESSAGE("elementType: " << elementType);
1404         }
1405
1406         if (txt == "__BEGIN_GROUP__") {  // __BEGIN_GROUP__
1407           while (isOK && (txt != "__END_GROUP__")) {
1408             isOK = static_cast<bool>(load >> txt);
1409             if (txt != "__END_GROUP__") {
1410               if (!groupName.empty())
1411                 groupName += " ";
1412               groupName += txt;
1413             }
1414           } // while
1415           MESSAGE("groupName: " << groupName);
1416         } // if
1417
1418         if (txt == "__PERSIST_ID__") {
1419           isOK = static_cast<bool>(load >> persistID);
1420           MESSAGE("persistID: " << persistID);
1421         }
1422         //std::cout << "isOK: " << isOK << std::endl;
1423       } // while
1424       //                } // if
1425       isOK = static_cast<bool>(load >> txt);  // __BEGIN_ENF_MESH__
1426     } // while
1427   } // if
1428
1429   return load;
1430 }
1431
1432 //=======================================================================
1433 //function : SetParametersByMesh
1434 //=======================================================================
1435
1436 bool GHS3DPlugin_Hypothesis::SetParametersByMesh(const SMESH_Mesh* ,const TopoDS_Shape&)
1437 {
1438   return false;
1439 }
1440
1441
1442 //================================================================================
1443 /*!
1444  * \brief Sets myToMakeGroupsOfDomains depending on whether theMesh is on shape or not
1445  */
1446 //================================================================================
1447
1448 bool GHS3DPlugin_Hypothesis::SetParametersByDefaults(const TDefaults&  dflts,
1449                                                      const SMESH_Mesh* /*theMesh*/)
1450 {
1451   myToMakeGroupsOfDomains = ( !dflts._shape || dflts._shape->IsNull() );
1452   return true;
1453 }
1454
1455 //================================================================================
1456 /*!
1457  * \brief Return command to run MG-Tetra mesher excluding file prefix (-f)
1458  */
1459 //================================================================================
1460
1461 std::string GHS3DPlugin_Hypothesis::CommandToRun(const GHS3DPlugin_Hypothesis* hyp,
1462                                                  const bool         hasShapeToMesh)
1463 {
1464   TCollection_AsciiString cmd = GetExeName().c_str();
1465   // check if any option is overridden by hyp->myTextOption
1466   bool max_memory   = hyp ? ( hyp->myTextOption.find("--max_memory")  == std::string::npos ) : true;
1467   bool auto_memory   = hyp ? ( hyp->myTextOption.find("--automatic_memory")  == std::string::npos ) : true;
1468   bool comp   = hyp ? ( hyp->myTextOption.find("--components")  == std::string::npos ) : true;
1469   bool optim_level   = hyp ? ( hyp->myTextOption.find("--optimisation_level")  == std::string::npos ) : true;
1470   bool no_int_points  = hyp ? ( hyp->myTextOption.find("--no_internal_points") == std::string::npos ) : true;
1471   bool C   = hyp ? ( hyp->myTextOption.find("-C")  == std::string::npos ) : true;
1472   bool verbose   = hyp ? ( hyp->myTextOption.find("--verbose")  == std::string::npos ) : true;
1473   bool fem = hyp ? ( hyp->myTextOption.find("-FEM")== std::string::npos ) : true;
1474   bool rem = hyp ? ( hyp->myTextOption.find("--no_initial_central_point")== std::string::npos ) : true;
1475   bool gra = hyp ? ( hyp->myTextOption.find("-Dcpropa")== std::string::npos ) : true;
1476
1477   // if use boundary recovery version, few options are allowed
1478   bool useBndRecovery = !C;
1479   if ( !useBndRecovery && hyp )
1480     useBndRecovery = hyp->myToUseBoundaryRecoveryVersion;
1481
1482   // MG-Tetra needs to know amount of memory it may use (MB).
1483   // Default memory is defined at MG-Tetra installation but it may be not enough,
1484   // so allow to use about all available memory
1485   if ( max_memory ) {
1486     long aMaximumMemory = hyp ? hyp->myMaximumMemory : -1;
1487     ostringstream tmpMaximumMemory;
1488     cmd += " --max_memory ";
1489     if ( aMaximumMemory < 0 )
1490       tmpMaximumMemory << DefaultMaximumMemory();
1491     else
1492       tmpMaximumMemory << aMaximumMemory;
1493     cmd += tmpMaximumMemory.str().c_str();
1494   }
1495   if ( auto_memory && !useBndRecovery ) {
1496     long aInitialMemory = hyp ? hyp->myInitialMemory : -1;
1497     cmd += " --automatic_memory ";
1498     if ( aInitialMemory > 0 )
1499       cmd += (int)aInitialMemory;
1500     else
1501       cmd += "100";
1502   }
1503   // component to mesh
1504   if ( comp && !useBndRecovery ) {
1505     // We always run MG-Tetra with "to mesh holes'==TRUE (see PAL19680)
1506     if ( hasShapeToMesh )
1507       cmd += " --components all";
1508     else {
1509       bool aToMeshHoles = hyp ? hyp->myToMeshHoles : DefaultMeshHoles();
1510       if ( aToMeshHoles )
1511         cmd += " --components all";
1512       else
1513         cmd += " --components outside_components";
1514     }
1515   }
1516   const bool toCreateNewNodes = ( no_int_points && ( !hyp || hyp->myToCreateNewNodes ));
1517
1518   // optimization level
1519   // This option need to be improved concerning new mg-tetra version
1520   if ( optim_level && hyp && !useBndRecovery && toCreateNewNodes ) {
1521     if ( hyp->myOptimizationLevel >= 0 && hyp->myOptimizationLevel < 5 ) {
1522       const char* level[] = { "none" , "light" , "standard" , "standard+" , "strong" };
1523       cmd += " --optimisation_level ";
1524       cmd += level[ hyp->myOptimizationLevel ];
1525     }
1526   }
1527   if ( !toCreateNewNodes ) {
1528     cmd += " --optimisation_level none"; // issue 22608
1529   }
1530
1531   // to create internal nodes
1532   if ( no_int_points && !toCreateNewNodes ) {
1533     cmd += " --no_internal_points";
1534   }
1535
1536   // verbose mode
1537   if ( verbose && hyp ) {
1538     cmd += " --verbose ";
1539     cmd += hyp->myVerboseLevel;
1540   }
1541
1542   // boundary recovery version
1543   if ( useBndRecovery ) {
1544     cmd += " -C";
1545   }
1546
1547   // to use FEM correction
1548   if ( fem && hyp && hyp->myToUseFemCorrection) {
1549     cmd += " -FEM";
1550   }
1551
1552   // to remove initial central point.
1553   if ( rem && hyp && hyp->myToRemoveCentralPoint) {
1554     cmd += " --no_initial_central_point";
1555   }
1556
1557   // options as text
1558   if ( hyp && !hyp->myTextOption.empty() ) {
1559     cmd += " ";
1560     cmd += (char*) hyp->myTextOption.c_str();
1561   }
1562
1563   // to define volumic gradation.
1564   if ( gra && hyp) {
1565     cmd += " -Dcpropa=";
1566     cmd += hyp->myGradation;
1567   }
1568
1569 #ifdef WIN32
1570   cmd += " < NUL";
1571 #endif
1572
1573   return cmd.ToCString();
1574 }
1575
1576 //================================================================================
1577 /*!
1578  * \brief Return a unique file name
1579  */
1580 //================================================================================
1581
1582 std::string GHS3DPlugin_Hypothesis::GetFileName(const GHS3DPlugin_Hypothesis* hyp)
1583 {
1584   std::string aTmpDir = hyp ? hyp->GetWorkingDirectory() : DefaultWorkingDirectory();
1585   const char lastChar = *aTmpDir.rbegin();
1586 #ifdef WIN32
1587     if(lastChar != '\\') aTmpDir+='\\';
1588 #else
1589     if(lastChar != '/') aTmpDir+='/';
1590 #endif      
1591
1592   TCollection_AsciiString aGenericName = (char*)aTmpDir.c_str();
1593   aGenericName += "GHS3D_";
1594   aGenericName += getpid();
1595   aGenericName += "_";
1596   aGenericName += Abs((Standard_Integer)(long) aGenericName.ToCString());
1597
1598   return aGenericName.ToCString();
1599 }
1600
1601 //================================================================================
1602 /*
1603  * Return the name of executable
1604  */
1605 //================================================================================
1606
1607 std::string GHS3DPlugin_Hypothesis::GetExeName()
1608 {
1609   return "mg-tetra.exe";
1610 }
1611
1612 //================================================================================
1613 /*!
1614 * \brief Return the enforced vertices
1615 */
1616 //================================================================================
1617
1618 GHS3DPlugin_Hypothesis::TGHS3DEnforcedVertexList GHS3DPlugin_Hypothesis::GetEnforcedVertices(const GHS3DPlugin_Hypothesis* hyp)
1619 {
1620   return hyp ? hyp->_GetEnforcedVertices():DefaultGHS3DEnforcedVertexList();
1621 }
1622
1623 GHS3DPlugin_Hypothesis::TGHS3DEnforcedVertexCoordsValues GHS3DPlugin_Hypothesis::GetEnforcedVerticesCoordsSize (const GHS3DPlugin_Hypothesis* hyp)
1624 {  
1625   return hyp ? hyp->_GetEnforcedVerticesCoordsSize(): DefaultGHS3DEnforcedVertexCoordsValues();
1626 }
1627
1628 GHS3DPlugin_Hypothesis::TGHS3DEnforcedVertexEntryValues GHS3DPlugin_Hypothesis::GetEnforcedVerticesEntrySize (const GHS3DPlugin_Hypothesis* hyp)
1629 {  
1630   return hyp ? hyp->_GetEnforcedVerticesEntrySize(): DefaultGHS3DEnforcedVertexEntryValues();
1631 }
1632
1633 GHS3DPlugin_Hypothesis::TCoordsGHS3DEnforcedVertexMap GHS3DPlugin_Hypothesis::GetEnforcedVerticesByCoords (const GHS3DPlugin_Hypothesis* hyp)
1634 {  
1635   return hyp ? hyp->_GetEnforcedVerticesByCoords(): DefaultCoordsGHS3DEnforcedVertexMap();
1636 }
1637
1638 GHS3DPlugin_Hypothesis::TGeomEntryGHS3DEnforcedVertexMap GHS3DPlugin_Hypothesis::GetEnforcedVerticesByEntry (const GHS3DPlugin_Hypothesis* hyp)
1639 {  
1640   return hyp ? hyp->_GetEnforcedVerticesByEntry(): DefaultGeomEntryGHS3DEnforcedVertexMap();
1641 }
1642
1643 GHS3DPlugin_Hypothesis::TIDSortedNodeGroupMap GHS3DPlugin_Hypothesis::GetEnforcedNodes(const GHS3DPlugin_Hypothesis* hyp)
1644 {
1645   return hyp ? hyp->_GetEnforcedNodes():DefaultIDSortedNodeGroupMap();
1646 }
1647
1648 GHS3DPlugin_Hypothesis::TIDSortedElemGroupMap GHS3DPlugin_Hypothesis::GetEnforcedEdges(const GHS3DPlugin_Hypothesis* hyp)
1649 {
1650   return hyp ? hyp->_GetEnforcedEdges():DefaultIDSortedElemGroupMap();
1651 }
1652
1653 GHS3DPlugin_Hypothesis::TIDSortedElemGroupMap GHS3DPlugin_Hypothesis::GetEnforcedTriangles(const GHS3DPlugin_Hypothesis* hyp)
1654 {
1655   return hyp ? hyp->_GetEnforcedTriangles():DefaultIDSortedElemGroupMap();
1656 }
1657
1658 GHS3DPlugin_Hypothesis::TID2SizeMap GHS3DPlugin_Hypothesis::GetNodeIDToSizeMap(const GHS3DPlugin_Hypothesis* hyp)
1659 {
1660   return hyp ? hyp->_GetNodeIDToSizeMap(): DefaultID2SizeMap();
1661 }
1662
1663 GHS3DPlugin_Hypothesis::TSetStrings GHS3DPlugin_Hypothesis::GetGroupsToRemove(const GHS3DPlugin_Hypothesis* hyp)
1664 {
1665   return hyp ? hyp->_GetGroupsToRemove(): DefaultGroupsToRemove();
1666 }