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