+ ::SMESH_MeshEditor anEditor( myMesh );
+ SMESH::SMESH_MeshEditor::Sew_Error error =
+ convError( anEditor.SewSideElements (aSide1Elems, aSide2Elems,
+ aFirstNode1ToMerge,
+ aFirstNode2ToMerge,
+ aSecondNode1ToMerge,
+ aSecondNode2ToMerge));
+
+ storeResult(anEditor);
+
+ return error;
+}
+
+//================================================================================
+/*!
+ * \brief Set new nodes for given element
+ * \param ide - element id
+ * \param newIDs - new node ids
+ * \retval CORBA::Boolean - true if result is OK
+ */
+//================================================================================
+
+CORBA::Boolean SMESH_MeshEditor_i::ChangeElemNodes(CORBA::Long ide,
+ const SMESH::long_array& newIDs)
+{
+ initData();
+
+ const SMDS_MeshElement* elem = GetMeshDS()->FindElement(ide);
+ if(!elem) return false;
+
+ int nbn = newIDs.length();
+ int i=0;
+ vector<const SMDS_MeshNode*> aNodes(nbn);
+ int nbn1=-1;
+ for(; i<nbn; i++) {
+ const SMDS_MeshNode* aNode = GetMeshDS()->FindNode(newIDs[i]);
+ if(aNode) {
+ nbn1++;
+ aNodes[nbn1] = aNode;
+ }
+ }
+ TPythonDump() << "isDone = " << this << ".ChangeElemNodes( "
+ << ide << ", " << newIDs << " )";
+#ifdef _DEBUG_
+ TPythonDump() << "print 'ChangeElemNodes: ', isDone";
+#endif
+
+ return GetMeshDS()->ChangeElementNodes( elem, & aNodes[0], nbn1+1 );
+}
+
+//================================================================================
+/*!
+ * \brief Update myLastCreated* or myPreviewData
+ * \param anEditor - it contains last modification results
+ */
+//================================================================================
+
+void SMESH_MeshEditor_i::storeResult(::SMESH_MeshEditor& anEditor)
+{
+ if ( myPreviewMode ) { // --- MeshPreviewStruct filling ---
+
+ list<int> aNodesConnectivity;
+ typedef map<int, int> TNodesMap;
+ TNodesMap nodesMap;
+
+ TPreviewMesh * aPreviewMesh = dynamic_cast< TPreviewMesh* >( anEditor.GetMesh() );
+ SMDSAbs_ElementType previewType = aPreviewMesh->myPreviewType;
+
+ SMESHDS_Mesh* aMeshDS = anEditor.GetMeshDS();
+ int nbEdges = aMeshDS->NbEdges();
+ int nbFaces = aMeshDS->NbFaces();
+ int nbVolum = aMeshDS->NbVolumes();
+ switch ( previewType ) {
+ case SMDSAbs_Edge : nbFaces = nbVolum = 0; break;
+ case SMDSAbs_Face : nbEdges = nbVolum = 0; break;
+ case SMDSAbs_Volume: nbEdges = nbFaces = 0; break;
+ default:;
+ }
+ myPreviewData->nodesXYZ.length(aMeshDS->NbNodes());
+ myPreviewData->elementTypes.length(nbEdges + nbFaces + nbVolum);
+ int i = 0, j = 0;
+ SMDS_ElemIteratorPtr itMeshElems = aMeshDS->elementsIterator();
+
+ while ( itMeshElems->more() ) {
+ const SMDS_MeshElement* aMeshElem = itMeshElems->next();
+ if ( previewType != SMDSAbs_All && aMeshElem->GetType() != previewType )
+ continue;
+
+ SMDS_ElemIteratorPtr itElemNodes = aMeshElem->nodesIterator();
+ while ( itElemNodes->more() ) {
+ const SMDS_MeshNode* aMeshNode =
+ static_cast<const SMDS_MeshNode*>( itElemNodes->next() );
+ int aNodeID = aMeshNode->GetID();
+ TNodesMap::iterator anIter = nodesMap.find(aNodeID);
+ if ( anIter == nodesMap.end() ) {
+ // filling the nodes coordinates
+ myPreviewData->nodesXYZ[j].x = aMeshNode->X();
+ myPreviewData->nodesXYZ[j].y = aMeshNode->Y();
+ myPreviewData->nodesXYZ[j].z = aMeshNode->Z();
+ anIter = nodesMap.insert( make_pair(aNodeID, j) ).first;
+ j++;
+ }
+ aNodesConnectivity.push_back(anIter->second);
+ }
+
+ // filling the elements types
+ SMDSAbs_ElementType aType;
+ bool isPoly;
+ /*if (aMeshElem->GetType() == SMDSAbs_Volume) {
+ aType = SMDSAbs_Node;
+ isPoly = false;
+ }
+ else*/ {
+ aType = aMeshElem->GetType();
+ isPoly = aMeshElem->IsPoly();
+ }
+
+ myPreviewData->elementTypes[i].SMDS_ElementType = (SMESH::ElementType) aType;
+ myPreviewData->elementTypes[i].isPoly = isPoly;
+ myPreviewData->elementTypes[i].nbNodesInElement = aMeshElem->NbNodes();
+ i++;
+
+ }
+ myPreviewData->nodesXYZ.length( j );
+
+ // filling the elements connectivities
+ list<int>::iterator aConnIter = aNodesConnectivity.begin();
+ myPreviewData->elementConnectivities.length(aNodesConnectivity.size());
+ for( int i = 0; aConnIter != aNodesConnectivity.end(); aConnIter++, i++ )
+ myPreviewData->elementConnectivities[i] = *aConnIter;
+
+ return;
+ }
+
+ {
+ // add new nodes into myLastCreatedNodes
+ const SMESH_SequenceOfElemPtr& aSeq = anEditor.GetLastCreatedNodes();
+ myLastCreatedNodes->length(aSeq.Length());
+ for(int i=0; i<aSeq.Length(); i++)
+ myLastCreatedNodes[i] = aSeq.Value(i+1)->GetID();
+ }
+ {
+ // add new elements into myLastCreatedElems
+ const SMESH_SequenceOfElemPtr& aSeq = anEditor.GetLastCreatedElems();
+ myLastCreatedElems->length(aSeq.Length());
+ for(int i=0; i<aSeq.Length(); i++)
+ myLastCreatedElems[i] = aSeq.Value(i+1)->GetID();
+ }
+}
+
+//================================================================================
+/*!
+ * Return data of mesh edition preview
+ */
+//================================================================================
+
+SMESH::MeshPreviewStruct* SMESH_MeshEditor_i::GetPreviewData()
+{
+ return myPreviewData._retn();
+}
+
+//================================================================================
+/*!
+ * \brief Returns list of it's IDs of created nodes
+ * \retval SMESH::long_array* - list of node ID
+ */
+//================================================================================
+
+SMESH::long_array* SMESH_MeshEditor_i::GetLastCreatedNodes()
+{
+ return myLastCreatedNodes._retn();
+}
+
+//================================================================================
+/*!
+ * \brief Returns list of it's IDs of created elements
+ * \retval SMESH::long_array* - list of elements' ID
+ */
+//================================================================================
+
+SMESH::long_array* SMESH_MeshEditor_i::GetLastCreatedElems()
+{
+ return myLastCreatedElems._retn();
+}
+
+//=======================================================================
+//function : ConvertToQuadratic
+//purpose :
+//=======================================================================
+
+void SMESH_MeshEditor_i::ConvertToQuadratic(CORBA::Boolean theForce3d)
+{
+ ::SMESH_MeshEditor anEditor( myMesh );
+ anEditor.ConvertToQuadratic(theForce3d);
+ TPythonDump() << this << ".ConvertToQuadratic( " << theForce3d << " )";
+}
+
+//=======================================================================
+//function : ConvertFromQuadratic
+//purpose :
+//=======================================================================
+
+CORBA::Boolean SMESH_MeshEditor_i::ConvertFromQuadratic()
+{
+ ::SMESH_MeshEditor anEditor( myMesh );
+ CORBA::Boolean isDone = anEditor.ConvertFromQuadratic();
+ TPythonDump() << this << ".ConvertFromQuadratic()";
+ return isDone;
+}
+
+//=======================================================================
+//function : makeMesh
+//purpose : create a named imported mesh
+//=======================================================================
+
+SMESH::SMESH_Mesh_ptr SMESH_MeshEditor_i::makeMesh(const char* theMeshName)
+{
+ SMESH_Gen_i* gen = SMESH_Gen_i::GetSMESHGen();
+ SMESH::SMESH_Mesh_var mesh = gen->CreateEmptyMesh();
+ SALOMEDS::Study_var study = gen->GetCurrentStudy();
+ SALOMEDS::SObject_var meshSO = gen->ObjectToSObject( study, mesh );
+ gen->SetName( meshSO, theMeshName, "Mesh" );
+ gen->SetPixMap( meshSO, "ICON_SMESH_TREE_MESH_IMPORTED");
+
+ return mesh._retn();
+}
+
+//=======================================================================
+//function : DumpGroupsList
+//purpose :
+//=======================================================================
+void SMESH_MeshEditor_i::DumpGroupsList(TPythonDump & theDumpPython,
+ const SMESH::ListOfGroups * theGroupList)
+{
+ bool isDumpGroupList = theGroupList && theGroupList->length() > 0;
+ if(isDumpGroupList) {
+ theDumpPython << theGroupList << " = ";
+ }
+}
+
+//================================================================================
+/*!
+ \brief Creates a hole in a mesh by doubling the nodes of some particular elements
+ \param theElems - the list of elements (edges or faces) to be replicated
+ The nodes for duplication could be found from these elements
+ \param theNodesNot - list of nodes to NOT replicate
+ \param theAffectedElems - the list of elements (cells and edges) to which the
+ replicated nodes should be associated to.
+ \return TRUE if operation has been completed successfully, FALSE otherwise
+ \sa DoubleNodeGroup(), DoubleNodeGroups()
+*/
+//================================================================================
+
+CORBA::Boolean SMESH_MeshEditor_i::DoubleNodes( const SMESH::long_array& theElems,
+ const SMESH::long_array& theNodesNot,
+ const SMESH::long_array& theAffectedElems )
+
+{
+ initData();
+
+ ::SMESH_MeshEditor aMeshEditor( myMesh );
+
+ SMESHDS_Mesh* aMeshDS = GetMeshDS();
+ TIDSortedElemSet anElems, aNodes, anAffected;
+ arrayToSet(theElems, aMeshDS, anElems, SMDSAbs_All);
+ arrayToSet(theNodesNot, aMeshDS, aNodes, SMDSAbs_Node);
+ arrayToSet(theAffectedElems, aMeshDS, anAffected, SMDSAbs_All);
+
+ bool aResult = aMeshEditor.DoubleNodes( anElems, aNodes, anAffected );
+
+ storeResult( aMeshEditor) ;
+
+ return aResult;
+}
+
+//================================================================================
+/*!
+ \brief Creates a hole in a mesh by doubling the nodes of some particular elements
+ \param theElems - the list of elements (edges or faces) to be replicated
+ The nodes for duplication could be found from these elements
+ \param theNodesNot - list of nodes to NOT replicate
+ \param theShape - shape to detect affected elements (element which geometric center
+ located on or inside shape).
+ The replicated nodes should be associated to affected elements.
+ \return TRUE if operation has been completed successfully, FALSE otherwise
+ \sa DoubleNodeGroupInRegion(), DoubleNodeGroupsInRegion()
+*/
+//================================================================================
+
+CORBA::Boolean SMESH_MeshEditor_i::DoubleNodesInRegion
+( const SMESH::long_array& theElems,
+ const SMESH::long_array& theNodesNot,
+ GEOM::GEOM_Object_ptr theShape )
+
+{
+ initData();
+
+ ::SMESH_MeshEditor aMeshEditor( myMesh );
+
+ SMESHDS_Mesh* aMeshDS = GetMeshDS();
+ TIDSortedElemSet anElems, aNodes;
+ arrayToSet(theElems, aMeshDS, anElems, SMDSAbs_All);
+ arrayToSet(theNodesNot, aMeshDS, aNodes, SMDSAbs_Node);
+
+ TopoDS_Shape aShape = SMESH_Gen_i::GetSMESHGen()->GeomObjectToShape( theShape );
+ bool aResult = aMeshEditor.DoubleNodesInRegion( anElems, aNodes, aShape );
+
+ storeResult( aMeshEditor) ;
+
+ return aResult;
+}
+
+//================================================================================
+/*!
+ \brief Creates a hole in a mesh by doubling the nodes of some particular elements
+ \param theElems - group of of elements (edges or faces) to be replicated
+ \param theNodesNot - group of nodes not to replicated
+ \param theAffectedElems - group of elements to which the replicated nodes
+ should be associated to.
+ \return TRUE if operation has been completed successfully, FALSE otherwise
+ \sa DoubleNodes(), DoubleNodeGroups()
+*/
+//================================================================================
+
+static void groupToSet(SMESH::SMESH_GroupBase_ptr theGrp,
+ SMESHDS_Mesh* theMeshDS,
+ TIDSortedElemSet& theElemSet,
+ const SMDSAbs_ElementType theType)
+
+{
+ if ( CORBA::is_nil( theGrp ) )
+ return;
+ SMESH::long_array_var anIDs = theGrp->GetIDs();
+ arrayToSet( anIDs, theMeshDS, theElemSet, theType);
+}
+
+CORBA::Boolean SMESH_MeshEditor_i::DoubleNodeGroup(
+ SMESH::SMESH_GroupBase_ptr theElems,
+ SMESH::SMESH_GroupBase_ptr theNodesNot,
+ SMESH::SMESH_GroupBase_ptr theAffectedElems )
+
+{
+ if ( CORBA::is_nil( theElems ) && theElems->GetType() == SMESH::NODE )
+ return false;
+
+ initData();
+
+ ::SMESH_MeshEditor aMeshEditor( myMesh );
+
+ SMESHDS_Mesh* aMeshDS = GetMeshDS();
+ TIDSortedElemSet anElems, aNodes, anAffected;
+ groupToSet( theElems, aMeshDS, anElems, SMDSAbs_All );
+ groupToSet( theNodesNot, aMeshDS, aNodes, SMDSAbs_Node );
+ groupToSet( theAffectedElems, aMeshDS, anAffected, SMDSAbs_All );
+
+ bool aResult = aMeshEditor.DoubleNodes( anElems, aNodes, anAffected );
+
+ storeResult( aMeshEditor) ;
+
+ return aResult;
+}
+
+//================================================================================
+/*!
+ \brief Creates a hole in a mesh by doubling the nodes of some particular elements
+ \param theElems - group of of elements (edges or faces) to be replicated
+ \param theNodesNot - group of nodes not to replicated
+ \param theShape - shape to detect affected elements (element which geometric center
+ located on or inside shape).
+ The replicated nodes should be associated to affected elements.
+ \return TRUE if operation has been completed successfully, FALSE otherwise
+ \sa DoubleNodesInRegion(), DoubleNodeGroupsInRegion()
+*/
+//================================================================================
+
+CORBA::Boolean SMESH_MeshEditor_i::DoubleNodeGroupInRegion(
+ SMESH::SMESH_GroupBase_ptr theElems,
+ SMESH::SMESH_GroupBase_ptr theNodesNot,
+ GEOM::GEOM_Object_ptr theShape )
+
+{
+ if ( CORBA::is_nil( theElems ) && theElems->GetType() == SMESH::NODE )
+ return false;
+
+ initData();
+
+ ::SMESH_MeshEditor aMeshEditor( myMesh );
+
+ SMESHDS_Mesh* aMeshDS = GetMeshDS();
+ TIDSortedElemSet anElems, aNodes, anAffected;
+ groupToSet( theElems, aMeshDS, anElems, SMDSAbs_All );
+ groupToSet( theNodesNot, aMeshDS, aNodes, SMDSAbs_Node );
+
+ TopoDS_Shape aShape = SMESH_Gen_i::GetSMESHGen()->GeomObjectToShape( theShape );
+ bool aResult = aMeshEditor.DoubleNodesInRegion( anElems, aNodes, aShape );
+
+ storeResult( aMeshEditor) ;
+
+ return aResult;
+}
+
+//================================================================================
+/*!
+ \brief Creates a hole in a mesh by doubling the nodes of some particular elements
+ This method provided for convenience works as DoubleNodes() described above.
+ \param theElems - list of groups of elements (edges or faces) to be replicated
+ \param theNodesNot - list of groups of nodes not to replicated
+ \param theAffectedElems - group of elements to which the replicated nodes
+ should be associated to.
+ \return TRUE if operation has been completed successfully, FALSE otherwise
+ \sa DoubleNodeGroup(), DoubleNodes()
+*/
+//================================================================================
+
+static void listOfGroupToSet(const SMESH::ListOfGroups& theGrpList,
+ SMESHDS_Mesh* theMeshDS,
+ TIDSortedElemSet& theElemSet,
+ const bool theIsNodeGrp)
+{
+ for ( int i = 0, n = theGrpList.length(); i < n; i++ )
+ {
+ SMESH::SMESH_GroupBase_var aGrp = theGrpList[ i ];
+ if ( !CORBA::is_nil( aGrp ) && (theIsNodeGrp ? aGrp->GetType() == SMESH::NODE
+ : aGrp->GetType() != SMESH::NODE ) )
+ {
+ SMESH::long_array_var anIDs = aGrp->GetIDs();
+ arrayToSet( anIDs, theMeshDS, theElemSet, theIsNodeGrp ? SMDSAbs_Node : SMDSAbs_All );
+ }
+ }
+}
+
+CORBA::Boolean SMESH_MeshEditor_i::DoubleNodeGroups(
+ const SMESH::ListOfGroups& theElems,
+ const SMESH::ListOfGroups& theNodesNot,
+ const SMESH::ListOfGroups& theAffectedElems )
+{
+ initData();
+
+ ::SMESH_MeshEditor aMeshEditor( myMesh );
+
+ SMESHDS_Mesh* aMeshDS = GetMeshDS();
+ TIDSortedElemSet anElems, aNodes, anAffected;
+ listOfGroupToSet(theElems, aMeshDS, anElems, false );
+ listOfGroupToSet(theNodesNot, aMeshDS, aNodes, true );
+ listOfGroupToSet(theAffectedElems, aMeshDS, anAffected, false );
+
+ bool aResult = aMeshEditor.DoubleNodes( anElems, aNodes, anAffected );
+
+ storeResult( aMeshEditor) ;
+
+ return aResult;
+}
+
+//================================================================================
+/*!
+ \brief Creates a hole in a mesh by doubling the nodes of some particular elements
+ This method provided for convenience works as DoubleNodes() described above.
+ \param theElems - list of groups of elements (edges or faces) to be replicated
+ \param theNodesNot - list of groups of nodes not to replicated
+ \param theShape - shape to detect affected elements (element which geometric center
+ located on or inside shape).
+ The replicated nodes should be associated to affected elements.
+ \return TRUE if operation has been completed successfully, FALSE otherwise
+ \sa DoubleNodeGroupInRegion(), DoubleNodesInRegion()
+*/
+//================================================================================
+
+CORBA::Boolean SMESH_MeshEditor_i::DoubleNodeGroupsInRegion(
+ const SMESH::ListOfGroups& theElems,
+ const SMESH::ListOfGroups& theNodesNot,
+ GEOM::GEOM_Object_ptr theShape )
+{
+ initData();
+
+ ::SMESH_MeshEditor aMeshEditor( myMesh );
+
+ SMESHDS_Mesh* aMeshDS = GetMeshDS();
+ TIDSortedElemSet anElems, aNodes;
+ listOfGroupToSet(theElems, aMeshDS, anElems,false );
+ listOfGroupToSet(theNodesNot, aMeshDS, aNodes, true );
+
+ TopoDS_Shape aShape = SMESH_Gen_i::GetSMESHGen()->GeomObjectToShape( theShape );
+ bool aResult = aMeshEditor.DoubleNodesInRegion( anElems, aNodes, aShape );
+
+ storeResult( aMeshEditor) ;
+
+ return aResult;