1 // Copyright (C) 2007-2012 CEA/DEN, EDF R&D, OPEN CASCADE
3 // Copyright (C) 2003-2007 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
6 // This library is free software; you can redistribute it and/or
7 // modify it under the terms of the GNU Lesser General Public
8 // License as published by the Free Software Foundation; either
9 // version 2.1 of the License.
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 // Lesser General Public License for more details.
16 // You should have received a copy of the GNU Lesser General Public
17 // License along with this library; if not, write to the Free Software
18 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
22 // File : SMESH_MeshEditor_i.cxx
23 // Author : Nicolas REJNERI
30 #include "SMESH_MeshEditor_i.hxx"
32 #include "SMDS_LinearEdge.hxx"
33 #include "SMDS_Mesh0DElement.hxx"
34 #include "SMDS_MeshFace.hxx"
35 #include "SMDS_MeshVolume.hxx"
36 #include "SMDS_PolyhedralVolumeOfNodes.hxx"
37 #include "SMDS_SetIterator.hxx"
38 #include "SMESHDS_Group.hxx"
39 #include "SMESH_ControlsDef.hxx"
40 #include "SMESH_Filter_i.hxx"
41 #include "SMESH_Gen_i.hxx"
42 #include "SMESH_Group_i.hxx"
43 #include "SMESH_PythonDump.hxx"
44 #include "SMESH_subMeshEventListener.hxx"
45 #include "SMESH_subMesh_i.hxx"
47 #include "utilities.h"
48 #include "Utils_ExceptHandlers.hxx"
49 #include "Utils_CorbaException.hxx"
51 #include <BRepAdaptor_Surface.hxx>
52 #include <BRep_Tool.hxx>
53 #include <TopExp_Explorer.hxx>
55 #include <TopoDS_Edge.hxx>
56 #include <TopoDS_Face.hxx>
61 #if (OCC_VERSION_MAJOR << 16 | OCC_VERSION_MINOR << 8 | OCC_VERSION_MAINTENANCE) > 0x060100
65 #include <Standard_Failure.hxx>
68 #include <Standard_ErrorHandler.hxx>
74 #define cast2Node(elem) static_cast<const SMDS_MeshNode*>( elem )
77 using SMESH::TPythonDump;
82 //=============================================================================
84 * \brief Mesh to apply modifications for preview purposes
86 //=============================================================================
88 struct TPreviewMesh: public SMESH_Mesh
90 SMDSAbs_ElementType myPreviewType; // type to show
92 TPreviewMesh(SMDSAbs_ElementType previewElements = SMDSAbs_All) {
93 _isShapeToMesh = (_id =_studyId =_idDoc = 0);
94 _myMeshDS = new SMESHDS_Mesh( _id, true );
95 myPreviewType = previewElements;
98 virtual ~TPreviewMesh() { delete _myMeshDS; _myMeshDS = 0; }
99 //!< Copy a set of elements
100 void Copy(const TIDSortedElemSet & theElements,
101 TIDSortedElemSet& theCopyElements,
102 SMDSAbs_ElementType theSelectType = SMDSAbs_All,
103 SMDSAbs_ElementType theAvoidType = SMDSAbs_All)
105 // loop on theIDsOfElements
106 TIDSortedElemSet::const_iterator eIt = theElements.begin();
107 for ( ; eIt != theElements.end(); ++eIt )
109 const SMDS_MeshElement* anElem = *eIt;
110 if ( !anElem ) continue;
111 SMDSAbs_ElementType type = anElem->GetType();
112 if ( type == theAvoidType ||
113 ( theSelectType != SMDSAbs_All && type != theSelectType ))
115 const SMDS_MeshElement* anElemCopy;
116 if ( type == SMDSAbs_Node)
117 anElemCopy = Copy( cast2Node(anElem) );
119 anElemCopy = Copy( anElem );
121 theCopyElements.insert( theCopyElements.end(), anElemCopy );
125 SMDS_MeshElement* Copy( const SMDS_MeshElement* anElem )
127 // copy element nodes
128 int anElemNbNodes = anElem->NbNodes();
129 vector< int > anElemNodesID( anElemNbNodes ) ;
130 SMDS_ElemIteratorPtr itElemNodes = anElem->nodesIterator();
131 for ( int i = 0; itElemNodes->more(); i++)
133 const SMDS_MeshNode* anElemNode = cast2Node( itElemNodes->next() );
135 anElemNodesID[i] = anElemNode->GetID();
138 // creates a corresponding element on copied nodes
139 SMDS_MeshElement* anElemCopy = 0;
140 if ( anElem->IsPoly() && anElem->GetType() == SMDSAbs_Volume )
142 const SMDS_VtkVolume* ph =
143 dynamic_cast<const SMDS_VtkVolume*> (anElem);
145 anElemCopy = _myMeshDS->AddPolyhedralVolumeWithID
146 (anElemNodesID, ph->GetQuantities(),anElem->GetID());
149 anElemCopy = ::SMESH_MeshEditor(this).AddElement( anElemNodesID,
156 SMDS_MeshNode* Copy( const SMDS_MeshNode* anElemNode )
158 return _myMeshDS->AddNodeWithID(anElemNode->X(), anElemNode->Y(), anElemNode->Z(),
159 anElemNode->GetID());
161 };// struct TPreviewMesh
163 static SMESH_NodeSearcher * theNodeSearcher = 0;
164 static SMESH_ElementSearcher * theElementSearcher = 0;
166 //=============================================================================
168 * \brief Deleter of theNodeSearcher at any compute event occured
170 //=============================================================================
172 struct TSearchersDeleter : public SMESH_subMeshEventListener
175 string myMeshPartIOR;
177 TSearchersDeleter(): SMESH_subMeshEventListener( false, // won't be deleted by submesh
178 "SMESH_MeshEditor_i::TSearchersDeleter"),
180 //!< Delete theNodeSearcher
183 if ( theNodeSearcher ) delete theNodeSearcher; theNodeSearcher = 0;
184 if ( theElementSearcher ) delete theElementSearcher; theElementSearcher = 0;
186 typedef map < int, SMESH_subMesh * > TDependsOnMap;
187 //!< The meshod called by submesh: do my main job
188 void ProcessEvent(const int, const int eventType, SMESH_subMesh* sm,
189 SMESH_subMeshEventListenerData*,const SMESH_Hypothesis*)
191 if ( eventType == SMESH_subMesh::COMPUTE_EVENT ) {
193 Unset( sm->GetFather() );
196 //!< set self on all submeshes and delete theNodeSearcher if other mesh is set
197 void Set(SMESH_Mesh* mesh, const string& meshPartIOR = string())
199 if ( myMesh != mesh || myMeshPartIOR != meshPartIOR)
206 myMeshPartIOR = meshPartIOR;
207 if ( SMESH_subMesh* myMainSubMesh = mesh->GetSubMeshContaining(1) ) {
208 const TDependsOnMap & subMeshes = myMainSubMesh->DependsOn();
209 TDependsOnMap::const_iterator sm;
210 for (sm = subMeshes.begin(); sm != subMeshes.end(); sm++)
211 sm->second->SetEventListener( this, 0, sm->second );
215 //!< delete self from all submeshes
216 void Unset(SMESH_Mesh* mesh)
218 if ( SMESH_subMesh* myMainSubMesh = mesh->GetSubMeshContaining(1) ) {
219 const TDependsOnMap & subMeshes = myMainSubMesh->DependsOn();
220 TDependsOnMap::const_iterator sm;
221 for (sm = subMeshes.begin(); sm != subMeshes.end(); sm++)
222 sm->second->DeleteEventListener( this );
227 } theSearchersDeleter;
229 TCollection_AsciiString mirrorTypeName( SMESH::SMESH_MeshEditor::MirrorType theMirrorType )
231 TCollection_AsciiString typeStr;
232 switch ( theMirrorType ) {
233 case SMESH::SMESH_MeshEditor::POINT:
234 typeStr = "SMESH.SMESH_MeshEditor.POINT";
236 case SMESH::SMESH_MeshEditor::AXIS:
237 typeStr = "SMESH.SMESH_MeshEditor.AXIS";
240 typeStr = "SMESH.SMESH_MeshEditor.PLANE";
244 //================================================================================
246 * \brief function for conversion of long_array to TIDSortedElemSet
247 * \param IDs - array of IDs
248 * \param aMesh - mesh
249 * \param aMap - collection to fill
250 * \param aType - element type
252 //================================================================================
254 void arrayToSet(const SMESH::long_array & IDs,
255 const SMESHDS_Mesh* aMesh,
256 TIDSortedElemSet& aMap,
257 const SMDSAbs_ElementType aType = SMDSAbs_All )
259 for (int i=0; i<IDs.length(); i++) {
260 CORBA::Long ind = IDs[i];
261 const SMDS_MeshElement * elem =
262 (aType == SMDSAbs_Node ? aMesh->FindNode(ind) : aMesh->FindElement(ind));
263 if ( elem && ( aType == SMDSAbs_All || elem->GetType() == aType ))
267 //================================================================================
269 * \brief Retrieve elements of given type from SMESH_IDSource
271 //================================================================================
273 bool idSourceToSet(SMESH::SMESH_IDSource_ptr theIDSource,
274 const SMESHDS_Mesh* theMeshDS,
275 TIDSortedElemSet& theElemSet,
276 const SMDSAbs_ElementType theType,
277 const bool emptyIfIsMesh=false)
280 if ( CORBA::is_nil( theIDSource ) )
282 if ( emptyIfIsMesh && SMESH::DownCast<SMESH_Mesh_i*>( theIDSource ))
285 SMESH::long_array_var anIDs = theIDSource->GetIDs();
286 if ( anIDs->length() == 0 )
288 SMESH::array_of_ElementType_var types = theIDSource->GetTypes();
289 if ( types->length() == 1 && types[0] == SMESH::NODE ) // group of nodes
291 if ( theType == SMDSAbs_All || theType == SMDSAbs_Node )
292 arrayToSet( anIDs, theMeshDS, theElemSet, SMDSAbs_Node );
298 arrayToSet( anIDs, theMeshDS, theElemSet, theType);
299 return bool(anIDs->length()) == bool(theElemSet.size());
303 //================================================================================
305 * \brief Retrieve nodes from SMESH_IDSource
307 //================================================================================
309 void idSourceToNodeSet(SMESH::SMESH_IDSource_ptr theObject,
310 const SMESHDS_Mesh* theMeshDS,
311 TIDSortedNodeSet& theNodeSet)
314 if ( CORBA::is_nil( theObject ) )
316 SMESH::array_of_ElementType_var types = theObject->GetTypes();
317 SMESH::long_array_var aElementsId = theObject->GetIDs();
318 if ( types->length() == 1 && types[0] == SMESH::NODE)
320 for(int i = 0; i < aElementsId->length(); i++)
321 if ( const SMDS_MeshNode * n = theMeshDS->FindNode( aElementsId[i] ))
322 theNodeSet.insert( theNodeSet.end(), n);
324 else if ( SMESH::DownCast<SMESH_Mesh_i*>( theObject ))
326 SMDS_NodeIteratorPtr nIt = theMeshDS->nodesIterator();
327 while ( nIt->more( ))
328 if( const SMDS_MeshElement * elem = nIt->next() )
329 theNodeSet.insert( elem->begin_nodes(), elem->end_nodes());
333 for(int i = 0; i < aElementsId->length(); i++)
334 if( const SMDS_MeshElement * elem = theMeshDS->FindElement( aElementsId[i] ))
335 theNodeSet.insert( elem->begin_nodes(), elem->end_nodes());
339 //================================================================================
341 * \brief Returns elements connected to the given elements
343 //================================================================================
345 void getElementsAround(const TIDSortedElemSet& theElements,
346 const SMESHDS_Mesh* theMeshDS,
347 TIDSortedElemSet& theElementsAround)
349 if ( theElements.empty() ) return;
351 SMDSAbs_ElementType elemType = (*theElements.begin())->GetType();
352 bool sameElemType = ( elemType == (*theElements.rbegin())->GetType() );
354 theMeshDS->GetMeshInfo().NbElements( elemType ) == theElements.size() )
355 return; // all the elements are in theElements
358 elemType = SMDSAbs_All;
360 TIDSortedElemSet visitedNodes;
361 TIDSortedElemSet::const_iterator elemIt = theElements.begin();
362 for ( ; elemIt != theElements.end(); ++elemIt )
364 const SMDS_MeshElement* e = *elemIt;
365 int i = e->NbCornerNodes();
368 const SMDS_MeshNode* n = e->GetNode( i );
369 if ( visitedNodes.insert( n ).second )
371 SMDS_ElemIteratorPtr invIt = n->GetInverseElementIterator(elemType);
372 while ( invIt->more() )
374 const SMDS_MeshElement* elemAround = invIt->next();
375 if ( !theElements.count( elemAround ))
376 theElementsAround.insert( elemAround );
383 //================================================================================
385 * \brief Return a string used to detect change of mesh part on which theElementSearcher
386 * is going to be used
388 //================================================================================
390 string getPartIOR( SMESH::SMESH_IDSource_ptr theMeshPart, SMESH::ElementType type)
392 string partIOR = SMESH_Gen_i::GetORB()->object_to_string( theMeshPart );
393 if ( SMESH_Group_i* group_i = SMESH::DownCast<SMESH_Group_i*>( theMeshPart ))
394 // take into account passible group modification
395 partIOR += SMESH_Comment( ((SMESHDS_Group*)group_i->GetGroupDS())->SMDSGroup().Tic() );
396 partIOR += SMESH_Comment( type );
402 //=============================================================================
406 //=============================================================================
408 SMESH_MeshEditor_i::SMESH_MeshEditor_i(SMESH_Mesh_i* theMesh, bool isPreview):
410 myMesh( &theMesh->GetImpl() ),
412 myPreviewMode ( isPreview )
416 //================================================================================
420 //================================================================================
422 SMESH_MeshEditor_i::~SMESH_MeshEditor_i()
426 //================================================================================
428 * \brief Clear members
430 //================================================================================
432 void SMESH_MeshEditor_i::initData(bool deleteSearchers)
434 if ( myPreviewMode ) {
435 //myPreviewData = new SMESH::MeshPreviewStruct();
438 if ( deleteSearchers )
439 TSearchersDeleter::Delete();
443 //================================================================================
445 * \brief Now does nothing
447 //================================================================================
449 void SMESH_MeshEditor_i::storeResult(::SMESH_MeshEditor& )
453 //================================================================================
455 * Return data of mesh edition preview
457 //================================================================================
459 SMESH::MeshPreviewStruct* SMESH_MeshEditor_i::GetPreviewData()
461 if ( myPreviewMode ) { // --- MeshPreviewStruct filling ---
463 list<int> aNodesConnectivity;
464 typedef map<int, int> TNodesMap;
467 SMESHDS_Mesh* aMeshDS = myEditor.GetMeshDS();
468 int nbEdges = aMeshDS->NbEdges();
469 int nbFaces = aMeshDS->NbFaces();
470 int nbVolum = aMeshDS->NbVolumes();
471 myPreviewData = new SMESH::MeshPreviewStruct();
472 myPreviewData->nodesXYZ.length(aMeshDS->NbNodes());
474 TPreviewMesh * aPreviewMesh = dynamic_cast< TPreviewMesh* >( myEditor.GetMesh() );
475 SMDSAbs_ElementType previewType = SMDSAbs_All;
477 previewType = aPreviewMesh->myPreviewType;
478 switch ( previewType ) {
479 case SMDSAbs_Edge : nbFaces = nbVolum = 0; break;
480 case SMDSAbs_Face : nbEdges = nbVolum = 0; break;
481 case SMDSAbs_Volume: nbEdges = nbFaces = 0; break;
486 myPreviewData->elementTypes.length(nbEdges + nbFaces + nbVolum);
488 SMDS_ElemIteratorPtr itMeshElems = aMeshDS->elementsIterator();
490 while ( itMeshElems->more() ) {
491 const SMDS_MeshElement* aMeshElem = itMeshElems->next();
492 if ( previewType != SMDSAbs_All && aMeshElem->GetType() != previewType )
495 SMDS_ElemIteratorPtr itElemNodes = aMeshElem->nodesIterator();
496 while ( itElemNodes->more() ) {
497 const SMDS_MeshNode* aMeshNode =
498 static_cast<const SMDS_MeshNode*>( itElemNodes->next() );
499 int aNodeID = aMeshNode->GetID();
500 TNodesMap::iterator anIter = nodesMap.find(aNodeID);
501 if ( anIter == nodesMap.end() ) {
502 // filling the nodes coordinates
503 myPreviewData->nodesXYZ[j].x = aMeshNode->X();
504 myPreviewData->nodesXYZ[j].y = aMeshNode->Y();
505 myPreviewData->nodesXYZ[j].z = aMeshNode->Z();
506 anIter = nodesMap.insert( make_pair(aNodeID, j) ).first;
509 aNodesConnectivity.push_back(anIter->second);
512 // filling the elements types
513 SMDSAbs_ElementType aType = aMeshElem->GetType();
514 bool isPoly = aMeshElem->IsPoly();
516 myPreviewData->elementTypes[i].SMDS_ElementType = (SMESH::ElementType) aType;
517 myPreviewData->elementTypes[i].isPoly = isPoly;
518 myPreviewData->elementTypes[i].nbNodesInElement = aMeshElem->NbNodes();
522 myPreviewData->nodesXYZ.length( j );
524 // filling the elements connectivities
525 list<int>::iterator aConnIter = aNodesConnectivity.begin();
526 myPreviewData->elementConnectivities.length(aNodesConnectivity.size());
527 for( int i = 0; aConnIter != aNodesConnectivity.end(); aConnIter++, i++ )
528 myPreviewData->elementConnectivities[i] = *aConnIter;
531 return myPreviewData._retn();
534 //================================================================================
536 * \brief Returns list of it's IDs of created nodes
537 * \retval SMESH::long_array* - list of node ID
539 //================================================================================
541 SMESH::long_array* SMESH_MeshEditor_i::GetLastCreatedNodes()
543 SMESH::long_array_var myLastCreatedNodes = new SMESH::long_array();
544 const SMESH_SequenceOfElemPtr& aSeq = myEditor.GetLastCreatedNodes();
545 myLastCreatedNodes->length( aSeq.Length() );
546 for (int i = 1; i <= aSeq.Length(); i++)
547 myLastCreatedNodes[i-1] = aSeq.Value(i)->GetID();
548 return myLastCreatedNodes._retn();
551 //================================================================================
553 * \brief Returns list of it's IDs of created elements
554 * \retval SMESH::long_array* - list of elements' ID
556 //================================================================================
558 SMESH::long_array* SMESH_MeshEditor_i::GetLastCreatedElems()
560 SMESH::long_array_var myLastCreatedElems = new SMESH::long_array();
561 const SMESH_SequenceOfElemPtr& aSeq = myEditor.GetLastCreatedElems();
562 myLastCreatedElems->length( aSeq.Length() );
563 for ( int i = 1; i <= aSeq.Length(); i++ )
564 myLastCreatedElems[i-1] = aSeq.Value(i)->GetID();
565 return myLastCreatedElems._retn();
568 //=======================================================================
569 //function : MakeIDSource
570 //purpose : Wrap a sequence of ids in a SMESH_IDSource
571 //=======================================================================
573 struct _IDSource : public POA_SMESH::SMESH_IDSource
575 SMESH::long_array _ids;
576 SMESH::ElementType _type;
577 SMESH::SMESH_Mesh_ptr _mesh;
578 SMESH::long_array* GetIDs() { return new SMESH::long_array( _ids ); }
579 SMESH::long_array* GetMeshInfo() { return 0; }
580 SMESH::SMESH_Mesh_ptr GetMesh() { return SMESH::SMESH_Mesh::_duplicate( _mesh ); }
581 bool IsMeshInfoCorrect() { return true; }
582 SMESH::array_of_ElementType* GetTypes()
584 SMESH::array_of_ElementType_var types = new SMESH::array_of_ElementType;
585 if ( _ids.length() > 0 ) {
589 return types._retn();
593 SMESH::SMESH_IDSource_ptr SMESH_MeshEditor_i::MakeIDSource(const SMESH::long_array& ids,
594 SMESH::ElementType type)
596 _IDSource* anIDSource = new _IDSource;
597 anIDSource->_ids = ids;
598 anIDSource->_type = type;
599 anIDSource->_mesh = myMesh_i->_this();
600 SMESH::SMESH_IDSource_var anIDSourceVar = anIDSource->_this();
602 return anIDSourceVar._retn();
605 //=============================================================================
609 //=============================================================================
612 SMESH_MeshEditor_i::RemoveElements(const SMESH::long_array & IDsOfElements)
618 for (int i = 0; i < IDsOfElements.length(); i++)
619 IdList.push_back( IDsOfElements[i] );
621 // Update Python script
622 TPythonDump() << "isDone = " << this << ".RemoveElements( " << IDsOfElements << " )";
625 bool ret = myEditor.Remove( IdList, false );
626 myMesh->GetMeshDS()->Modified();
627 if ( IDsOfElements.length() )
628 myMesh->SetIsModified( true ); // issue 0020693
632 //=============================================================================
636 //=============================================================================
638 CORBA::Boolean SMESH_MeshEditor_i::RemoveNodes(const SMESH::long_array & IDsOfNodes)
643 for (int i = 0; i < IDsOfNodes.length(); i++)
644 IdList.push_back( IDsOfNodes[i] );
646 // Update Python script
647 TPythonDump() << "isDone = " << this << ".RemoveNodes( " << IDsOfNodes << " )";
649 bool ret = myEditor.Remove( IdList, true );
650 myMesh->GetMeshDS()->Modified();
651 if ( IDsOfNodes.length() )
652 myMesh->SetIsModified( true ); // issue 0020693
656 //=============================================================================
660 //=============================================================================
662 CORBA::Long SMESH_MeshEditor_i::RemoveOrphanNodes()
667 // Update Python script
668 TPythonDump() << "nbRemoved = " << this << ".RemoveOrphanNodes()";
670 // Create filter to find all orphan nodes
671 SMESH::Controls::Filter::TIdSequence seq;
672 SMESH::Controls::PredicatePtr predicate( new SMESH::Controls::FreeNodes() );
673 SMESH::Controls::Filter::GetElementsId( GetMeshDS(), predicate, seq );
675 // remove orphan nodes (if there are any)
677 for ( int i = 0; i < seq.size(); i++ )
678 IdList.push_back( seq[i] );
680 int nbNodesBefore = myMesh->NbNodes();
681 myEditor.Remove( IdList, true );
682 myMesh->GetMeshDS()->Modified();
684 myMesh->SetIsModified( true );
685 int nbNodesAfter = myMesh->NbNodes();
687 return nbNodesBefore - nbNodesAfter;
690 //=============================================================================
694 //=============================================================================
696 CORBA::Long SMESH_MeshEditor_i::AddNode(CORBA::Double x,
697 CORBA::Double y, CORBA::Double z)
701 const SMDS_MeshNode* N = GetMeshDS()->AddNode(x, y, z);
703 // Update Python script
704 TPythonDump() << "nodeID = " << this << ".AddNode( "
705 << TVar( x ) << ", " << TVar( y ) << ", " << TVar( z )<< " )";
707 myMesh->GetMeshDS()->Modified();
708 myMesh->SetIsModified( true ); // issue 0020693
712 //=============================================================================
714 * Create 0D element on the given node.
716 //=============================================================================
718 CORBA::Long SMESH_MeshEditor_i::Add0DElement(CORBA::Long IDOfNode)
722 const SMDS_MeshNode* aNode = GetMeshDS()->FindNode(IDOfNode);
723 SMDS_MeshElement* elem = GetMeshDS()->Add0DElement(aNode);
725 // Update Python script
726 TPythonDump() << "elem0d = " << this << ".Add0DElement( " << IDOfNode <<" )";
728 myMesh->GetMeshDS()->Modified();
729 myMesh->SetIsModified( true ); // issue 0020693
732 return elem->GetID();
737 //=============================================================================
739 * Create a ball element on the given node.
741 //=============================================================================
743 CORBA::Long SMESH_MeshEditor_i::AddBall(CORBA::Long IDOfNode, CORBA::Double diameter)
744 throw (SALOME::SALOME_Exception)
748 if ( diameter < std::numeric_limits<double>::min() )
749 THROW_SALOME_CORBA_EXCEPTION("Invalid diameter", SALOME::BAD_PARAM);
751 const SMDS_MeshNode* aNode = GetMeshDS()->FindNode(IDOfNode);
752 SMDS_MeshElement* elem = GetMeshDS()->AddBall(aNode, diameter);
754 // Update Python script
755 TPythonDump() << "ballElem = "
756 << this << ".AddBall( " << IDOfNode << ", " << diameter <<" )";
758 myMesh->GetMeshDS()->Modified();
759 myMesh->SetIsModified( true ); // issue 0020693
762 return elem->GetID();
767 //=============================================================================
769 * Create an edge, either linear and quadratic (this is determed
770 * by number of given nodes, two or three)
772 //=============================================================================
774 CORBA::Long SMESH_MeshEditor_i::AddEdge(const SMESH::long_array & IDsOfNodes)
778 int NbNodes = IDsOfNodes.length();
779 SMDS_MeshElement* elem = 0;
782 CORBA::Long index1 = IDsOfNodes[0];
783 CORBA::Long index2 = IDsOfNodes[1];
784 elem = GetMeshDS()->AddEdge(GetMeshDS()->FindNode(index1), GetMeshDS()->FindNode(index2));
786 // Update Python script
787 TPythonDump() << "edge = " << this << ".AddEdge([ "
788 << index1 << ", " << index2 <<" ])";
791 CORBA::Long n1 = IDsOfNodes[0];
792 CORBA::Long n2 = IDsOfNodes[1];
793 CORBA::Long n12 = IDsOfNodes[2];
794 elem = GetMeshDS()->AddEdge(GetMeshDS()->FindNode(n1),
795 GetMeshDS()->FindNode(n2),
796 GetMeshDS()->FindNode(n12));
797 // Update Python script
798 TPythonDump() << "edgeID = " << this << ".AddEdge([ "
799 <<n1<<", "<<n2<<", "<<n12<<" ])";
802 myMesh->GetMeshDS()->Modified();
804 return myMesh->SetIsModified( true ), elem->GetID();
809 //=============================================================================
813 //=============================================================================
815 CORBA::Long SMESH_MeshEditor_i::AddFace(const SMESH::long_array & IDsOfNodes)
819 int NbNodes = IDsOfNodes.length();
825 std::vector<const SMDS_MeshNode*> nodes (NbNodes);
826 for (int i = 0; i < NbNodes; i++)
827 nodes[i] = GetMeshDS()->FindNode(IDsOfNodes[i]);
829 SMDS_MeshElement* elem = 0;
831 elem = GetMeshDS()->AddFace(nodes[0], nodes[1], nodes[2]);
833 else if (NbNodes == 4) {
834 elem = GetMeshDS()->AddFace(nodes[0], nodes[1], nodes[2], nodes[3]);
836 else if (NbNodes == 6) {
837 elem = GetMeshDS()->AddFace(nodes[0], nodes[1], nodes[2], nodes[3],
840 else if (NbNodes == 8) {
841 elem = GetMeshDS()->AddFace(nodes[0], nodes[1], nodes[2], nodes[3],
842 nodes[4], nodes[5], nodes[6], nodes[7]);
844 else if (NbNodes == 9) {
845 elem = GetMeshDS()->AddFace(nodes[0], nodes[1], nodes[2], nodes[3],
846 nodes[4], nodes[5], nodes[6], nodes[7], nodes[8] );
848 else if (NbNodes > 2) {
849 elem = GetMeshDS()->AddPolygonalFace(nodes);
852 // Update Python script
853 TPythonDump() << "faceID = " << this << ".AddFace( " << IDsOfNodes << " )";
855 myMesh->GetMeshDS()->Modified();
857 return myMesh->SetIsModified( true ), elem->GetID();
862 //=============================================================================
866 //=============================================================================
867 CORBA::Long SMESH_MeshEditor_i::AddPolygonalFace (const SMESH::long_array & IDsOfNodes)
871 int NbNodes = IDsOfNodes.length();
872 std::vector<const SMDS_MeshNode*> nodes (NbNodes);
873 for (int i = 0; i < NbNodes; i++)
874 nodes[i] = GetMeshDS()->FindNode(IDsOfNodes[i]);
876 const SMDS_MeshElement* elem = GetMeshDS()->AddPolygonalFace(nodes);
878 // Update Python script
879 TPythonDump() <<"faceID = "<<this<<".AddPolygonalFace( "<<IDsOfNodes<<" )";
881 myMesh->GetMeshDS()->Modified();
882 return elem ? ( myMesh->SetIsModified( true ), elem->GetID()) : 0;
885 //=============================================================================
887 * Create volume, either linear and quadratic (this is determed
888 * by number of given nodes)
890 //=============================================================================
892 CORBA::Long SMESH_MeshEditor_i::AddVolume(const SMESH::long_array & IDsOfNodes)
896 int NbNodes = IDsOfNodes.length();
897 vector< const SMDS_MeshNode*> n(NbNodes);
898 for(int i=0;i<NbNodes;i++)
899 n[i]=GetMeshDS()->FindNode(IDsOfNodes[i]);
901 SMDS_MeshElement* elem = 0;
904 case 4 :elem = GetMeshDS()->AddVolume(n[0],n[1],n[2],n[3]); break;
905 case 5 :elem = GetMeshDS()->AddVolume(n[0],n[1],n[2],n[3],n[4]); break;
906 case 6 :elem = GetMeshDS()->AddVolume(n[0],n[1],n[2],n[3],n[4],n[5]); break;
907 case 8 :elem = GetMeshDS()->AddVolume(n[0],n[1],n[2],n[3],n[4],n[5],n[6],n[7]); break;
908 case 10:elem = GetMeshDS()->AddVolume(n[0],n[1],n[2],n[3],n[4],n[5],
909 n[6],n[7],n[8],n[9]);
911 case 12:elem = GetMeshDS()->AddVolume(n[0],n[1],n[2],n[3],n[4],n[5],
912 n[6],n[7],n[8],n[9],n[10],n[11]);
914 case 13:elem = GetMeshDS()->AddVolume(n[0],n[1],n[2],n[3],n[4],n[5],n[6],
915 n[7],n[8],n[9],n[10],n[11],n[12]);
917 case 15:elem = GetMeshDS()->AddVolume(n[0],n[1],n[2],n[3],n[4],n[5],n[6],n[7],n[8],
918 n[9],n[10],n[11],n[12],n[13],n[14]);
920 case 20:elem = GetMeshDS()->AddVolume(n[0],n[1],n[2],n[3],n[4],n[5],n[6],n[7],
921 n[8],n[9],n[10],n[11],n[12],n[13],n[14],
922 n[15],n[16],n[17],n[18],n[19]);
924 case 27:elem = GetMeshDS()->AddVolume(n[0],n[1],n[2],n[3],n[4],n[5],n[6],n[7],
925 n[8],n[9],n[10],n[11],n[12],n[13],n[14],
926 n[15],n[16],n[17],n[18],n[19],
927 n[20],n[21],n[22],n[23],n[24],n[25],n[26]);
931 // Update Python script
932 TPythonDump() << "volID = " << this << ".AddVolume( " << IDsOfNodes << " )";
934 myMesh->GetMeshDS()->Modified();
936 return myMesh->SetIsModified( true ), elem->GetID();
941 //=============================================================================
943 * AddPolyhedralVolume
945 //=============================================================================
946 CORBA::Long SMESH_MeshEditor_i::AddPolyhedralVolume (const SMESH::long_array & IDsOfNodes,
947 const SMESH::long_array & Quantities)
951 int NbNodes = IDsOfNodes.length();
952 std::vector<const SMDS_MeshNode*> n (NbNodes);
953 for (int i = 0; i < NbNodes; i++)
955 const SMDS_MeshNode* aNode = GetMeshDS()->FindNode(IDsOfNodes[i]);
956 if (!aNode) return 0;
960 int NbFaces = Quantities.length();
961 std::vector<int> q (NbFaces);
962 for (int j = 0; j < NbFaces; j++)
963 q[j] = Quantities[j];
965 const SMDS_MeshElement* elem = GetMeshDS()->AddPolyhedralVolume(n, q);
967 // Update Python script
968 TPythonDump() << "volID = " << this << ".AddPolyhedralVolume( "
969 << IDsOfNodes << ", " << Quantities << " )";
970 myMesh->GetMeshDS()->Modified();
972 return elem ? ( myMesh->SetIsModified( true ), elem->GetID()) : 0;
975 //=============================================================================
977 * AddPolyhedralVolumeByFaces
979 //=============================================================================
980 CORBA::Long SMESH_MeshEditor_i::AddPolyhedralVolumeByFaces (const SMESH::long_array & IdsOfFaces)
984 int NbFaces = IdsOfFaces.length();
985 std::vector<const SMDS_MeshNode*> poly_nodes;
986 std::vector<int> quantities (NbFaces);
988 for (int i = 0; i < NbFaces; i++) {
989 const SMDS_MeshElement* aFace = GetMeshDS()->FindElement(IdsOfFaces[i]);
990 quantities[i] = aFace->NbNodes();
992 SMDS_ElemIteratorPtr It = aFace->nodesIterator();
994 poly_nodes.push_back(static_cast<const SMDS_MeshNode *>(It->next()));
998 const SMDS_MeshElement* elem = GetMeshDS()->AddPolyhedralVolume(poly_nodes, quantities);
1000 // Update Python script
1001 TPythonDump() << "volID = " << this << ".AddPolyhedralVolumeByFaces( "
1002 << IdsOfFaces << " )";
1003 myMesh->GetMeshDS()->Modified();
1005 return elem ? ( myMesh->SetIsModified( true ), elem->GetID()) : 0;
1008 //=============================================================================
1010 * \brief Bind a node to a vertex
1011 * \param NodeID - node ID
1012 * \param VertexID - vertex ID available through GEOM_Object.GetSubShapeIndices()[0]
1013 * \retval boolean - false if NodeID or VertexID is invalid
1015 //=============================================================================
1017 void SMESH_MeshEditor_i::SetNodeOnVertex(CORBA::Long NodeID, CORBA::Long VertexID)
1018 throw (SALOME::SALOME_Exception)
1020 Unexpect aCatch(SALOME_SalomeException);
1022 SMESHDS_Mesh * mesh = GetMeshDS();
1023 SMDS_MeshNode* node = const_cast<SMDS_MeshNode*>( mesh->FindNode(NodeID) );
1025 THROW_SALOME_CORBA_EXCEPTION("Invalid NodeID", SALOME::BAD_PARAM);
1027 if ( mesh->MaxShapeIndex() < VertexID )
1028 THROW_SALOME_CORBA_EXCEPTION("Invalid VertexID", SALOME::BAD_PARAM);
1030 TopoDS_Shape shape = mesh->IndexToShape( VertexID );
1031 if ( shape.ShapeType() != TopAbs_VERTEX )
1032 THROW_SALOME_CORBA_EXCEPTION("Invalid VertexID", SALOME::BAD_PARAM);
1034 mesh->SetNodeOnVertex( node, VertexID );
1036 myMesh->SetIsModified( true );
1039 //=============================================================================
1041 * \brief Store node position on an edge
1042 * \param NodeID - node ID
1043 * \param EdgeID - edge ID available through GEOM_Object.GetSubShapeIndices()[0]
1044 * \param paramOnEdge - parameter on edge where the node is located
1045 * \retval boolean - false if any parameter is invalid
1047 //=============================================================================
1049 void SMESH_MeshEditor_i::SetNodeOnEdge(CORBA::Long NodeID, CORBA::Long EdgeID,
1050 CORBA::Double paramOnEdge)
1051 throw (SALOME::SALOME_Exception)
1053 Unexpect aCatch(SALOME_SalomeException);
1055 SMESHDS_Mesh * mesh = GetMeshDS();
1056 SMDS_MeshNode* node = const_cast<SMDS_MeshNode*>( mesh->FindNode(NodeID) );
1058 THROW_SALOME_CORBA_EXCEPTION("Invalid NodeID", SALOME::BAD_PARAM);
1060 if ( mesh->MaxShapeIndex() < EdgeID )
1061 THROW_SALOME_CORBA_EXCEPTION("Invalid EdgeID", SALOME::BAD_PARAM);
1063 TopoDS_Shape shape = mesh->IndexToShape( EdgeID );
1064 if ( shape.ShapeType() != TopAbs_EDGE )
1065 THROW_SALOME_CORBA_EXCEPTION("Invalid EdgeID", SALOME::BAD_PARAM);
1068 BRep_Tool::Range( TopoDS::Edge( shape ), f,l);
1069 if ( paramOnEdge < f || paramOnEdge > l )
1070 THROW_SALOME_CORBA_EXCEPTION("Invalid paramOnEdge", SALOME::BAD_PARAM);
1072 mesh->SetNodeOnEdge( node, EdgeID, paramOnEdge );
1074 myMesh->SetIsModified( true );
1077 //=============================================================================
1079 * \brief Store node position on a face
1080 * \param NodeID - node ID
1081 * \param FaceID - face ID available through GEOM_Object.GetSubShapeIndices()[0]
1082 * \param u - U parameter on face where the node is located
1083 * \param v - V parameter on face where the node is located
1084 * \retval boolean - false if any parameter is invalid
1086 //=============================================================================
1088 void SMESH_MeshEditor_i::SetNodeOnFace(CORBA::Long NodeID, CORBA::Long FaceID,
1089 CORBA::Double u, CORBA::Double v)
1090 throw (SALOME::SALOME_Exception)
1092 Unexpect aCatch(SALOME_SalomeException);
1094 SMESHDS_Mesh * mesh = GetMeshDS();
1095 SMDS_MeshNode* node = const_cast<SMDS_MeshNode*>( mesh->FindNode(NodeID) );
1097 THROW_SALOME_CORBA_EXCEPTION("Invalid NodeID", SALOME::BAD_PARAM);
1099 if ( mesh->MaxShapeIndex() < FaceID )
1100 THROW_SALOME_CORBA_EXCEPTION("Invalid FaceID", SALOME::BAD_PARAM);
1102 TopoDS_Shape shape = mesh->IndexToShape( FaceID );
1103 if ( shape.ShapeType() != TopAbs_FACE )
1104 THROW_SALOME_CORBA_EXCEPTION("Invalid FaceID", SALOME::BAD_PARAM);
1106 BRepAdaptor_Surface surf( TopoDS::Face( shape ));
1107 bool isOut = ( u < surf.FirstUParameter() ||
1108 u > surf.LastUParameter() ||
1109 v < surf.FirstVParameter() ||
1110 v > surf.LastVParameter() );
1114 MESSAGE ( "FACE " << FaceID << " (" << u << "," << v << ") out of "
1115 << " u( " << surf.FirstUParameter()
1116 << "," << surf.LastUParameter()
1117 << ") v( " << surf.FirstVParameter()
1118 << "," << surf.LastVParameter() << ")" );
1120 THROW_SALOME_CORBA_EXCEPTION("Invalid UV", SALOME::BAD_PARAM);
1123 mesh->SetNodeOnFace( node, FaceID, u, v );
1124 myMesh->SetIsModified( true );
1127 //=============================================================================
1129 * \brief Bind a node to a solid
1130 * \param NodeID - node ID
1131 * \param SolidID - vertex ID available through GEOM_Object.GetSubShapeIndices()[0]
1132 * \retval boolean - false if NodeID or SolidID is invalid
1134 //=============================================================================
1136 void SMESH_MeshEditor_i::SetNodeInVolume(CORBA::Long NodeID, CORBA::Long SolidID)
1137 throw (SALOME::SALOME_Exception)
1139 Unexpect aCatch(SALOME_SalomeException);
1141 SMESHDS_Mesh * mesh = GetMeshDS();
1142 SMDS_MeshNode* node = const_cast<SMDS_MeshNode*>( mesh->FindNode(NodeID) );
1144 THROW_SALOME_CORBA_EXCEPTION("Invalid NodeID", SALOME::BAD_PARAM);
1146 if ( mesh->MaxShapeIndex() < SolidID )
1147 THROW_SALOME_CORBA_EXCEPTION("Invalid SolidID", SALOME::BAD_PARAM);
1149 TopoDS_Shape shape = mesh->IndexToShape( SolidID );
1150 if ( shape.ShapeType() != TopAbs_SOLID &&
1151 shape.ShapeType() != TopAbs_SHELL)
1152 THROW_SALOME_CORBA_EXCEPTION("Invalid SolidID", SALOME::BAD_PARAM);
1154 mesh->SetNodeInVolume( node, SolidID );
1156 // myMesh->SetIsModified( true ); - SetNodeInVolume() can't prevent re-compute, I believe
1159 //=============================================================================
1161 * \brief Bind an element to a shape
1162 * \param ElementID - element ID
1163 * \param ShapeID - shape ID available through GEOM_Object.GetSubShapeIndices()[0]
1164 * \retval boolean - false if ElementID or ShapeID is invalid
1166 //=============================================================================
1168 void SMESH_MeshEditor_i::SetMeshElementOnShape(CORBA::Long ElementID,
1169 CORBA::Long ShapeID)
1170 throw (SALOME::SALOME_Exception)
1172 Unexpect aCatch(SALOME_SalomeException);
1174 SMESHDS_Mesh * mesh = GetMeshDS();
1175 SMDS_MeshElement* elem = const_cast<SMDS_MeshElement*>(mesh->FindElement(ElementID));
1177 THROW_SALOME_CORBA_EXCEPTION("Invalid ElementID", SALOME::BAD_PARAM);
1179 if ( mesh->MaxShapeIndex() < ShapeID )
1180 THROW_SALOME_CORBA_EXCEPTION("Invalid ShapeID", SALOME::BAD_PARAM);
1182 TopoDS_Shape shape = mesh->IndexToShape( ShapeID );
1183 if ( shape.ShapeType() != TopAbs_EDGE &&
1184 shape.ShapeType() != TopAbs_FACE &&
1185 shape.ShapeType() != TopAbs_SOLID &&
1186 shape.ShapeType() != TopAbs_SHELL )
1187 THROW_SALOME_CORBA_EXCEPTION("Invalid shape type", SALOME::BAD_PARAM);
1189 mesh->SetMeshElementOnShape( elem, ShapeID );
1191 myMesh->SetIsModified( true );
1194 //=============================================================================
1198 //=============================================================================
1200 CORBA::Boolean SMESH_MeshEditor_i::InverseDiag(CORBA::Long NodeID1,
1201 CORBA::Long NodeID2)
1205 const SMDS_MeshNode * n1 = GetMeshDS()->FindNode( NodeID1 );
1206 const SMDS_MeshNode * n2 = GetMeshDS()->FindNode( NodeID2 );
1210 // Update Python script
1211 TPythonDump() << "isDone = " << this << ".InverseDiag( "
1212 << NodeID1 << ", " << NodeID2 << " )";
1215 int ret = myEditor.InverseDiag ( n1, n2 );
1216 myMesh->GetMeshDS()->Modified();
1217 myMesh->SetIsModified( true );
1221 //=============================================================================
1225 //=============================================================================
1227 CORBA::Boolean SMESH_MeshEditor_i::DeleteDiag(CORBA::Long NodeID1,
1228 CORBA::Long NodeID2)
1232 const SMDS_MeshNode * n1 = GetMeshDS()->FindNode( NodeID1 );
1233 const SMDS_MeshNode * n2 = GetMeshDS()->FindNode( NodeID2 );
1237 // Update Python script
1238 TPythonDump() << "isDone = " << this << ".DeleteDiag( "
1239 << NodeID1 << ", " << NodeID2 << " )";
1242 bool stat = myEditor.DeleteDiag ( n1, n2 );
1244 myMesh->GetMeshDS()->Modified();
1246 myMesh->SetIsModified( true ); // issue 0020693
1248 storeResult(myEditor);
1253 //=============================================================================
1257 //=============================================================================
1259 CORBA::Boolean SMESH_MeshEditor_i::Reorient(const SMESH::long_array & IDsOfElements)
1263 for (int i = 0; i < IDsOfElements.length(); i++)
1265 CORBA::Long index = IDsOfElements[i];
1266 const SMDS_MeshElement * elem = GetMeshDS()->FindElement(index);
1268 myEditor.Reorient( elem );
1270 // Update Python script
1271 TPythonDump() << "isDone = " << this << ".Reorient( " << IDsOfElements << " )";
1273 myMesh->GetMeshDS()->Modified();
1274 if ( IDsOfElements.length() )
1275 myMesh->SetIsModified( true ); // issue 0020693
1281 //=============================================================================
1285 //=============================================================================
1287 CORBA::Boolean SMESH_MeshEditor_i::ReorientObject(SMESH::SMESH_IDSource_ptr theObject)
1291 TPythonDump aTPythonDump; // suppress dump in Reorient()
1293 SMESH::long_array_var anElementsId = theObject->GetIDs();
1294 CORBA::Boolean isDone = Reorient(anElementsId);
1296 // Update Python script
1297 aTPythonDump << "isDone = " << this << ".ReorientObject( " << theObject << " )";
1302 //=======================================================================
1303 //function : Reorient2D
1304 //purpose : Reorient faces contained in \a the2Dgroup.
1305 // the2Dgroup - the mesh or its part to reorient
1306 // theDirection - desired direction of normal of \a theFace
1307 // theFace - ID of face whose orientation is checked.
1308 // It can be < 1 then \a thePoint is used to find a face.
1309 // thePoint - is used to find a face if \a theFace < 1.
1310 // return number of reoriented elements.
1311 //=======================================================================
1313 CORBA::Long SMESH_MeshEditor_i::Reorient2D(SMESH::SMESH_IDSource_ptr the2Dgroup,
1314 const SMESH::DirStruct& theDirection,
1315 CORBA::Long theFace,
1316 const SMESH::PointStruct& thePoint)
1317 throw (SALOME::SALOME_Exception)
1319 Unexpect aCatch(SALOME_SalomeException);
1321 initData(/*deleteSearchers=*/false);
1323 TIDSortedElemSet elements;
1324 if ( !idSourceToSet( the2Dgroup, GetMeshDS(), elements, SMDSAbs_Face, /*emptyIfIsMesh=*/1))
1325 THROW_SALOME_CORBA_EXCEPTION("No faces in given group", SALOME::BAD_PARAM);
1328 const SMDS_MeshElement* face = 0;
1331 face = GetMeshDS()->FindElement( theFace );
1333 THROW_SALOME_CORBA_EXCEPTION("Inexistent face given", SALOME::BAD_PARAM);
1334 if ( face->GetType() != SMDSAbs_Face )
1335 THROW_SALOME_CORBA_EXCEPTION("Wrong element type", SALOME::BAD_PARAM);
1339 // create theElementSearcher if needed
1340 theSearchersDeleter.Set( myMesh, getPartIOR( the2Dgroup, SMESH::FACE ));
1341 if ( !theElementSearcher )
1343 if ( elements.empty() ) // search in the whole mesh
1345 if ( myMesh->NbFaces() == 0 )
1346 THROW_SALOME_CORBA_EXCEPTION("No faces in the mesh", SALOME::BAD_PARAM);
1348 theElementSearcher = myEditor.GetElementSearcher();
1352 typedef SMDS_SetIterator<const SMDS_MeshElement*, TIDSortedElemSet::const_iterator > TIter;
1353 SMDS_ElemIteratorPtr elemsIt( new TIter( elements.begin(), elements.end() ));
1355 theElementSearcher = myEditor.GetElementSearcher(elemsIt);
1359 gp_Pnt p( thePoint.x, thePoint.y, thePoint.z );
1360 face = theElementSearcher->FindClosestTo( p, SMDSAbs_Face );
1363 THROW_SALOME_CORBA_EXCEPTION("No face found by point", SALOME::INTERNAL_ERROR );
1364 if ( !elements.empty() && !elements.count( face ))
1365 THROW_SALOME_CORBA_EXCEPTION("Found face is not in the group", SALOME::BAD_PARAM );
1368 const SMESH::PointStruct * P = &theDirection.PS;
1369 gp_Vec dirVec( P->x, P->y, P->z );
1370 if ( dirVec.Magnitude() < std::numeric_limits< double >::min() )
1371 THROW_SALOME_CORBA_EXCEPTION("Zero size vector", SALOME::BAD_PARAM);
1373 int nbReori = myEditor.Reorient2D( elements, dirVec, face );
1374 storeResult(myEditor);
1377 myMesh->SetIsModified( true );
1378 myMesh->GetMeshDS()->Modified();
1380 TPythonDump() << this << ".Reorient2D( "
1381 << the2Dgroup << ", "
1382 << theDirection << ", "
1384 << thePoint << " )";
1389 //=============================================================================
1393 //=============================================================================
1394 CORBA::Boolean SMESH_MeshEditor_i::TriToQuad (const SMESH::long_array & IDsOfElements,
1395 SMESH::NumericalFunctor_ptr Criterion,
1396 CORBA::Double MaxAngle)
1400 SMESHDS_Mesh* aMesh = GetMeshDS();
1401 TIDSortedElemSet faces;
1402 arrayToSet(IDsOfElements, aMesh, faces, SMDSAbs_Face);
1404 SMESH::NumericalFunctor_i* aNumericalFunctor =
1405 dynamic_cast<SMESH::NumericalFunctor_i*>( SMESH_Gen_i::GetServant( Criterion ).in() );
1406 SMESH::Controls::NumericalFunctorPtr aCrit;
1407 if ( !aNumericalFunctor )
1408 aCrit.reset( new SMESH::Controls::AspectRatio() );
1410 aCrit = aNumericalFunctor->GetNumericalFunctor();
1412 // Update Python script
1413 TPythonDump() << "isDone = " << this << ".TriToQuad( "
1414 << IDsOfElements << ", " << aNumericalFunctor << ", " << TVar( MaxAngle ) << " )";
1417 bool stat = myEditor.TriToQuad( faces, aCrit, MaxAngle );
1418 myMesh->GetMeshDS()->Modified();
1420 myMesh->SetIsModified( true ); // issue 0020693
1422 storeResult(myEditor);
1428 //=============================================================================
1432 //=============================================================================
1433 CORBA::Boolean SMESH_MeshEditor_i::TriToQuadObject (SMESH::SMESH_IDSource_ptr theObject,
1434 SMESH::NumericalFunctor_ptr Criterion,
1435 CORBA::Double MaxAngle)
1439 TPythonDump aTPythonDump; // suppress dump in TriToQuad()
1440 SMESH::long_array_var anElementsId = theObject->GetIDs();
1441 CORBA::Boolean isDone = TriToQuad(anElementsId, Criterion, MaxAngle);
1443 SMESH::NumericalFunctor_i* aNumericalFunctor =
1444 SMESH::DownCast<SMESH::NumericalFunctor_i*>( Criterion );
1446 // Update Python script
1447 aTPythonDump << "isDone = " << this << ".TriToQuadObject("
1448 << theObject << ", " << aNumericalFunctor << ", " << TVar( MaxAngle ) << " )";
1454 //=============================================================================
1458 //=============================================================================
1459 CORBA::Boolean SMESH_MeshEditor_i::QuadToTri (const SMESH::long_array & IDsOfElements,
1460 SMESH::NumericalFunctor_ptr Criterion)
1464 SMESHDS_Mesh* aMesh = GetMeshDS();
1465 TIDSortedElemSet faces;
1466 arrayToSet(IDsOfElements, aMesh, faces, SMDSAbs_Face);
1468 SMESH::NumericalFunctor_i* aNumericalFunctor =
1469 dynamic_cast<SMESH::NumericalFunctor_i*>( SMESH_Gen_i::GetServant( Criterion ).in() );
1470 SMESH::Controls::NumericalFunctorPtr aCrit;
1471 if ( !aNumericalFunctor )
1472 aCrit.reset( new SMESH::Controls::AspectRatio() );
1474 aCrit = aNumericalFunctor->GetNumericalFunctor();
1477 // Update Python script
1478 TPythonDump() << "isDone = " << this << ".QuadToTri( " << IDsOfElements << ", " << aNumericalFunctor << " )";
1480 CORBA::Boolean stat = myEditor.QuadToTri( faces, aCrit );
1481 myMesh->GetMeshDS()->Modified();
1483 myMesh->SetIsModified( true ); // issue 0020693
1485 storeResult(myEditor);
1491 //=============================================================================
1495 //=============================================================================
1496 CORBA::Boolean SMESH_MeshEditor_i::QuadToTriObject (SMESH::SMESH_IDSource_ptr theObject,
1497 SMESH::NumericalFunctor_ptr Criterion)
1501 TPythonDump aTPythonDump; // suppress dump in QuadToTri()
1503 SMESH::long_array_var anElementsId = theObject->GetIDs();
1504 CORBA::Boolean isDone = QuadToTri(anElementsId, Criterion);
1506 SMESH::NumericalFunctor_i* aNumericalFunctor =
1507 SMESH::DownCast<SMESH::NumericalFunctor_i*>( Criterion );
1509 // Update Python script
1510 aTPythonDump << "isDone = " << this << ".QuadToTriObject( " << theObject << ", " << aNumericalFunctor << " )";
1516 //=============================================================================
1520 //=============================================================================
1521 CORBA::Boolean SMESH_MeshEditor_i::SplitQuad (const SMESH::long_array & IDsOfElements,
1522 CORBA::Boolean Diag13)
1526 SMESHDS_Mesh* aMesh = GetMeshDS();
1527 TIDSortedElemSet faces;
1528 arrayToSet(IDsOfElements, aMesh, faces, SMDSAbs_Face);
1530 // Update Python script
1531 TPythonDump() << "isDone = " << this << ".SplitQuad( "
1532 << IDsOfElements << ", " << Diag13 << " )";
1534 CORBA::Boolean stat = myEditor.QuadToTri( faces, Diag13 );
1535 myMesh->GetMeshDS()->Modified();
1537 myMesh->SetIsModified( true ); // issue 0020693
1540 storeResult(myEditor);
1546 //=============================================================================
1550 //=============================================================================
1551 CORBA::Boolean SMESH_MeshEditor_i::SplitQuadObject (SMESH::SMESH_IDSource_ptr theObject,
1552 CORBA::Boolean Diag13)
1556 TPythonDump aTPythonDump; // suppress dump in SplitQuad()
1558 SMESH::long_array_var anElementsId = theObject->GetIDs();
1559 CORBA::Boolean isDone = SplitQuad(anElementsId, Diag13);
1561 // Update Python script
1562 aTPythonDump << "isDone = " << this << ".SplitQuadObject( "
1563 << theObject << ", " << Diag13 << " )";
1569 //=============================================================================
1573 //=============================================================================
1574 CORBA::Long SMESH_MeshEditor_i::BestSplit (CORBA::Long IDOfQuad,
1575 SMESH::NumericalFunctor_ptr Criterion)
1579 const SMDS_MeshElement* quad = GetMeshDS()->FindElement(IDOfQuad);
1580 if (quad && quad->GetType() == SMDSAbs_Face && quad->NbNodes() == 4)
1582 SMESH::NumericalFunctor_i* aNumericalFunctor =
1583 dynamic_cast<SMESH::NumericalFunctor_i*>(SMESH_Gen_i::GetServant(Criterion).in());
1584 SMESH::Controls::NumericalFunctorPtr aCrit;
1585 if (aNumericalFunctor)
1586 aCrit = aNumericalFunctor->GetNumericalFunctor();
1588 aCrit.reset(new SMESH::Controls::AspectRatio());
1590 return myEditor.BestSplit(quad, aCrit);
1595 //================================================================================
1597 * \brief Split volumic elements into tetrahedrons
1599 //================================================================================
1601 void SMESH_MeshEditor_i::SplitVolumesIntoTetra (SMESH::SMESH_IDSource_ptr elems,
1602 CORBA::Short methodFlags)
1603 throw (SALOME::SALOME_Exception)
1605 Unexpect aCatch(SALOME_SalomeException);
1609 SMESH::long_array_var anElementsId = elems->GetIDs();
1610 TIDSortedElemSet elemSet;
1611 arrayToSet( anElementsId, GetMeshDS(), elemSet, SMDSAbs_Volume );
1613 myEditor.SplitVolumesIntoTetra( elemSet, int( methodFlags ));
1614 myMesh->GetMeshDS()->Modified();
1616 storeResult(myEditor);
1618 // if ( myLastCreatedElems.length() ) - it does not influence Compute()
1619 // myMesh->SetIsModified( true ); // issue 0020693
1621 TPythonDump() << this << ".SplitVolumesIntoTetra( "
1622 << elems << ", " << methodFlags << " )";
1625 //=======================================================================
1628 //=======================================================================
1631 SMESH_MeshEditor_i::Smooth(const SMESH::long_array & IDsOfElements,
1632 const SMESH::long_array & IDsOfFixedNodes,
1633 CORBA::Long MaxNbOfIterations,
1634 CORBA::Double MaxAspectRatio,
1635 SMESH::SMESH_MeshEditor::Smooth_Method Method)
1637 return smooth( IDsOfElements, IDsOfFixedNodes, MaxNbOfIterations,
1638 MaxAspectRatio, Method, false );
1642 //=======================================================================
1643 //function : SmoothParametric
1645 //=======================================================================
1648 SMESH_MeshEditor_i::SmoothParametric(const SMESH::long_array & IDsOfElements,
1649 const SMESH::long_array & IDsOfFixedNodes,
1650 CORBA::Long MaxNbOfIterations,
1651 CORBA::Double MaxAspectRatio,
1652 SMESH::SMESH_MeshEditor::Smooth_Method Method)
1654 return smooth( IDsOfElements, IDsOfFixedNodes, MaxNbOfIterations,
1655 MaxAspectRatio, Method, true );
1659 //=======================================================================
1660 //function : SmoothObject
1662 //=======================================================================
1665 SMESH_MeshEditor_i::SmoothObject(SMESH::SMESH_IDSource_ptr theObject,
1666 const SMESH::long_array & IDsOfFixedNodes,
1667 CORBA::Long MaxNbOfIterations,
1668 CORBA::Double MaxAspectRatio,
1669 SMESH::SMESH_MeshEditor::Smooth_Method Method)
1671 return smoothObject (theObject, IDsOfFixedNodes, MaxNbOfIterations,
1672 MaxAspectRatio, Method, false);
1676 //=======================================================================
1677 //function : SmoothParametricObject
1679 //=======================================================================
1682 SMESH_MeshEditor_i::SmoothParametricObject(SMESH::SMESH_IDSource_ptr theObject,
1683 const SMESH::long_array & IDsOfFixedNodes,
1684 CORBA::Long MaxNbOfIterations,
1685 CORBA::Double MaxAspectRatio,
1686 SMESH::SMESH_MeshEditor::Smooth_Method Method)
1688 return smoothObject (theObject, IDsOfFixedNodes, MaxNbOfIterations,
1689 MaxAspectRatio, Method, true);
1693 //=============================================================================
1697 //=============================================================================
1700 SMESH_MeshEditor_i::smooth(const SMESH::long_array & IDsOfElements,
1701 const SMESH::long_array & IDsOfFixedNodes,
1702 CORBA::Long MaxNbOfIterations,
1703 CORBA::Double MaxAspectRatio,
1704 SMESH::SMESH_MeshEditor::Smooth_Method Method,
1709 SMESHDS_Mesh* aMesh = GetMeshDS();
1711 TIDSortedElemSet elements;
1712 arrayToSet(IDsOfElements, aMesh, elements, SMDSAbs_Face);
1714 set<const SMDS_MeshNode*> fixedNodes;
1715 for (int i = 0; i < IDsOfFixedNodes.length(); i++) {
1716 CORBA::Long index = IDsOfFixedNodes[i];
1717 const SMDS_MeshNode * node = aMesh->FindNode(index);
1719 fixedNodes.insert( node );
1721 ::SMESH_MeshEditor::SmoothMethod method = ::SMESH_MeshEditor::LAPLACIAN;
1722 if ( Method != SMESH::SMESH_MeshEditor::LAPLACIAN_SMOOTH )
1723 method = ::SMESH_MeshEditor::CENTROIDAL;
1725 myEditor.Smooth(elements, fixedNodes, method,
1726 MaxNbOfIterations, MaxAspectRatio, IsParametric );
1728 myMesh->GetMeshDS()->Modified();
1729 myMesh->SetIsModified( true ); // issue 0020693
1731 storeResult(myEditor);
1733 // Update Python script
1734 TPythonDump() << "isDone = " << this << "."
1735 << (IsParametric ? "SmoothParametric( " : "Smooth( ")
1736 << IDsOfElements << ", " << IDsOfFixedNodes << ", "
1737 << TVar( MaxNbOfIterations ) << ", " << TVar( MaxAspectRatio ) << ", "
1738 << "SMESH.SMESH_MeshEditor."
1739 << ( Method == SMESH::SMESH_MeshEditor::CENTROIDAL_SMOOTH ?
1740 "CENTROIDAL_SMOOTH )" : "LAPLACIAN_SMOOTH )");
1746 //=============================================================================
1750 //=============================================================================
1753 SMESH_MeshEditor_i::smoothObject(SMESH::SMESH_IDSource_ptr theObject,
1754 const SMESH::long_array & IDsOfFixedNodes,
1755 CORBA::Long MaxNbOfIterations,
1756 CORBA::Double MaxAspectRatio,
1757 SMESH::SMESH_MeshEditor::Smooth_Method Method,
1762 TPythonDump aTPythonDump; // suppress dump in smooth()
1764 SMESH::long_array_var anElementsId = theObject->GetIDs();
1765 CORBA::Boolean isDone = smooth (anElementsId, IDsOfFixedNodes, MaxNbOfIterations,
1766 MaxAspectRatio, Method, IsParametric);
1768 // Update Python script
1769 aTPythonDump << "isDone = " << this << "."
1770 << (IsParametric ? "SmoothParametricObject( " : "SmoothObject( ")
1771 << theObject << ", " << IDsOfFixedNodes << ", "
1772 << TVar( MaxNbOfIterations ) << ", " << TVar( MaxAspectRatio ) << ", "
1773 << "SMESH.SMESH_MeshEditor."
1774 << ( Method == SMESH::SMESH_MeshEditor::CENTROIDAL_SMOOTH ?
1775 "CENTROIDAL_SMOOTH )" : "LAPLACIAN_SMOOTH )");
1781 //=============================================================================
1785 //=============================================================================
1787 void SMESH_MeshEditor_i::RenumberNodes()
1789 // Update Python script
1790 TPythonDump() << this << ".RenumberNodes()";
1792 GetMeshDS()->Renumber( true );
1796 //=============================================================================
1800 //=============================================================================
1802 void SMESH_MeshEditor_i::RenumberElements()
1804 // Update Python script
1805 TPythonDump() << this << ".RenumberElements()";
1807 GetMeshDS()->Renumber( false );
1810 //=======================================================================
1812 * \brief Return groups by their IDs
1814 //=======================================================================
1816 SMESH::ListOfGroups* SMESH_MeshEditor_i::getGroups(const std::list<int>* groupIDs)
1820 myMesh_i->CreateGroupServants();
1821 return myMesh_i->GetGroups( *groupIDs );
1824 //=======================================================================
1825 //function : rotationSweep
1827 //=======================================================================
1829 SMESH::ListOfGroups*
1830 SMESH_MeshEditor_i::rotationSweep(const SMESH::long_array & theIDsOfElements,
1831 const SMESH::AxisStruct & theAxis,
1832 CORBA::Double theAngleInRadians,
1833 CORBA::Long theNbOfSteps,
1834 CORBA::Double theTolerance,
1835 const bool theMakeGroups,
1836 const SMDSAbs_ElementType theElementType)
1840 TIDSortedElemSet inElements, copyElements;
1841 arrayToSet(theIDsOfElements, GetMeshDS(), inElements, theElementType);
1843 TIDSortedElemSet* workElements = & inElements;
1844 TPreviewMesh tmpMesh( SMDSAbs_Face );
1845 SMESH_Mesh* mesh = 0;
1846 bool makeWalls=true;
1847 if ( myPreviewMode )
1849 SMDSAbs_ElementType select = SMDSAbs_All, avoid = SMDSAbs_Volume;
1850 tmpMesh.Copy( inElements, copyElements, select, avoid );
1852 workElements = & copyElements;
1853 //makeWalls = false;
1860 gp_Ax1 Ax1 (gp_Pnt( theAxis.x, theAxis.y, theAxis.z ),
1861 gp_Vec( theAxis.vx, theAxis.vy, theAxis.vz ));
1863 ::SMESH_MeshEditor::PGroupIDs groupIds =
1864 myEditor.RotationSweep (*workElements, Ax1, theAngleInRadians,
1865 theNbOfSteps, theTolerance, theMakeGroups, makeWalls);
1866 storeResult(myEditor);
1867 myMesh->GetMeshDS()->Modified();
1869 // myMesh->SetIsModified( true ); -- it does not influence Compute()
1871 return theMakeGroups ? getGroups(groupIds.get()) : 0;
1874 //=======================================================================
1875 //function : RotationSweep
1877 //=======================================================================
1879 void SMESH_MeshEditor_i::RotationSweep(const SMESH::long_array & theIDsOfElements,
1880 const SMESH::AxisStruct & theAxis,
1881 CORBA::Double theAngleInRadians,
1882 CORBA::Long theNbOfSteps,
1883 CORBA::Double theTolerance)
1885 if ( !myPreviewMode ) {
1886 TPythonDump() << this << ".RotationSweep( "
1887 << theIDsOfElements << ", "
1889 << TVar( theAngleInRadians ) << ", "
1890 << TVar( theNbOfSteps ) << ", "
1891 << TVar( theTolerance ) << " )";
1893 rotationSweep(theIDsOfElements,
1901 //=======================================================================
1902 //function : RotationSweepMakeGroups
1904 //=======================================================================
1906 SMESH::ListOfGroups*
1907 SMESH_MeshEditor_i::RotationSweepMakeGroups(const SMESH::long_array& theIDsOfElements,
1908 const SMESH::AxisStruct& theAxis,
1909 CORBA::Double theAngleInRadians,
1910 CORBA::Long theNbOfSteps,
1911 CORBA::Double theTolerance)
1913 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
1915 SMESH::ListOfGroups *aGroups = rotationSweep(theIDsOfElements,
1921 if (!myPreviewMode) {
1922 DumpGroupsList(aPythonDump, aGroups);
1923 aPythonDump << this << ".RotationSweepMakeGroups( "
1924 << theIDsOfElements << ", "
1926 << TVar( theAngleInRadians ) << ", "
1927 << TVar( theNbOfSteps ) << ", "
1928 << TVar( theTolerance ) << " )";
1933 //=======================================================================
1934 //function : RotationSweepObject
1936 //=======================================================================
1938 void SMESH_MeshEditor_i::RotationSweepObject(SMESH::SMESH_IDSource_ptr theObject,
1939 const SMESH::AxisStruct & theAxis,
1940 CORBA::Double theAngleInRadians,
1941 CORBA::Long theNbOfSteps,
1942 CORBA::Double theTolerance)
1944 if ( !myPreviewMode ) {
1945 TPythonDump() << this << ".RotationSweepObject( "
1946 << theObject << ", "
1948 << theAngleInRadians << ", "
1949 << theNbOfSteps << ", "
1950 << theTolerance << " )";
1952 SMESH::long_array_var anElementsId = theObject->GetIDs();
1953 rotationSweep(anElementsId,
1961 //=======================================================================
1962 //function : RotationSweepObject1D
1964 //=======================================================================
1966 void SMESH_MeshEditor_i::RotationSweepObject1D(SMESH::SMESH_IDSource_ptr theObject,
1967 const SMESH::AxisStruct & theAxis,
1968 CORBA::Double theAngleInRadians,
1969 CORBA::Long theNbOfSteps,
1970 CORBA::Double theTolerance)
1972 if ( !myPreviewMode ) {
1973 TPythonDump() << this << ".RotationSweepObject1D( "
1974 << theObject << ", "
1976 << TVar( theAngleInRadians ) << ", "
1977 << TVar( theNbOfSteps ) << ", "
1978 << TVar( theTolerance ) << " )";
1980 SMESH::long_array_var anElementsId = theObject->GetIDs();
1981 rotationSweep(anElementsId,
1990 //=======================================================================
1991 //function : RotationSweepObject2D
1993 //=======================================================================
1995 void SMESH_MeshEditor_i::RotationSweepObject2D(SMESH::SMESH_IDSource_ptr theObject,
1996 const SMESH::AxisStruct & theAxis,
1997 CORBA::Double theAngleInRadians,
1998 CORBA::Long theNbOfSteps,
1999 CORBA::Double theTolerance)
2001 if ( !myPreviewMode ) {
2002 TPythonDump() << this << ".RotationSweepObject2D( "
2003 << theObject << ", "
2005 << TVar( theAngleInRadians ) << ", "
2006 << TVar( theNbOfSteps ) << ", "
2007 << TVar( theTolerance ) << " )";
2009 SMESH::long_array_var anElementsId = theObject->GetIDs();
2010 rotationSweep(anElementsId,
2019 //=======================================================================
2020 //function : RotationSweepObjectMakeGroups
2022 //=======================================================================
2024 SMESH::ListOfGroups*
2025 SMESH_MeshEditor_i::RotationSweepObjectMakeGroups(SMESH::SMESH_IDSource_ptr theObject,
2026 const SMESH::AxisStruct& theAxis,
2027 CORBA::Double theAngleInRadians,
2028 CORBA::Long theNbOfSteps,
2029 CORBA::Double theTolerance)
2031 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
2033 SMESH::long_array_var anElementsId = theObject->GetIDs();
2034 SMESH::ListOfGroups *aGroups = rotationSweep(anElementsId,
2040 if (!myPreviewMode) {
2041 DumpGroupsList(aPythonDump, aGroups);
2042 aPythonDump << this << ".RotationSweepObjectMakeGroups( "
2043 << theObject << ", "
2045 << theAngleInRadians << ", "
2046 << theNbOfSteps << ", "
2047 << theTolerance << " )";
2052 //=======================================================================
2053 //function : RotationSweepObject1DMakeGroups
2055 //=======================================================================
2057 SMESH::ListOfGroups*
2058 SMESH_MeshEditor_i::RotationSweepObject1DMakeGroups(SMESH::SMESH_IDSource_ptr theObject,
2059 const SMESH::AxisStruct& theAxis,
2060 CORBA::Double theAngleInRadians,
2061 CORBA::Long theNbOfSteps,
2062 CORBA::Double theTolerance)
2064 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
2066 SMESH::long_array_var anElementsId = theObject->GetIDs();
2067 SMESH::ListOfGroups *aGroups = rotationSweep(anElementsId,
2074 if (!myPreviewMode) {
2075 DumpGroupsList(aPythonDump, aGroups);
2076 aPythonDump << this << ".RotationSweepObject1DMakeGroups( "
2077 << theObject << ", "
2079 << TVar( theAngleInRadians ) << ", "
2080 << TVar( theNbOfSteps ) << ", "
2081 << TVar( theTolerance ) << " )";
2086 //=======================================================================
2087 //function : RotationSweepObject2DMakeGroups
2089 //=======================================================================
2091 SMESH::ListOfGroups*
2092 SMESH_MeshEditor_i::RotationSweepObject2DMakeGroups(SMESH::SMESH_IDSource_ptr theObject,
2093 const SMESH::AxisStruct& theAxis,
2094 CORBA::Double theAngleInRadians,
2095 CORBA::Long theNbOfSteps,
2096 CORBA::Double theTolerance)
2098 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
2100 SMESH::long_array_var anElementsId = theObject->GetIDs();
2101 SMESH::ListOfGroups *aGroups = rotationSweep(anElementsId,
2108 if (!myPreviewMode) {
2109 DumpGroupsList(aPythonDump, aGroups);
2110 aPythonDump << this << ".RotationSweepObject2DMakeGroups( "
2111 << theObject << ", "
2113 << TVar( theAngleInRadians ) << ", "
2114 << TVar( theNbOfSteps ) << ", "
2115 << TVar( theTolerance ) << " )";
2121 //=======================================================================
2122 //function : extrusionSweep
2124 //=======================================================================
2126 SMESH::ListOfGroups*
2127 SMESH_MeshEditor_i::extrusionSweep(const SMESH::long_array & theIDsOfElements,
2128 const SMESH::DirStruct & theStepVector,
2129 CORBA::Long theNbOfSteps,
2131 const SMDSAbs_ElementType theElementType)
2139 TIDSortedElemSet elements, copyElements;
2140 arrayToSet(theIDsOfElements, GetMeshDS(), elements, theElementType);
2142 const SMESH::PointStruct * P = &theStepVector.PS;
2143 gp_Vec stepVec( P->x, P->y, P->z );
2145 TIDSortedElemSet* workElements = & elements;
2147 SMDSAbs_ElementType aType = SMDSAbs_Face;
2148 //::SMESH_MeshEditor::ExtrusionFlags aFlag = ::SMESH_MeshEditor::ExtrusionFlags::EXTRUSION_FLAG_BOUNDARY;
2149 if (theElementType == SMDSAbs_Node)
2151 aType = SMDSAbs_Edge;
2152 //aFlag = ::SMESH_MeshEditor::ExtrusionFlags::EXTRUSION_FLAG_SEW;
2154 TPreviewMesh tmpMesh( aType );
2155 SMESH_Mesh* mesh = myMesh;
2157 if ( myPreviewMode ) {
2158 SMDSAbs_ElementType select = SMDSAbs_All, avoid = SMDSAbs_Volume;
2159 tmpMesh.Copy( elements, copyElements, select, avoid );
2161 workElements = & copyElements;
2162 theMakeGroups = false;
2165 TElemOfElemListMap aHystory;
2166 ::SMESH_MeshEditor::PGroupIDs groupIds =
2167 myEditor.ExtrusionSweep (*workElements, stepVec, theNbOfSteps, aHystory, theMakeGroups);
2169 myMesh->GetMeshDS()->Modified();
2170 storeResult(myEditor);
2172 return theMakeGroups ? getGroups(groupIds.get()) : 0;
2174 } catch(Standard_Failure) {
2175 Handle(Standard_Failure) aFail = Standard_Failure::Caught();
2176 INFOS( "SMESH_MeshEditor_i::ExtrusionSweep fails - "<< aFail->GetMessageString() );
2181 //=======================================================================
2182 //function : ExtrusionSweep
2184 //=======================================================================
2186 void SMESH_MeshEditor_i::ExtrusionSweep(const SMESH::long_array & theIDsOfElements,
2187 const SMESH::DirStruct & theStepVector,
2188 CORBA::Long theNbOfSteps)
2190 extrusionSweep (theIDsOfElements, theStepVector, theNbOfSteps, false );
2191 if (!myPreviewMode) {
2192 TPythonDump() << this << ".ExtrusionSweep( "
2193 << theIDsOfElements << ", " << theStepVector <<", " << TVar(theNbOfSteps) << " )";
2197 //=======================================================================
2198 //function : ExtrusionSweep0D
2200 //=======================================================================
2202 void SMESH_MeshEditor_i::ExtrusionSweep0D(const SMESH::long_array & theIDsOfElements,
2203 const SMESH::DirStruct & theStepVector,
2204 CORBA::Long theNbOfSteps)
2206 extrusionSweep (theIDsOfElements, theStepVector, theNbOfSteps, false, SMDSAbs_Node );
2207 if (!myPreviewMode) {
2208 TPythonDump() << this << ".ExtrusionSweep0D( "
2209 << theIDsOfElements << ", " << theStepVector <<", " << TVar(theNbOfSteps)<< " )";
2213 //=======================================================================
2214 //function : ExtrusionSweepObject
2216 //=======================================================================
2218 void SMESH_MeshEditor_i::ExtrusionSweepObject(SMESH::SMESH_IDSource_ptr theObject,
2219 const SMESH::DirStruct & theStepVector,
2220 CORBA::Long theNbOfSteps)
2222 SMESH::long_array_var anElementsId = theObject->GetIDs();
2223 extrusionSweep (anElementsId, theStepVector, theNbOfSteps, false );
2224 if (!myPreviewMode) {
2225 TPythonDump() << this << ".ExtrusionSweepObject( "
2226 << theObject << ", " << theStepVector << ", " << theNbOfSteps << " )";
2230 //=======================================================================
2231 //function : ExtrusionSweepObject0D
2233 //=======================================================================
2235 void SMESH_MeshEditor_i::ExtrusionSweepObject0D(SMESH::SMESH_IDSource_ptr theObject,
2236 const SMESH::DirStruct & theStepVector,
2237 CORBA::Long theNbOfSteps)
2239 SMESH::long_array_var anElementsId = theObject->GetIDs();
2240 extrusionSweep (anElementsId, theStepVector, theNbOfSteps, false, SMDSAbs_Node );
2241 if ( !myPreviewMode ) {
2242 TPythonDump() << this << ".ExtrusionSweepObject0D( "
2243 << theObject << ", " << theStepVector << ", " << TVar( theNbOfSteps ) << " )";
2247 //=======================================================================
2248 //function : ExtrusionSweepObject1D
2250 //=======================================================================
2252 void SMESH_MeshEditor_i::ExtrusionSweepObject1D(SMESH::SMESH_IDSource_ptr theObject,
2253 const SMESH::DirStruct & theStepVector,
2254 CORBA::Long theNbOfSteps)
2256 SMESH::long_array_var anElementsId = theObject->GetIDs();
2257 extrusionSweep (anElementsId, theStepVector, theNbOfSteps, false, SMDSAbs_Edge );
2258 if ( !myPreviewMode ) {
2259 TPythonDump() << this << ".ExtrusionSweepObject1D( "
2260 << theObject << ", " << theStepVector << ", " << TVar( theNbOfSteps ) << " )";
2264 //=======================================================================
2265 //function : ExtrusionSweepObject2D
2267 //=======================================================================
2269 void SMESH_MeshEditor_i::ExtrusionSweepObject2D(SMESH::SMESH_IDSource_ptr theObject,
2270 const SMESH::DirStruct & theStepVector,
2271 CORBA::Long theNbOfSteps)
2273 SMESH::long_array_var anElementsId = theObject->GetIDs();
2274 extrusionSweep (anElementsId, theStepVector, theNbOfSteps, false, SMDSAbs_Face );
2275 if ( !myPreviewMode ) {
2276 TPythonDump() << this << ".ExtrusionSweepObject2D( "
2277 << theObject << ", " << theStepVector << ", " << TVar( theNbOfSteps ) << " )";
2281 //=======================================================================
2282 //function : ExtrusionSweepMakeGroups
2284 //=======================================================================
2286 SMESH::ListOfGroups*
2287 SMESH_MeshEditor_i::ExtrusionSweepMakeGroups(const SMESH::long_array& theIDsOfElements,
2288 const SMESH::DirStruct& theStepVector,
2289 CORBA::Long theNbOfSteps)
2291 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
2293 SMESH::ListOfGroups* aGroups = extrusionSweep(theIDsOfElements, theStepVector, theNbOfSteps, true);
2295 if (!myPreviewMode) {
2296 DumpGroupsList(aPythonDump, aGroups);
2297 aPythonDump << this << ".ExtrusionSweepMakeGroups( " << theIDsOfElements
2298 << ", " << theStepVector <<", " << TVar( theNbOfSteps ) << " )";
2303 //=======================================================================
2304 //function : ExtrusionSweepMakeGroups0D
2306 //=======================================================================
2308 SMESH::ListOfGroups*
2309 SMESH_MeshEditor_i::ExtrusionSweepMakeGroups0D(const SMESH::long_array& theIDsOfElements,
2310 const SMESH::DirStruct& theStepVector,
2311 CORBA::Long theNbOfSteps)
2313 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
2315 SMESH::ListOfGroups* aGroups = extrusionSweep(theIDsOfElements, theStepVector, theNbOfSteps, true,SMDSAbs_Node);
2317 if (!myPreviewMode) {
2318 DumpGroupsList(aPythonDump, aGroups);
2319 aPythonDump << this << ".ExtrusionSweepMakeGroups0D( " << theIDsOfElements
2320 << ", " << theStepVector <<", " << TVar( theNbOfSteps ) << " )";
2325 //=======================================================================
2326 //function : ExtrusionSweepObjectMakeGroups
2328 //=======================================================================
2330 SMESH::ListOfGroups*
2331 SMESH_MeshEditor_i::ExtrusionSweepObjectMakeGroups(SMESH::SMESH_IDSource_ptr theObject,
2332 const SMESH::DirStruct& theStepVector,
2333 CORBA::Long theNbOfSteps)
2335 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
2337 SMESH::long_array_var anElementsId = theObject->GetIDs();
2338 SMESH::ListOfGroups * aGroups = extrusionSweep(anElementsId, theStepVector, theNbOfSteps, true);
2340 if (!myPreviewMode) {
2341 DumpGroupsList(aPythonDump, aGroups);
2342 aPythonDump << this << ".ExtrusionSweepObjectMakeGroups( " << theObject
2343 << ", " << theStepVector << ", " << theNbOfSteps << " )";
2348 //=======================================================================
2349 //function : ExtrusionSweepObject0DMakeGroups
2351 //=======================================================================
2353 SMESH::ListOfGroups*
2354 SMESH_MeshEditor_i::ExtrusionSweepObject0DMakeGroups(SMESH::SMESH_IDSource_ptr theObject,
2355 const SMESH::DirStruct& theStepVector,
2356 CORBA::Long theNbOfSteps)
2358 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
2360 SMESH::long_array_var anElementsId = theObject->GetIDs();
2361 SMESH::ListOfGroups * aGroups = extrusionSweep(anElementsId, theStepVector,
2362 theNbOfSteps, true, SMDSAbs_Node);
2363 if (!myPreviewMode) {
2364 DumpGroupsList(aPythonDump, aGroups);
2365 aPythonDump << this << ".ExtrusionSweepObject0DMakeGroups( " << theObject
2366 << ", " << theStepVector << ", " << TVar( theNbOfSteps ) << " )";
2371 //=======================================================================
2372 //function : ExtrusionSweepObject1DMakeGroups
2374 //=======================================================================
2376 SMESH::ListOfGroups*
2377 SMESH_MeshEditor_i::ExtrusionSweepObject1DMakeGroups(SMESH::SMESH_IDSource_ptr theObject,
2378 const SMESH::DirStruct& theStepVector,
2379 CORBA::Long theNbOfSteps)
2381 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
2383 SMESH::long_array_var anElementsId = theObject->GetIDs();
2384 SMESH::ListOfGroups * aGroups = extrusionSweep(anElementsId, theStepVector,
2385 theNbOfSteps, true, SMDSAbs_Edge);
2386 if (!myPreviewMode) {
2387 DumpGroupsList(aPythonDump, aGroups);
2388 aPythonDump << this << ".ExtrusionSweepObject1DMakeGroups( " << theObject
2389 << ", " << theStepVector << ", " << TVar( theNbOfSteps ) << " )";
2394 //=======================================================================
2395 //function : ExtrusionSweepObject2DMakeGroups
2397 //=======================================================================
2399 SMESH::ListOfGroups*
2400 SMESH_MeshEditor_i::ExtrusionSweepObject2DMakeGroups(SMESH::SMESH_IDSource_ptr theObject,
2401 const SMESH::DirStruct& theStepVector,
2402 CORBA::Long theNbOfSteps)
2404 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
2406 SMESH::long_array_var anElementsId = theObject->GetIDs();
2407 SMESH::ListOfGroups * aGroups = extrusionSweep(anElementsId, theStepVector,
2408 theNbOfSteps, true, SMDSAbs_Face);
2409 if (!myPreviewMode) {
2410 DumpGroupsList(aPythonDump, aGroups);
2411 aPythonDump << this << ".ExtrusionSweepObject2DMakeGroups( " << theObject
2412 << ", " << theStepVector << ", " << TVar( theNbOfSteps ) << " )";
2418 //=======================================================================
2419 //function : advancedExtrusion
2421 //=======================================================================
2423 SMESH::ListOfGroups*
2424 SMESH_MeshEditor_i::advancedExtrusion(const SMESH::long_array & theIDsOfElements,
2425 const SMESH::DirStruct & theStepVector,
2426 CORBA::Long theNbOfSteps,
2427 CORBA::Long theExtrFlags,
2428 CORBA::Double theSewTolerance,
2429 const bool theMakeGroups)
2433 TIDSortedElemSet elements;
2434 arrayToSet(theIDsOfElements, GetMeshDS(), elements);
2436 const SMESH::PointStruct * P = &theStepVector.PS;
2437 gp_Vec stepVec( P->x, P->y, P->z );
2439 TElemOfElemListMap aHystory;
2440 ::SMESH_MeshEditor::PGroupIDs groupIds =
2441 myEditor.ExtrusionSweep (elements, stepVec, theNbOfSteps, aHystory,
2442 theMakeGroups, theExtrFlags, theSewTolerance);
2443 storeResult(myEditor);
2445 return theMakeGroups ? getGroups(groupIds.get()) : 0;
2448 //=======================================================================
2449 //function : AdvancedExtrusion
2451 //=======================================================================
2453 void SMESH_MeshEditor_i::AdvancedExtrusion(const SMESH::long_array & theIDsOfElements,
2454 const SMESH::DirStruct & theStepVector,
2455 CORBA::Long theNbOfSteps,
2456 CORBA::Long theExtrFlags,
2457 CORBA::Double theSewTolerance)
2459 if ( !myPreviewMode ) {
2460 TPythonDump() << "stepVector = " << theStepVector;
2461 TPythonDump() << this << ".AdvancedExtrusion("
2464 << theNbOfSteps << ","
2465 << theExtrFlags << ", "
2466 << theSewTolerance << " )";
2468 advancedExtrusion( theIDsOfElements,
2476 //=======================================================================
2477 //function : AdvancedExtrusionMakeGroups
2479 //=======================================================================
2480 SMESH::ListOfGroups*
2481 SMESH_MeshEditor_i::AdvancedExtrusionMakeGroups(const SMESH::long_array& theIDsOfElements,
2482 const SMESH::DirStruct& theStepVector,
2483 CORBA::Long theNbOfSteps,
2484 CORBA::Long theExtrFlags,
2485 CORBA::Double theSewTolerance)
2487 if (!myPreviewMode) {
2488 TPythonDump() << "stepVector = " << theStepVector;
2490 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
2492 SMESH::ListOfGroups * aGroups = advancedExtrusion( theIDsOfElements,
2499 if (!myPreviewMode) {
2500 DumpGroupsList(aPythonDump, aGroups);
2501 aPythonDump << this << ".AdvancedExtrusionMakeGroups("
2504 << theNbOfSteps << ","
2505 << theExtrFlags << ", "
2506 << theSewTolerance << " )";
2512 //================================================================================
2514 * \brief Convert extrusion error to IDL enum
2516 //================================================================================
2518 #define RETCASE(enm) case ::SMESH_MeshEditor::enm: return SMESH::SMESH_MeshEditor::enm;
2520 static SMESH::SMESH_MeshEditor::Extrusion_Error convExtrError( const::SMESH_MeshEditor::Extrusion_Error e )
2524 RETCASE( EXTR_NO_ELEMENTS );
2525 RETCASE( EXTR_PATH_NOT_EDGE );
2526 RETCASE( EXTR_BAD_PATH_SHAPE );
2527 RETCASE( EXTR_BAD_STARTING_NODE );
2528 RETCASE( EXTR_BAD_ANGLES_NUMBER );
2529 RETCASE( EXTR_CANT_GET_TANGENT );
2531 return SMESH::SMESH_MeshEditor::EXTR_OK;
2535 //=======================================================================
2536 //function : extrusionAlongPath
2538 //=======================================================================
2539 SMESH::ListOfGroups*
2540 SMESH_MeshEditor_i::extrusionAlongPath(const SMESH::long_array & theIDsOfElements,
2541 SMESH::SMESH_Mesh_ptr thePathMesh,
2542 GEOM::GEOM_Object_ptr thePathShape,
2543 CORBA::Long theNodeStart,
2544 CORBA::Boolean theHasAngles,
2545 const SMESH::double_array & theAngles,
2546 CORBA::Boolean theHasRefPoint,
2547 const SMESH::PointStruct & theRefPoint,
2548 const bool theMakeGroups,
2549 SMESH::SMESH_MeshEditor::Extrusion_Error & theError,
2550 const SMDSAbs_ElementType theElementType)
2552 MESSAGE("extrusionAlongPath");
2555 if ( thePathMesh->_is_nil() || thePathShape->_is_nil() ) {
2556 theError = SMESH::SMESH_MeshEditor::EXTR_BAD_PATH_SHAPE;
2559 SMESH_Mesh_i* aMeshImp = SMESH::DownCast<SMESH_Mesh_i*>( thePathMesh );
2561 TopoDS_Shape aShape = SMESH_Gen_i::GetSMESHGen()->GeomObjectToShape( thePathShape );
2562 SMESH_subMesh* aSubMesh = aMeshImp->GetImpl().GetSubMesh( aShape );
2564 if ( !aSubMesh || !aSubMesh->GetSubMeshDS()) {
2565 theError = SMESH::SMESH_MeshEditor::EXTR_BAD_PATH_SHAPE;
2569 SMDS_MeshNode* nodeStart = (SMDS_MeshNode*)aMeshImp->GetImpl().GetMeshDS()->FindNode(theNodeStart);
2571 theError = SMESH::SMESH_MeshEditor::EXTR_BAD_STARTING_NODE;
2575 TIDSortedElemSet elements;
2576 arrayToSet(theIDsOfElements, GetMeshDS(), elements, theElementType);
2578 list<double> angles;
2579 for (int i = 0; i < theAngles.length(); i++) {
2580 angles.push_back( theAngles[i] );
2583 gp_Pnt refPnt( theRefPoint.x, theRefPoint.y, theRefPoint.z );
2585 int nbOldGroups = myMesh->NbGroup();
2587 ::SMESH_MeshEditor::Extrusion_Error error =
2588 myEditor.ExtrusionAlongTrack( elements, aSubMesh, nodeStart,
2589 theHasAngles, angles, false,
2590 theHasRefPoint, refPnt, theMakeGroups );
2591 myMesh->GetMeshDS()->Modified();
2592 storeResult(myEditor);
2593 theError = convExtrError( error );
2595 if ( theMakeGroups ) {
2596 list<int> groupIDs = myMesh->GetGroupIds();
2597 list<int>::iterator newBegin = groupIDs.begin();
2598 std::advance( newBegin, nbOldGroups ); // skip old groups
2599 groupIDs.erase( groupIDs.begin(), newBegin );
2600 return getGroups( & groupIDs );
2606 //=======================================================================
2607 //function : extrusionAlongPathX
2609 //=======================================================================
2610 SMESH::ListOfGroups*
2611 SMESH_MeshEditor_i::extrusionAlongPathX(const SMESH::long_array & IDsOfElements,
2612 SMESH::SMESH_IDSource_ptr Path,
2613 CORBA::Long NodeStart,
2614 CORBA::Boolean HasAngles,
2615 const SMESH::double_array& Angles,
2616 CORBA::Boolean LinearVariation,
2617 CORBA::Boolean HasRefPoint,
2618 const SMESH::PointStruct& RefPoint,
2620 const SMDSAbs_ElementType ElementType,
2621 SMESH::SMESH_MeshEditor::Extrusion_Error & Error)
2623 SMESH::ListOfGroups* EmptyGr = new SMESH::ListOfGroups;
2627 list<double> angles;
2628 for (int i = 0; i < Angles.length(); i++) {
2629 angles.push_back( Angles[i] );
2631 gp_Pnt refPnt( RefPoint.x, RefPoint.y, RefPoint.z );
2632 int nbOldGroups = myMesh->NbGroup();
2634 if ( Path->_is_nil() ) {
2635 Error = SMESH::SMESH_MeshEditor::EXTR_BAD_PATH_SHAPE;
2639 TIDSortedElemSet elements, copyElements;
2640 arrayToSet(IDsOfElements, GetMeshDS(), elements, ElementType);
2642 TIDSortedElemSet* workElements = &elements;
2643 TPreviewMesh tmpMesh( SMDSAbs_Face );
2644 SMESH_Mesh* mesh = myMesh;
2646 if ( myPreviewMode )
2648 SMDSAbs_ElementType select = SMDSAbs_All, avoid = SMDSAbs_Volume;
2649 tmpMesh.Copy( elements, copyElements, select, avoid );
2651 workElements = & copyElements;
2655 ::SMESH_MeshEditor::Extrusion_Error error;
2657 if ( SMESH_Mesh_i* aMeshImp = SMESH::DownCast<SMESH_Mesh_i*>( Path ))
2660 SMDS_MeshNode* aNodeStart =
2661 (SMDS_MeshNode*)aMeshImp->GetImpl().GetMeshDS()->FindNode(NodeStart);
2662 if ( !aNodeStart ) {
2663 Error = SMESH::SMESH_MeshEditor::EXTR_BAD_STARTING_NODE;
2666 error = myEditor.ExtrusionAlongTrack( *workElements, &(aMeshImp->GetImpl()), aNodeStart,
2667 HasAngles, angles, LinearVariation,
2668 HasRefPoint, refPnt, MakeGroups );
2669 myMesh->GetMeshDS()->Modified();
2671 else if ( SMESH_subMesh_i* aSubMeshImp = SMESH::DownCast<SMESH_subMesh_i*>( Path ))
2674 SMESH::SMESH_Mesh_ptr aPathMesh = aSubMeshImp->GetFather();
2675 aMeshImp = SMESH::DownCast<SMESH_Mesh_i*>( aPathMesh );
2676 SMDS_MeshNode* aNodeStart =
2677 (SMDS_MeshNode*)aMeshImp->GetImpl().GetMeshDS()->FindNode(NodeStart);
2678 if ( !aNodeStart ) {
2679 Error = SMESH::SMESH_MeshEditor::EXTR_BAD_STARTING_NODE;
2682 SMESH_subMesh* aSubMesh =
2683 aMeshImp->GetImpl().GetSubMeshContaining(aSubMeshImp->GetId());
2684 error = myEditor.ExtrusionAlongTrack( *workElements, aSubMesh, aNodeStart,
2685 HasAngles, angles, LinearVariation,
2686 HasRefPoint, refPnt, MakeGroups );
2687 myMesh->GetMeshDS()->Modified();
2689 else if ( SMESH::DownCast<SMESH_Group_i*>( Path ))
2691 // path as group of 1D elements
2697 Error = SMESH::SMESH_MeshEditor::EXTR_BAD_PATH_SHAPE;
2701 storeResult(myEditor);
2702 Error = convExtrError( error );
2705 list<int> groupIDs = myMesh->GetGroupIds();
2706 list<int>::iterator newBegin = groupIDs.begin();
2707 std::advance( newBegin, nbOldGroups ); // skip old groups
2708 groupIDs.erase( groupIDs.begin(), newBegin );
2709 return getGroups( & groupIDs );
2715 //=======================================================================
2716 //function : ExtrusionAlongPath
2718 //=======================================================================
2719 SMESH::SMESH_MeshEditor::Extrusion_Error
2720 SMESH_MeshEditor_i::ExtrusionAlongPath(const SMESH::long_array & theIDsOfElements,
2721 SMESH::SMESH_Mesh_ptr thePathMesh,
2722 GEOM::GEOM_Object_ptr thePathShape,
2723 CORBA::Long theNodeStart,
2724 CORBA::Boolean theHasAngles,
2725 const SMESH::double_array & theAngles,
2726 CORBA::Boolean theHasRefPoint,
2727 const SMESH::PointStruct & theRefPoint)
2729 MESSAGE("ExtrusionAlongPath");
2730 if ( !myPreviewMode ) {
2731 TPythonDump() << "error = " << this << ".ExtrusionAlongPath( "
2732 << theIDsOfElements << ", "
2733 << thePathMesh << ", "
2734 << thePathShape << ", "
2735 << theNodeStart << ", "
2736 << theHasAngles << ", "
2737 << theAngles << ", "
2738 << theHasRefPoint << ", "
2739 << "SMESH.PointStruct( "
2740 << ( theHasRefPoint ? theRefPoint.x : 0 ) << ", "
2741 << ( theHasRefPoint ? theRefPoint.y : 0 ) << ", "
2742 << ( theHasRefPoint ? theRefPoint.z : 0 ) << " ) )";
2744 SMESH::SMESH_MeshEditor::Extrusion_Error anError;
2745 extrusionAlongPath( theIDsOfElements,
2758 //=======================================================================
2759 //function : ExtrusionAlongPathObject
2761 //=======================================================================
2762 SMESH::SMESH_MeshEditor::Extrusion_Error
2763 SMESH_MeshEditor_i::ExtrusionAlongPathObject(SMESH::SMESH_IDSource_ptr theObject,
2764 SMESH::SMESH_Mesh_ptr thePathMesh,
2765 GEOM::GEOM_Object_ptr thePathShape,
2766 CORBA::Long theNodeStart,
2767 CORBA::Boolean theHasAngles,
2768 const SMESH::double_array & theAngles,
2769 CORBA::Boolean theHasRefPoint,
2770 const SMESH::PointStruct & theRefPoint)
2772 if ( !myPreviewMode ) {
2773 TPythonDump() << "error = " << this << ".ExtrusionAlongPathObject( "
2774 << theObject << ", "
2775 << thePathMesh << ", "
2776 << thePathShape << ", "
2777 << theNodeStart << ", "
2778 << theHasAngles << ", "
2779 << theAngles << ", "
2780 << theHasRefPoint << ", "
2781 << "SMESH.PointStruct( "
2782 << ( theHasRefPoint ? theRefPoint.x : 0 ) << ", "
2783 << ( theHasRefPoint ? theRefPoint.y : 0 ) << ", "
2784 << ( theHasRefPoint ? theRefPoint.z : 0 ) << " ) )";
2786 SMESH::SMESH_MeshEditor::Extrusion_Error anError;
2787 SMESH::long_array_var anElementsId = theObject->GetIDs();
2788 extrusionAlongPath( anElementsId,
2801 //=======================================================================
2802 //function : ExtrusionAlongPathObject1D
2804 //=======================================================================
2805 SMESH::SMESH_MeshEditor::Extrusion_Error
2806 SMESH_MeshEditor_i::ExtrusionAlongPathObject1D(SMESH::SMESH_IDSource_ptr theObject,
2807 SMESH::SMESH_Mesh_ptr thePathMesh,
2808 GEOM::GEOM_Object_ptr thePathShape,
2809 CORBA::Long theNodeStart,
2810 CORBA::Boolean theHasAngles,
2811 const SMESH::double_array & theAngles,
2812 CORBA::Boolean theHasRefPoint,
2813 const SMESH::PointStruct & theRefPoint)
2815 if ( !myPreviewMode ) {
2816 TPythonDump() << "error = " << this << ".ExtrusionAlongPathObject1D( "
2817 << theObject << ", "
2818 << thePathMesh << ", "
2819 << thePathShape << ", "
2820 << theNodeStart << ", "
2821 << theHasAngles << ", "
2822 << theAngles << ", "
2823 << theHasRefPoint << ", "
2824 << "SMESH.PointStruct( "
2825 << ( theHasRefPoint ? theRefPoint.x : 0 ) << ", "
2826 << ( theHasRefPoint ? theRefPoint.y : 0 ) << ", "
2827 << ( theHasRefPoint ? theRefPoint.z : 0 ) << " ) )";
2829 SMESH::SMESH_MeshEditor::Extrusion_Error anError;
2830 SMESH::long_array_var anElementsId = theObject->GetIDs();
2831 extrusionAlongPath( anElementsId,
2845 //=======================================================================
2846 //function : ExtrusionAlongPathObject2D
2848 //=======================================================================
2849 SMESH::SMESH_MeshEditor::Extrusion_Error
2850 SMESH_MeshEditor_i::ExtrusionAlongPathObject2D(SMESH::SMESH_IDSource_ptr theObject,
2851 SMESH::SMESH_Mesh_ptr thePathMesh,
2852 GEOM::GEOM_Object_ptr thePathShape,
2853 CORBA::Long theNodeStart,
2854 CORBA::Boolean theHasAngles,
2855 const SMESH::double_array & theAngles,
2856 CORBA::Boolean theHasRefPoint,
2857 const SMESH::PointStruct & theRefPoint)
2859 if ( !myPreviewMode ) {
2860 TPythonDump() << "error = " << this << ".ExtrusionAlongPathObject2D( "
2861 << theObject << ", "
2862 << thePathMesh << ", "
2863 << thePathShape << ", "
2864 << theNodeStart << ", "
2865 << theHasAngles << ", "
2866 << theAngles << ", "
2867 << theHasRefPoint << ", "
2868 << "SMESH.PointStruct( "
2869 << ( theHasRefPoint ? theRefPoint.x : 0 ) << ", "
2870 << ( theHasRefPoint ? theRefPoint.y : 0 ) << ", "
2871 << ( theHasRefPoint ? theRefPoint.z : 0 ) << " ) )";
2873 SMESH::SMESH_MeshEditor::Extrusion_Error anError;
2874 SMESH::long_array_var anElementsId = theObject->GetIDs();
2875 extrusionAlongPath( anElementsId,
2890 //=======================================================================
2891 //function : ExtrusionAlongPathMakeGroups
2893 //=======================================================================
2894 SMESH::ListOfGroups*
2895 SMESH_MeshEditor_i::ExtrusionAlongPathMakeGroups(const SMESH::long_array& theIDsOfElements,
2896 SMESH::SMESH_Mesh_ptr thePathMesh,
2897 GEOM::GEOM_Object_ptr thePathShape,
2898 CORBA::Long theNodeStart,
2899 CORBA::Boolean theHasAngles,
2900 const SMESH::double_array& theAngles,
2901 CORBA::Boolean theHasRefPoint,
2902 const SMESH::PointStruct& theRefPoint,
2903 SMESH::SMESH_MeshEditor::Extrusion_Error& Error)
2905 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
2907 SMESH::ListOfGroups * aGroups = extrusionAlongPath( theIDsOfElements,
2917 if (!myPreviewMode) {
2918 bool isDumpGroups = aGroups && aGroups->length() > 0;
2920 aPythonDump << "(" << aGroups << ", error)";
2922 aPythonDump <<"error";
2924 aPythonDump<<" = "<< this << ".ExtrusionAlongPathMakeGroups( "
2925 << theIDsOfElements << ", "
2926 << thePathMesh << ", "
2927 << thePathShape << ", "
2928 << theNodeStart << ", "
2929 << theHasAngles << ", "
2930 << theAngles << ", "
2931 << theHasRefPoint << ", "
2932 << "SMESH.PointStruct( "
2933 << ( theHasRefPoint ? theRefPoint.x : 0 ) << ", "
2934 << ( theHasRefPoint ? theRefPoint.y : 0 ) << ", "
2935 << ( theHasRefPoint ? theRefPoint.z : 0 ) << " ) )";
2940 //=======================================================================
2941 //function : ExtrusionAlongPathObjectMakeGroups
2943 //=======================================================================
2944 SMESH::ListOfGroups* SMESH_MeshEditor_i::
2945 ExtrusionAlongPathObjectMakeGroups(SMESH::SMESH_IDSource_ptr theObject,
2946 SMESH::SMESH_Mesh_ptr thePathMesh,
2947 GEOM::GEOM_Object_ptr thePathShape,
2948 CORBA::Long theNodeStart,
2949 CORBA::Boolean theHasAngles,
2950 const SMESH::double_array& theAngles,
2951 CORBA::Boolean theHasRefPoint,
2952 const SMESH::PointStruct& theRefPoint,
2953 SMESH::SMESH_MeshEditor::Extrusion_Error& Error)
2955 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
2957 SMESH::long_array_var anElementsId = theObject->GetIDs();
2958 SMESH::ListOfGroups * aGroups = extrusionAlongPath( anElementsId,
2969 if (!myPreviewMode) {
2970 bool isDumpGroups = aGroups && aGroups->length() > 0;
2972 aPythonDump << "(" << aGroups << ", error)";
2974 aPythonDump <<"error";
2976 aPythonDump << " = " << this << ".ExtrusionAlongPathObjectMakeGroups( "
2977 << theObject << ", "
2978 << thePathMesh << ", "
2979 << thePathShape << ", "
2980 << theNodeStart << ", "
2981 << theHasAngles << ", "
2982 << theAngles << ", "
2983 << theHasRefPoint << ", "
2984 << "SMESH.PointStruct( "
2985 << ( theHasRefPoint ? theRefPoint.x : 0 ) << ", "
2986 << ( theHasRefPoint ? theRefPoint.y : 0 ) << ", "
2987 << ( theHasRefPoint ? theRefPoint.z : 0 ) << " ) )";
2992 //=======================================================================
2993 //function : ExtrusionAlongPathObject1DMakeGroups
2995 //=======================================================================
2996 SMESH::ListOfGroups* SMESH_MeshEditor_i::
2997 ExtrusionAlongPathObject1DMakeGroups(SMESH::SMESH_IDSource_ptr theObject,
2998 SMESH::SMESH_Mesh_ptr thePathMesh,
2999 GEOM::GEOM_Object_ptr thePathShape,
3000 CORBA::Long theNodeStart,
3001 CORBA::Boolean theHasAngles,
3002 const SMESH::double_array& theAngles,
3003 CORBA::Boolean theHasRefPoint,
3004 const SMESH::PointStruct& theRefPoint,
3005 SMESH::SMESH_MeshEditor::Extrusion_Error& Error)
3007 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
3009 SMESH::long_array_var anElementsId = theObject->GetIDs();
3010 SMESH::ListOfGroups * aGroups = extrusionAlongPath( anElementsId,
3022 if (!myPreviewMode) {
3023 bool isDumpGroups = aGroups && aGroups->length() > 0;
3025 aPythonDump << "(" << aGroups << ", error)";
3027 aPythonDump << "error";
3029 aPythonDump << " = " << this << ".ExtrusionAlongPathObject1DMakeGroups( "
3030 << theObject << ", "
3031 << thePathMesh << ", "
3032 << thePathShape << ", "
3033 << theNodeStart << ", "
3034 << theHasAngles << ", "
3035 << theAngles << ", "
3036 << theHasRefPoint << ", "
3037 << "SMESH.PointStruct( "
3038 << ( theHasRefPoint ? theRefPoint.x : 0 ) << ", "
3039 << ( theHasRefPoint ? theRefPoint.y : 0 ) << ", "
3040 << ( theHasRefPoint ? theRefPoint.z : 0 ) << " ) )";
3045 //=======================================================================
3046 //function : ExtrusionAlongPathObject2DMakeGroups
3048 //=======================================================================
3049 SMESH::ListOfGroups* SMESH_MeshEditor_i::
3050 ExtrusionAlongPathObject2DMakeGroups(SMESH::SMESH_IDSource_ptr theObject,
3051 SMESH::SMESH_Mesh_ptr thePathMesh,
3052 GEOM::GEOM_Object_ptr thePathShape,
3053 CORBA::Long theNodeStart,
3054 CORBA::Boolean theHasAngles,
3055 const SMESH::double_array& theAngles,
3056 CORBA::Boolean theHasRefPoint,
3057 const SMESH::PointStruct& theRefPoint,
3058 SMESH::SMESH_MeshEditor::Extrusion_Error& Error)
3060 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
3062 SMESH::long_array_var anElementsId = theObject->GetIDs();
3063 SMESH::ListOfGroups * aGroups = extrusionAlongPath( anElementsId,
3075 if (!myPreviewMode) {
3076 bool isDumpGroups = aGroups && aGroups->length() > 0;
3078 aPythonDump << "(" << aGroups << ", error)";
3080 aPythonDump << "error";
3082 aPythonDump << " = " << this << ".ExtrusionAlongPathObject2DMakeGroups( "
3083 << theObject << ", "
3084 << thePathMesh << ", "
3085 << thePathShape << ", "
3086 << theNodeStart << ", "
3087 << theHasAngles << ", "
3088 << theAngles << ", "
3089 << theHasRefPoint << ", "
3090 << "SMESH.PointStruct( "
3091 << ( theHasRefPoint ? theRefPoint.x : 0 ) << ", "
3092 << ( theHasRefPoint ? theRefPoint.y : 0 ) << ", "
3093 << ( theHasRefPoint ? theRefPoint.z : 0 ) << " ) )";
3099 //=======================================================================
3100 //function : ExtrusionAlongPathObjX
3102 //=======================================================================
3103 SMESH::ListOfGroups* SMESH_MeshEditor_i::
3104 ExtrusionAlongPathObjX(SMESH::SMESH_IDSource_ptr Object,
3105 SMESH::SMESH_IDSource_ptr Path,
3106 CORBA::Long NodeStart,
3107 CORBA::Boolean HasAngles,
3108 const SMESH::double_array& Angles,
3109 CORBA::Boolean LinearVariation,
3110 CORBA::Boolean HasRefPoint,
3111 const SMESH::PointStruct& RefPoint,
3112 CORBA::Boolean MakeGroups,
3113 SMESH::ElementType ElemType,
3114 SMESH::SMESH_MeshEditor::Extrusion_Error& Error)
3116 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
3118 SMESH::long_array_var anElementsId = Object->GetIDs();
3119 SMESH::ListOfGroups * aGroups = extrusionAlongPathX(anElementsId,
3128 (SMDSAbs_ElementType)ElemType,
3131 if (!myPreviewMode) {
3132 bool isDumpGroups = aGroups && aGroups->length() > 0;
3134 aPythonDump << "(" << *aGroups << ", error)";
3136 aPythonDump << "error";
3138 aPythonDump << " = " << this << ".ExtrusionAlongPathObjX( "
3141 << NodeStart << ", "
3142 << HasAngles << ", "
3143 << TVar( Angles ) << ", "
3144 << LinearVariation << ", "
3145 << HasRefPoint << ", "
3146 << "SMESH.PointStruct( "
3147 << TVar( HasRefPoint ? RefPoint.x : 0 ) << ", "
3148 << TVar( HasRefPoint ? RefPoint.y : 0 ) << ", "
3149 << TVar( HasRefPoint ? RefPoint.z : 0 ) << " ), "
3150 << MakeGroups << ", "
3151 << ElemType << " )";
3157 //=======================================================================
3158 //function : ExtrusionAlongPathX
3160 //=======================================================================
3161 SMESH::ListOfGroups* SMESH_MeshEditor_i::
3162 ExtrusionAlongPathX(const SMESH::long_array& IDsOfElements,
3163 SMESH::SMESH_IDSource_ptr Path,
3164 CORBA::Long NodeStart,
3165 CORBA::Boolean HasAngles,
3166 const SMESH::double_array& Angles,
3167 CORBA::Boolean LinearVariation,
3168 CORBA::Boolean HasRefPoint,
3169 const SMESH::PointStruct& RefPoint,
3170 CORBA::Boolean MakeGroups,
3171 SMESH::ElementType ElemType,
3172 SMESH::SMESH_MeshEditor::Extrusion_Error& Error)
3174 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
3176 SMESH::ListOfGroups * aGroups = extrusionAlongPathX(IDsOfElements,
3185 (SMDSAbs_ElementType)ElemType,
3188 if (!myPreviewMode) {
3189 bool isDumpGroups = aGroups && aGroups->length() > 0;
3191 aPythonDump << "(" << *aGroups << ", error)";
3193 aPythonDump <<"error";
3195 aPythonDump << " = " << this << ".ExtrusionAlongPathX( "
3196 << IDsOfElements << ", "
3198 << NodeStart << ", "
3199 << HasAngles << ", "
3200 << TVar( Angles ) << ", "
3201 << LinearVariation << ", "
3202 << HasRefPoint << ", "
3203 << "SMESH.PointStruct( "
3204 << TVar( HasRefPoint ? RefPoint.x : 0 ) << ", "
3205 << TVar( HasRefPoint ? RefPoint.y : 0 ) << ", "
3206 << TVar( HasRefPoint ? RefPoint.z : 0 ) << " ), "
3207 << MakeGroups << ", "
3208 << ElemType << " )";
3214 //================================================================================
3216 * \brief Compute rotation angles for ExtrusionAlongPath as linear variation
3217 * of given angles along path steps
3218 * \param PathMesh mesh containing a 1D sub-mesh on the edge, along
3219 * which proceeds the extrusion
3220 * \param PathShape is shape(edge); as the mesh can be complex, the edge
3221 * is used to define the sub-mesh for the path
3223 //================================================================================
3225 SMESH::double_array*
3226 SMESH_MeshEditor_i::LinearAnglesVariation(SMESH::SMESH_Mesh_ptr thePathMesh,
3227 GEOM::GEOM_Object_ptr thePathShape,
3228 const SMESH::double_array & theAngles)
3230 SMESH::double_array_var aResult = new SMESH::double_array();
3231 int nbAngles = theAngles.length();
3232 if ( nbAngles > 0 && !thePathMesh->_is_nil() && !thePathShape->_is_nil() )
3234 SMESH_Mesh_i* aMeshImp = SMESH::DownCast<SMESH_Mesh_i*>( thePathMesh );
3235 TopoDS_Shape aShape = SMESH_Gen_i::GetSMESHGen()->GeomObjectToShape( thePathShape );
3236 SMESH_subMesh* aSubMesh = aMeshImp->GetImpl().GetSubMesh( aShape );
3237 if ( !aSubMesh || !aSubMesh->GetSubMeshDS())
3238 return aResult._retn();
3239 int nbSteps = aSubMesh->GetSubMeshDS()->NbElements();
3240 if ( nbSteps == nbAngles )
3242 aResult.inout() = theAngles;
3246 aResult->length( nbSteps );
3247 double rAn2St = double( nbAngles ) / double( nbSteps );
3248 double angPrev = 0, angle;
3249 for ( int iSt = 0; iSt < nbSteps; ++iSt )
3251 double angCur = rAn2St * ( iSt+1 );
3252 double angCurFloor = floor( angCur );
3253 double angPrevFloor = floor( angPrev );
3254 if ( angPrevFloor == angCurFloor )
3255 angle = rAn2St * theAngles[ int( angCurFloor ) ];
3258 int iP = int( angPrevFloor );
3259 double angPrevCeil = ceil(angPrev);
3260 angle = ( angPrevCeil - angPrev ) * theAngles[ iP ];
3262 int iC = int( angCurFloor );
3263 if ( iC < nbAngles )
3264 angle += ( angCur - angCurFloor ) * theAngles[ iC ];
3266 iP = int( angPrevCeil );
3268 angle += theAngles[ iC ];
3270 aResult[ iSt ] = angle;
3275 // Update Python script
3276 TPythonDump() << "rotAngles = " << theAngles;
3277 TPythonDump() << "rotAngles = " << this << ".LinearAnglesVariation( "
3278 << thePathMesh << ", "
3279 << thePathShape << ", "
3282 return aResult._retn();
3286 //=======================================================================
3289 //=======================================================================
3291 SMESH::ListOfGroups*
3292 SMESH_MeshEditor_i::mirror(TIDSortedElemSet & theElements,
3293 const SMESH::AxisStruct & theAxis,
3294 SMESH::SMESH_MeshEditor::MirrorType theMirrorType,
3295 CORBA::Boolean theCopy,
3297 ::SMESH_Mesh* theTargetMesh)
3301 gp_Pnt P ( theAxis.x, theAxis.y, theAxis.z );
3302 gp_Vec V ( theAxis.vx, theAxis.vy, theAxis.vz );
3304 if ( theTargetMesh )
3308 switch ( theMirrorType ) {
3309 case SMESH::SMESH_MeshEditor::POINT:
3310 aTrsf.SetMirror( P );
3312 case SMESH::SMESH_MeshEditor::AXIS:
3313 aTrsf.SetMirror( gp_Ax1( P, V ));
3316 aTrsf.SetMirror( gp_Ax2( P, V ));
3319 TIDSortedElemSet copyElements;
3320 TPreviewMesh tmpMesh;
3321 TIDSortedElemSet* workElements = & theElements;
3322 SMESH_Mesh* mesh = myMesh;
3324 if ( myPreviewMode )
3326 tmpMesh.Copy( theElements, copyElements);
3327 if ( !theCopy && !theTargetMesh )
3329 TIDSortedElemSet elemsAround, elemsAroundCopy;
3330 getElementsAround( theElements, GetMeshDS(), elemsAround );
3331 tmpMesh.Copy( elemsAround, elemsAroundCopy);
3334 workElements = & copyElements;
3335 theMakeGroups = false;
3338 ::SMESH_MeshEditor::PGroupIDs groupIds =
3339 myEditor.Transform (*workElements, aTrsf, theCopy, theMakeGroups, theTargetMesh);
3341 if(theCopy || myPreviewMode)
3342 storeResult(myEditor); // store preview data or new elements
3344 if ( !myPreviewMode )
3346 if ( theTargetMesh )
3348 theTargetMesh->GetMeshDS()->Modified();
3352 myMesh->GetMeshDS()->Modified();
3353 myMesh->SetIsModified( true );
3356 return theMakeGroups ? getGroups(groupIds.get()) : 0;
3359 //=======================================================================
3362 //=======================================================================
3364 void SMESH_MeshEditor_i::Mirror(const SMESH::long_array & theIDsOfElements,
3365 const SMESH::AxisStruct & theAxis,
3366 SMESH::SMESH_MeshEditor::MirrorType theMirrorType,
3367 CORBA::Boolean theCopy)
3369 if ( !myPreviewMode ) {
3370 TPythonDump() << this << ".Mirror( "
3371 << theIDsOfElements << ", "
3373 << mirrorTypeName(theMirrorType) << ", "
3376 if ( theIDsOfElements.length() > 0 )
3378 TIDSortedElemSet elements;
3379 arrayToSet(theIDsOfElements, GetMeshDS(), elements);
3380 mirror(elements, theAxis, theMirrorType, theCopy, false);
3385 //=======================================================================
3386 //function : MirrorObject
3388 //=======================================================================
3390 void SMESH_MeshEditor_i::MirrorObject(SMESH::SMESH_IDSource_ptr theObject,
3391 const SMESH::AxisStruct & theAxis,
3392 SMESH::SMESH_MeshEditor::MirrorType theMirrorType,
3393 CORBA::Boolean theCopy)
3395 if ( !myPreviewMode ) {
3396 TPythonDump() << this << ".MirrorObject( "
3397 << theObject << ", "
3399 << mirrorTypeName(theMirrorType) << ", "
3402 TIDSortedElemSet elements;
3404 bool emptyIfIsMesh = myPreviewMode ? false : true;
3406 if (idSourceToSet(theObject, GetMeshDS(), elements, SMDSAbs_All, emptyIfIsMesh))
3407 mirror(elements, theAxis, theMirrorType, theCopy, false);
3410 //=======================================================================
3411 //function : MirrorMakeGroups
3413 //=======================================================================
3415 SMESH::ListOfGroups*
3416 SMESH_MeshEditor_i::MirrorMakeGroups(const SMESH::long_array& theIDsOfElements,
3417 const SMESH::AxisStruct& theMirror,
3418 SMESH::SMESH_MeshEditor::MirrorType theMirrorType)
3420 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
3422 SMESH::ListOfGroups * aGroups = 0;
3423 if ( theIDsOfElements.length() > 0 )
3425 TIDSortedElemSet elements;
3426 arrayToSet(theIDsOfElements, GetMeshDS(), elements);
3427 aGroups = mirror(elements, theMirror, theMirrorType, true, true);
3429 if (!myPreviewMode) {
3430 DumpGroupsList(aPythonDump, aGroups);
3431 aPythonDump << this << ".MirrorMakeGroups( "
3432 << theIDsOfElements << ", "
3433 << theMirror << ", "
3434 << mirrorTypeName(theMirrorType) << " )";
3439 //=======================================================================
3440 //function : MirrorObjectMakeGroups
3442 //=======================================================================
3444 SMESH::ListOfGroups*
3445 SMESH_MeshEditor_i::MirrorObjectMakeGroups(SMESH::SMESH_IDSource_ptr theObject,
3446 const SMESH::AxisStruct& theMirror,
3447 SMESH::SMESH_MeshEditor::MirrorType theMirrorType)
3449 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
3451 SMESH::ListOfGroups * aGroups = 0;
3452 TIDSortedElemSet elements;
3453 if ( idSourceToSet(theObject, GetMeshDS(), elements, SMDSAbs_All, /*emptyIfIsMesh=*/1))
3454 aGroups = mirror(elements, theMirror, theMirrorType, true, true);
3458 DumpGroupsList(aPythonDump,aGroups);
3459 aPythonDump << this << ".MirrorObjectMakeGroups( "
3460 << theObject << ", "
3461 << theMirror << ", "
3462 << mirrorTypeName(theMirrorType) << " )";
3467 //=======================================================================
3468 //function : MirrorMakeMesh
3470 //=======================================================================
3472 SMESH::SMESH_Mesh_ptr
3473 SMESH_MeshEditor_i::MirrorMakeMesh(const SMESH::long_array& theIDsOfElements,
3474 const SMESH::AxisStruct& theMirror,
3475 SMESH::SMESH_MeshEditor::MirrorType theMirrorType,
3476 CORBA::Boolean theCopyGroups,
3477 const char* theMeshName)
3479 SMESH_Mesh_i* mesh_i;
3480 SMESH::SMESH_Mesh_var mesh;
3481 { // open new scope to dump "MakeMesh" command
3482 // and then "GetGroups" using SMESH_Mesh::GetGroups()
3484 TPythonDump pydump; // to prevent dump at mesh creation
3486 mesh = makeMesh( theMeshName );
3487 mesh_i = SMESH::DownCast<SMESH_Mesh_i*>( mesh );
3488 if (mesh_i && theIDsOfElements.length() > 0 )
3490 TIDSortedElemSet elements;
3491 arrayToSet(theIDsOfElements, GetMeshDS(), elements);
3492 mirror(elements, theMirror, theMirrorType,
3493 false, theCopyGroups, & mesh_i->GetImpl());
3494 mesh_i->CreateGroupServants();
3497 if (!myPreviewMode) {
3498 pydump << mesh << " = " << this << ".MirrorMakeMesh( "
3499 << theIDsOfElements << ", "
3500 << theMirror << ", "
3501 << mirrorTypeName(theMirrorType) << ", "
3502 << theCopyGroups << ", '"
3503 << theMeshName << "' )";
3508 if (!myPreviewMode && mesh_i)
3509 mesh_i->GetGroups();
3511 return mesh._retn();
3514 //=======================================================================
3515 //function : MirrorObjectMakeMesh
3517 //=======================================================================
3519 SMESH::SMESH_Mesh_ptr
3520 SMESH_MeshEditor_i::MirrorObjectMakeMesh(SMESH::SMESH_IDSource_ptr theObject,
3521 const SMESH::AxisStruct& theMirror,
3522 SMESH::SMESH_MeshEditor::MirrorType theMirrorType,
3523 CORBA::Boolean theCopyGroups,
3524 const char* theMeshName)
3526 SMESH_Mesh_i* mesh_i;
3527 SMESH::SMESH_Mesh_var mesh;
3528 { // open new scope to dump "MakeMesh" command
3529 // and then "GetGroups" using SMESH_Mesh::GetGroups()
3531 TPythonDump pydump; // to prevent dump at mesh creation
3533 mesh = makeMesh( theMeshName );
3534 mesh_i = SMESH::DownCast<SMESH_Mesh_i*>( mesh );
3535 TIDSortedElemSet elements;
3537 idSourceToSet(theObject, GetMeshDS(), elements, SMDSAbs_All, /*emptyIfIsMesh=*/1))
3539 mirror(elements, theMirror, theMirrorType,
3540 false, theCopyGroups, & mesh_i->GetImpl());
3541 mesh_i->CreateGroupServants();
3543 if (!myPreviewMode) {
3544 pydump << mesh << " = " << this << ".MirrorObjectMakeMesh( "
3545 << theObject << ", "
3546 << theMirror << ", "
3547 << mirrorTypeName(theMirrorType) << ", "
3548 << theCopyGroups << ", '"
3549 << theMeshName << "' )";
3554 if (!myPreviewMode && mesh_i)
3555 mesh_i->GetGroups();
3557 return mesh._retn();
3560 //=======================================================================
3561 //function : translate
3563 //=======================================================================
3565 SMESH::ListOfGroups*
3566 SMESH_MeshEditor_i::translate(TIDSortedElemSet & theElements,
3567 const SMESH::DirStruct & theVector,
3568 CORBA::Boolean theCopy,
3570 ::SMESH_Mesh* theTargetMesh)
3574 if ( theTargetMesh )
3578 const SMESH::PointStruct * P = &theVector.PS;
3579 aTrsf.SetTranslation( gp_Vec( P->x, P->y, P->z ));
3581 TIDSortedElemSet copyElements;
3582 TIDSortedElemSet* workElements = &theElements;
3583 TPreviewMesh tmpMesh;
3584 SMESH_Mesh* mesh = myMesh;
3586 if ( myPreviewMode )
3588 tmpMesh.Copy( theElements, copyElements);
3589 if ( !theCopy && !theTargetMesh )
3591 TIDSortedElemSet elemsAround, elemsAroundCopy;
3592 getElementsAround( theElements, GetMeshDS(), elemsAround );
3593 tmpMesh.Copy( elemsAround, elemsAroundCopy);
3596 workElements = & copyElements;
3597 theMakeGroups = false;
3600 ::SMESH_MeshEditor::PGroupIDs groupIds =
3601 myEditor.Transform (*workElements, aTrsf, theCopy, theMakeGroups, theTargetMesh);
3603 if(theCopy || myPreviewMode)
3604 storeResult(myEditor);
3606 if ( !myPreviewMode )
3608 if ( theTargetMesh )
3610 theTargetMesh->GetMeshDS()->Modified();
3614 myMesh->GetMeshDS()->Modified();
3615 myMesh->SetIsModified( true );
3619 return theMakeGroups ? getGroups(groupIds.get()) : 0;
3622 //=======================================================================
3623 //function : Translate
3625 //=======================================================================
3627 void SMESH_MeshEditor_i::Translate(const SMESH::long_array & theIDsOfElements,
3628 const SMESH::DirStruct & theVector,
3629 CORBA::Boolean theCopy)
3631 if (!myPreviewMode) {
3632 TPythonDump() << this << ".Translate( "
3633 << theIDsOfElements << ", "
3634 << theVector << ", "
3637 if (theIDsOfElements.length()) {
3638 TIDSortedElemSet elements;
3639 arrayToSet(theIDsOfElements, GetMeshDS(), elements);
3640 translate(elements, theVector, theCopy, false);
3644 //=======================================================================
3645 //function : TranslateObject
3647 //=======================================================================
3649 void SMESH_MeshEditor_i::TranslateObject(SMESH::SMESH_IDSource_ptr theObject,
3650 const SMESH::DirStruct & theVector,
3651 CORBA::Boolean theCopy)
3653 if (!myPreviewMode) {
3654 TPythonDump() << this << ".TranslateObject( "
3655 << theObject << ", "
3656 << theVector << ", "
3659 TIDSortedElemSet elements;
3661 bool emptyIfIsMesh = myPreviewMode ? false : true;
3663 if (idSourceToSet(theObject, GetMeshDS(), elements, SMDSAbs_All, emptyIfIsMesh))
3664 translate(elements, theVector, theCopy, false);
3667 //=======================================================================
3668 //function : TranslateMakeGroups
3670 //=======================================================================
3672 SMESH::ListOfGroups*
3673 SMESH_MeshEditor_i::TranslateMakeGroups(const SMESH::long_array& theIDsOfElements,
3674 const SMESH::DirStruct& theVector)
3676 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
3678 SMESH::ListOfGroups * aGroups = 0;
3679 if (theIDsOfElements.length()) {
3680 TIDSortedElemSet elements;
3681 arrayToSet(theIDsOfElements, GetMeshDS(), elements);
3682 aGroups = translate(elements,theVector,true,true);
3684 if (!myPreviewMode) {
3685 DumpGroupsList(aPythonDump, aGroups);
3686 aPythonDump << this << ".TranslateMakeGroups( "
3687 << theIDsOfElements << ", "
3688 << theVector << " )";
3693 //=======================================================================
3694 //function : TranslateObjectMakeGroups
3696 //=======================================================================
3698 SMESH::ListOfGroups*
3699 SMESH_MeshEditor_i::TranslateObjectMakeGroups(SMESH::SMESH_IDSource_ptr theObject,
3700 const SMESH::DirStruct& theVector)
3702 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
3704 SMESH::ListOfGroups * aGroups = 0;
3705 TIDSortedElemSet elements;
3706 if (idSourceToSet(theObject, GetMeshDS(), elements, SMDSAbs_All, /*emptyIfIsMesh=*/1))
3707 aGroups = translate(elements, theVector, true, true);
3709 if (!myPreviewMode) {
3710 DumpGroupsList(aPythonDump, aGroups);
3711 aPythonDump << this << ".TranslateObjectMakeGroups( "
3712 << theObject << ", "
3713 << theVector << " )";
3718 //=======================================================================
3719 //function : TranslateMakeMesh
3721 //=======================================================================
3723 SMESH::SMESH_Mesh_ptr
3724 SMESH_MeshEditor_i::TranslateMakeMesh(const SMESH::long_array& theIDsOfElements,
3725 const SMESH::DirStruct& theVector,
3726 CORBA::Boolean theCopyGroups,
3727 const char* theMeshName)
3729 SMESH_Mesh_i* mesh_i;
3730 SMESH::SMESH_Mesh_var mesh;
3732 { // open new scope to dump "MakeMesh" command
3733 // and then "GetGroups" using SMESH_Mesh::GetGroups()
3735 TPythonDump pydump; // to prevent dump at mesh creation
3737 mesh = makeMesh( theMeshName );
3738 mesh_i = SMESH::DownCast<SMESH_Mesh_i*>( mesh );
3740 if ( mesh_i && theIDsOfElements.length() )
3742 TIDSortedElemSet elements;
3743 arrayToSet(theIDsOfElements, GetMeshDS(), elements);
3744 translate(elements, theVector, false, theCopyGroups, & mesh_i->GetImpl());
3745 mesh_i->CreateGroupServants();
3748 if ( !myPreviewMode ) {
3749 pydump << mesh << " = " << this << ".TranslateMakeMesh( "
3750 << theIDsOfElements << ", "
3751 << theVector << ", "
3752 << theCopyGroups << ", '"
3753 << theMeshName << "' )";
3758 if (!myPreviewMode && mesh_i)
3759 mesh_i->GetGroups();
3761 return mesh._retn();
3764 //=======================================================================
3765 //function : TranslateObjectMakeMesh
3767 //=======================================================================
3769 SMESH::SMESH_Mesh_ptr
3770 SMESH_MeshEditor_i::TranslateObjectMakeMesh(SMESH::SMESH_IDSource_ptr theObject,
3771 const SMESH::DirStruct& theVector,
3772 CORBA::Boolean theCopyGroups,
3773 const char* theMeshName)
3775 SMESH_Mesh_i* mesh_i;
3776 SMESH::SMESH_Mesh_var mesh;
3777 { // open new scope to dump "MakeMesh" command
3778 // and then "GetGroups" using SMESH_Mesh::GetGroups()
3780 TPythonDump pydump; // to prevent dump at mesh creation
3781 mesh = makeMesh( theMeshName );
3782 mesh_i = SMESH::DownCast<SMESH_Mesh_i*>( mesh );
3784 TIDSortedElemSet elements;
3786 idSourceToSet(theObject, GetMeshDS(), elements, SMDSAbs_All, /*emptyIfIsMesh=*/1))
3788 translate(elements, theVector,false, theCopyGroups, & mesh_i->GetImpl());
3789 mesh_i->CreateGroupServants();
3791 if ( !myPreviewMode ) {
3792 pydump << mesh << " = " << this << ".TranslateObjectMakeMesh( "
3793 << theObject << ", "
3794 << theVector << ", "
3795 << theCopyGroups << ", '"
3796 << theMeshName << "' )";
3801 if (!myPreviewMode && mesh_i)
3802 mesh_i->GetGroups();
3804 return mesh._retn();
3807 //=======================================================================
3810 //=======================================================================
3812 SMESH::ListOfGroups*
3813 SMESH_MeshEditor_i::rotate(TIDSortedElemSet & theElements,
3814 const SMESH::AxisStruct & theAxis,
3815 CORBA::Double theAngle,
3816 CORBA::Boolean theCopy,
3818 ::SMESH_Mesh* theTargetMesh)
3822 if ( theTargetMesh )
3825 gp_Pnt P ( theAxis.x, theAxis.y, theAxis.z );
3826 gp_Vec V ( theAxis.vx, theAxis.vy, theAxis.vz );
3829 aTrsf.SetRotation( gp_Ax1( P, V ), theAngle);
3831 TIDSortedElemSet copyElements;
3832 TIDSortedElemSet* workElements = &theElements;
3833 TPreviewMesh tmpMesh;
3834 SMESH_Mesh* mesh = myMesh;
3836 if ( myPreviewMode ) {
3837 tmpMesh.Copy( theElements, copyElements );
3838 if ( !theCopy && !theTargetMesh )
3840 TIDSortedElemSet elemsAround, elemsAroundCopy;
3841 getElementsAround( theElements, GetMeshDS(), elemsAround );
3842 tmpMesh.Copy( elemsAround, elemsAroundCopy);
3845 workElements = ©Elements;
3846 theMakeGroups = false;
3849 ::SMESH_MeshEditor::PGroupIDs groupIds =
3850 myEditor.Transform (*workElements, aTrsf, theCopy, theMakeGroups, theTargetMesh);
3852 if(theCopy || myPreviewMode)
3853 storeResult(myEditor);
3855 if ( !myPreviewMode )
3857 if ( theTargetMesh )
3859 theTargetMesh->GetMeshDS()->Modified();
3863 myMesh->GetMeshDS()->Modified();
3864 myMesh->SetIsModified( true );
3868 return theMakeGroups ? getGroups(groupIds.get()) : 0;
3871 //=======================================================================
3874 //=======================================================================
3876 void SMESH_MeshEditor_i::Rotate(const SMESH::long_array & theIDsOfElements,
3877 const SMESH::AxisStruct & theAxis,
3878 CORBA::Double theAngle,
3879 CORBA::Boolean theCopy)
3881 if (!myPreviewMode) {
3882 TPythonDump() << this << ".Rotate( "
3883 << theIDsOfElements << ", "
3885 << TVar( theAngle ) << ", "
3888 if (theIDsOfElements.length() > 0)
3890 TIDSortedElemSet elements;
3891 arrayToSet(theIDsOfElements, GetMeshDS(), elements);
3892 rotate(elements,theAxis,theAngle,theCopy,false);
3896 //=======================================================================
3897 //function : RotateObject
3899 //=======================================================================
3901 void SMESH_MeshEditor_i::RotateObject(SMESH::SMESH_IDSource_ptr theObject,
3902 const SMESH::AxisStruct & theAxis,
3903 CORBA::Double theAngle,
3904 CORBA::Boolean theCopy)
3906 if ( !myPreviewMode ) {
3907 TPythonDump() << this << ".RotateObject( "
3908 << theObject << ", "
3910 << TVar( theAngle ) << ", "
3913 TIDSortedElemSet elements;
3914 bool emptyIfIsMesh = myPreviewMode ? false : true;
3915 if (idSourceToSet(theObject, GetMeshDS(), elements, SMDSAbs_All, emptyIfIsMesh))
3916 rotate(elements,theAxis,theAngle,theCopy,false);
3919 //=======================================================================
3920 //function : RotateMakeGroups
3922 //=======================================================================
3924 SMESH::ListOfGroups*
3925 SMESH_MeshEditor_i::RotateMakeGroups(const SMESH::long_array& theIDsOfElements,
3926 const SMESH::AxisStruct& theAxis,
3927 CORBA::Double theAngle)
3929 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
3931 SMESH::ListOfGroups * aGroups = 0;
3932 if (theIDsOfElements.length() > 0)
3934 TIDSortedElemSet elements;
3935 arrayToSet(theIDsOfElements, GetMeshDS(), elements);
3936 aGroups = rotate(elements,theAxis,theAngle,true,true);
3938 if (!myPreviewMode) {
3939 DumpGroupsList(aPythonDump, aGroups);
3940 aPythonDump << this << ".RotateMakeGroups( "
3941 << theIDsOfElements << ", "
3943 << TVar( theAngle ) << " )";
3948 //=======================================================================
3949 //function : RotateObjectMakeGroups
3951 //=======================================================================
3953 SMESH::ListOfGroups*
3954 SMESH_MeshEditor_i::RotateObjectMakeGroups(SMESH::SMESH_IDSource_ptr theObject,
3955 const SMESH::AxisStruct& theAxis,
3956 CORBA::Double theAngle)
3958 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
3960 SMESH::ListOfGroups * aGroups = 0;
3961 TIDSortedElemSet elements;
3962 if (idSourceToSet(theObject, GetMeshDS(), elements, SMDSAbs_All, /*emptyIfIsMesh=*/1))
3963 aGroups = rotate(elements, theAxis, theAngle, true, true);
3965 if (!myPreviewMode) {
3966 DumpGroupsList(aPythonDump, aGroups);
3967 aPythonDump << this << ".RotateObjectMakeGroups( "
3968 << theObject << ", "
3970 << TVar( theAngle ) << " )";
3975 //=======================================================================
3976 //function : RotateMakeMesh
3978 //=======================================================================
3980 SMESH::SMESH_Mesh_ptr
3981 SMESH_MeshEditor_i::RotateMakeMesh(const SMESH::long_array& theIDsOfElements,
3982 const SMESH::AxisStruct& theAxis,
3983 CORBA::Double theAngleInRadians,
3984 CORBA::Boolean theCopyGroups,
3985 const char* theMeshName)
3987 SMESH::SMESH_Mesh_var mesh;
3988 SMESH_Mesh_i* mesh_i;
3990 { // open new scope to dump "MakeMesh" command
3991 // and then "GetGroups" using SMESH_Mesh::GetGroups()
3993 TPythonDump pydump; // to prevent dump at mesh creation
3995 mesh = makeMesh( theMeshName );
3996 mesh_i = SMESH::DownCast<SMESH_Mesh_i*>( mesh );
3998 if ( mesh_i && theIDsOfElements.length() > 0 )
4000 TIDSortedElemSet elements;
4001 arrayToSet(theIDsOfElements, GetMeshDS(), elements);
4002 rotate(elements, theAxis, theAngleInRadians,
4003 false, theCopyGroups, & mesh_i->GetImpl());
4004 mesh_i->CreateGroupServants();
4006 if ( !myPreviewMode ) {
4007 pydump << mesh << " = " << this << ".RotateMakeMesh( "
4008 << theIDsOfElements << ", "
4010 << TVar( theAngleInRadians ) << ", "
4011 << theCopyGroups << ", '"
4012 << theMeshName << "' )";
4017 if (!myPreviewMode && mesh_i && theIDsOfElements.length() > 0 )
4018 mesh_i->GetGroups();
4020 return mesh._retn();
4023 //=======================================================================
4024 //function : RotateObjectMakeMesh
4026 //=======================================================================
4028 SMESH::SMESH_Mesh_ptr
4029 SMESH_MeshEditor_i::RotateObjectMakeMesh(SMESH::SMESH_IDSource_ptr theObject,
4030 const SMESH::AxisStruct& theAxis,
4031 CORBA::Double theAngleInRadians,
4032 CORBA::Boolean theCopyGroups,
4033 const char* theMeshName)
4035 SMESH::SMESH_Mesh_var mesh;
4036 SMESH_Mesh_i* mesh_i;
4038 {// open new scope to dump "MakeMesh" command
4039 // and then "GetGroups" using SMESH_Mesh::GetGroups()
4041 TPythonDump pydump; // to prevent dump at mesh creation
4042 mesh = makeMesh( theMeshName );
4043 mesh_i = SMESH::DownCast<SMESH_Mesh_i*>( mesh );
4045 TIDSortedElemSet elements;
4047 idSourceToSet(theObject, GetMeshDS(), elements, SMDSAbs_All, /*emptyIfIsMesh=*/1))
4049 rotate(elements, theAxis, theAngleInRadians,
4050 false, theCopyGroups, & mesh_i->GetImpl());
4051 mesh_i->CreateGroupServants();
4053 if ( !myPreviewMode ) {
4054 pydump << mesh << " = " << this << ".RotateObjectMakeMesh( "
4055 << theObject << ", "
4057 << TVar( theAngleInRadians ) << ", "
4058 << theCopyGroups << ", '"
4059 << theMeshName << "' )";
4064 if (!myPreviewMode && mesh_i)
4065 mesh_i->GetGroups();
4067 return mesh._retn();
4070 //=======================================================================
4073 //=======================================================================
4075 SMESH::ListOfGroups*
4076 SMESH_MeshEditor_i::scale(SMESH::SMESH_IDSource_ptr theObject,
4077 const SMESH::PointStruct& thePoint,
4078 const SMESH::double_array& theScaleFact,
4079 CORBA::Boolean theCopy,
4081 ::SMESH_Mesh* theTargetMesh)
4084 if ( theScaleFact.length() < 1 )
4085 THROW_SALOME_CORBA_EXCEPTION("Scale factor not given", SALOME::BAD_PARAM);
4086 if ( theScaleFact.length() == 2 )
4087 THROW_SALOME_CORBA_EXCEPTION("Invalid nb of scale factors : 2", SALOME::BAD_PARAM);
4089 if ( theTargetMesh )
4092 TIDSortedElemSet elements;
4093 bool emptyIfIsMesh = myPreviewMode ? false : true;
4094 if ( !idSourceToSet(theObject, GetMeshDS(), elements, SMDSAbs_All, emptyIfIsMesh))
4099 (theScaleFact.length() == 1) ? theScaleFact[0] : theScaleFact[1],
4100 (theScaleFact.length() == 1) ? theScaleFact[0] : theScaleFact[2],
4102 double tol = std::numeric_limits<double>::max();
4104 aTrsf.SetValues( S[0], 0, 0, thePoint.x * (1-S[0]),
4105 0, S[1], 0, thePoint.y * (1-S[1]),
4106 0, 0, S[2], thePoint.z * (1-S[2]), tol, tol);
4108 TIDSortedElemSet copyElements;
4109 TPreviewMesh tmpMesh;
4110 TIDSortedElemSet* workElements = &elements;
4111 SMESH_Mesh* mesh = myMesh;
4113 if ( myPreviewMode )
4115 tmpMesh.Copy( elements, copyElements);
4116 if ( !theCopy && !theTargetMesh )
4118 TIDSortedElemSet elemsAround, elemsAroundCopy;
4119 getElementsAround( elements, GetMeshDS(), elemsAround );
4120 tmpMesh.Copy( elemsAround, elemsAroundCopy);
4123 workElements = & copyElements;
4124 theMakeGroups = false;
4127 ::SMESH_MeshEditor::PGroupIDs groupIds =
4128 myEditor.Transform (*workElements, aTrsf, theCopy, theMakeGroups, theTargetMesh);
4130 if(theCopy || myPreviewMode )
4131 storeResult(myEditor);
4133 if ( !myPreviewMode )
4135 if ( theTargetMesh )
4137 theTargetMesh->GetMeshDS()->Modified();
4141 myMesh->GetMeshDS()->Modified();
4142 myMesh->SetIsModified( true );
4146 return theMakeGroups ? getGroups(groupIds.get()) : 0;
4149 //=======================================================================
4152 //=======================================================================
4154 void SMESH_MeshEditor_i::Scale(SMESH::SMESH_IDSource_ptr theObject,
4155 const SMESH::PointStruct& thePoint,
4156 const SMESH::double_array& theScaleFact,
4157 CORBA::Boolean theCopy)
4159 if ( !myPreviewMode ) {
4160 TPythonDump() << this << ".Scale( "
4161 << theObject << ", "
4163 << TVar( theScaleFact ) << ", "
4166 scale(theObject, thePoint, theScaleFact, theCopy, false);
4170 //=======================================================================
4171 //function : ScaleMakeGroups
4173 //=======================================================================
4175 SMESH::ListOfGroups*
4176 SMESH_MeshEditor_i::ScaleMakeGroups(SMESH::SMESH_IDSource_ptr theObject,
4177 const SMESH::PointStruct& thePoint,
4178 const SMESH::double_array& theScaleFact)
4180 TPythonDump aPythonDump; // it is here to prevent dump of GetGroups()
4182 SMESH::ListOfGroups * aGroups = scale(theObject, thePoint, theScaleFact, true, true);
4183 if (!myPreviewMode) {
4184 DumpGroupsList(aPythonDump, aGroups);
4185 aPythonDump << this << ".Scale("
4188 << TVar( theScaleFact ) << ",True,True)";
4194 //=======================================================================
4195 //function : ScaleMakeMesh
4197 //=======================================================================
4199 SMESH::SMESH_Mesh_ptr
4200 SMESH_MeshEditor_i::ScaleMakeMesh(SMESH::SMESH_IDSource_ptr theObject,
4201 const SMESH::PointStruct& thePoint,
4202 const SMESH::double_array& theScaleFact,
4203 CORBA::Boolean theCopyGroups,
4204 const char* theMeshName)
4206 SMESH_Mesh_i* mesh_i;
4207 SMESH::SMESH_Mesh_var mesh;
4208 { // open new scope to dump "MakeMesh" command
4209 // and then "GetGroups" using SMESH_Mesh::GetGroups()
4211 TPythonDump pydump; // to prevent dump at mesh creation
4212 mesh = makeMesh( theMeshName );
4213 mesh_i = SMESH::DownCast<SMESH_Mesh_i*>( mesh );
4217 scale(theObject, thePoint, theScaleFact,false, theCopyGroups, & mesh_i->GetImpl());
4218 mesh_i->CreateGroupServants();
4220 if ( !myPreviewMode )
4221 pydump << mesh << " = " << this << ".ScaleMakeMesh( "
4222 << theObject << ", "
4224 << TVar( theScaleFact ) << ", "
4225 << theCopyGroups << ", '"
4226 << theMeshName << "' )";
4230 if (!myPreviewMode && mesh_i)
4231 mesh_i->GetGroups();
4233 return mesh._retn();
4237 //=======================================================================
4238 //function : FindCoincidentNodes
4240 //=======================================================================
4242 void SMESH_MeshEditor_i::FindCoincidentNodes (CORBA::Double Tolerance,
4243 SMESH::array_of_long_array_out GroupsOfNodes)
4247 ::SMESH_MeshEditor::TListOfListOfNodes aListOfListOfNodes;
4248 TIDSortedNodeSet nodes; // no input nodes
4249 myEditor.FindCoincidentNodes( nodes, Tolerance, aListOfListOfNodes );
4251 GroupsOfNodes = new SMESH::array_of_long_array;
4252 GroupsOfNodes->length( aListOfListOfNodes.size() );
4253 ::SMESH_MeshEditor::TListOfListOfNodes::iterator llIt = aListOfListOfNodes.begin();
4254 for ( CORBA::Long i = 0; llIt != aListOfListOfNodes.end(); llIt++, i++ ) {
4255 list< const SMDS_MeshNode* >& aListOfNodes = *llIt;
4256 list< const SMDS_MeshNode* >::iterator lIt = aListOfNodes.begin();;
4257 SMESH::long_array& aGroup = (*GroupsOfNodes)[ i ];
4258 aGroup.length( aListOfNodes.size() );
4259 for ( int j = 0; lIt != aListOfNodes.end(); lIt++, j++ )
4260 aGroup[ j ] = (*lIt)->GetID();
4262 TPythonDump() << "coincident_nodes = " << this << ".FindCoincidentNodes( "
4263 << Tolerance << " )";
4266 //=======================================================================
4267 //function : FindCoincidentNodesOnPart
4269 //=======================================================================
4270 void SMESH_MeshEditor_i::FindCoincidentNodesOnPart(SMESH::SMESH_IDSource_ptr theObject,
4271 CORBA::Double Tolerance,
4272 SMESH::array_of_long_array_out GroupsOfNodes)
4276 TIDSortedNodeSet nodes;
4277 idSourceToNodeSet( theObject, GetMeshDS(), nodes );
4279 ::SMESH_MeshEditor::TListOfListOfNodes aListOfListOfNodes;
4281 myEditor.FindCoincidentNodes( nodes, Tolerance, aListOfListOfNodes );
4283 GroupsOfNodes = new SMESH::array_of_long_array;
4284 GroupsOfNodes->length( aListOfListOfNodes.size() );
4285 ::SMESH_MeshEditor::TListOfListOfNodes::iterator llIt = aListOfListOfNodes.begin();
4286 for ( CORBA::Long i = 0; llIt != aListOfListOfNodes.end(); llIt++, i++ )
4288 list< const SMDS_MeshNode* >& aListOfNodes = *llIt;
4289 list< const SMDS_MeshNode* >::iterator lIt = aListOfNodes.begin();;
4290 SMESH::long_array& aGroup = (*GroupsOfNodes)[ i ];
4291 aGroup.length( aListOfNodes.size() );
4292 for ( int j = 0; lIt != aListOfNodes.end(); lIt++, j++ )
4293 aGroup[ j ] = (*lIt)->GetID();
4295 TPythonDump() << "coincident_nodes_on_part = " << this << ".FindCoincidentNodesOnPart( "
4297 << Tolerance << " )";
4300 //================================================================================
4302 * \brief Finds nodes coinsident with Tolerance within Object excluding nodes within
4303 * ExceptSubMeshOrGroups
4305 //================================================================================
4307 void SMESH_MeshEditor_i::
4308 FindCoincidentNodesOnPartBut(SMESH::SMESH_IDSource_ptr theObject,
4309 CORBA::Double theTolerance,
4310 SMESH::array_of_long_array_out theGroupsOfNodes,
4311 const SMESH::ListOfIDSources& theExceptSubMeshOrGroups)
4315 TIDSortedNodeSet nodes;
4316 idSourceToNodeSet( theObject, GetMeshDS(), nodes );
4318 for ( int i = 0; i < theExceptSubMeshOrGroups.length(); ++i )
4320 TIDSortedNodeSet exceptNodes;
4321 idSourceToNodeSet( theExceptSubMeshOrGroups[i], GetMeshDS(), exceptNodes );
4322 TIDSortedNodeSet::iterator avoidNode = exceptNodes.begin();
4323 for ( ; avoidNode != exceptNodes.end(); ++avoidNode)
4324 nodes.erase( *avoidNode );
4326 ::SMESH_MeshEditor::TListOfListOfNodes aListOfListOfNodes;
4328 myEditor.FindCoincidentNodes( nodes, theTolerance, aListOfListOfNodes );
4330 theGroupsOfNodes = new SMESH::array_of_long_array;
4331 theGroupsOfNodes->length( aListOfListOfNodes.size() );
4332 ::SMESH_MeshEditor::TListOfListOfNodes::iterator llIt = aListOfListOfNodes.begin();
4333 for ( CORBA::Long i = 0; llIt != aListOfListOfNodes.end(); llIt++, i++ )
4335 list< const SMDS_MeshNode* >& aListOfNodes = *llIt;
4336 list< const SMDS_MeshNode* >::iterator lIt = aListOfNodes.begin();;
4337 SMESH::long_array& aGroup = (*theGroupsOfNodes)[ i ];
4338 aGroup.length( aListOfNodes.size() );
4339 for ( int j = 0; lIt != aListOfNodes.end(); lIt++, j++ )
4340 aGroup[ j ] = (*lIt)->GetID();
4342 TPythonDump() << "coincident_nodes_on_part = " << this << ".FindCoincidentNodesOnPartBut( "
4344 << theTolerance << ", "
4345 << theExceptSubMeshOrGroups << " )";
4348 //=======================================================================
4349 //function : MergeNodes
4351 //=======================================================================
4353 void SMESH_MeshEditor_i::MergeNodes (const SMESH::array_of_long_array& GroupsOfNodes)
4357 SMESHDS_Mesh* aMesh = GetMeshDS();
4359 TPythonDump aTPythonDump;
4360 aTPythonDump << this << ".MergeNodes([";
4361 ::SMESH_MeshEditor::TListOfListOfNodes aListOfListOfNodes;
4362 for (int i = 0; i < GroupsOfNodes.length(); i++)
4364 const SMESH::long_array& aNodeGroup = GroupsOfNodes[ i ];
4365 aListOfListOfNodes.push_back( list< const SMDS_MeshNode* >() );
4366 list< const SMDS_MeshNode* >& aListOfNodes = aListOfListOfNodes.back();
4367 for ( int j = 0; j < aNodeGroup.length(); j++ )
4369 CORBA::Long index = aNodeGroup[ j ];
4370 const SMDS_MeshNode * node = aMesh->FindNode(index);
4372 aListOfNodes.push_back( node );
4374 if ( aListOfNodes.size() < 2 )
4375 aListOfListOfNodes.pop_back();
4377 if ( i > 0 ) aTPythonDump << ", ";
4378 aTPythonDump << aNodeGroup;
4380 myEditor.MergeNodes( aListOfListOfNodes );
4382 aTPythonDump << "])";
4383 myMesh->GetMeshDS()->Modified();
4384 myMesh->SetIsModified( true );
4387 //=======================================================================
4388 //function : FindEqualElements
4390 //=======================================================================
4391 void SMESH_MeshEditor_i::FindEqualElements(SMESH::SMESH_IDSource_ptr theObject,
4392 SMESH::array_of_long_array_out GroupsOfElementsID)
4396 SMESH::SMESH_GroupBase_var group = SMESH::SMESH_GroupBase::_narrow(theObject);
4397 if ( !(!group->_is_nil() && group->GetType() == SMESH::NODE) )
4399 typedef list<int> TListOfIDs;
4400 set<const SMDS_MeshElement*> elems;
4401 SMESH::long_array_var aElementsId = theObject->GetIDs();
4402 SMESHDS_Mesh* aMesh = GetMeshDS();
4404 for(int i = 0; i < aElementsId->length(); i++) {
4405 CORBA::Long anID = aElementsId[i];
4406 const SMDS_MeshElement * elem = aMesh->FindElement(anID);
4412 ::SMESH_MeshEditor::TListOfListOfElementsID aListOfListOfElementsID;
4413 myEditor.FindEqualElements( elems, aListOfListOfElementsID );
4415 GroupsOfElementsID = new SMESH::array_of_long_array;
4416 GroupsOfElementsID->length( aListOfListOfElementsID.size() );
4418 ::SMESH_MeshEditor::TListOfListOfElementsID::iterator arraysIt = aListOfListOfElementsID.begin();
4419 for (CORBA::Long j = 0; arraysIt != aListOfListOfElementsID.end(); ++arraysIt, ++j) {
4420 SMESH::long_array& aGroup = (*GroupsOfElementsID)[ j ];
4421 TListOfIDs& listOfIDs = *arraysIt;
4422 aGroup.length( listOfIDs.size() );
4423 TListOfIDs::iterator idIt = listOfIDs.begin();
4424 for (int k = 0; idIt != listOfIDs.end(); ++idIt, ++k ) {
4425 aGroup[ k ] = *idIt;
4429 TPythonDump() << "equal_elements = " << this << ".FindEqualElements( "
4434 //=======================================================================
4435 //function : MergeElements
4437 //=======================================================================
4439 void SMESH_MeshEditor_i::MergeElements(const SMESH::array_of_long_array& GroupsOfElementsID)
4443 TPythonDump aTPythonDump;
4444 aTPythonDump << this << ".MergeElements( [";
4446 ::SMESH_MeshEditor::TListOfListOfElementsID aListOfListOfElementsID;
4448 for (int i = 0; i < GroupsOfElementsID.length(); i++) {
4449 const SMESH::long_array& anElemsIDGroup = GroupsOfElementsID[ i ];
4450 aListOfListOfElementsID.push_back( list< int >() );
4451 list< int >& aListOfElemsID = aListOfListOfElementsID.back();
4452 for ( int j = 0; j < anElemsIDGroup.length(); j++ ) {
4453 CORBA::Long id = anElemsIDGroup[ j ];
4454 aListOfElemsID.push_back( id );
4456 if ( aListOfElemsID.size() < 2 )
4457 aListOfListOfElementsID.pop_back();
4458 if ( i > 0 ) aTPythonDump << ", ";
4459 aTPythonDump << anElemsIDGroup;
4462 myEditor.MergeElements(aListOfListOfElementsID);
4463 myMesh->GetMeshDS()->Modified();
4464 myMesh->SetIsModified( true );
4466 aTPythonDump << "] )";
4469 //=======================================================================
4470 //function : MergeEqualElements
4472 //=======================================================================
4474 void SMESH_MeshEditor_i::MergeEqualElements()
4478 myEditor.MergeEqualElements();
4480 myMesh->GetMeshDS()->Modified();
4482 TPythonDump() << this << ".MergeEqualElements()";
4485 //=============================================================================
4487 * Move the node to a given point
4489 //=============================================================================
4491 CORBA::Boolean SMESH_MeshEditor_i::MoveNode(CORBA::Long NodeID,
4496 initData(/*deleteSearchers=*/false);
4498 const SMDS_MeshNode * node = GetMeshDS()->FindNode( NodeID );
4502 if ( theNodeSearcher )
4503 theSearchersDeleter.Set( myMesh ); // remove theNodeSearcher if mesh is other
4505 if ( myPreviewMode ) // make preview data
4507 // in a preview mesh, make edges linked to a node
4508 TPreviewMesh tmpMesh;
4509 TIDSortedElemSet linkedNodes;
4510 ::SMESH_MeshEditor::GetLinkedNodes( node, linkedNodes );
4511 TIDSortedElemSet::iterator nIt = linkedNodes.begin();
4512 SMDS_MeshNode *nodeCpy1 = tmpMesh.Copy(node);
4513 for ( ; nIt != linkedNodes.end(); ++nIt )
4515 SMDS_MeshNode *nodeCpy2 = tmpMesh.Copy ( cast2Node( *nIt ));
4516 tmpMesh.GetMeshDS()->AddEdge(nodeCpy1, nodeCpy2);
4520 tmpMesh.GetMeshDS()->MoveNode(nodeCpy1, x, y, z);
4521 // fill preview data
4522 storeResult( myEditor );
4524 else if ( theNodeSearcher ) // move node and update theNodeSearcher data accordingly
4525 theNodeSearcher->MoveNode(node, gp_Pnt( x,y,z ));
4527 GetMeshDS()->MoveNode(node, x, y, z);
4529 if ( !myPreviewMode )
4531 // Update Python script
4532 TPythonDump() << "isDone = " << this << ".MoveNode( "
4533 << NodeID << ", " << TVar(x) << ", " << TVar(y) << ", " << TVar(z) << " )";
4534 myMesh->GetMeshDS()->Modified();
4535 myMesh->SetIsModified( true );
4541 //================================================================================
4543 * \brief Return ID of node closest to a given point
4545 //================================================================================
4547 CORBA::Long SMESH_MeshEditor_i::FindNodeClosestTo(CORBA::Double x,
4551 theSearchersDeleter.Set( myMesh ); // remove theNodeSearcher if mesh is other
4553 if ( !theNodeSearcher ) {
4554 theNodeSearcher = myEditor.GetNodeSearcher();
4557 if ( const SMDS_MeshNode* node = theNodeSearcher->FindClosestTo( p ))
4558 return node->GetID();
4563 //================================================================================
4565 * \brief If the given ID is a valid node ID (nodeID > 0), just move this node, else
4566 * move the node closest to the point to point's location and return ID of the node
4568 //================================================================================
4570 CORBA::Long SMESH_MeshEditor_i::MoveClosestNodeToPoint(CORBA::Double x,
4573 CORBA::Long theNodeID)
4575 // We keep theNodeSearcher until any mesh modification:
4576 // 1) initData() deletes theNodeSearcher at any edition,
4577 // 2) TSearchersDeleter - at any mesh compute event and mesh change
4579 initData(/*deleteSearchers=*/false);
4581 theSearchersDeleter.Set( myMesh ); // remove theNodeSearcher if mesh is other
4583 int nodeID = theNodeID;
4584 const SMDS_MeshNode* node = GetMeshDS()->FindNode( nodeID );
4585 if ( !node ) // preview moving node
4587 if ( !theNodeSearcher ) {
4588 theNodeSearcher = myEditor.GetNodeSearcher();
4591 node = theNodeSearcher->FindClosestTo( p );
4594 nodeID = node->GetID();
4595 if ( myPreviewMode ) // make preview data
4597 // in a preview mesh, make edges linked to a node
4598 TPreviewMesh tmpMesh;
4599 TIDSortedElemSet linkedNodes;
4600 ::SMESH_MeshEditor::GetLinkedNodes( node, linkedNodes );
4601 TIDSortedElemSet::iterator nIt = linkedNodes.begin();
4602 for ( ; nIt != linkedNodes.end(); ++nIt )
4604 SMDS_LinearEdge edge( node, cast2Node( *nIt ));
4605 tmpMesh.Copy( &edge );
4608 node = tmpMesh.GetMeshDS()->FindNode( nodeID );
4610 tmpMesh.GetMeshDS()->MoveNode(node, x, y, z);
4611 // fill preview data
4612 storeResult( myEditor );
4614 else if ( theNodeSearcher ) // move node and update theNodeSearcher data accordingly
4616 theNodeSearcher->MoveNode(node, gp_Pnt( x,y,z ));
4620 GetMeshDS()->MoveNode(node, x, y, z);
4624 if ( !myPreviewMode )
4626 TPythonDump() << "nodeID = " << this
4627 << ".MoveClosestNodeToPoint( "<< x << ", " << y << ", " << z
4628 << ", " << nodeID << " )";
4630 myMesh->GetMeshDS()->Modified();
4631 myMesh->SetIsModified( true );
4637 //=======================================================================
4639 * Return elements of given type where the given point is IN or ON.
4641 * 'ALL' type means elements of any type excluding nodes
4643 //=======================================================================
4645 SMESH::long_array* SMESH_MeshEditor_i::FindElementsByPoint(CORBA::Double x,
4648 SMESH::ElementType type)
4650 SMESH::long_array_var res = new SMESH::long_array;
4651 vector< const SMDS_MeshElement* > foundElems;
4653 theSearchersDeleter.Set( myMesh );
4654 if ( !theElementSearcher ) {
4655 theElementSearcher = myEditor.GetElementSearcher();
4657 theElementSearcher->FindElementsByPoint( gp_Pnt( x,y,z ),
4658 SMDSAbs_ElementType( type ),
4660 res->length( foundElems.size() );
4661 for ( int i = 0; i < foundElems.size(); ++i )
4662 res[i] = foundElems[i]->GetID();
4664 if ( !myPreviewMode ) // call from tui
4665 TPythonDump() << "res = " << this << ".FindElementsByPoint( "
4674 //=======================================================================
4675 //function : FindAmongElementsByPoint
4676 //purpose : Searching among the given elements, return elements of given type
4677 // where the given point is IN or ON.
4678 // 'ALL' type means elements of any type excluding nodes
4679 //=======================================================================
4682 SMESH_MeshEditor_i::FindAmongElementsByPoint(SMESH::SMESH_IDSource_ptr elementIDs,
4686 SMESH::ElementType type)
4688 SMESH::long_array_var res = new SMESH::long_array;
4690 SMESH::array_of_ElementType_var types = elementIDs->GetTypes();
4691 if ( types->length() == 1 && // a part contains only nodes or 0D elements
4692 ( types[0] == SMESH::NODE || types[0] == SMESH::ELEM0D || types[0] == SMESH::BALL) &&
4693 type != types[0] ) // but search of elements of dim > 0
4696 if ( SMESH::DownCast<SMESH_Mesh_i*>( elementIDs )) // elementIDs is the whole mesh
4697 return FindElementsByPoint( x,y,z, type );
4699 TIDSortedElemSet elements; // elems should live until FindElementsByPoint() finishes
4701 theSearchersDeleter.Set( myMesh, getPartIOR( elementIDs, type ));
4702 if ( !theElementSearcher )
4704 // create a searcher from elementIDs
4705 SMESH::SMESH_Mesh_var mesh = elementIDs->GetMesh();
4706 SMESHDS_Mesh* meshDS = SMESH::DownCast<SMESH_Mesh_i*>( mesh )->GetImpl().GetMeshDS();
4708 if ( !idSourceToSet( elementIDs, meshDS, elements,
4709 SMDSAbs_ElementType(type), /*emptyIfIsMesh=*/true))
4712 typedef SMDS_SetIterator<const SMDS_MeshElement*, TIDSortedElemSet::const_iterator > TIter;
4713 SMDS_ElemIteratorPtr elemsIt( new TIter( elements.begin(), elements.end() ));
4715 theElementSearcher = myEditor.GetElementSearcher(elemsIt);
4718 vector< const SMDS_MeshElement* > foundElems;
4720 theElementSearcher->FindElementsByPoint( gp_Pnt( x,y,z ),
4721 SMDSAbs_ElementType( type ),
4723 res->length( foundElems.size() );
4724 for ( int i = 0; i < foundElems.size(); ++i )
4725 res[i] = foundElems[i]->GetID();
4727 if ( !myPreviewMode ) // call from tui
4728 TPythonDump() << "res = " << this << ".FindAmongElementsByPoint( "
4729 << elementIDs << ", "
4738 //=======================================================================
4739 //function : GetPointState
4740 //purpose : Return point state in a closed 2D mesh in terms of TopAbs_State enumeration.
4741 // TopAbs_UNKNOWN state means that either mesh is wrong or the analysis fails.
4742 //=======================================================================
4744 CORBA::Short SMESH_MeshEditor_i::GetPointState(CORBA::Double x,
4748 theSearchersDeleter.Set( myMesh );
4749 if ( !theElementSearcher ) {
4750 theElementSearcher = myEditor.GetElementSearcher();
4752 return CORBA::Short( theElementSearcher->GetPointState( gp_Pnt( x,y,z )));
4755 //=======================================================================
4756 //function : convError
4758 //=======================================================================
4760 #define RETCASE(enm) case ::SMESH_MeshEditor::enm: return SMESH::SMESH_MeshEditor::enm;
4762 static SMESH::SMESH_MeshEditor::Sew_Error convError( const::SMESH_MeshEditor::Sew_Error e )
4766 RETCASE( SEW_BORDER1_NOT_FOUND );
4767 RETCASE( SEW_BORDER2_NOT_FOUND );
4768 RETCASE( SEW_BOTH_BORDERS_NOT_FOUND );
4769 RETCASE( SEW_BAD_SIDE_NODES );
4770 RETCASE( SEW_VOLUMES_TO_SPLIT );
4771 RETCASE( SEW_DIFF_NB_OF_ELEMENTS );
4772 RETCASE( SEW_TOPO_DIFF_SETS_OF_ELEMENTS );
4773 RETCASE( SEW_BAD_SIDE1_NODES );
4774 RETCASE( SEW_BAD_SIDE2_NODES );
4776 return SMESH::SMESH_MeshEditor::SEW_OK;
4779 //=======================================================================
4780 //function : SewFreeBorders
4782 //=======================================================================
4784 SMESH::SMESH_MeshEditor::Sew_Error
4785 SMESH_MeshEditor_i::SewFreeBorders(CORBA::Long FirstNodeID1,
4786 CORBA::Long SecondNodeID1,
4787 CORBA::Long LastNodeID1,
4788 CORBA::Long FirstNodeID2,
4789 CORBA::Long SecondNodeID2,
4790 CORBA::Long LastNodeID2,
4791 CORBA::Boolean CreatePolygons,
4792 CORBA::Boolean CreatePolyedrs)
4796 SMESHDS_Mesh* aMesh = GetMeshDS();
4798 const SMDS_MeshNode* aBorderFirstNode = aMesh->FindNode( FirstNodeID1 );
4799 const SMDS_MeshNode* aBorderSecondNode = aMesh->FindNode( SecondNodeID1 );
4800 const SMDS_MeshNode* aBorderLastNode = aMesh->FindNode( LastNodeID1 );
4801 const SMDS_MeshNode* aSide2FirstNode = aMesh->FindNode( FirstNodeID2 );
4802 const SMDS_MeshNode* aSide2SecondNode = aMesh->FindNode( SecondNodeID2 );
4803 const SMDS_MeshNode* aSide2ThirdNode = aMesh->FindNode( LastNodeID2 );
4805 if (!aBorderFirstNode ||
4806 !aBorderSecondNode||
4808 return SMESH::SMESH_MeshEditor::SEW_BORDER1_NOT_FOUND;
4809 if (!aSide2FirstNode ||
4810 !aSide2SecondNode ||
4812 return SMESH::SMESH_MeshEditor::SEW_BORDER2_NOT_FOUND;
4814 TPythonDump() << "error = " << this << ".SewFreeBorders( "
4815 << FirstNodeID1 << ", "
4816 << SecondNodeID1 << ", "
4817 << LastNodeID1 << ", "
4818 << FirstNodeID2 << ", "
4819 << SecondNodeID2 << ", "
4820 << LastNodeID2 << ", "
4821 << CreatePolygons<< ", "
4822 << CreatePolyedrs<< " )";
4824 SMESH::SMESH_MeshEditor::Sew_Error error =
4825 convError( myEditor.SewFreeBorder (aBorderFirstNode,
4835 storeResult(myEditor);
4837 myMesh->GetMeshDS()->Modified();
4838 myMesh->SetIsModified( true );
4844 //=======================================================================
4845 //function : SewConformFreeBorders
4847 //=======================================================================
4849 SMESH::SMESH_MeshEditor::Sew_Error
4850 SMESH_MeshEditor_i::SewConformFreeBorders(CORBA::Long FirstNodeID1,
4851 CORBA::Long SecondNodeID1,
4852 CORBA::Long LastNodeID1,
4853 CORBA::Long FirstNodeID2,
4854 CORBA::Long SecondNodeID2)
4858 SMESHDS_Mesh* aMesh = GetMeshDS();
4860 const SMDS_MeshNode* aBorderFirstNode = aMesh->FindNode( FirstNodeID1 );
4861 const SMDS_MeshNode* aBorderSecondNode = aMesh->FindNode( SecondNodeID1 );
4862 const SMDS_MeshNode* aBorderLastNode = aMesh->FindNode( LastNodeID1 );
4863 const SMDS_MeshNode* aSide2FirstNode = aMesh->FindNode( FirstNodeID2 );
4864 const SMDS_MeshNode* aSide2SecondNode = aMesh->FindNode( SecondNodeID2 );
4865 const SMDS_MeshNode* aSide2ThirdNode = 0;
4867 if (!aBorderFirstNode ||
4868 !aBorderSecondNode||
4870 return SMESH::SMESH_MeshEditor::SEW_BORDER1_NOT_FOUND;
4871 if (!aSide2FirstNode ||
4873 return SMESH::SMESH_MeshEditor::SEW_BORDER2_NOT_FOUND;
4875 TPythonDump() << "error = " << this << ".SewConformFreeBorders( "
4876 << FirstNodeID1 << ", "
4877 << SecondNodeID1 << ", "
4878 << LastNodeID1 << ", "
4879 << FirstNodeID2 << ", "
4880 << SecondNodeID2 << " )";
4882 SMESH::SMESH_MeshEditor::Sew_Error error =
4883 convError( myEditor.SewFreeBorder (aBorderFirstNode,
4892 storeResult(myEditor);
4894 myMesh->GetMeshDS()->Modified();
4895 myMesh->SetIsModified( true );
4901 //=======================================================================
4902 //function : SewBorderToSide
4904 //=======================================================================
4906 SMESH::SMESH_MeshEditor::Sew_Error
4907 SMESH_MeshEditor_i::SewBorderToSide(CORBA::Long FirstNodeIDOnFreeBorder,
4908 CORBA::Long SecondNodeIDOnFreeBorder,
4909 CORBA::Long LastNodeIDOnFreeBorder,
4910 CORBA::Long FirstNodeIDOnSide,
4911 CORBA::Long LastNodeIDOnSide,
4912 CORBA::Boolean CreatePolygons,
4913 CORBA::Boolean CreatePolyedrs)
4917 SMESHDS_Mesh* aMesh = GetMeshDS();
4919 const SMDS_MeshNode* aBorderFirstNode = aMesh->FindNode( FirstNodeIDOnFreeBorder );
4920 const SMDS_MeshNode* aBorderSecondNode = aMesh->FindNode( SecondNodeIDOnFreeBorder );
4921 const SMDS_MeshNode* aBorderLastNode = aMesh->FindNode( LastNodeIDOnFreeBorder );
4922 const SMDS_MeshNode* aSide2FirstNode = aMesh->FindNode( FirstNodeIDOnSide );
4923 const SMDS_MeshNode* aSide2SecondNode = aMesh->FindNode( LastNodeIDOnSide );
4924 const SMDS_MeshNode* aSide2ThirdNode = 0;
4926 if (!aBorderFirstNode ||
4927 !aBorderSecondNode||
4929 return SMESH::SMESH_MeshEditor::SEW_BORDER1_NOT_FOUND;
4930 if (!aSide2FirstNode ||
4932 return SMESH::SMESH_MeshEditor::SEW_BAD_SIDE_NODES;
4934 TPythonDump() << "error = " << this << ".SewBorderToSide( "
4935 << FirstNodeIDOnFreeBorder << ", "
4936 << SecondNodeIDOnFreeBorder << ", "
4937 << LastNodeIDOnFreeBorder << ", "
4938 << FirstNodeIDOnSide << ", "
4939 << LastNodeIDOnSide << ", "
4940 << CreatePolygons << ", "
4941 << CreatePolyedrs << ") ";
4943 SMESH::SMESH_MeshEditor::Sew_Error error =
4944 convError( myEditor.SewFreeBorder (aBorderFirstNode,
4954 storeResult(myEditor);
4956 myMesh->GetMeshDS()->Modified();
4957 myMesh->SetIsModified( true );
4963 //=======================================================================
4964 //function : SewSideElements
4966 //=======================================================================
4968 SMESH::SMESH_MeshEditor::Sew_Error
4969 SMESH_MeshEditor_i::SewSideElements(const SMESH::long_array& IDsOfSide1Elements,
4970 const SMESH::long_array& IDsOfSide2Elements,
4971 CORBA::Long NodeID1OfSide1ToMerge,
4972 CORBA::Long NodeID1OfSide2ToMerge,
4973 CORBA::Long NodeID2OfSide1ToMerge,
4974 CORBA::Long NodeID2OfSide2ToMerge)
4978 SMESHDS_Mesh* aMesh = GetMeshDS();
4980 const SMDS_MeshNode* aFirstNode1ToMerge = aMesh->FindNode( NodeID1OfSide1ToMerge );
4981 const SMDS_MeshNode* aFirstNode2ToMerge = aMesh->FindNode( NodeID1OfSide2ToMerge );
4982 const SMDS_MeshNode* aSecondNode1ToMerge = aMesh->FindNode( NodeID2OfSide1ToMerge );
4983 const SMDS_MeshNode* aSecondNode2ToMerge = aMesh->FindNode( NodeID2OfSide2ToMerge );
4985 if (!aFirstNode1ToMerge ||
4986 !aFirstNode2ToMerge )
4987 return SMESH::SMESH_MeshEditor::SEW_BAD_SIDE1_NODES;
4988 if (!aSecondNode1ToMerge||
4989 !aSecondNode2ToMerge)
4990 return SMESH::SMESH_MeshEditor::SEW_BAD_SIDE2_NODES;
4992 TIDSortedElemSet aSide1Elems, aSide2Elems;
4993 arrayToSet(IDsOfSide1Elements, aMesh, aSide1Elems);
4994 arrayToSet(IDsOfSide2Elements, aMesh, aSide2Elems);
4996 TPythonDump() << "error = " << this << ".SewSideElements( "
4997 << IDsOfSide1Elements << ", "
4998 << IDsOfSide2Elements << ", "
4999 << NodeID1OfSide1ToMerge << ", "
5000 << NodeID1OfSide2ToMerge << ", "
5001 << NodeID2OfSide1ToMerge << ", "
5002 << NodeID2OfSide2ToMerge << ")";
5004 SMESH::SMESH_MeshEditor::Sew_Error error =
5005 convError( myEditor.SewSideElements (aSide1Elems, aSide2Elems,
5008 aSecondNode1ToMerge,
5009 aSecondNode2ToMerge));
5011 storeResult(myEditor);
5013 myMesh->GetMeshDS()->Modified();
5014 myMesh->SetIsModified( true );
5019 //================================================================================
5021 * \brief Set new nodes for given element
5022 * \param ide - element id
5023 * \param newIDs - new node ids
5024 * \retval CORBA::Boolean - true if result is OK
5026 //================================================================================
5028 CORBA::Boolean SMESH_MeshEditor_i::ChangeElemNodes(CORBA::Long ide,
5029 const SMESH::long_array& newIDs)
5033 const SMDS_MeshElement* elem = GetMeshDS()->FindElement(ide);
5034 if(!elem) return false;
5036 int nbn = newIDs.length();
5038 vector<const SMDS_MeshNode*> aNodes(nbn);
5041 const SMDS_MeshNode* aNode = GetMeshDS()->FindNode(newIDs[i]);
5044 aNodes[nbn1] = aNode;
5047 TPythonDump() << "isDone = " << this << ".ChangeElemNodes( "
5048 << ide << ", " << newIDs << " )";
5050 MESSAGE("ChangeElementNodes");
5051 bool res = GetMeshDS()->ChangeElementNodes( elem, & aNodes[0], nbn1+1 );
5053 myMesh->GetMeshDS()->Modified();
5055 myMesh->SetIsModified( true );
5060 //=======================================================================
5061 //function : ConvertToQuadratic
5063 //=======================================================================
5065 void SMESH_MeshEditor_i::ConvertToQuadratic(CORBA::Boolean theForce3d)
5067 myEditor.ConvertToQuadratic(theForce3d);
5068 TPythonDump() << this << ".ConvertToQuadratic( " << theForce3d << " )";
5069 myMesh->GetMeshDS()->Modified();
5070 myMesh->SetIsModified( true );
5073 //=======================================================================
5074 //function : ConvertFromQuadratic
5076 //=======================================================================
5078 CORBA::Boolean SMESH_MeshEditor_i::ConvertFromQuadratic()
5080 CORBA::Boolean isDone = myEditor.ConvertFromQuadratic();
5081 TPythonDump() << this << ".ConvertFromQuadratic()";
5082 myMesh->GetMeshDS()->Modified();
5084 myMesh->SetIsModified( true );
5087 //================================================================================
5089 * \brief Makes a part of the mesh quadratic
5091 //================================================================================
5093 void SMESH_MeshEditor_i::ConvertToQuadraticObject(CORBA::Boolean theForce3d,
5094 SMESH::SMESH_IDSource_ptr theObject)
5095 throw (SALOME::SALOME_Exception)
5097 Unexpect aCatch(SALOME_SalomeException);
5099 TIDSortedElemSet elems;
5100 if ( idSourceToSet( theObject, GetMeshDS(), elems, SMDSAbs_All, /*emptyIfIsMesh=*/true ))
5102 if ( elems.empty() )
5104 ConvertToQuadratic( theForce3d );
5106 else if ( (*elems.begin())->GetType() == SMDSAbs_Node )
5108 THROW_SALOME_CORBA_EXCEPTION("Group of nodes is not allowed", SALOME::BAD_PARAM);
5112 myEditor.ConvertToQuadratic(theForce3d, elems);
5115 myMesh->GetMeshDS()->Modified();
5116 myMesh->SetIsModified( true );
5118 pyDump << this << ".ConvertToQuadraticObject( "<<theForce3d<<", "<<theObject<<" )";
5121 //================================================================================
5123 * \brief Makes a part of the mesh linear
5125 //================================================================================
5127 void SMESH_MeshEditor_i::ConvertFromQuadraticObject(SMESH::SMESH_IDSource_ptr theObject)
5128 throw (SALOME::SALOME_Exception)
5130 Unexpect aCatch(SALOME_SalomeException);
5132 TIDSortedElemSet elems;
5133 if ( idSourceToSet( theObject, GetMeshDS(), elems, SMDSAbs_All, /*emptyIfIsMesh=*/true ))
5135 if ( elems.empty() )
5137 ConvertFromQuadratic();
5139 else if ( (*elems.begin())->GetType() == SMDSAbs_Node )
5141 THROW_SALOME_CORBA_EXCEPTION("Group of nodes is not allowed", SALOME::BAD_PARAM);
5145 myEditor.ConvertFromQuadratic(elems);
5148 myMesh->GetMeshDS()->Modified();
5149 myMesh->SetIsModified( true );
5151 pyDump << this << ".ConvertFromQuadraticObject( "<<theObject<<" )";
5154 //=======================================================================
5155 //function : makeMesh
5156 //purpose : create a named imported mesh
5157 //=======================================================================
5159 SMESH::SMESH_Mesh_ptr SMESH_MeshEditor_i::makeMesh(const char* theMeshName)
5161 SMESH_Gen_i* gen = SMESH_Gen_i::GetSMESHGen();
5162 SMESH::SMESH_Mesh_var mesh = gen->CreateEmptyMesh();
5163 SALOMEDS::Study_var study = gen->GetCurrentStudy();
5164 SALOMEDS::SObject_var meshSO = gen->ObjectToSObject( study, mesh );
5165 gen->SetName( meshSO, theMeshName, "Mesh" );
5166 gen->SetPixMap( meshSO, "ICON_SMESH_TREE_MESH_IMPORTED");
5168 return mesh._retn();
5171 //=======================================================================
5172 //function : DumpGroupsList
5174 //=======================================================================
5175 void SMESH_MeshEditor_i::DumpGroupsList(TPythonDump & theDumpPython,
5176 const SMESH::ListOfGroups * theGroupList)
5178 bool isDumpGroupList = theGroupList && theGroupList->length() > 0;
5179 if(isDumpGroupList) {
5180 theDumpPython << theGroupList << " = ";
5184 //================================================================================
5186 \brief Generates the unique group name.
5187 \param thePrefix name prefix
5190 //================================================================================
5191 string SMESH_MeshEditor_i::generateGroupName(const string& thePrefix)
5193 SMESH::ListOfGroups_var groups = myMesh_i->GetGroups();
5194 set<string> groupNames;
5196 // Get existing group names
5197 for (int i = 0, nbGroups = groups->length(); i < nbGroups; i++ ) {
5198 SMESH::SMESH_GroupBase_var aGroup = groups[i];
5199 if (CORBA::is_nil(aGroup))
5202 groupNames.insert(aGroup->GetName());
5206 string name = thePrefix;
5209 while (!groupNames.insert(name).second) {
5214 TCollection_AsciiString nbStr(index+1);
5215 name.resize( name.rfind('_')+1 );
5216 name += nbStr.ToCString();
5224 //================================================================================
5226 \brief Creates a hole in a mesh by doubling the nodes of some particular elements
5227 \param theNodes - identifiers of nodes to be doubled
5228 \param theModifiedElems - identifiers of elements to be updated by the new (doubled)
5229 nodes. If list of element identifiers is empty then nodes are doubled but
5230 they not assigned to elements
5231 \return TRUE if operation has been completed successfully, FALSE otherwise
5232 \sa DoubleNode(), DoubleNodeGroup(), DoubleNodeGroups()
5234 //================================================================================
5236 CORBA::Boolean SMESH_MeshEditor_i::DoubleNodes( const SMESH::long_array& theNodes,
5237 const SMESH::long_array& theModifiedElems )
5241 list< int > aListOfNodes;
5243 for ( i = 0, n = theNodes.length(); i < n; i++ )
5244 aListOfNodes.push_back( theNodes[ i ] );
5246 list< int > aListOfElems;
5247 for ( i = 0, n = theModifiedElems.length(); i < n; i++ )
5248 aListOfElems.push_back( theModifiedElems[ i ] );
5250 bool aResult = myEditor.DoubleNodes( aListOfNodes, aListOfElems );
5252 myMesh->GetMeshDS()->Modified();
5253 storeResult( myEditor) ;
5255 myMesh->SetIsModified( true );
5257 // Update Python script
5258 TPythonDump() << this << ".DoubleNodes( " << theNodes << ", "<< theModifiedElems << " )";
5263 //================================================================================
5265 \brief Creates a hole in a mesh by doubling the nodes of some particular elements
5266 This method provided for convenience works as DoubleNodes() described above.
5267 \param theNodeId - identifier of node to be doubled.
5268 \param theModifiedElems - identifiers of elements to be updated.
5269 \return TRUE if operation has been completed successfully, FALSE otherwise
5270 \sa DoubleNodes(), DoubleNodeGroup(), DoubleNodeGroups()
5272 //================================================================================
5274 CORBA::Boolean SMESH_MeshEditor_i::DoubleNode( CORBA::Long theNodeId,
5275 const SMESH::long_array& theModifiedElems )
5277 SMESH::long_array_var aNodes = new SMESH::long_array;
5278 aNodes->length( 1 );
5279 aNodes[ 0 ] = theNodeId;
5281 TPythonDump pyDump; // suppress dump by the next line
5283 CORBA::Boolean done = DoubleNodes( aNodes, theModifiedElems );
5285 pyDump << this << ".DoubleNode( " << theNodeId << ", " << theModifiedElems << " )";
5290 //================================================================================
5292 \brief Creates a hole in a mesh by doubling the nodes of some particular elements
5293 This method provided for convenience works as DoubleNodes() described above.
5294 \param theNodes - group of nodes to be doubled.
5295 \param theModifiedElems - group of elements to be updated.
5296 \return TRUE if operation has been completed successfully, FALSE otherwise
5297 \sa DoubleNode(), DoubleNodes(), DoubleNodeGroups()
5299 //================================================================================
5301 CORBA::Boolean SMESH_MeshEditor_i::DoubleNodeGroup(SMESH::SMESH_GroupBase_ptr theNodes,
5302 SMESH::SMESH_GroupBase_ptr theModifiedElems )
5304 if ( CORBA::is_nil( theNodes ) && theNodes->GetType() != SMESH::NODE )
5307 SMESH::long_array_var aNodes = theNodes->GetListOfID();
5308 SMESH::long_array_var aModifiedElems;
5309 if ( !CORBA::is_nil( theModifiedElems ) )
5310 aModifiedElems = theModifiedElems->GetListOfID();
5313 aModifiedElems = new SMESH::long_array;
5314 aModifiedElems->length( 0 );
5317 TPythonDump pyDump; // suppress dump by the next line
5319 bool done = DoubleNodes( aNodes, aModifiedElems );
5321 pyDump << this << ".DoubleNodeGroup( " << theNodes << ", " << theModifiedElems << " )";
5327 * \brief Creates a hole in a mesh by doubling the nodes of some particular elements.
5328 * Works as DoubleNodeGroup(), but returns a new group with newly created nodes.
5329 * \param theNodes - group of nodes to be doubled.
5330 * \param theModifiedElems - group of elements to be updated.
5331 * \return a new group with newly created nodes
5332 * \sa DoubleNodeGroup()
5334 SMESH::SMESH_Group_ptr
5335 SMESH_MeshEditor_i::DoubleNodeGroupNew( SMESH::SMESH_GroupBase_ptr theNodes,
5336 SMESH::SMESH_GroupBase_ptr theModifiedElems )
5338 SMESH::SMESH_Group_var aNewGroup;
5340 if ( CORBA::is_nil( theNodes ) && theNodes->GetType() != SMESH::NODE )
5341 return aNewGroup._retn();
5344 SMESH::long_array_var aNodes = theNodes->GetListOfID();
5345 SMESH::long_array_var aModifiedElems;
5346 if ( !CORBA::is_nil( theModifiedElems ) )
5347 aModifiedElems = theModifiedElems->GetListOfID();
5349 aModifiedElems = new SMESH::long_array;
5350 aModifiedElems->length( 0 );
5353 TPythonDump pyDump; // suppress dump by the next line
5355 bool aResult = DoubleNodes( aNodes, aModifiedElems );
5358 // Create group with newly created nodes
5359 SMESH::long_array_var anIds = GetLastCreatedNodes();
5360 if (anIds->length() > 0) {
5361 string anUnindexedName (theNodes->GetName());
5362 string aNewName = generateGroupName(anUnindexedName + "_double");
5363 aNewGroup = myMesh_i->CreateGroup(SMESH::NODE, aNewName.c_str());
5364 aNewGroup->Add(anIds);
5365 pyDump << aNewGroup << " = ";
5369 pyDump << this << ".DoubleNodeGroupNew( " << theNodes << ", "
5370 << theModifiedElems << " )";
5372 return aNewGroup._retn();
5375 //================================================================================
5377 \brief Creates a hole in a mesh by doubling the nodes of some particular elements
5378 This method provided for convenience works as DoubleNodes() described above.
5379 \param theNodes - list of groups of nodes to be doubled
5380 \param theModifiedElems - list of groups of elements to be updated.
5381 \return TRUE if operation has been completed successfully, FALSE otherwise
5382 \sa DoubleNode(), DoubleNodeGroup(), DoubleNodes()
5384 //================================================================================
5386 CORBA::Boolean SMESH_MeshEditor_i::DoubleNodeGroups(const SMESH::ListOfGroups& theNodes,
5387 const SMESH::ListOfGroups& theModifiedElems )
5392 std::list< int > aNodes;
5394 for ( i = 0, n = theNodes.length(); i < n; i++ )
5396 SMESH::SMESH_GroupBase_var aGrp = theNodes[ i ];
5397 if ( !CORBA::is_nil( aGrp ) && aGrp->GetType() == SMESH::NODE )
5399 SMESH::long_array_var aCurr = aGrp->GetListOfID();
5400 for ( j = 0, m = aCurr->length(); j < m; j++ )
5401 aNodes.push_back( aCurr[ j ] );
5405 std::list< int > anElems;
5406 for ( i = 0, n = theModifiedElems.length(); i < n; i++ )
5408 SMESH::SMESH_GroupBase_var aGrp = theModifiedElems[ i ];
5409 if ( !CORBA::is_nil( aGrp ) && aGrp->GetType() != SMESH::NODE )
5411 SMESH::long_array_var aCurr = aGrp->GetListOfID();
5412 for ( j = 0, m = aCurr->length(); j < m; j++ )
5413 anElems.push_back( aCurr[ j ] );
5417 bool aResult = myEditor.DoubleNodes( aNodes, anElems );
5419 storeResult( myEditor) ;
5421 myMesh->GetMeshDS()->Modified();
5423 myMesh->SetIsModified( true );
5426 TPythonDump() << this << ".DoubleNodeGroups( " << theNodes << ", " << theModifiedElems << " )";
5431 //================================================================================
5433 * \brief Creates a hole in a mesh by doubling the nodes of some particular elements.
5434 * Works as DoubleNodeGroups(), but returns a new group with newly created nodes.
5435 * \param theNodes - group of nodes to be doubled.
5436 * \param theModifiedElems - group of elements to be updated.
5437 * \return a new group with newly created nodes
5438 * \sa DoubleNodeGroups()
5440 //================================================================================
5442 SMESH::SMESH_Group_ptr
5443 SMESH_MeshEditor_i::DoubleNodeGroupsNew( const SMESH::ListOfGroups& theNodes,
5444 const SMESH::ListOfGroups& theModifiedElems )
5446 SMESH::SMESH_Group_var aNewGroup;
5448 TPythonDump pyDump; // suppress dump by the next line
5450 bool aResult = DoubleNodeGroups( theNodes, theModifiedElems );
5454 // Create group with newly created nodes
5455 SMESH::long_array_var anIds = GetLastCreatedNodes();
5456 if (anIds->length() > 0) {
5457 string anUnindexedName (theNodes[0]->GetName());
5458 string aNewName = generateGroupName(anUnindexedName + "_double");
5459 aNewGroup = myMesh_i->CreateGroup(SMESH::NODE, aNewName.c_str());
5460 aNewGroup->Add(anIds);
5461 pyDump << aNewGroup << " = ";
5465 pyDump << this << ".DoubleNodeGroupsNew( " << theNodes << ", "
5466 << theModifiedElems << " )";
5468 return aNewGroup._retn();
5472 //================================================================================
5474 \brief Creates a hole in a mesh by doubling the nodes of some particular elements
5475 \param theElems - the list of elements (edges or faces) to be replicated
5476 The nodes for duplication could be found from these elements
5477 \param theNodesNot - list of nodes to NOT replicate
5478 \param theAffectedElems - the list of elements (cells and edges) to which the
5479 replicated nodes should be associated to.
5480 \return TRUE if operation has been completed successfully, FALSE otherwise
5481 \sa DoubleNodeGroup(), DoubleNodeGroups()
5483 //================================================================================
5485 CORBA::Boolean SMESH_MeshEditor_i::DoubleNodeElem( const SMESH::long_array& theElems,
5486 const SMESH::long_array& theNodesNot,
5487 const SMESH::long_array& theAffectedElems )
5493 SMESHDS_Mesh* aMeshDS = GetMeshDS();
5494 TIDSortedElemSet anElems, aNodes, anAffected;
5495 arrayToSet(theElems, aMeshDS, anElems, SMDSAbs_All);
5496 arrayToSet(theNodesNot, aMeshDS, aNodes, SMDSAbs_Node);
5497 arrayToSet(theAffectedElems, aMeshDS, anAffected, SMDSAbs_All);
5499 bool aResult = myEditor.DoubleNodes( anElems, aNodes, anAffected );
5501 storeResult( myEditor) ;
5503 myMesh->GetMeshDS()->Modified();
5505 myMesh->SetIsModified( true );
5507 // Update Python script
5508 TPythonDump() << this << ".DoubleNodeElem( " << theElems << ", "
5509 << theNodesNot << ", " << theAffectedElems << " )";
5513 //================================================================================
5515 \brief Creates a hole in a mesh by doubling the nodes of some particular elements
5516 \param theElems - the list of elements (edges or faces) to be replicated
5517 The nodes for duplication could be found from these elements
5518 \param theNodesNot - list of nodes to NOT replicate
5519 \param theShape - shape to detect affected elements (element which geometric center
5520 located on or inside shape).
5521 The replicated nodes should be associated to affected elements.
5522 \return TRUE if operation has been completed successfully, FALSE otherwise
5523 \sa DoubleNodeGroupInRegion(), DoubleNodeGroupsInRegion()
5525 //================================================================================
5527 CORBA::Boolean SMESH_MeshEditor_i::DoubleNodeElemInRegion ( const SMESH::long_array& theElems,
5528 const SMESH::long_array& theNodesNot,
5529 GEOM::GEOM_Object_ptr theShape )
5535 SMESHDS_Mesh* aMeshDS = GetMeshDS();
5536 TIDSortedElemSet anElems, aNodes;
5537 arrayToSet(theElems, aMeshDS, anElems, SMDSAbs_All);
5538 arrayToSet(theNodesNot, aMeshDS, aNodes, SMDSAbs_Node);
5540 TopoDS_Shape aShape = SMESH_Gen_i::GetSMESHGen()->GeomObjectToShape( theShape );
5541 bool aResult = myEditor.DoubleNodesInRegion( anElems, aNodes, aShape );
5543 storeResult( myEditor) ;
5545 myMesh->GetMeshDS()->Modified();
5547 myMesh->SetIsModified( true );
5549 // Update Python script
5550 TPythonDump() << "isDone = " << this << ".DoubleNodeElemInRegion( " << theElems << ", "
5551 << theNodesNot << ", " << theShape << " )";
5555 //================================================================================
5557 \brief Creates a hole in a mesh by doubling the nodes of some particular elements
5558 \param theElems - group of of elements (edges or faces) to be replicated
5559 \param theNodesNot - group of nodes not to replicated
5560 \param theAffectedElems - group of elements to which the replicated nodes
5561 should be associated to.
5562 \return TRUE if operation has been completed successfully, FALSE otherwise
5563 \sa DoubleNodes(), DoubleNodeGroups()
5565 //================================================================================
5567 CORBA::Boolean SMESH_MeshEditor_i::DoubleNodeElemGroup(SMESH::SMESH_GroupBase_ptr theElems,
5568 SMESH::SMESH_GroupBase_ptr theNodesNot,
5569 SMESH::SMESH_GroupBase_ptr theAffectedElems)
5571 if ( CORBA::is_nil( theElems ) && theElems->GetType() == SMESH::NODE )
5577 SMESHDS_Mesh* aMeshDS = GetMeshDS();
5578 TIDSortedElemSet anElems, aNodes, anAffected;
5579 idSourceToSet( theElems, aMeshDS, anElems, SMDSAbs_All );
5580 idSourceToSet( theNodesNot, aMeshDS, aNodes, SMDSAbs_Node );
5581 idSourceToSet( theAffectedElems, aMeshDS, anAffected, SMDSAbs_All );
5583 bool aResult = myEditor.DoubleNodes( anElems, aNodes, anAffected );
5585 storeResult( myEditor) ;
5587 myMesh->GetMeshDS()->Modified();
5589 myMesh->SetIsModified( true );
5591 // Update Python script
5592 TPythonDump() << "isDone = " << this << ".DoubleNodeElemGroup( " << theElems << ", "
5593 << theNodesNot << ", " << theAffectedElems << " )";
5598 * \brief Creates a hole in a mesh by doubling the nodes of some particular elements
5599 * Works as DoubleNodeElemGroup(), but returns a new group with newly created elements.
5600 * \param theElems - group of of elements (edges or faces) to be replicated
5601 * \param theNodesNot - group of nodes not to replicated
5602 * \param theAffectedElems - group of elements to which the replicated nodes
5603 * should be associated to.
5604 * \return a new group with newly created elements
5605 * \sa DoubleNodeElemGroup()
5607 SMESH::SMESH_Group_ptr
5608 SMESH_MeshEditor_i::DoubleNodeElemGroupNew(SMESH::SMESH_GroupBase_ptr theElems,
5609 SMESH::SMESH_GroupBase_ptr theNodesNot,
5610 SMESH::SMESH_GroupBase_ptr theAffectedElems)
5613 SMESH::ListOfGroups_var twoGroups = DoubleNodeElemGroup2New( theElems,
5617 SMESH::SMESH_GroupBase_var baseGroup = twoGroups[0].in();
5618 SMESH::SMESH_Group_var elemGroup = SMESH::SMESH_Group::_narrow( baseGroup );
5620 pyDump << elemGroup << " = " << this << ".DoubleNodeElemGroupNew( "
5622 << theNodesNot << ", "
5623 << theAffectedElems << " )";
5625 return elemGroup._retn();
5628 SMESH::ListOfGroups*
5629 SMESH_MeshEditor_i::DoubleNodeElemGroup2New(SMESH::SMESH_GroupBase_ptr theElems,
5630 SMESH::SMESH_GroupBase_ptr theNodesNot,
5631 SMESH::SMESH_GroupBase_ptr theAffectedElems,
5632 CORBA::Boolean theElemGroupNeeded,
5633 CORBA::Boolean theNodeGroupNeeded)
5635 SMESH::SMESH_Group_var aNewElemGroup, aNewNodeGroup;
5636 SMESH::ListOfGroups_var aTwoGroups = new SMESH::ListOfGroups();
5637 aTwoGroups->length( 2 );
5639 if ( CORBA::is_nil( theElems ) && theElems->GetType() == SMESH::NODE )
5640 return aTwoGroups._retn();
5645 SMESHDS_Mesh* aMeshDS = GetMeshDS();
5646 TIDSortedElemSet anElems, aNodes, anAffected;
5647 idSourceToSet( theElems, aMeshDS, anElems, SMDSAbs_All );
5648 idSourceToSet( theNodesNot, aMeshDS, aNodes, SMDSAbs_Node );
5649 idSourceToSet( theAffectedElems, aMeshDS, anAffected, SMDSAbs_All );
5652 bool aResult = myEditor.DoubleNodes( anElems, aNodes, anAffected );
5654 storeResult( myEditor) ;
5655 myMesh->GetMeshDS()->Modified();
5661 myMesh->SetIsModified( true );
5663 // Create group with newly created elements
5664 CORBA::String_var elemGroupName = theElems->GetName();
5665 string aNewName = generateGroupName( string(elemGroupName.in()) + "_double");
5666 if ( !myEditor.GetLastCreatedElems().IsEmpty() && theElemGroupNeeded )
5668 SMESH::long_array_var anIds = GetLastCreatedElems();
5669 SMESH::ElementType aGroupType = myMesh_i->GetElementType(anIds[0], true);
5670 aNewElemGroup = myMesh_i->CreateGroup(aGroupType, aNewName.c_str());
5671 aNewElemGroup->Add(anIds);
5673 if ( !myEditor.GetLastCreatedNodes().IsEmpty() && theNodeGroupNeeded )
5675 SMESH::long_array_var anIds = GetLastCreatedNodes();
5676 aNewNodeGroup = myMesh_i->CreateGroup(SMESH::NODE, aNewName.c_str());
5677 aNewNodeGroup->Add(anIds);
5681 // Update Python script
5684 if ( aNewElemGroup->_is_nil() ) pyDump << "nothing, ";
5685 else pyDump << aNewElemGroup << ", ";
5686 if ( aNewNodeGroup->_is_nil() ) pyDump << "nothing ] = ";
5687 else pyDump << aNewNodeGroup << " ] = ";
5689 pyDump << this << ".DoubleNodeElemGroup2New( " << theElems << ", "
5690 << theNodesNot << ", "
5691 << theAffectedElems << ", "
5692 << theElemGroupNeeded << ", "
5693 << theNodeGroupNeeded <<" )";
5695 aTwoGroups[0] = aNewElemGroup._retn();
5696 aTwoGroups[1] = aNewNodeGroup._retn();
5697 return aTwoGroups._retn();
5700 //================================================================================
5702 \brief Creates a hole in a mesh by doubling the nodes of some particular elements
5703 \param theElems - group of of elements (edges or faces) to be replicated
5704 \param theNodesNot - group of nodes not to replicated
5705 \param theShape - shape to detect affected elements (element which geometric center
5706 located on or inside shape).
5707 The replicated nodes should be associated to affected elements.
5708 \return TRUE if operation has been completed successfully, FALSE otherwise
5709 \sa DoubleNodesInRegion(), DoubleNodeGroupsInRegion()
5711 //================================================================================
5713 CORBA::Boolean SMESH_MeshEditor_i::DoubleNodeElemGroupInRegion(SMESH::SMESH_GroupBase_ptr theElems,
5714 SMESH::SMESH_GroupBase_ptr theNodesNot,
5715 GEOM::GEOM_Object_ptr theShape )
5718 if ( CORBA::is_nil( theElems ) && theElems->GetType() == SMESH::NODE )
5724 SMESHDS_Mesh* aMeshDS = GetMeshDS();
5725 TIDSortedElemSet anElems, aNodes, anAffected;
5726 idSourceToSet( theElems, aMeshDS, anElems, SMDSAbs_All );
5727 idSourceToSet( theNodesNot, aMeshDS, aNodes, SMDSAbs_Node );
5729 TopoDS_Shape aShape = SMESH_Gen_i::GetSMESHGen()->GeomObjectToShape( theShape );
5730 bool aResult = myEditor.DoubleNodesInRegion( anElems, aNodes, aShape );
5732 storeResult( myEditor) ;
5734 myMesh->GetMeshDS()->Modified();
5736 myMesh->SetIsModified( true );
5738 // Update Python script
5739 TPythonDump() << "isDone = " << this << ".DoubleNodeElemGroupInRegion( " << theElems << ", "
5740 << theNodesNot << ", " << theShape << " )";
5744 //================================================================================
5746 \brief Creates a hole in a mesh by doubling the nodes of some particular elements
5747 This method provided for convenience works as DoubleNodes() described above.
5748 \param theElems - list of groups of elements (edges or faces) to be replicated
5749 \param theNodesNot - list of groups of nodes not to replicated
5750 \param theAffectedElems - group of elements to which the replicated nodes
5751 should be associated to.
5752 \return TRUE if operation has been completed successfully, FALSE otherwise
5753 \sa DoubleNodeGroup(), DoubleNodes(), DoubleNodeElemGroupsNew()
5755 //================================================================================
5757 static void listOfGroupToSet(const SMESH::ListOfGroups& theGrpList,
5758 SMESHDS_Mesh* theMeshDS,
5759 TIDSortedElemSet& theElemSet,
5760 const bool theIsNodeGrp)
5762 for ( int i = 0, n = theGrpList.length(); i < n; i++ )
5764 SMESH::SMESH_GroupBase_var aGrp = theGrpList[ i ];
5765 if ( !CORBA::is_nil( aGrp ) && (theIsNodeGrp ? aGrp->GetType() == SMESH::NODE
5766 : aGrp->GetType() != SMESH::NODE ) )
5768 SMESH::long_array_var anIDs = aGrp->GetIDs();
5769 arrayToSet( anIDs, theMeshDS, theElemSet, theIsNodeGrp ? SMDSAbs_Node : SMDSAbs_All );
5774 CORBA::Boolean SMESH_MeshEditor_i::DoubleNodeElemGroups(const SMESH::ListOfGroups& theElems,
5775 const SMESH::ListOfGroups& theNodesNot,
5776 const SMESH::ListOfGroups& theAffectedElems)
5781 SMESHDS_Mesh* aMeshDS = GetMeshDS();
5782 TIDSortedElemSet anElems, aNodes, anAffected;
5783 listOfGroupToSet(theElems, aMeshDS, anElems, false );
5784 listOfGroupToSet(theNodesNot, aMeshDS, aNodes, true );
5785 listOfGroupToSet(theAffectedElems, aMeshDS, anAffected, false );
5787 bool aResult = myEditor.DoubleNodes( anElems, aNodes, anAffected );
5789 storeResult( myEditor) ;
5791 myMesh->GetMeshDS()->Modified();
5793 myMesh->SetIsModified( true );
5795 // Update Python script
5796 TPythonDump() << "isDone = " << this << ".DoubleNodeElemGroups( " << &theElems << ", "
5797 << &theNodesNot << ", " << &theAffectedElems << " )";
5801 //================================================================================
5803 * \brief Creates a hole in a mesh by doubling the nodes of some particular elements
5804 * Works as DoubleNodeElemGroups(), but returns a new group with newly created elements.
5805 \param theElems - list of groups of elements (edges or faces) to be replicated
5806 \param theNodesNot - list of groups of nodes not to replicated
5807 \param theAffectedElems - group of elements to which the replicated nodes
5808 should be associated to.
5809 * \return a new group with newly created elements
5810 * \sa DoubleNodeElemGroups()
5812 //================================================================================
5814 SMESH::SMESH_Group_ptr
5815 SMESH_MeshEditor_i::DoubleNodeElemGroupsNew(const SMESH::ListOfGroups& theElems,
5816 const SMESH::ListOfGroups& theNodesNot,
5817 const SMESH::ListOfGroups& theAffectedElems)
5820 SMESH::ListOfGroups_var twoGroups = DoubleNodeElemGroups2New( theElems,
5824 SMESH::SMESH_GroupBase_var baseGroup = twoGroups[0].in();
5825 SMESH::SMESH_Group_var elemGroup = SMESH::SMESH_Group::_narrow( baseGroup );
5827 pyDump << elemGroup << " = " << this << ".DoubleNodeElemGroupsNew( "
5829 << theNodesNot << ", "
5830 << theAffectedElems << " )";
5832 return elemGroup._retn();
5835 SMESH::ListOfGroups*
5836 SMESH_MeshEditor_i::DoubleNodeElemGroups2New(const SMESH::ListOfGroups& theElems,
5837 const SMESH::ListOfGroups& theNodesNot,
5838 const SMESH::ListOfGroups& theAffectedElems,
5839 CORBA::Boolean theElemGroupNeeded,
5840 CORBA::Boolean theNodeGroupNeeded)
5842 SMESH::SMESH_Group_var aNewElemGroup, aNewNodeGroup;
5843 SMESH::ListOfGroups_var aTwoGroups = new SMESH::ListOfGroups();
5844 aTwoGroups->length( 2 );
5849 SMESHDS_Mesh* aMeshDS = GetMeshDS();
5850 TIDSortedElemSet anElems, aNodes, anAffected;
5851 listOfGroupToSet(theElems, aMeshDS, anElems, false );
5852 listOfGroupToSet(theNodesNot, aMeshDS, aNodes, true );
5853 listOfGroupToSet(theAffectedElems, aMeshDS, anAffected, false );
5855 bool aResult = myEditor.DoubleNodes( anElems, aNodes, anAffected );
5857 storeResult( myEditor) ;
5859 myMesh->GetMeshDS()->Modified();
5863 myMesh->SetIsModified( true );
5865 // Create group with newly created elements
5866 CORBA::String_var elemGroupName = theElems[0]->GetName();
5867 string aNewName = generateGroupName( string(elemGroupName.in()) + "_double");
5868 if ( !myEditor.GetLastCreatedElems().IsEmpty() && theElemGroupNeeded )
5870 SMESH::long_array_var anIds = GetLastCreatedElems();
5871 SMESH::ElementType aGroupType = myMesh_i->GetElementType(anIds[0], true);
5872 aNewElemGroup = myMesh_i->CreateGroup(aGroupType, aNewName.c_str());
5873 aNewElemGroup->Add(anIds);
5875 if ( !myEditor.GetLastCreatedNodes().IsEmpty() && theNodeGroupNeeded )
5877 SMESH::long_array_var anIds = GetLastCreatedNodes();
5878 aNewNodeGroup = myMesh_i->CreateGroup(SMESH::NODE, aNewName.c_str());
5879 aNewNodeGroup->Add(anIds);
5883 // Update Python script
5886 if ( aNewElemGroup->_is_nil() ) pyDump << "nothing, ";
5887 else pyDump << aNewElemGroup << ", ";
5888 if ( aNewNodeGroup->_is_nil() ) pyDump << "nothing ] = ";
5889 else pyDump << aNewNodeGroup << " ] = ";
5891 pyDump << this << ".DoubleNodeElemGroups2New( " << &theElems << ", "
5892 << &theNodesNot << ", "
5893 << &theAffectedElems << ", "
5894 << theElemGroupNeeded << ", "
5895 << theNodeGroupNeeded << " )";
5897 aTwoGroups[0] = aNewElemGroup._retn();
5898 aTwoGroups[1] = aNewNodeGroup._retn();
5899 return aTwoGroups._retn();
5902 //================================================================================
5904 \brief Creates a hole in a mesh by doubling the nodes of some particular elements
5905 This method provided for convenience works as DoubleNodes() described above.
5906 \param theElems - list of groups of elements (edges or faces) to be replicated
5907 \param theNodesNot - list of groups of nodes not to replicated
5908 \param theShape - shape to detect affected elements (element which geometric center
5909 located on or inside shape).
5910 The replicated nodes should be associated to affected elements.
5911 \return TRUE if operation has been completed successfully, FALSE otherwise
5912 \sa DoubleNodeGroupInRegion(), DoubleNodesInRegion()
5914 //================================================================================
5917 SMESH_MeshEditor_i::DoubleNodeElemGroupsInRegion(const SMESH::ListOfGroups& theElems,
5918 const SMESH::ListOfGroups& theNodesNot,
5919 GEOM::GEOM_Object_ptr theShape )
5924 SMESHDS_Mesh* aMeshDS = GetMeshDS();
5925 TIDSortedElemSet anElems, aNodes;
5926 listOfGroupToSet(theElems, aMeshDS, anElems,false );
5927 listOfGroupToSet(theNodesNot, aMeshDS, aNodes, true );
5929 TopoDS_Shape aShape = SMESH_Gen_i::GetSMESHGen()->GeomObjectToShape( theShape );
5930 bool aResult = myEditor.DoubleNodesInRegion( anElems, aNodes, aShape );
5932 storeResult( myEditor) ;
5934 myMesh->GetMeshDS()->Modified();
5936 myMesh->SetIsModified( true );
5938 // Update Python script
5939 TPythonDump() << "isDone = " << this << ".DoubleNodeElemGroupsInRegion( " << &theElems << ", "
5940 << &theNodesNot << ", " << theShape << " )";
5944 //================================================================================
5946 \brief Generated skin mesh (containing 2D cells) from 3D mesh
5947 The created 2D mesh elements based on nodes of free faces of boundary volumes
5948 \return TRUE if operation has been completed successfully, FALSE otherwise
5950 //================================================================================
5952 CORBA::Boolean SMESH_MeshEditor_i::Make2DMeshFrom3D()
5956 bool aResult = myEditor.Make2DMeshFrom3D();
5957 storeResult( myEditor) ;
5958 myMesh->GetMeshDS()->Modified();
5959 TPythonDump() << "isDone = " << this << ".Make2DMeshFrom3D()";
5963 //================================================================================
5965 * \brief Double nodes on shared faces between groups of volumes and create flat elements on demand.
5966 * The list of groups must describe a partition of the mesh volumes.
5967 * The nodes of the internal faces at the boundaries of the groups are doubled.
5968 * In option, the internal faces are replaced by flat elements.
5969 * Triangles are transformed in prisms, and quadrangles in hexahedrons.
5970 * The flat elements are stored in groups of volumes.
5971 * @param theDomains - list of groups of volumes
5972 * @param createJointElems - if TRUE, create the elements
5973 * @return TRUE if operation has been completed successfully, FALSE otherwise
5975 //================================================================================
5977 CORBA::Boolean SMESH_MeshEditor_i::DoubleNodesOnGroupBoundaries( const SMESH::ListOfGroups& theDomains,
5978 CORBA::Boolean createJointElems )
5979 throw (SALOME::SALOME_Exception)
5984 SMESHDS_Mesh* aMeshDS = GetMeshDS();
5986 vector<TIDSortedElemSet> domains;
5989 for ( int i = 0, n = theDomains.length(); i < n; i++ )
5991 SMESH::SMESH_GroupBase_var aGrp = theDomains[ i ];
5992 if ( !CORBA::is_nil( aGrp ) /*&& ( aGrp->GetType() != SMESH::NODE )*/ )
5994 // if ( aGrp->GetType() != SMESH::VOLUME )
5995 // THROW_SALOME_CORBA_EXCEPTION("Not a volume group", SALOME::BAD_PARAM);
5996 TIDSortedElemSet domain;
5998 domains.push_back(domain);
5999 SMESH::long_array_var anIDs = aGrp->GetIDs();
6000 arrayToSet( anIDs, aMeshDS, domains[ i ], SMDSAbs_All );
6004 bool aResult = myEditor.DoubleNodesOnGroupBoundaries( domains, createJointElems );
6005 // TODO publish the groups of flat elements in study
6007 storeResult( myEditor) ;
6008 myMesh->GetMeshDS()->Modified();
6010 // Update Python script
6011 TPythonDump() << "isDone = " << this << ".DoubleNodesOnGroupBoundaries( " << &theDomains
6012 << ", " << createJointElems << " )";
6016 //================================================================================
6018 * \brief Double nodes on some external faces and create flat elements.
6019 * Flat elements are mainly used by some types of mechanic calculations.
6021 * Each group of the list must be constituted of faces.
6022 * Triangles are transformed in prisms, and quadrangles in hexahedrons.
6023 * @param theGroupsOfFaces - list of groups of faces
6024 * @return TRUE if operation has been completed successfully, FALSE otherwise
6026 //================================================================================
6028 CORBA::Boolean SMESH_MeshEditor_i::CreateFlatElementsOnFacesGroups( const SMESH::ListOfGroups& theGroupsOfFaces )
6033 SMESHDS_Mesh* aMeshDS = GetMeshDS();
6035 vector<TIDSortedElemSet> faceGroups;
6038 for ( int i = 0, n = theGroupsOfFaces.length(); i < n; i++ )
6040 SMESH::SMESH_GroupBase_var aGrp = theGroupsOfFaces[ i ];
6041 if ( !CORBA::is_nil( aGrp ) && ( aGrp->GetType() != SMESH::NODE ) )
6043 TIDSortedElemSet faceGroup;
6045 faceGroups.push_back(faceGroup);
6046 SMESH::long_array_var anIDs = aGrp->GetIDs();
6047 arrayToSet( anIDs, aMeshDS, faceGroups[ i ], SMDSAbs_All );
6051 bool aResult = myEditor.CreateFlatElementsOnFacesGroups( faceGroups );
6052 // TODO publish the groups of flat elements in study
6054 storeResult( myEditor) ;
6055 myMesh->GetMeshDS()->Modified();
6057 // Update Python script
6058 TPythonDump() << "isDone = " << this << ".CreateFlatElementsOnFacesGroups( " << &theGroupsOfFaces << " )";
6062 // issue 20749 ===================================================================
6064 * \brief Creates missing boundary elements
6065 * \param elements - elements whose boundary is to be checked
6066 * \param dimension - defines type of boundary elements to create
6067 * \param groupName - a name of group to store created boundary elements in,
6068 * "" means not to create the group
6069 * \param meshName - a name of new mesh to store created boundary elements in,
6070 * "" means not to create the new mesh
6071 * \param toCopyElements - if true, the checked elements will be copied into the new mesh
6072 * \param toCopyExistingBondary - if true, not only new but also pre-existing
6073 * boundary elements will be copied into the new mesh
6074 * \param group - returns the create group, if any
6075 * \retval SMESH::SMESH_Mesh - the mesh where elements were added to
6077 // ================================================================================
6079 SMESH::SMESH_Mesh_ptr
6080 SMESH_MeshEditor_i::MakeBoundaryMesh(SMESH::SMESH_IDSource_ptr idSource,
6081 SMESH::Bnd_Dimension dim,
6082 const char* groupName,
6083 const char* meshName,
6084 CORBA::Boolean toCopyElements,
6085 CORBA::Boolean toCopyExistingBondary,
6086 SMESH::SMESH_Group_out group)
6090 if ( dim > SMESH::BND_1DFROM2D )
6091 THROW_SALOME_CORBA_EXCEPTION("Invalid boundary dimension", SALOME::BAD_PARAM);
6093 SMESHDS_Mesh* aMeshDS = GetMeshDS();
6095 SMESH::SMESH_Mesh_var mesh_var;
6096 SMESH::SMESH_Group_var group_var;
6100 TIDSortedElemSet elements;
6101 SMDSAbs_ElementType elemType = (dim == SMESH::BND_1DFROM2D) ? SMDSAbs_Face : SMDSAbs_Volume;
6102 if ( idSourceToSet( idSource, aMeshDS, elements, elemType,/*emptyIfIsMesh=*/true ))
6106 strlen(meshName) ? makeMesh(meshName) : SMESH::SMESH_Mesh::_duplicate(myMesh_i->_this());
6107 SMESH_Mesh_i* mesh_i = SMESH::DownCast<SMESH_Mesh_i*>( mesh_var );
6109 SMESH_Mesh* smesh_mesh = (mesh_i==myMesh_i) ? (SMESH_Mesh*)0 : &mesh_i->GetImpl();
6111 // group of new boundary elements
6112 SMESH_Group* smesh_group = 0;
6113 if ( strlen(groupName) )
6115 group_var = mesh_i->CreateGroup( SMESH::ElementType(int(elemType)-1),groupName);
6116 if ( SMESH_GroupBase_i* group_i = SMESH::DownCast<SMESH_GroupBase_i*>( group_var ))
6117 smesh_group = group_i->GetSmeshGroup();
6121 myEditor.MakeBoundaryMesh( elements,
6122 ::SMESH_MeshEditor::Bnd_Dimension(dim),
6126 toCopyExistingBondary);
6127 storeResult( myEditor );
6130 smesh_mesh->GetMeshDS()->Modified();
6133 const char* dimName[] = { "BND_2DFROM3D", "BND_1DFROM3D", "BND_1DFROM2D" };
6135 // result of MakeBoundaryMesh() is a tuple (mesh, group)
6136 if ( mesh_var->_is_nil() )
6137 pyDump << myMesh_i->_this() << ", ";
6139 pyDump << mesh_var << ", ";
6140 if ( group_var->_is_nil() )
6141 pyDump << "_NoneGroup = "; // assignment to None is forbiden
6143 pyDump << group_var << " = ";
6144 pyDump << this << ".MakeBoundaryMesh( "
6146 << "SMESH." << dimName[int(dim)] << ", "
6147 << "'" << groupName << "', "
6148 << "'" << meshName<< "', "
6149 << toCopyElements << ", "
6150 << toCopyExistingBondary << ")";
6152 group = group_var._retn();
6153 return mesh_var._retn();
6156 //================================================================================
6158 * \brief Creates missing boundary elements
6159 * \param dimension - defines type of boundary elements to create
6160 * \param groupName - a name of group to store all boundary elements in,
6161 * "" means not to create the group
6162 * \param meshName - a name of a new mesh, which is a copy of the initial
6163 * mesh + created boundary elements; "" means not to create the new mesh
6164 * \param toCopyAll - if true, the whole initial mesh will be copied into
6165 * the new mesh else only boundary elements will be copied into the new mesh
6166 * \param groups - optional groups of elements to make boundary around
6167 * \param mesh - returns the mesh where elements were added to
6168 * \param group - returns the created group, if any
6169 * \retval long - number of added boundary elements
6171 //================================================================================
6173 CORBA::Long SMESH_MeshEditor_i::MakeBoundaryElements(SMESH::Bnd_Dimension dim,
6174 const char* groupName,
6175 const char* meshName,
6176 CORBA::Boolean toCopyAll,
6177 const SMESH::ListOfIDSources& groups,
6178 SMESH::SMESH_Mesh_out mesh,
6179 SMESH::SMESH_Group_out group)
6180 throw (SALOME::SALOME_Exception)
6182 Unexpect aCatch(SALOME_SalomeException);
6186 if ( dim > SMESH::BND_1DFROM2D )
6187 THROW_SALOME_CORBA_EXCEPTION("Invalid boundary dimension", SALOME::BAD_PARAM);
6189 // separate groups belonging to this and other mesh
6190 SMESH::ListOfIDSources_var groupsOfThisMesh = new SMESH::ListOfIDSources;
6191 SMESH::ListOfIDSources_var groupsOfOtherMesh = new SMESH::ListOfIDSources;
6192 groupsOfThisMesh->length( groups.length() );
6193 groupsOfOtherMesh->length( groups.length() );
6194 int nbGroups = 0, nbGroupsOfOtherMesh = 0;
6195 for ( int i = 0; i < groups.length(); ++i )
6197 SMESH::SMESH_Mesh_var m = groups[i]->GetMesh();
6198 if ( myMesh_i != SMESH::DownCast<SMESH_Mesh_i*>( m ))
6199 groupsOfOtherMesh[ nbGroupsOfOtherMesh++ ] = groups[i];
6201 groupsOfThisMesh[ nbGroups++ ] = groups[i];
6202 if ( SMESH::DownCast<SMESH_Mesh_i*>( groups[i] ))
6203 THROW_SALOME_CORBA_EXCEPTION("expect a group but recieve a mesh", SALOME::BAD_PARAM);
6205 groupsOfThisMesh->length( nbGroups );
6206 groupsOfOtherMesh->length( nbGroupsOfOtherMesh );
6211 if ( nbGroupsOfOtherMesh > 0 )
6213 // process groups belonging to another mesh
6214 SMESH::SMESH_Mesh_var otherMesh = groupsOfOtherMesh[0]->GetMesh();
6215 SMESH::SMESH_MeshEditor_var editor = otherMesh->GetMeshEditor();
6216 nbAdded += editor->MakeBoundaryElements( dim, groupName, meshName, toCopyAll,
6217 groupsOfOtherMesh, mesh, group );
6220 SMESH::SMESH_Mesh_var mesh_var;
6221 SMESH::SMESH_Group_var group_var;
6224 mesh_var = SMESH::SMESH_Mesh::_duplicate( myMesh_i->_this() );
6225 const bool toCopyMesh = ( strlen( meshName ) > 0 );
6229 mesh_var = SMESH_Gen_i::GetSMESHGen()->CopyMesh(mesh_var,
6231 /*toCopyGroups=*/false,
6232 /*toKeepIDs=*/true);
6234 mesh_var = makeMesh(meshName);
6236 SMESH_Mesh_i* mesh_i = SMESH::DownCast<SMESH_Mesh_i*>( mesh_var );
6237 SMESH_Mesh* tgtMesh = &mesh_i->GetImpl();
6240 SMESH_Mesh* srcMesh = ( toCopyMesh && !toCopyAll ) ? myMesh : tgtMesh;
6241 SMESHDS_Mesh* srcMeshDS = srcMesh->GetMeshDS();
6243 // group of boundary elements
6244 SMESH_Group* smesh_group = 0;
6245 SMDSAbs_ElementType elemType = (dim == SMESH::BND_2DFROM3D) ? SMDSAbs_Volume : SMDSAbs_Face;
6246 if ( strlen(groupName) )
6248 SMESH::ElementType groupType = SMESH::ElementType( int(elemType)-1 );
6249 group_var = mesh_i->CreateGroup( groupType, groupName );
6250 if ( SMESH_GroupBase_i* group_i = SMESH::DownCast<SMESH_GroupBase_i*>( group_var ))
6251 smesh_group = group_i->GetSmeshGroup();
6254 TIDSortedElemSet elements;
6256 if ( groups.length() > 0 )
6258 for ( int i = 0; i < nbGroups; ++i )
6261 if ( idSourceToSet( groupsOfThisMesh[i], srcMeshDS, elements, elemType,/*emptyIfIsMesh=*/0 ))
6263 SMESH::Bnd_Dimension bdim =
6264 ( elemType == SMDSAbs_Volume ) ? SMESH::BND_2DFROM3D : SMESH::BND_1DFROM2D;
6265 nbAdded += myEditor.MakeBoundaryMesh( elements,
6266 ::SMESH_MeshEditor::Bnd_Dimension(bdim),
6269 /*toCopyElements=*/false,
6270 /*toCopyExistingBondary=*/srcMesh != tgtMesh,
6271 /*toAddExistingBondary=*/true,
6272 /*aroundElements=*/true);
6273 storeResult( myEditor );
6279 nbAdded += myEditor.MakeBoundaryMesh( elements,
6280 ::SMESH_MeshEditor::Bnd_Dimension(dim),
6283 /*toCopyElements=*/false,
6284 /*toCopyExistingBondary=*/srcMesh != tgtMesh,
6285 /*toAddExistingBondary=*/true);
6286 storeResult( myEditor );
6288 tgtMesh->GetMeshDS()->Modified();
6290 const char* dimName[] = { "BND_2DFROM3D", "BND_1DFROM3D", "BND_1DFROM2D" };
6292 // result of MakeBoundaryElements() is a tuple (nb, mesh, group)
6293 pyDump << "nbAdded, ";
6294 if ( mesh_var->_is_nil() )
6295 pyDump << myMesh_i->_this() << ", ";
6297 pyDump << mesh_var << ", ";
6298 if ( group_var->_is_nil() )
6299 pyDump << "_NoneGroup = "; // assignment to None is forbiden
6301 pyDump << group_var << " = ";
6302 pyDump << this << ".MakeBoundaryElements( "
6303 << "SMESH." << dimName[int(dim)] << ", "
6304 << "'" << groupName << "', "
6305 << "'" << meshName<< "', "
6306 << toCopyAll << ", "
6309 mesh = mesh_var._retn();
6310 group = group_var._retn();