]> SALOME platform Git repositories - modules/smesh.git/blob - src/SMESH_I/SMESH_MeshEditor_i.cxx
Salome HOME
Dump Python. Add AddToCurrentPyScript(), AddArray(), AddObject()
[modules/smesh.git] / src / SMESH_I / SMESH_MeshEditor_i.cxx
1 //  SMESH SMESH_I : idl implementation based on 'SMESH' unit's calsses
2 //
3 //  Copyright (C) 2003  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 //  CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS 
5 // 
6 //  This library is free software; you can redistribute it and/or 
7 //  modify it under the terms of the GNU Lesser General Public 
8 //  License as published by the Free Software Foundation; either 
9 //  version 2.1 of the License. 
10 // 
11 //  This library is distributed in the hope that it will be useful, 
12 //  but WITHOUT ANY WARRANTY; without even the implied warranty of 
13 //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU 
14 //  Lesser General Public License for more details. 
15 // 
16 //  You should have received a copy of the GNU Lesser General Public 
17 //  License along with this library; if not, write to the Free Software 
18 //  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA 
19 // 
20 //  See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org 
21 //
22 //
23 //
24 //  File   : SMESH_MeshEditor_i.cxx
25 //  Author : Nicolas REJNERI
26 //  Module : SMESH
27 //  $Header$
28
29 #include "SMESH_MeshEditor_i.hxx"
30
31 #include "SMDS_MeshEdge.hxx"
32 #include "SMDS_MeshFace.hxx"
33 #include "SMDS_MeshVolume.hxx"
34
35 #include "SMESH_MeshEditor.hxx"
36
37 #include "SMESH_Gen_i.hxx"
38 #include "SMESH_Filter_i.hxx"
39
40 #include "utilities.h"
41
42 #include <gp_Ax1.hxx>
43 #include <gp_Ax2.hxx>
44 #include <gp_Vec.hxx>
45
46 #include <sstream>
47
48 using namespace std;
49
50 //=======================================================================
51 //function : addArray
52 //purpose  : put array contents into theStr like this: "[ 1, 2, 5 ]"
53 //=======================================================================
54
55 template <class _array>
56   TCollection_AsciiString& addArray(TCollection_AsciiString& theStr,
57                                     const _array &           IDs)
58 {
59   ostringstream sout; // can convert long int, and TCollection_AsciiString cant
60   sout << "[ ";
61   for (int i = 1; i <= IDs.length(); i++) {
62     sout << IDs[i-1];
63     if ( i < IDs.length() )
64       sout << ", ";
65   }
66   sout << " ]";
67   theStr += (char*) sout.str().c_str();
68   return theStr;
69 }
70
71 //=======================================================================
72 //function : addObject
73 //purpose  : add object to script string
74 //=======================================================================
75
76 static TCollection_AsciiString& addObject(TCollection_AsciiString& theStr,
77                                           CORBA::Object_ptr        theObject)
78 {
79   SMESH_Gen_i* aSMESHGen = SMESH_Gen_i::GetSMESHGen();
80   SALOMEDS::SObject_var aSO =
81     aSMESHGen->ObjectToSObject(aSMESHGen->GetCurrentStudy(), theObject);
82   if ( !aSO->_is_nil() )
83     theStr += aSO->GetID();
84   else if ( !CORBA::is_nil( theObject ) )
85     theStr += aSMESHGen->GetORB()->object_to_string( theObject );
86   else
87     theStr += "None";
88   return theStr;
89 }
90
91 //=======================================================================
92 //function : addAxis
93 //purpose  : 
94 //=======================================================================
95
96 static TCollection_AsciiString& addAxis(TCollection_AsciiString&  theStr,
97                                         const SMESH::AxisStruct & theAxis)
98 {
99   theStr += "SMESH.AxisStruct( ";
100   theStr += TCollection_AsciiString( theAxis.x  ) + ", ";
101   theStr += TCollection_AsciiString( theAxis.y  ) + ", ";
102   theStr += TCollection_AsciiString( theAxis.z  ) + ", ";
103   theStr += TCollection_AsciiString( theAxis.vx ) + ", ";
104   theStr += TCollection_AsciiString( theAxis.vy ) + ", ";
105   theStr += TCollection_AsciiString( theAxis.vz ) + " )";
106   return theStr;
107 }
108
109 //=======================================================================
110 //function : addToPythonScript
111 //purpose  : add theStr to python script of the current study
112 //=======================================================================
113
114 static inline void addToPythonScript(const TCollection_AsciiString& theStr)
115 {
116   SMESH_Gen_i* aSMESHGen = SMESH_Gen_i::GetSMESHGen();
117   aSMESHGen->AddToPythonScript(aSMESHGen->GetCurrentStudy()->StudyId(), theStr);
118 }
119
120 //=============================================================================
121 /*!
122  *  
123  */
124 //=============================================================================
125
126 SMESH_MeshEditor_i::SMESH_MeshEditor_i(SMESH_Mesh* theMesh)
127 {
128         _myMesh = theMesh;
129 };
130
131 //=============================================================================
132 /*!
133  *  
134  */
135 //=============================================================================
136
137 CORBA::Boolean
138   SMESH_MeshEditor_i::RemoveElements(const SMESH::long_array & IDsOfElements)
139 {
140   ::SMESH_MeshEditor anEditor( _myMesh );
141   list< int > IdList;
142
143   for (int i = 0; i < IDsOfElements.length(); i++)
144     IdList.push_back( IDsOfElements[i] );
145
146   // Update Python script
147   TCollection_AsciiString str ("isDone = mesh_editor.RemoveElements(");
148   addArray( str, IDsOfElements ) += ")";
149   addToPythonScript( str );
150 #ifdef _DEBUG_
151   addToPythonScript( "print \"RemoveElements: \", isDone" );
152 #endif
153   // Remove Elements
154   return anEditor.Remove( IdList, false );
155 };
156
157 //=============================================================================
158 /*!
159  *  
160  */
161 //=============================================================================
162
163 CORBA::Boolean SMESH_MeshEditor_i::RemoveNodes(const SMESH::
164         long_array & IDsOfNodes)
165 {
166   ::SMESH_MeshEditor anEditor( _myMesh );
167   list< int > IdList;
168   for (int i = 0; i < IDsOfNodes.length(); i++)
169     IdList.push_back( IDsOfNodes[i] );
170
171   // Update Python script
172   TCollection_AsciiString str ("isDone = mesh_editor.RemoveNodes(");
173   addArray( str, IDsOfNodes ) += ")";
174   addToPythonScript( str );
175 #ifdef _DEBUG_
176   addToPythonScript( "print \"RemoveNodes: \", isDone" );
177 #endif
178
179   return anEditor.Remove( IdList, true );
180 };
181
182 //=============================================================================
183 /*!
184  *  
185  */
186 //=============================================================================
187
188 CORBA::Boolean SMESH_MeshEditor_i::AddEdge(const SMESH::long_array & IDsOfNodes)
189 {
190   int NbNodes = IDsOfNodes.length();
191   if (NbNodes == 2)
192   {
193     CORBA::Long index1 = IDsOfNodes[0];
194     CORBA::Long index2 = IDsOfNodes[1];
195     GetMeshDS()->AddEdge(GetMeshDS()->FindNode(index1), GetMeshDS()->FindNode(index2));
196
197     // Update Python script
198     TCollection_AsciiString str ("isDone = mesh_editor.AddEdge([");
199     str += TCollection_AsciiString((int) index1) + ", ";
200     str += TCollection_AsciiString((int) index2) + " ])";
201     addToPythonScript( str );
202   }
203   return true;
204 }
205
206 //=============================================================================
207 /*!
208  *  
209  */
210 //=============================================================================
211
212 CORBA::Boolean SMESH_MeshEditor_i::AddNode(CORBA::Double x,
213                                            CORBA::Double y, CORBA::Double z)
214 {
215   GetMeshDS()->AddNode(x, y, z);
216
217   // Update Python script
218   TCollection_AsciiString str ("isDone = mesh_editor.AddNode(");
219   str += TCollection_AsciiString( x ) + ", ";
220   str += TCollection_AsciiString( y ) + ", ";
221   str += TCollection_AsciiString( z ) + " )";
222   addToPythonScript( str );
223
224   return true;
225 }
226
227 //=============================================================================
228 /*!
229  *  AddFace
230  */
231 //=============================================================================
232
233 CORBA::Boolean SMESH_MeshEditor_i::AddFace(const SMESH::long_array & IDsOfNodes)
234 {
235   int NbNodes = IDsOfNodes.length();
236   if (NbNodes < 3)
237   {
238     return false;
239   }
240
241   std::vector<const SMDS_MeshNode*> nodes (NbNodes);
242   for (int i = 0; i < NbNodes; i++)
243     nodes[i] = GetMeshDS()->FindNode(IDsOfNodes[i]);
244
245   if (NbNodes == 3)
246   {
247     GetMeshDS()->AddFace(nodes[0], nodes[1], nodes[2]);
248   }
249   else if (NbNodes == 4)
250   {
251     GetMeshDS()->AddFace(nodes[0], nodes[1], nodes[2], nodes[3]);
252   }
253   else
254   {
255     GetMeshDS()->AddPolygonalFace(nodes);
256   }
257
258   // Update Python script
259   TCollection_AsciiString str ("isDone = mesh_editor.AddFace(");
260   addArray( str, IDsOfNodes ) += ")";
261   addToPythonScript( str );
262 #ifdef _DEBUG_
263   addToPythonScript( "print \"AddFace: \", isDone" );
264 #endif
265
266   return true;
267 };
268
269 //=============================================================================
270 /*!
271  *  
272  */
273 //=============================================================================
274
275 CORBA::Boolean SMESH_MeshEditor_i::AddVolume(const SMESH::
276                                              long_array & IDsOfNodes)
277 {
278   int NbNodes = IDsOfNodes.length();
279   vector< const SMDS_MeshNode*> n(NbNodes);
280   for(int i=0;i<NbNodes;i++)
281     n[i]=GetMeshDS()->FindNode(IDsOfNodes[i]);
282
283   switch(NbNodes)
284   {
285   case 4:GetMeshDS()->AddVolume(n[0],n[1],n[2],n[3]); break;
286   case 5:GetMeshDS()->AddVolume(n[0],n[1],n[2],n[3],n[4]); break;
287   case 6:GetMeshDS()->AddVolume(n[0],n[1],n[2],n[3],n[4],n[5]); break;
288   case 8:GetMeshDS()->AddVolume(n[0],n[1],n[2],n[3],n[4],n[5],n[6],n[7]); break;
289   }
290   // Update Python script
291   TCollection_AsciiString str ("isDone = mesh_editor.AddVolume(");
292   addArray( str, IDsOfNodes ) += ")";
293   addToPythonScript( str );
294 #ifdef _DEBUG_
295   addToPythonScript( "print \"AddVolume: \", isDone" );
296 #endif
297   
298   return true;
299 };
300
301 //=============================================================================
302 /*!
303  *  AddPolyhedralVolume
304  */
305 //=============================================================================
306 CORBA::Boolean SMESH_MeshEditor_i::AddPolyhedralVolume
307                                    (const SMESH::long_array & IDsOfNodes,
308                                     const SMESH::long_array & Quantities)
309 {
310   int NbNodes = IDsOfNodes.length();
311   std::vector<const SMDS_MeshNode*> n (NbNodes);
312   for (int i = 0; i < NbNodes; i++)
313     n[i] = GetMeshDS()->FindNode(IDsOfNodes[i]);
314
315   int NbFaces = Quantities.length();
316   std::vector<int> q (NbFaces);
317   for (int j = 0; j < NbFaces; j++)
318     q[j] = Quantities[j];
319
320   GetMeshDS()->AddPolyhedralVolume(n, q);
321
322   // Update Python script
323   TCollection_AsciiString str ("isDone = mesh_editor.AddPolyhedralVolume(");
324   addArray( str, IDsOfNodes ) += ", ";
325   addArray( str, Quantities ) += ")";
326   addToPythonScript( str );
327 #ifdef _DEBUG_
328   addToPythonScript( "print \"AddPolyhedralVolume: \", isDone" );
329 #endif
330
331   return true;
332 };
333
334 //=============================================================================
335 /*!
336  *  AddPolyhedralVolumeByFaces
337  */
338 //=============================================================================
339 CORBA::Boolean SMESH_MeshEditor_i::AddPolyhedralVolumeByFaces
340                                    (const SMESH::long_array & IdsOfFaces)
341 {
342   int NbFaces = IdsOfFaces.length();
343   std::vector<const SMDS_MeshNode*> poly_nodes;
344   std::vector<int> quantities (NbFaces);
345
346   for (int i = 0; i < NbFaces; i++) {
347     const SMDS_MeshElement* aFace = GetMeshDS()->FindElement(IdsOfFaces[i]);
348     quantities[i] = aFace->NbNodes();
349
350     SMDS_ElemIteratorPtr It = aFace->nodesIterator();
351     while (It->more()) {
352       poly_nodes.push_back(static_cast<const SMDS_MeshNode *>(It->next()));
353     }
354   }
355
356   GetMeshDS()->AddPolyhedralVolume(poly_nodes, quantities);
357
358   // Update Python script
359   TCollection_AsciiString str ("isDone = mesh_editor.AddPolyhedralVolumeByFaces(");
360   addArray( str, IdsOfFaces ) += ")";
361   addToPythonScript( str );
362 #ifdef _DEBUG_
363   addToPythonScript( "print \"AddPolyhedralVolume: \", isDone" );
364 #endif
365
366   return true;
367 };
368
369 //=============================================================================
370 /*!
371  *  
372  */
373 //=============================================================================
374
375 CORBA::Boolean SMESH_MeshEditor_i::MoveNode(CORBA::Long   NodeID,
376                                             CORBA::Double x,
377                                             CORBA::Double y,
378                                             CORBA::Double z)
379 {
380   const SMDS_MeshNode * node = GetMeshDS()->FindNode( NodeID );
381   if ( !node )
382     return false;
383   
384   GetMeshDS()->MoveNode(node, x, y, z);
385
386   // Update Python script
387   TCollection_AsciiString str ("isDone = mesh_editor.MoveNode(");
388   str += TCollection_AsciiString((Standard_Integer) NodeID) + ", ";
389   str += TCollection_AsciiString((Standard_Real) x) + ", ";
390   str += TCollection_AsciiString((Standard_Real) y) + ", ";
391   str += TCollection_AsciiString((Standard_Real) z) + " )";
392   addToPythonScript( str );
393
394   return true;
395 }
396
397 //=============================================================================
398 /*!
399  *  
400  */
401 //=============================================================================
402
403 CORBA::Boolean SMESH_MeshEditor_i::InverseDiag(CORBA::Long NodeID1,
404                                                CORBA::Long NodeID2)
405 {
406   const SMDS_MeshNode * n1 = GetMeshDS()->FindNode( NodeID1 );
407   const SMDS_MeshNode * n2 = GetMeshDS()->FindNode( NodeID2 );
408   if ( !n1 || !n2 )
409     return false;
410
411   // Update Python script
412   TCollection_AsciiString str ("isDone = mesh_editor.InverseDiag(");
413   str += TCollection_AsciiString((Standard_Integer) NodeID1) + ", ";
414   str += TCollection_AsciiString((Standard_Integer) NodeID2) + " )";
415   addToPythonScript( str );
416
417   ::SMESH_MeshEditor aMeshEditor( _myMesh );
418   return aMeshEditor.InverseDiag ( n1, n2 );
419 }
420
421 //=============================================================================
422 /*!
423  *  
424  */
425 //=============================================================================
426
427 CORBA::Boolean SMESH_MeshEditor_i::DeleteDiag(CORBA::Long NodeID1,
428                                               CORBA::Long NodeID2)
429 {
430   const SMDS_MeshNode * n1 = GetMeshDS()->FindNode( NodeID1 );
431   const SMDS_MeshNode * n2 = GetMeshDS()->FindNode( NodeID2 );
432   if ( !n1 || !n2 )
433     return false;
434
435   // Update Python script
436   TCollection_AsciiString str ("isDone = mesh_editor.DeleteDiag(");
437   str += TCollection_AsciiString((Standard_Integer) NodeID1) + ", ";
438   str += TCollection_AsciiString((Standard_Integer) NodeID2) + " )";
439   addToPythonScript( str );
440
441   ::SMESH_MeshEditor aMeshEditor( _myMesh );
442   return aMeshEditor.DeleteDiag ( n1, n2 );
443 }
444
445 //=============================================================================
446 /*!
447  *  
448  */
449 //=============================================================================
450
451 CORBA::Boolean SMESH_MeshEditor_i::Reorient(const SMESH::long_array & IDsOfElements)
452 {
453   ::SMESH_MeshEditor anEditor( _myMesh );
454   for (int i = 0; i < IDsOfElements.length(); i++)
455   {
456     CORBA::Long index = IDsOfElements[i];
457     const SMDS_MeshElement * elem = GetMeshDS()->FindElement(index);
458     if ( elem )
459       anEditor.Reorient( elem );
460   }
461   // Update Python script
462   TCollection_AsciiString str ("isDone = mesh_editor.Reorient(");
463   addArray( str, IDsOfElements ) += ")";
464   addToPythonScript( str );
465 #ifdef _DEBUG_
466   addToPythonScript( "print \"Reorient: \", isDone" );
467 #endif
468
469   return true;
470 }
471
472
473 //=============================================================================
474 /*!
475  *  
476  */
477 //=============================================================================
478
479 CORBA::Boolean SMESH_MeshEditor_i::ReorientObject(SMESH::SMESH_IDSource_ptr theObject)
480 {
481   SMESH::long_array_var anElementsId = theObject->GetIDs();
482   return Reorient(anElementsId);
483 }
484
485 //=============================================================================
486 /*!
487  *  
488  */
489 //=============================================================================
490
491 CORBA::Boolean
492   SMESH_MeshEditor_i::TriToQuad (const SMESH::long_array &   IDsOfElements,
493                                  SMESH::NumericalFunctor_ptr Criterion,
494                                  CORBA::Double               MaxAngle)
495 {
496   set<const SMDS_MeshElement*> faces;
497   for (int i = 0; i < IDsOfElements.length(); i++)
498   {
499     CORBA::Long index = IDsOfElements[i];
500     const SMDS_MeshElement * elem = GetMeshDS()->FindElement(index);
501     if ( elem && elem->GetType() == SMDSAbs_Face)
502       faces.insert( elem );
503   }
504   SMESH::NumericalFunctor_i* aNumericalFunctor = 
505     dynamic_cast<SMESH::NumericalFunctor_i*>( SMESH_Gen_i::GetServant( Criterion ).in() );
506   SMESH::Controls::NumericalFunctorPtr aCrit;
507   if ( !aNumericalFunctor )
508     aCrit.reset( new SMESH::Controls::AspectRatio() );
509   else
510     aCrit = aNumericalFunctor->GetNumericalFunctor();
511
512   // Update Python script
513   TCollection_AsciiString str ("isDone = mesh_editor.TriToQuad(");
514   addArray( str, IDsOfElements ) += ", None, ";
515   str += (Standard_Real) MaxAngle;
516   addToPythonScript( str + ")" );
517 #ifdef _DEBUG_
518   addToPythonScript( "print \"TriToQuad: \", isDone" );
519 #endif
520
521   ::SMESH_MeshEditor anEditor( _myMesh );
522   return anEditor.TriToQuad( faces, aCrit, MaxAngle );
523 }
524
525 //=============================================================================
526 /*!
527  *  
528  */
529 //=============================================================================
530
531 CORBA::Boolean
532   SMESH_MeshEditor_i::TriToQuadObject (SMESH::SMESH_IDSource_ptr   theObject,
533                                        SMESH::NumericalFunctor_ptr Criterion,
534                                        CORBA::Double               MaxAngle)
535 {
536   SMESH::long_array_var anElementsId = theObject->GetIDs();
537   return TriToQuad(anElementsId, Criterion, MaxAngle);
538 }
539
540 //=============================================================================
541 /*!
542  *  
543  */
544 //=============================================================================
545
546 CORBA::Boolean
547   SMESH_MeshEditor_i::QuadToTri(const SMESH::long_array &   IDsOfElements,
548                                 SMESH::NumericalFunctor_ptr Criterion)
549 {
550   set<const SMDS_MeshElement*> faces;
551   for (int i = 0; i < IDsOfElements.length(); i++)
552   {
553     CORBA::Long index = IDsOfElements[i];
554     const SMDS_MeshElement * elem = GetMeshDS()->FindElement(index);
555     if ( elem && elem->GetType() == SMDSAbs_Face)
556       faces.insert( elem );
557   }
558   SMESH::NumericalFunctor_i* aNumericalFunctor = 
559     dynamic_cast<SMESH::NumericalFunctor_i*>( SMESH_Gen_i::GetServant( Criterion ).in() );
560   SMESH::Controls::NumericalFunctorPtr aCrit;
561   if ( !aNumericalFunctor )
562     aCrit.reset( new SMESH::Controls::AspectRatio() );
563   else
564     aCrit = aNumericalFunctor->GetNumericalFunctor();
565
566
567   // Update Python script
568   TCollection_AsciiString str ("isDone = mesh_editor.QuadToTri(");
569   addArray( str, IDsOfElements ) += ", None ), ";
570   addToPythonScript( str );
571 #ifdef _DEBUG_
572   addToPythonScript( "print \"QuadToTri: \", isDone" );
573 #endif
574
575   ::SMESH_MeshEditor anEditor( _myMesh );
576   return anEditor.QuadToTri( faces, aCrit );
577 }
578
579 //=============================================================================
580 /*!
581  *  
582  */
583 //=============================================================================
584
585 CORBA::Boolean
586   SMESH_MeshEditor_i::SplitQuad(const SMESH::long_array & IDsOfElements,
587                                 CORBA::Boolean            Diag13)
588 {
589   set<const SMDS_MeshElement*> faces;
590   for (int i = 0; i < IDsOfElements.length(); i++)
591   {
592     CORBA::Long index = IDsOfElements[i];
593     const SMDS_MeshElement * elem = GetMeshDS()->FindElement(index);
594     if ( elem && elem->GetType() == SMDSAbs_Face)
595       faces.insert( elem );
596   }
597
598   // Update Python script
599   TCollection_AsciiString str ("isDone = mesh_editor.SplitQuad(");
600   addArray( str, IDsOfElements ) += ", ";
601   str += TCollection_AsciiString( Diag13 );
602   addToPythonScript( str + ")" );
603 #ifdef _DEBUG_
604   addToPythonScript( "print \"SplitQuad: \", isDone" );
605 #endif
606
607   ::SMESH_MeshEditor anEditor( _myMesh );
608   return anEditor.QuadToTri( faces, Diag13 );
609 }
610
611 //=============================================================================
612 /*!
613  *  
614  */
615 //=============================================================================
616
617 CORBA::Boolean
618   SMESH_MeshEditor_i::SplitQuadObject(SMESH::SMESH_IDSource_ptr theObject,
619                                       CORBA::Boolean            Diag13)
620 {
621   SMESH::long_array_var anElementsId = theObject->GetIDs();
622   return SplitQuad(anElementsId, Diag13);
623 }
624
625 //=============================================================================
626 /*!
627  *  
628  */
629 //=============================================================================
630
631 CORBA::Boolean
632   SMESH_MeshEditor_i::Smooth(const SMESH::long_array &              IDsOfElements,
633                              const SMESH::long_array &              IDsOfFixedNodes,
634                              CORBA::Long                            MaxNbOfIterations,
635                              CORBA::Double                          MaxAspectRatio,
636                              SMESH::SMESH_MeshEditor::Smooth_Method Method)
637 {
638   SMESHDS_Mesh* aMesh = GetMeshDS();
639
640   set<const SMDS_MeshElement*> elements;
641   for (int i = 0; i < IDsOfElements.length(); i++)
642   {
643     CORBA::Long index = IDsOfElements[i];
644     const SMDS_MeshElement * elem = aMesh->FindElement(index);
645     if ( elem && elem->GetType() == SMDSAbs_Face)
646       elements.insert( elem );
647   }
648
649   set<const SMDS_MeshNode*> fixedNodes;
650   for (int i = 0; i < IDsOfFixedNodes.length(); i++)
651   {
652     CORBA::Long index = IDsOfFixedNodes[i];
653     const SMDS_MeshNode * node = aMesh->FindNode(index);
654     if ( node )
655       fixedNodes.insert( node );
656   }
657   ::SMESH_MeshEditor::SmoothMethod method = ::SMESH_MeshEditor::LAPLACIAN;
658   if ( Method != SMESH::SMESH_MeshEditor::LAPLACIAN_SMOOTH )
659     method = ::SMESH_MeshEditor::CENTROIDAL;
660
661   ::SMESH_MeshEditor anEditor( _myMesh );
662   anEditor.Smooth( elements, fixedNodes, method, MaxNbOfIterations, MaxAspectRatio );
663
664   // Update Python script
665   TCollection_AsciiString str ("isDone = mesh_editor.Smooth(");
666   addArray( str, IDsOfElements ) += ", ";
667   addArray( str, IDsOfFixedNodes ) += ", ";
668   str += (Standard_Integer) MaxNbOfIterations;
669   str += ", ";
670   str += (Standard_Real) MaxAspectRatio;
671   str += ", ";
672   if ( method == ::SMESH_MeshEditor::CENTROIDAL )
673     str += "SMESH.SMESH_MeshEditor.LAPLACIAN_SMOOTH )";
674   else
675     str += "SMESH.SMESH_MeshEditor.CENTROIDAL_SMOOTH )";
676   addToPythonScript( str );
677 #ifdef _DEBUG_
678   addToPythonScript( "print \"SplitQuad: \", isDone" );
679 #endif
680
681   return true;
682 }
683
684 //=============================================================================
685 /*!
686  *  
687  */
688 //=============================================================================
689
690 CORBA::Boolean
691   SMESH_MeshEditor_i::SmoothObject(SMESH::SMESH_IDSource_ptr              theObject,
692                                    const SMESH::long_array &              IDsOfFixedNodes,
693                                    CORBA::Long                            MaxNbOfIterations,
694                                    CORBA::Double                          MaxAspectRatio,
695                                    SMESH::SMESH_MeshEditor::Smooth_Method Method)
696 {
697   SMESH::long_array_var anElementsId = theObject->GetIDs();
698   return Smooth(anElementsId, IDsOfFixedNodes, MaxNbOfIterations, MaxAspectRatio, Method);
699 }
700
701 //=============================================================================
702 /*!
703  *  
704  */
705 //=============================================================================
706
707 void SMESH_MeshEditor_i::RenumberNodes()
708 {
709   // Update Python script
710   addToPythonScript( "mesh_editor.RenumberNodes()" );
711
712   GetMeshDS()->Renumber( true );
713 }
714
715 //=============================================================================
716 /*!
717  *  
718  */
719 //=============================================================================
720
721 void SMESH_MeshEditor_i::RenumberElements()
722 {
723   // Update Python script
724   addToPythonScript( "mesh_editor.RenumberElements()" );
725
726   GetMeshDS()->Renumber( false );
727 }
728
729 //=======================================================================
730 //function : RotationSweep
731 //purpose  : 
732 //=======================================================================
733
734 void SMESH_MeshEditor_i::RotationSweep(const SMESH::long_array & theIDsOfElements,
735                                        const SMESH::AxisStruct & theAxis,
736                                        CORBA::Double             theAngleInRadians,
737                                        CORBA::Long               theNbOfSteps,
738                                        CORBA::Double             theTolerance)
739 {
740   SMESHDS_Mesh* aMesh = GetMeshDS();
741
742   set<const SMDS_MeshElement*> elements;
743   for (int i = 0; i < theIDsOfElements.length(); i++)
744   {
745     CORBA::Long index = theIDsOfElements[i];
746     const SMDS_MeshElement * elem = aMesh->FindElement(index);
747     if ( elem )
748       elements.insert( elem );
749   }
750   gp_Ax1 Ax1 (gp_Pnt( theAxis.x, theAxis.y, theAxis.z ),
751               gp_Vec( theAxis.vx, theAxis.vy, theAxis.vz ));
752
753   ::SMESH_MeshEditor anEditor( _myMesh );
754   anEditor.RotationSweep (elements, Ax1, theAngleInRadians,
755                           theNbOfSteps, theTolerance);
756
757   // Update Python script
758   TCollection_AsciiString str = "axis = ";
759   addAxis( str, theAxis );
760   addToPythonScript( str );
761   str = ("mesh_editor.RotationSweep(");
762   addArray( str, theIDsOfElements ) += ", axis, ";
763   str += TCollection_AsciiString( theAngleInRadians ) + ", ";
764   str += TCollection_AsciiString( (int)theNbOfSteps ) + ", ";
765   str += TCollection_AsciiString( theTolerance      ) + " )";
766   addToPythonScript( str );
767 }
768
769 //=======================================================================
770 //function : RotationSweepObject
771 //purpose  : 
772 //=======================================================================
773
774 void SMESH_MeshEditor_i::RotationSweepObject(SMESH::SMESH_IDSource_ptr theObject,
775                                              const SMESH::AxisStruct & theAxis,
776                                              CORBA::Double             theAngleInRadians,
777                                              CORBA::Long               theNbOfSteps,
778                                              CORBA::Double             theTolerance)
779 {
780   SMESH::long_array_var anElementsId = theObject->GetIDs();
781   RotationSweep(anElementsId, theAxis, theAngleInRadians, theNbOfSteps, theTolerance);
782 }
783
784 //=======================================================================
785 //function : ExtrusionSweep
786 //purpose  : 
787 //=======================================================================
788
789 void SMESH_MeshEditor_i::ExtrusionSweep(const SMESH::long_array & theIDsOfElements,
790                                         const SMESH::DirStruct &  theStepVector,
791                                         CORBA::Long               theNbOfSteps)
792 {
793   SMESHDS_Mesh* aMesh = GetMeshDS();
794
795   set<const SMDS_MeshElement*> elements;
796   for (int i = 0; i < theIDsOfElements.length(); i++)
797   {
798     CORBA::Long index = theIDsOfElements[i];
799     const SMDS_MeshElement * elem = aMesh->FindElement(index);
800     if ( elem )
801       elements.insert( elem );
802   }
803   const SMESH::PointStruct * P = &theStepVector.PS;
804   gp_Vec stepVec( P->x, P->y, P->z );
805
806   ::SMESH_MeshEditor anEditor( _myMesh );
807   anEditor.ExtrusionSweep (elements, stepVec, theNbOfSteps);
808
809   // Update Python script
810   TCollection_AsciiString str = "stepVector = SMESH.DirStruct( SMESH.PointStruct ( ";
811   str += (TCollection_AsciiString) stepVec.X() + ", ";
812   str += (TCollection_AsciiString) stepVec.Y() + ", ";
813   str += (TCollection_AsciiString) stepVec.Z() + " ))";
814   addToPythonScript( str );
815   str = ("mesh_editor.ExtrusionSweep(");
816   addArray( str, theIDsOfElements ) += ", stepVector, ";
817   str += TCollection_AsciiString((int)theNbOfSteps) + " )";
818   addToPythonScript( str );
819 }
820
821
822 //=======================================================================
823 //function : ExtrusionSweepObject
824 //purpose  : 
825 //=======================================================================
826
827 void SMESH_MeshEditor_i::ExtrusionSweepObject(SMESH::SMESH_IDSource_ptr theObject,
828                                               const SMESH::DirStruct &  theStepVector,
829                                               CORBA::Long               theNbOfSteps)
830 {
831   SMESH::long_array_var anElementsId = theObject->GetIDs();
832   ExtrusionSweep(anElementsId, theStepVector, theNbOfSteps);
833 }
834
835 #define RETCASE(enm) case ::SMESH_MeshEditor::enm: return SMESH::SMESH_MeshEditor::enm;
836
837 static SMESH::SMESH_MeshEditor::Extrusion_Error convExtrError( const::SMESH_MeshEditor::Extrusion_Error e )
838 {
839   switch ( e ) {
840   RETCASE( EXTR_OK );
841   RETCASE( EXTR_NO_ELEMENTS );
842   RETCASE( EXTR_PATH_NOT_EDGE );
843   RETCASE( EXTR_BAD_PATH_SHAPE );
844   RETCASE( EXTR_BAD_STARTING_NODE );
845   RETCASE( EXTR_BAD_ANGLES_NUMBER );
846   RETCASE( EXTR_CANT_GET_TANGENT );
847   }
848   return SMESH::SMESH_MeshEditor::EXTR_OK;
849 }
850
851 //=======================================================================
852 //function : ExtrusionAlongPath
853 //purpose  : 
854 //=======================================================================
855
856 SMESH::SMESH_MeshEditor::Extrusion_Error
857   SMESH_MeshEditor_i::ExtrusionAlongPath(const SMESH::long_array &   theIDsOfElements,
858                                          SMESH::SMESH_Mesh_ptr       thePathMesh,
859                                          GEOM::GEOM_Object_ptr       thePathShape,
860                                          CORBA::Long                 theNodeStart,
861                                          CORBA::Boolean              theHasAngles,
862                                          const SMESH::double_array & theAngles,
863                                          CORBA::Boolean              theHasRefPoint,
864                                          const SMESH::PointStruct &  theRefPoint)
865 {
866   SMESHDS_Mesh*  aMesh = GetMeshDS();
867
868   if ( thePathMesh->_is_nil() || thePathShape->_is_nil() )
869     return SMESH::SMESH_MeshEditor::EXTR_BAD_PATH_SHAPE;
870
871   SMESH_Mesh_i* aMeshImp = dynamic_cast<SMESH_Mesh_i*>( SMESH_Gen_i::GetServant( thePathMesh ).in() );
872   TopoDS_Shape aShape = SMESH_Gen_i::GetSMESHGen()->GeomObjectToShape( thePathShape );
873   SMESH_subMesh* aSubMesh = aMeshImp->GetImpl().GetSubMesh( aShape );
874
875   if ( !aSubMesh )
876     return SMESH::SMESH_MeshEditor::EXTR_BAD_PATH_SHAPE;
877
878   SMDS_MeshNode* nodeStart = (SMDS_MeshNode*)aMeshImp->GetImpl().GetMeshDS()->FindNode(theNodeStart);
879   if ( !nodeStart )
880     return SMESH::SMESH_MeshEditor::EXTR_BAD_STARTING_NODE;
881
882   set<const SMDS_MeshElement*> elements;
883   for (int i = 0; i < theIDsOfElements.length(); i++)
884   {
885     CORBA::Long index = theIDsOfElements[i];
886     const SMDS_MeshElement * elem = aMesh->FindElement(index);
887     if ( elem )
888       elements.insert( elem );
889   }
890
891   list<double> angles;
892   for (int i = 0; i < theAngles.length(); i++)
893   {
894     angles.push_back( theAngles[i] );
895   }
896
897   gp_Pnt refPnt( theRefPoint.x, theRefPoint.y, theRefPoint.z );
898
899   // Update Python script
900   TCollection_AsciiString str = "refPoint = SMESH.PointStruct( ";
901   str += (TCollection_AsciiString) refPnt.X() + ", ";
902   str += (TCollection_AsciiString) refPnt.Y() + ", ";
903   str += (TCollection_AsciiString) refPnt.Z() + " )";
904   addToPythonScript( str );
905   str = ("error = mesh_editor.ExtrusionAlongPath(");
906   addArray ( str, theIDsOfElements ) += ", ";
907   addObject( str, thePathMesh ) += ", salome.IDToObject(\"";
908   addObject( str, thePathShape ) += "\"), ";
909   str += TCollection_AsciiString( (int)theNodeStart ) + ", ";
910   str += TCollection_AsciiString( (int)theHasAngles ) + ", ";
911   addArray ( str, theAngles ) += ", ";
912   str += (TCollection_AsciiString) theHasRefPoint + ", refPoint )";
913   addToPythonScript( str );
914
915   ::SMESH_MeshEditor anEditor( _myMesh );
916   return convExtrError( anEditor.ExtrusionAlongTrack( elements, aSubMesh, nodeStart, theHasAngles, angles, theHasRefPoint, refPnt ) );
917 }
918
919 //=======================================================================
920 //function : ExtrusionAlongPathObject
921 //purpose  : 
922 //=======================================================================
923
924 SMESH::SMESH_MeshEditor::Extrusion_Error
925   SMESH_MeshEditor_i::ExtrusionAlongPathObject(SMESH::SMESH_IDSource_ptr   theObject,
926                                                SMESH::SMESH_Mesh_ptr       thePathMesh,
927                                                GEOM::GEOM_Object_ptr       thePathShape,
928                                                CORBA::Long                 theNodeStart,
929                                                CORBA::Boolean              theHasAngles,
930                                                const SMESH::double_array & theAngles,
931                                                CORBA::Boolean              theHasRefPoint,
932                                                const SMESH::PointStruct &  theRefPoint)
933 {
934   SMESH::long_array_var anElementsId = theObject->GetIDs();
935   return ExtrusionAlongPath( anElementsId, thePathMesh, thePathShape, theNodeStart, theHasAngles, theAngles, theHasRefPoint, theRefPoint );
936 }
937
938 //=======================================================================
939 //function : Mirror
940 //purpose  : 
941 //=======================================================================
942
943 void SMESH_MeshEditor_i::Mirror(const SMESH::long_array &           theIDsOfElements,
944                                 const SMESH::AxisStruct &           theAxis,
945                                 SMESH::SMESH_MeshEditor::MirrorType theMirrorType,
946                                 CORBA::Boolean                      theCopy)
947 {
948   SMESHDS_Mesh* aMesh = GetMeshDS();
949
950   set<const SMDS_MeshElement*> elements;
951   for (int i = 0; i < theIDsOfElements.length(); i++)
952   {
953     CORBA::Long index = theIDsOfElements[i];
954     const SMDS_MeshElement * elem = aMesh->FindElement(index);
955     if ( elem )
956       elements.insert( elem );
957   }
958   gp_Pnt P ( theAxis.x, theAxis.y, theAxis.z );
959   gp_Vec V ( theAxis.vx, theAxis.vy, theAxis.vz );
960
961   gp_Trsf aTrsf;
962   TCollection_AsciiString typeStr, copyStr( theCopy );
963   switch ( theMirrorType ) {
964   case  SMESH::SMESH_MeshEditor::POINT:
965     aTrsf.SetMirror( P );
966     typeStr = "SMESH.SMESH_MeshEditor.POINT";
967     break;
968   case  SMESH::SMESH_MeshEditor::AXIS:
969     aTrsf.SetMirror( gp_Ax1( P, V ));
970     typeStr = "SMESH.SMESH_MeshEditor.AXIS";
971     break;
972   default:
973     aTrsf.SetMirror( gp_Ax2( P, V ));
974     typeStr = "SMESH.SMESH_MeshEditor.PLANE";
975   }
976
977   // Update Python script
978   TCollection_AsciiString str ("mesh_editor.Mirror(");
979   addArray( str, theIDsOfElements ) += ", ";
980   addAxis( str, theAxis )           += ", ";
981   str += typeStr                     + ", ";
982   str += copyStr                     + " )";
983   addToPythonScript( str );
984
985   ::SMESH_MeshEditor anEditor( _myMesh );
986   anEditor.Transform (elements, aTrsf, theCopy);
987 }
988
989 //=======================================================================
990 //function : MirrorObject
991 //purpose  : 
992 //=======================================================================
993
994 void SMESH_MeshEditor_i::MirrorObject(SMESH::SMESH_IDSource_ptr           theObject,
995                                       const SMESH::AxisStruct &           theAxis,
996                                       SMESH::SMESH_MeshEditor::MirrorType theMirrorType,
997                                       CORBA::Boolean                      theCopy)
998 {
999   SMESH::long_array_var anElementsId = theObject->GetIDs();
1000   Mirror(anElementsId, theAxis, theMirrorType, theCopy);
1001 }
1002
1003 //=======================================================================
1004 //function : Translate
1005 //purpose  : 
1006 //=======================================================================
1007
1008 void SMESH_MeshEditor_i::Translate(const SMESH::long_array & theIDsOfElements,
1009                                    const SMESH::DirStruct &  theVector,
1010                                    CORBA::Boolean            theCopy)
1011 {
1012   SMESHDS_Mesh* aMesh = GetMeshDS();
1013
1014   set<const SMDS_MeshElement*> elements;
1015   for (int i = 0; i < theIDsOfElements.length(); i++)
1016   {
1017     CORBA::Long index = theIDsOfElements[i];
1018     const SMDS_MeshElement * elem = aMesh->FindElement(index);
1019     if ( elem )
1020       elements.insert( elem );
1021   }
1022   gp_Trsf aTrsf;
1023   const SMESH::PointStruct * P = &theVector.PS;
1024   aTrsf.SetTranslation( gp_Vec( P->x, P->y, P->z ));
1025
1026   ::SMESH_MeshEditor anEditor( _myMesh );
1027   anEditor.Transform (elements, aTrsf, theCopy);
1028
1029   // Update Python script
1030   TCollection_AsciiString str = "vector = SMESH.DirStruct( SMESH.PointStruct ( ";
1031   str += (TCollection_AsciiString) P->x + ", ";
1032   str += (TCollection_AsciiString) P->y + ", ";
1033   str += (TCollection_AsciiString) P->z + " ))";
1034   addToPythonScript( str );
1035   str = ("mesh_editor.Translate(");
1036   addArray( str, theIDsOfElements ) += ", vector, ";
1037   str += (TCollection_AsciiString) theCopy + " )";
1038   addToPythonScript( str );
1039 }
1040
1041 //=======================================================================
1042 //function : TranslateObject
1043 //purpose  : 
1044 //=======================================================================
1045
1046 void SMESH_MeshEditor_i::TranslateObject(SMESH::SMESH_IDSource_ptr theObject,
1047                                          const SMESH::DirStruct &  theVector,
1048                                          CORBA::Boolean            theCopy)
1049 {
1050   SMESH::long_array_var anElementsId = theObject->GetIDs();
1051   Translate(anElementsId, theVector, theCopy);
1052 }
1053
1054 //=======================================================================
1055 //function : Rotate
1056 //purpose  : 
1057 //=======================================================================
1058
1059 void SMESH_MeshEditor_i::Rotate(const SMESH::long_array & theIDsOfElements,
1060                                 const SMESH::AxisStruct & theAxis,
1061                                 CORBA::Double             theAngle,
1062                                 CORBA::Boolean            theCopy)
1063 {
1064   SMESHDS_Mesh* aMesh = GetMeshDS();
1065
1066   set<const SMDS_MeshElement*> elements;
1067   for (int i = 0; i < theIDsOfElements.length(); i++)
1068   {
1069     CORBA::Long index = theIDsOfElements[i];
1070     const SMDS_MeshElement * elem = aMesh->FindElement(index);
1071     if ( elem )
1072       elements.insert( elem );
1073   }
1074   gp_Pnt P ( theAxis.x, theAxis.y, theAxis.z );
1075   gp_Vec V ( theAxis.vx, theAxis.vy, theAxis.vz );
1076
1077   gp_Trsf aTrsf;
1078   aTrsf.SetRotation( gp_Ax1( P, V ), theAngle);
1079   
1080   ::SMESH_MeshEditor anEditor( _myMesh );
1081   anEditor.Transform (elements, aTrsf, theCopy);
1082
1083   // Update Python script
1084   TCollection_AsciiString str ("axis = ");
1085   addAxis( str, theAxis );
1086   addToPythonScript( str );
1087   str = ("mesh_editor.Rotate(");
1088   addArray( str, theIDsOfElements ) += ", axis, ";
1089   str += (TCollection_AsciiString) theAngle + ", ";
1090   str += (TCollection_AsciiString) theCopy + " )";
1091   addToPythonScript( str );
1092 }
1093
1094 //=======================================================================
1095 //function : RotateObject
1096 //purpose  : 
1097 //=======================================================================
1098
1099 void SMESH_MeshEditor_i::RotateObject(SMESH::SMESH_IDSource_ptr theObject,
1100                                       const SMESH::AxisStruct & theAxis,
1101                                       CORBA::Double             theAngle,
1102                                       CORBA::Boolean            theCopy)
1103 {
1104   SMESH::long_array_var anElementsId = theObject->GetIDs();
1105   Rotate(anElementsId, theAxis, theAngle, theCopy);
1106 }
1107
1108 //=======================================================================
1109 //function : FindCoincidentNodes
1110 //purpose  : 
1111 //=======================================================================
1112
1113 void SMESH_MeshEditor_i::FindCoincidentNodes (CORBA::Double                  Tolerance,
1114                                               SMESH::array_of_long_array_out GroupsOfNodes)
1115 {
1116   ::SMESH_MeshEditor::TListOfListOfNodes aListOfListOfNodes;
1117   ::SMESH_MeshEditor anEditor( _myMesh );
1118   set<const SMDS_MeshNode*> nodes; // no input nodes
1119   anEditor.FindCoincidentNodes( nodes, Tolerance, aListOfListOfNodes );
1120
1121   GroupsOfNodes = new SMESH::array_of_long_array;
1122   GroupsOfNodes->length( aListOfListOfNodes.size() );
1123   ::SMESH_MeshEditor::TListOfListOfNodes::iterator llIt = aListOfListOfNodes.begin();
1124   for ( CORBA::Long i = 0; llIt != aListOfListOfNodes.end(); llIt++, i++ )
1125   {
1126     list< const SMDS_MeshNode* >& aListOfNodes = *llIt;
1127     list< const SMDS_MeshNode* >::iterator lIt = aListOfNodes.begin();;
1128     SMESH::long_array& aGroup = GroupsOfNodes[ i ];
1129     aGroup.length( aListOfNodes.size() );
1130     for ( int j = 0; lIt != aListOfNodes.end(); lIt++, j++ )
1131       aGroup[ j ] = (*lIt)->GetID();
1132   }
1133 }
1134
1135 //=======================================================================
1136 //function : MergeNodes
1137 //purpose  : 
1138 //=======================================================================
1139
1140 void SMESH_MeshEditor_i::MergeNodes (const SMESH::array_of_long_array& GroupsOfNodes)
1141 {
1142   SMESHDS_Mesh* aMesh = GetMeshDS();
1143
1144   TCollection_AsciiString str( "mesh_editor.MergeNodes([" );
1145   ::SMESH_MeshEditor::TListOfListOfNodes aListOfListOfNodes;
1146   for (int i = 0; i < GroupsOfNodes.length(); i++)
1147   {
1148     const SMESH::long_array& aNodeGroup = GroupsOfNodes[ i ];
1149     aListOfListOfNodes.push_back( list< const SMDS_MeshNode* >() );
1150     list< const SMDS_MeshNode* >& aListOfNodes = aListOfListOfNodes.back();
1151     for ( int j = 0; j < aNodeGroup.length(); j++ )
1152     {
1153       CORBA::Long index = aNodeGroup[ j ];
1154       const SMDS_MeshNode * node = aMesh->FindNode(index);
1155       if ( node )
1156         aListOfNodes.push_back( node );
1157     }
1158     if ( aListOfNodes.size() < 2 )
1159       aListOfListOfNodes.pop_back();
1160
1161     if ( i > 0 )
1162       str += ",";
1163     addArray( str, aNodeGroup );
1164   }
1165   ::SMESH_MeshEditor anEditor( _myMesh );
1166   anEditor.MergeNodes( aListOfListOfNodes );
1167
1168   // Update Python script
1169   addToPythonScript( str + "])" );
1170 }
1171
1172 //=======================================================================
1173 //function : MergeEqualElements
1174 //purpose  : 
1175 //=======================================================================
1176
1177 void SMESH_MeshEditor_i::MergeEqualElements()
1178 {
1179   ::SMESH_MeshEditor anEditor( _myMesh );
1180   anEditor.MergeEqualElements();
1181
1182   // Update Python script
1183   addToPythonScript( "mesh_editor.MergeEqualElements()" );
1184 }
1185
1186 //=======================================================================
1187 //function : operator
1188 //purpose  : 
1189 //=======================================================================
1190
1191 #define RETCASE(enm) case ::SMESH_MeshEditor::enm: return SMESH::SMESH_MeshEditor::enm;
1192
1193 static SMESH::SMESH_MeshEditor::Sew_Error convError( const::SMESH_MeshEditor::Sew_Error e )
1194 {
1195   switch ( e ) {
1196   RETCASE( SEW_OK );
1197   RETCASE( SEW_BORDER1_NOT_FOUND );
1198   RETCASE( SEW_BORDER2_NOT_FOUND );
1199   RETCASE( SEW_BOTH_BORDERS_NOT_FOUND );
1200   RETCASE( SEW_BAD_SIDE_NODES );
1201   RETCASE( SEW_VOLUMES_TO_SPLIT );
1202   RETCASE( SEW_DIFF_NB_OF_ELEMENTS );
1203   RETCASE( SEW_TOPO_DIFF_SETS_OF_ELEMENTS );
1204   RETCASE( SEW_BAD_SIDE1_NODES );
1205   RETCASE( SEW_BAD_SIDE2_NODES );
1206   }
1207   return SMESH::SMESH_MeshEditor::SEW_OK;
1208 }
1209
1210 //=======================================================================
1211 //function : SewFreeBorders
1212 //purpose  : 
1213 //=======================================================================
1214
1215 SMESH::SMESH_MeshEditor::Sew_Error
1216   SMESH_MeshEditor_i::SewFreeBorders(CORBA::Long FirstNodeID1,
1217                                      CORBA::Long SecondNodeID1,
1218                                      CORBA::Long LastNodeID1,
1219                                      CORBA::Long FirstNodeID2,
1220                                      CORBA::Long SecondNodeID2,
1221                                      CORBA::Long LastNodeID2,
1222                                      CORBA::Boolean CreatePolygons,
1223                                      CORBA::Boolean CreatePolyedrs)
1224 {
1225   SMESHDS_Mesh* aMesh = GetMeshDS();
1226
1227   const SMDS_MeshNode* aBorderFirstNode  = aMesh->FindNode( FirstNodeID1  );
1228   const SMDS_MeshNode* aBorderSecondNode = aMesh->FindNode( SecondNodeID1 );
1229   const SMDS_MeshNode* aBorderLastNode   = aMesh->FindNode( LastNodeID1   );
1230   const SMDS_MeshNode* aSide2FirstNode   = aMesh->FindNode( FirstNodeID2  );
1231   const SMDS_MeshNode* aSide2SecondNode  = aMesh->FindNode( SecondNodeID2 );
1232   const SMDS_MeshNode* aSide2ThirdNode   = aMesh->FindNode( LastNodeID2   );
1233
1234   if (!aBorderFirstNode ||
1235       !aBorderSecondNode||
1236       !aBorderLastNode)
1237     return SMESH::SMESH_MeshEditor::SEW_BORDER1_NOT_FOUND;
1238   if (!aSide2FirstNode  ||
1239       !aSide2SecondNode ||
1240       !aSide2ThirdNode)
1241     return SMESH::SMESH_MeshEditor::SEW_BORDER2_NOT_FOUND;
1242
1243   // Update Python script
1244   TCollection_AsciiString str ("error = mesh_editor.SewFreeBorders( ");
1245   str += TCollection_AsciiString( (int) FirstNodeID1  )  + ", ";
1246   str += TCollection_AsciiString( (int) SecondNodeID1 )  + ", ";
1247   str += TCollection_AsciiString( (int) LastNodeID1   )  + ", ";
1248   str += TCollection_AsciiString( (int) FirstNodeID2  )  + ", ";
1249   str += TCollection_AsciiString( (int) SecondNodeID2 )  + ", ";
1250   str += TCollection_AsciiString( (int) LastNodeID2   )  + ", ";
1251   str += TCollection_AsciiString( CreatePolygons      )  + ", ";
1252   str += TCollection_AsciiString( CreatePolyedrs      )  + ") ";
1253   addToPythonScript( str );
1254
1255   ::SMESH_MeshEditor anEditor( _myMesh );
1256   return convError( anEditor.SewFreeBorder (aBorderFirstNode,
1257                                             aBorderSecondNode,
1258                                             aBorderLastNode,
1259                                             aSide2FirstNode,
1260                                             aSide2SecondNode,
1261                                             aSide2ThirdNode,
1262                                             true,
1263                                             CreatePolygons,
1264                                             CreatePolyedrs) );
1265 }
1266
1267 //=======================================================================
1268 //function : SewConformFreeBorders
1269 //purpose  : 
1270 //=======================================================================
1271
1272 SMESH::SMESH_MeshEditor::Sew_Error
1273   SMESH_MeshEditor_i::SewConformFreeBorders(CORBA::Long FirstNodeID1,
1274                                             CORBA::Long SecondNodeID1,
1275                                             CORBA::Long LastNodeID1,
1276                                             CORBA::Long FirstNodeID2,
1277                                             CORBA::Long SecondNodeID2)
1278 {
1279   SMESHDS_Mesh* aMesh = GetMeshDS();
1280
1281   const SMDS_MeshNode* aBorderFirstNode  = aMesh->FindNode( FirstNodeID1  );
1282   const SMDS_MeshNode* aBorderSecondNode = aMesh->FindNode( SecondNodeID1 );
1283   const SMDS_MeshNode* aBorderLastNode   = aMesh->FindNode( LastNodeID1   );
1284   const SMDS_MeshNode* aSide2FirstNode   = aMesh->FindNode( FirstNodeID2  );
1285   const SMDS_MeshNode* aSide2SecondNode  = aMesh->FindNode( SecondNodeID2 );
1286   const SMDS_MeshNode* aSide2ThirdNode   = 0;
1287
1288   if (!aBorderFirstNode ||
1289       !aBorderSecondNode||
1290       !aBorderLastNode )
1291     return SMESH::SMESH_MeshEditor::SEW_BORDER1_NOT_FOUND;
1292   if (!aSide2FirstNode  ||
1293       !aSide2SecondNode)
1294     return SMESH::SMESH_MeshEditor::SEW_BORDER2_NOT_FOUND;
1295
1296   // Update Python script
1297   TCollection_AsciiString str ("error = mesh_editor.SewConformFreeBorders( ");
1298   str += TCollection_AsciiString( (int) FirstNodeID1  )  + ", ";
1299   str += TCollection_AsciiString( (int) SecondNodeID1 )  + ", ";
1300   str += TCollection_AsciiString( (int) LastNodeID1   )  + ", ";
1301   str += TCollection_AsciiString( (int) FirstNodeID2  )  + ", ";
1302   str += TCollection_AsciiString( (int) SecondNodeID2 )  + ")";
1303   addToPythonScript( str );
1304
1305   ::SMESH_MeshEditor anEditor( _myMesh );
1306   return convError( anEditor.SewFreeBorder (aBorderFirstNode,
1307                                             aBorderSecondNode,
1308                                             aBorderLastNode,
1309                                             aSide2FirstNode,
1310                                             aSide2SecondNode,
1311                                             aSide2ThirdNode,
1312                                             true,
1313                                             false, false) );
1314 }
1315
1316 //=======================================================================
1317 //function : SewBorderToSide
1318 //purpose  : 
1319 //=======================================================================
1320
1321 SMESH::SMESH_MeshEditor::Sew_Error
1322   SMESH_MeshEditor_i::SewBorderToSide(CORBA::Long FirstNodeIDOnFreeBorder,
1323                                       CORBA::Long SecondNodeIDOnFreeBorder,
1324                                       CORBA::Long LastNodeIDOnFreeBorder,
1325                                       CORBA::Long FirstNodeIDOnSide,
1326                                       CORBA::Long LastNodeIDOnSide,
1327                                       CORBA::Boolean CreatePolygons,
1328                                       CORBA::Boolean CreatePolyedrs)
1329 {
1330   SMESHDS_Mesh* aMesh = GetMeshDS();
1331
1332   const SMDS_MeshNode* aBorderFirstNode  = aMesh->FindNode( FirstNodeIDOnFreeBorder  );
1333   const SMDS_MeshNode* aBorderSecondNode = aMesh->FindNode( SecondNodeIDOnFreeBorder );
1334   const SMDS_MeshNode* aBorderLastNode   = aMesh->FindNode( LastNodeIDOnFreeBorder   );
1335   const SMDS_MeshNode* aSide2FirstNode   = aMesh->FindNode( FirstNodeIDOnSide  );
1336   const SMDS_MeshNode* aSide2SecondNode  = aMesh->FindNode( LastNodeIDOnSide );
1337   const SMDS_MeshNode* aSide2ThirdNode   = 0;
1338
1339   if (!aBorderFirstNode ||
1340       !aBorderSecondNode||
1341       !aBorderLastNode  )
1342     return SMESH::SMESH_MeshEditor::SEW_BORDER1_NOT_FOUND;
1343   if (!aSide2FirstNode  ||
1344       !aSide2SecondNode)
1345     return SMESH::SMESH_MeshEditor::SEW_BAD_SIDE_NODES;
1346
1347   // Update Python script
1348   TCollection_AsciiString str ("error = mesh_editor.SewBorderToSide( ");
1349   str += TCollection_AsciiString( (int) FirstNodeIDOnFreeBorder  ) + ", ";
1350   str += TCollection_AsciiString( (int) SecondNodeIDOnFreeBorder ) + ", ";
1351   str += TCollection_AsciiString( (int) LastNodeIDOnFreeBorder   ) + ", ";
1352   str += TCollection_AsciiString( (int) FirstNodeIDOnSide        ) + ", ";
1353   str += TCollection_AsciiString( (int) LastNodeIDOnSide         ) + ", ";
1354   str += TCollection_AsciiString( CreatePolygons                 ) + ", ";
1355   str += TCollection_AsciiString( CreatePolyedrs                 ) + ") ";
1356   addToPythonScript( str );
1357
1358   ::SMESH_MeshEditor anEditor( _myMesh );
1359   return convError( anEditor.SewFreeBorder (aBorderFirstNode,
1360                                             aBorderSecondNode,
1361                                             aBorderLastNode,
1362                                             aSide2FirstNode,
1363                                             aSide2SecondNode,
1364                                             aSide2ThirdNode,
1365                                             false,
1366                                             CreatePolygons,
1367                                             CreatePolyedrs) );
1368 }
1369
1370 //=======================================================================
1371 //function : SewSideElements
1372 //purpose  : 
1373 //=======================================================================
1374
1375 SMESH::SMESH_MeshEditor::Sew_Error
1376   SMESH_MeshEditor_i::SewSideElements(const SMESH::long_array& IDsOfSide1Elements,
1377                                       const SMESH::long_array& IDsOfSide2Elements,
1378                                       CORBA::Long NodeID1OfSide1ToMerge,
1379                                       CORBA::Long NodeID1OfSide2ToMerge,
1380                                       CORBA::Long NodeID2OfSide1ToMerge,
1381                                       CORBA::Long NodeID2OfSide2ToMerge)
1382 {
1383   SMESHDS_Mesh* aMesh = GetMeshDS();
1384
1385   const SMDS_MeshNode* aFirstNode1ToMerge  = aMesh->FindNode( NodeID1OfSide1ToMerge );
1386   const SMDS_MeshNode* aFirstNode2ToMerge  = aMesh->FindNode( NodeID1OfSide2ToMerge );
1387   const SMDS_MeshNode* aSecondNode1ToMerge = aMesh->FindNode( NodeID2OfSide1ToMerge );
1388   const SMDS_MeshNode* aSecondNode2ToMerge = aMesh->FindNode( NodeID2OfSide2ToMerge );
1389
1390   if (!aFirstNode1ToMerge ||
1391       !aFirstNode2ToMerge )
1392     return SMESH::SMESH_MeshEditor::SEW_BAD_SIDE1_NODES;
1393   if (!aSecondNode1ToMerge||
1394       !aSecondNode2ToMerge)
1395     return SMESH::SMESH_MeshEditor::SEW_BAD_SIDE2_NODES;
1396
1397   set<const SMDS_MeshElement*> aSide1Elems, aSide2Elems;
1398   for (int i = 0; i < IDsOfSide1Elements.length(); i++)
1399   {
1400     CORBA::Long index = IDsOfSide1Elements[i];
1401     const SMDS_MeshElement * elem = aMesh->FindElement(index);
1402     if ( elem )
1403       aSide1Elems.insert( elem );
1404   }
1405   for (int i = 0; i < IDsOfSide2Elements.length(); i++)
1406   {
1407     CORBA::Long index = IDsOfSide2Elements[i];
1408     const SMDS_MeshElement * elem = aMesh->FindElement(index);
1409     if ( elem )
1410       aSide2Elems.insert( elem );
1411   }
1412   // Update Python script
1413   TCollection_AsciiString str ("error = mesh_editor.SewSideElements( ");
1414   addArray( str, IDsOfSide1Elements ) += ", ";
1415   addArray( str, IDsOfSide2Elements ) += ", ";
1416   str += TCollection_AsciiString( (int) NodeID1OfSide1ToMerge ) + ", ";
1417   str += TCollection_AsciiString( (int) NodeID1OfSide2ToMerge ) + ", ";
1418   str += TCollection_AsciiString( (int) NodeID2OfSide1ToMerge ) + ", ";
1419   str += TCollection_AsciiString( (int) NodeID2OfSide2ToMerge ) + ")";
1420   addToPythonScript( str );
1421
1422   ::SMESH_MeshEditor anEditor( _myMesh );
1423   return convError( anEditor.SewSideElements (aSide1Elems, aSide2Elems,
1424                                               aFirstNode1ToMerge,
1425                                               aFirstNode2ToMerge,
1426                                               aSecondNode1ToMerge,
1427                                               aSecondNode2ToMerge));
1428 }