]> SALOME platform Git repositories - modules/smesh.git/commitdiff
Salome HOME
Revert "23418: [OCC] Mesh: Minimization of memory usage of SMESH" uhz/V8_5_BR_wo_min_of_memory_usage
authoruhz <ulysse.humbert-gonzalez@opencascade.com>
Mon, 16 Apr 2018 08:57:55 +0000 (10:57 +0200)
committerTMA Salome <tma.edf@opencascade.com>
Mon, 16 Apr 2018 09:05:49 +0000 (11:05 +0200)
This reverts commit 4c16067d4281f56bd07d3f92fb63fff9c0c1d169.

148 files changed:
src/Controls/SMESH_Controls.cxx
src/Driver/CMakeLists.txt
src/DriverCGNS/DriverCGNS_Read.cxx
src/DriverCGNS/DriverCGNS_Write.cxx
src/DriverDAT/DriverDAT_W_SMDS_Mesh.cxx
src/DriverGMF/DriverGMF_Read.cxx
src/DriverMED/DriverMED_Family.cxx
src/DriverMED/DriverMED_Family.h
src/DriverMED/DriverMED_R_SMESHDS_Mesh.cxx
src/DriverMED/DriverMED_W_Field.cxx
src/DriverMED/DriverMED_W_SMESHDS_Mesh.cxx
src/DriverMED/DriverMED_W_SMESHDS_Mesh.h
src/DriverSTL/DriverSTL_R_SMDS_Mesh.cxx
src/DriverUNV/DriverUNV_R_SMDS_Mesh.cxx
src/DriverUNV/DriverUNV_R_SMDS_Mesh.h
src/DriverUNV/DriverUNV_W_SMDS_Mesh.cxx
src/DriverUNV/UNV2417_Structure.hxx
src/OBJECT/SMESH_Object.cxx
src/SMDS/CMakeLists.txt
src/SMDS/Notes [new file with mode: 0644]
src/SMDS/ObjectPool.hxx
src/SMDS/SMDS_BallElement.cxx
src/SMDS/SMDS_BallElement.hxx
src/SMDS/SMDS_CellOfNodes.cxx [deleted file]
src/SMDS/SMDS_CellOfNodes.hxx [deleted file]
src/SMDS/SMDS_Downward.cxx
src/SMDS/SMDS_EdgePosition.cxx [new file with mode: 0644]
src/SMDS/SMDS_EdgePosition.hxx
src/SMDS/SMDS_ElementFactory.cxx [deleted file]
src/SMDS/SMDS_ElementFactory.hxx [deleted file]
src/SMDS/SMDS_ElementHolder.cxx [deleted file]
src/SMDS/SMDS_ElementHolder.hxx [deleted file]
src/SMDS/SMDS_FaceOfEdges.cxx [new file with mode: 0644]
src/SMDS/SMDS_FaceOfEdges.hxx [new file with mode: 0644]
src/SMDS/SMDS_FaceOfNodes.cxx
src/SMDS/SMDS_FaceOfNodes.hxx
src/SMDS/SMDS_FacePosition.cxx
src/SMDS/SMDS_FacePosition.hxx
src/SMDS/SMDS_Iterator.hxx
src/SMDS/SMDS_IteratorOfElements.cxx [new file with mode: 0644]
src/SMDS/SMDS_IteratorOfElements.hxx [new file with mode: 0644]
src/SMDS/SMDS_LinearEdge.cxx
src/SMDS/SMDS_LinearEdge.hxx
src/SMDS/SMDS_Mesh.cxx
src/SMDS/SMDS_Mesh.hxx
src/SMDS/SMDS_Mesh0DElement.cxx [new file with mode: 0644]
src/SMDS/SMDS_Mesh0DElement.hxx
src/SMDS/SMDS_MeshCell.cxx
src/SMDS/SMDS_MeshCell.hxx
src/SMDS/SMDS_MeshEdge.cxx [new file with mode: 0644]
src/SMDS/SMDS_MeshEdge.hxx
src/SMDS/SMDS_MeshElement.cxx
src/SMDS/SMDS_MeshElement.hxx
src/SMDS/SMDS_MeshElementIDFactory.cxx [new file with mode: 0644]
src/SMDS/SMDS_MeshElementIDFactory.hxx [new file with mode: 0644]
src/SMDS/SMDS_MeshFace.cxx [new file with mode: 0644]
src/SMDS/SMDS_MeshFace.hxx
src/SMDS/SMDS_MeshGroup.cxx
src/SMDS/SMDS_MeshGroup.hxx
src/SMDS/SMDS_MeshIDFactory.cxx [new file with mode: 0644]
src/SMDS/SMDS_MeshIDFactory.hxx [new file with mode: 0644]
src/SMDS/SMDS_MeshNode.cxx
src/SMDS/SMDS_MeshNode.hxx
src/SMDS/SMDS_MeshNodeIDFactory.cxx [new file with mode: 0644]
src/SMDS/SMDS_MeshNodeIDFactory.hxx [new file with mode: 0644]
src/SMDS/SMDS_MeshVolume.cxx
src/SMDS/SMDS_MeshVolume.hxx
src/SMDS/SMDS_PolygonalFaceOfNodes.cxx
src/SMDS/SMDS_PolygonalFaceOfNodes.hxx
src/SMDS/SMDS_PolyhedralVolumeOfNodes.cxx [new file with mode: 0644]
src/SMDS/SMDS_PolyhedralVolumeOfNodes.hxx [new file with mode: 0644]
src/SMDS/SMDS_Position.cxx [new file with mode: 0644]
src/SMDS/SMDS_Position.hxx
src/SMDS/SMDS_QuadraticEdge.cxx [new file with mode: 0644]
src/SMDS/SMDS_QuadraticEdge.hxx [new file with mode: 0644]
src/SMDS/SMDS_QuadraticFaceOfNodes.cxx [new file with mode: 0644]
src/SMDS/SMDS_QuadraticFaceOfNodes.hxx [new file with mode: 0644]
src/SMDS/SMDS_QuadraticVolumeOfNodes.cxx [new file with mode: 0644]
src/SMDS/SMDS_QuadraticVolumeOfNodes.hxx [new file with mode: 0644]
src/SMDS/SMDS_SpacePosition.cxx
src/SMDS/SMDS_SpacePosition.hxx
src/SMDS/SMDS_UnstructuredGrid.cxx
src/SMDS/SMDS_UnstructuredGrid.hxx
src/SMDS/SMDS_VertexPosition.cxx [new file with mode: 0644]
src/SMDS/SMDS_VertexPosition.hxx
src/SMDS/SMDS_VolumeOfFaces.cxx [new file with mode: 0644]
src/SMDS/SMDS_VolumeOfFaces.hxx [new file with mode: 0644]
src/SMDS/SMDS_VolumeOfNodes.cxx
src/SMDS/SMDS_VolumeOfNodes.hxx
src/SMDS/SMDS_VolumeTool.cxx
src/SMDS/SMDS_VolumeTool.hxx
src/SMDS/SMDS_VtkCellIterator.cxx
src/SMDS/SMDS_VtkCellIterator.hxx
src/SMDS/SMDS_VtkEdge.cxx [new file with mode: 0644]
src/SMDS/SMDS_VtkEdge.hxx [new file with mode: 0644]
src/SMDS/SMDS_VtkFace.cxx [new file with mode: 0644]
src/SMDS/SMDS_VtkFace.hxx [new file with mode: 0644]
src/SMDS/SMDS_VtkVolume.cxx [new file with mode: 0644]
src/SMDS/SMDS_VtkVolume.hxx [new file with mode: 0644]
src/SMESH/SMESH_Algo.cxx
src/SMESH/SMESH_Algo.hxx
src/SMESH/SMESH_Gen.cxx
src/SMESH/SMESH_Mesh.cxx
src/SMESH/SMESH_MeshEditor.cxx
src/SMESH/SMESH_MesherHelper.cxx
src/SMESH/SMESH_Pattern.cxx
src/SMESH/SMESH_ProxyMesh.cxx
src/SMESH/SMESH_ProxyMesh.hxx
src/SMESH/SMESH_subMesh.cxx
src/SMESHClient/SMESH_Client.cxx
src/SMESHDS/SMESHDS_Group.cxx
src/SMESHDS/SMESHDS_GroupOnFilter.cxx
src/SMESHDS/SMESHDS_GroupOnFilter.hxx
src/SMESHDS/SMESHDS_Mesh.cxx
src/SMESHDS/SMESHDS_Mesh.hxx
src/SMESHDS/SMESHDS_SubMesh.cxx
src/SMESHDS/SMESHDS_SubMesh.hxx
src/SMESHGUI/SMESHGUI_ExtrusionDlg.cxx
src/SMESHGUI/SMESHGUI_GroupDlg.cxx
src/SMESHGUI/SMESHGUI_MeshInfo.cxx
src/SMESHGUI/SMESHGUI_PreVisualObj.cxx
src/SMESHGUI/SMESHGUI_RevolutionDlg.cxx
src/SMESHUtils/SMESH_ComputeError.hxx
src/SMESHUtils/SMESH_FillHole.cxx
src/SMESHUtils/SMESH_FreeBorders.cxx
src/SMESHUtils/SMESH_MeshAlgos.cxx
src/SMESHUtils/SMESH_TryCatch.cxx
src/SMESH_I/SMESH_Gen_i.cxx
src/SMESH_I/SMESH_Measurements_i.cxx
src/SMESH_I/SMESH_MeshEditor_i.cxx
src/SMESH_I/SMESH_MeshPartDS.hxx
src/SMESH_I/SMESH_Mesh_i.cxx
src/SMESH_I/SMESH_PreMeshInfo.cxx
src/StdMeshers/StdMeshers_Cartesian_3D.cxx
src/StdMeshers/StdMeshers_FaceSide.cxx
src/StdMeshers/StdMeshers_HexaFromSkin_3D.cxx
src/StdMeshers/StdMeshers_Import_1D2D.cxx
src/StdMeshers/StdMeshers_MEFISTO_2D.cxx
src/StdMeshers/StdMeshers_Penta_3D.cxx
src/StdMeshers/StdMeshers_Prism_3D.cxx
src/StdMeshers/StdMeshers_ProjectionUtils.cxx
src/StdMeshers/StdMeshers_Projection_1D2D.cxx
src/StdMeshers/StdMeshers_Projection_2D.cxx
src/StdMeshers/StdMeshers_Projection_3D.cxx
src/StdMeshers/StdMeshers_QuadToTriaAdaptor.cxx
src/StdMeshers/StdMeshers_Quadrangle_2D.cxx
src/StdMeshers/StdMeshers_ViscousLayers.cxx
src/StdMeshers/StdMeshers_ViscousLayers2D.cxx

index 1ccd96f9905611d39a69424bcebb65a90f437dc6..b1279a6594d78ec63fecc1d34b2f792ea758e6c3 100644 (file)
@@ -28,6 +28,8 @@
 #include "SMDS_Mesh.hxx"
 #include "SMDS_MeshElement.hxx"
 #include "SMDS_MeshNode.hxx"
+#include "SMDS_QuadraticEdge.hxx"
+#include "SMDS_QuadraticFaceOfNodes.hxx"
 #include "SMDS_VolumeTool.hxx"
 #include "SMESHDS_GroupBase.hxx"
 #include "SMESHDS_GroupOnFilter.hxx"
@@ -251,7 +253,26 @@ bool NumericalFunctor::GetPoints(const SMDS_MeshElement* anElem,
   theRes.setElement( anElem );
 
   // Get nodes of the element
-  SMDS_NodeIteratorPtr anIter= anElem->interlacedNodesIterator();
+  SMDS_ElemIteratorPtr anIter;
+
+  if ( anElem->IsQuadratic() ) {
+    switch ( anElem->GetType() ) {
+    case SMDSAbs_Edge:
+      anIter = dynamic_cast<const SMDS_VtkEdge*>
+        (anElem)->interlacedNodesElemIterator();
+      break;
+    case SMDSAbs_Face:
+      anIter = dynamic_cast<const SMDS_VtkFace*>
+        (anElem)->interlacedNodesElemIterator();
+      break;
+    default:
+      anIter = anElem->nodesIterator();
+    }
+  }
+  else {
+    anIter = anElem->nodesIterator();
+  }
+
   if ( anIter ) {
     SMESH_NodeXYZ p;
     while( anIter->more() ) {
@@ -750,8 +771,8 @@ double AspectRatio::GetValue( long theId )
   if ( myCurrElement && myCurrElement->GetVtkType() == VTK_QUAD )
   {
     // issue 21723
-    vtkUnstructuredGrid* grid = const_cast<SMDS_Mesh*>( myMesh )->GetGrid();
-    if ( vtkCell* avtkCell = grid->GetCell( myCurrElement->GetVtkID() ))
+    vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myCurrElement->getMeshId()]->getGrid();
+    if ( vtkCell* avtkCell = grid->GetCell( myCurrElement->getVtkId() ))
       aVal = Round( vtkMeshQuality::QuadAspectRatio( avtkCell ));
   }
   else
@@ -994,8 +1015,8 @@ double AspectRatio3D::GetValue( long theId )
     // Action from CoTech | ACTION 31.3:
     // EURIWARE BO: Homogenize the formulas used to calculate the Controls in SMESH to fit with
     // those of ParaView. The library used by ParaView for those calculations can be reused in SMESH.
-    vtkUnstructuredGrid* grid = const_cast<SMDS_Mesh*>( myMesh )->GetGrid();
-    if ( vtkCell* avtkCell = grid->GetCell( myCurrElement->GetVtkID() ))
+    vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myCurrElement->getMeshId()]->getGrid();
+    if ( vtkCell* avtkCell = grid->GetCell( myCurrElement->getVtkId() ))
       aVal = Round( vtkMeshQuality::TetAspectRatio( avtkCell ));
   }
   else
@@ -1014,7 +1035,7 @@ double AspectRatio3D::GetValue( const TSequenceOfXYZ& P )
 
   int nbNodes = P.size();
 
-  if( myCurrElement->IsQuadratic() ) {
+  if(myCurrElement->IsQuadratic()) {
     if(nbNodes==10) nbNodes=4; // quadratic tetrahedron
     else if(nbNodes==13) nbNodes=5; // quadratic pyramid
     else if(nbNodes==15) nbNodes=6; // quadratic pentahedron
@@ -1806,33 +1827,35 @@ bool Length2D::Value::operator<(const Length2D::Value& x) const
 void Length2D::GetValues(TValues& theValues)
 {
   TValues aValues;
-  for ( SMDS_FaceIteratorPtr anIter = myMesh->facesIterator(); anIter->more(); )
-  {
+  SMDS_FaceIteratorPtr anIter = myMesh->facesIterator();
+  for(; anIter->more(); ){
     const SMDS_MeshFace* anElem = anIter->next();
-    if ( anElem->IsQuadratic() )
-    {
+
+    if(anElem->IsQuadratic()) {
+      const SMDS_VtkFace* F =
+        dynamic_cast<const SMDS_VtkFace*>(anElem);
       // use special nodes iterator
-      SMDS_NodeIteratorPtr anIter = anElem->interlacedNodesIterator();
+      SMDS_ElemIteratorPtr anIter = F->interlacedNodesElemIterator();
       long aNodeId[4] = { 0,0,0,0 };
       gp_Pnt P[4];
 
       double aLength = 0;
-      if ( anIter->more() )
-      {
-        const SMDS_MeshNode* aNode = anIter->next();
-        P[0] = P[1] = SMESH_NodeXYZ( aNode );
+      const SMDS_MeshElement* aNode;
+      if(anIter->more()){
+        aNode = anIter->next();
+        const SMDS_MeshNode* aNodes = (SMDS_MeshNode*) aNode;
+        P[0] = P[1] = gp_Pnt(aNodes->X(),aNodes->Y(),aNodes->Z());
         aNodeId[0] = aNodeId[1] = aNode->GetID();
         aLength = 0;
       }
-      for ( ; anIter->more(); )
-      {
-        const SMDS_MeshNode* N1 = anIter->next();
-        P[2] = SMESH_NodeXYZ( N1 );
+      for(; anIter->more(); ){
+        const SMDS_MeshNode* N1 = static_cast<const SMDS_MeshNode*> (anIter->next());
+        P[2] = gp_Pnt(N1->X(),N1->Y(),N1->Z());
         aNodeId[2] = N1->GetID();
         aLength = P[1].Distance(P[2]);
         if(!anIter->more()) break;
-        const SMDS_MeshNode* N2 = anIter->next();
-        P[3] = SMESH_NodeXYZ( N2 );
+        const SMDS_MeshNode* N2 = static_cast<const SMDS_MeshNode*> (anIter->next());
+        P[3] = gp_Pnt(N2->X(),N2->Y(),N2->Z());
         aNodeId[3] = N2->GetID();
         aLength += P[2].Distance(P[3]);
         Value aValue1(aLength,aNodeId[1],aNodeId[2]);
@@ -1849,28 +1872,28 @@ void Length2D::GetValues(TValues& theValues)
       theValues.insert(aValue2);
     }
     else {
-      SMDS_NodeIteratorPtr aNodesIter = anElem->nodeIterator();
+      SMDS_ElemIteratorPtr aNodesIter = anElem->nodesIterator();
       long aNodeId[2] = {0,0};
       gp_Pnt P[3];
 
       double aLength;
       const SMDS_MeshElement* aNode;
-      if ( aNodesIter->more())
-      {
+      if(aNodesIter->more()){
         aNode = aNodesIter->next();
-        P[0] = P[1] = SMESH_NodeXYZ( aNode );
+        const SMDS_MeshNode* aNodes = (SMDS_MeshNode*) aNode;
+        P[0] = P[1] = gp_Pnt(aNodes->X(),aNodes->Y(),aNodes->Z());
         aNodeId[0] = aNodeId[1] = aNode->GetID();
         aLength = 0;
       }
-      for( ; aNodesIter->more(); )
-      {
+      for(; aNodesIter->more(); ){
         aNode = aNodesIter->next();
+        const SMDS_MeshNode* aNodes = (SMDS_MeshNode*) aNode;
         long anId = aNode->GetID();
-
-        P[2] = SMESH_NodeXYZ( aNode );
-
+        
+        P[2] = gp_Pnt(aNodes->X(),aNodes->Y(),aNodes->Z());
+        
         aLength = P[1].Distance(P[2]);
-
+        
         Value aValue(aLength,aNodeId[1],anId);
         aNodeId[1] = anId;
         P[1] = P[2];
@@ -1924,7 +1947,8 @@ double Deflection2D::GetValue( const TSequenceOfXYZ& P )
       {
         gc += P(i+1);
 
-        if ( SMDS_FacePositionPtr fPos = P.getElement()->GetNode( i )->GetPosition() )
+        if ( const SMDS_FacePosition* fPos = dynamic_cast<const SMDS_FacePosition*>
+             ( P.getElement()->GetNode( i )->GetPosition() ))
         {
           uv.ChangeCoord(1) += fPos->GetUParameter();
           uv.ChangeCoord(2) += fPos->GetVParameter();
@@ -2100,24 +2124,59 @@ bool MultiConnection2D::Value::operator<(const MultiConnection2D::Value& x) cons
 void MultiConnection2D::GetValues(MValues& theValues)
 {
   if ( !myMesh ) return;
-  for ( SMDS_FaceIteratorPtr anIter = myMesh->facesIterator(); anIter->more(); )
-  {
-    const SMDS_MeshFace*     anElem = anIter->next();
-    SMDS_NodeIteratorPtr aNodesIter = anElem->interlacedNodesIterator();
+  SMDS_FaceIteratorPtr anIter = myMesh->facesIterator();
+  for(; anIter->more(); ){
+    const SMDS_MeshFace* anElem = anIter->next();
+    SMDS_ElemIteratorPtr aNodesIter;
+    if ( anElem->IsQuadratic() )
+      aNodesIter = dynamic_cast<const SMDS_VtkFace*>
+        (anElem)->interlacedNodesElemIterator();
+    else
+      aNodesIter = anElem->nodesIterator();
+    long aNodeId[3] = {0,0,0};
 
-    const SMDS_MeshNode* aNode1 = anElem->GetNode( anElem->NbNodes() - 1 );
+    //int aNbConnects=0;
+    const SMDS_MeshNode* aNode0;
+    const SMDS_MeshNode* aNode1;
     const SMDS_MeshNode* aNode2;
-    for ( ; aNodesIter->more(); )
-    {
-      aNode2 = aNodesIter->next();
-
-      Value aValue ( aNode1->GetID(), aNode2->GetID() );
-      MValues::iterator aItr = theValues.insert( std::make_pair( aValue, 0 )).first;
-      aItr->second++;
+    if(aNodesIter->more()){
+      aNode0 = (SMDS_MeshNode*) aNodesIter->next();
+      aNode1 = aNode0;
+      const SMDS_MeshNode* aNodes = (SMDS_MeshNode*) aNode1;
+      aNodeId[0] = aNodeId[1] = aNodes->GetID();
+    }
+    for(; aNodesIter->more(); ) {
+      aNode2 = (SMDS_MeshNode*) aNodesIter->next();
+      long anId = aNode2->GetID();
+      aNodeId[2] = anId;
+
+      Value aValue(aNodeId[1],aNodeId[2]);
+      MValues::iterator aItr = theValues.find(aValue);
+      if (aItr != theValues.end()){
+        aItr->second += 1;
+        //aNbConnects = nb;
+      }
+      else {
+        theValues[aValue] = 1;
+        //aNbConnects = 1;
+      }
+      //cout << "NodeIds: "<<aNodeId[1]<<","<<aNodeId[2]<<" nbconn="<<aNbConnects<<endl;
+      aNodeId[1] = aNodeId[2];
       aNode1 = aNode2;
     }
+    Value aValue(aNodeId[0],aNodeId[2]);
+    MValues::iterator aItr = theValues.find(aValue);
+    if (aItr != theValues.end()) {
+      aItr->second += 1;
+      //aNbConnects = nb;
+    }
+    else {
+      theValues[aValue] = 1;
+      //aNbConnects = 1;
+    }
+    //cout << "NodeIds: "<<aNodeId[0]<<","<<aNodeId[2]<<" nbconn="<<aNbConnects<<endl;
   }
-  return;
+
 }
 
 //================================================================================
@@ -2132,7 +2191,7 @@ double BallDiameter::GetValue( long theId )
   double diameter = 0;
 
   if ( const SMDS_BallElement* ball =
-       myMesh->DownCast< SMDS_BallElement >( myMesh->FindElement( theId )))
+       dynamic_cast<const SMDS_BallElement*>( myMesh->FindElement( theId )))
   {
     diameter = ball->GetDiameter();
   }
@@ -2370,7 +2429,7 @@ void CoincidentNodes::SetMesh( const SMDS_Mesh* theMesh )
   if ( myMeshModifTracer.IsMeshModified() )
   {
     TIDSortedNodeSet nodesToCheck;
-    SMDS_NodeIteratorPtr nIt = theMesh->nodesIterator();
+    SMDS_NodeIteratorPtr nIt = theMesh->nodesIterator(/*idInceasingOrder=*/true);
     while ( nIt->more() )
       nodesToCheck.insert( nodesToCheck.end(), nIt->next() );
 
@@ -2573,21 +2632,31 @@ inline void UpdateBorders(const FreeEdges::Border& theBorder,
 void FreeEdges::GetBoreders(TBorders& theBorders)
 {
   TBorders aRegistry;
-  for ( SMDS_FaceIteratorPtr anIter = myMesh->facesIterator(); anIter->more(); )
-  {
+  SMDS_FaceIteratorPtr anIter = myMesh->facesIterator();
+  for(; anIter->more(); ){
     const SMDS_MeshFace* anElem = anIter->next();
     long anElemId = anElem->GetID();
-    SMDS_NodeIteratorPtr aNodesIter = anElem->interlacedNodesIterator();
-    if ( !aNodesIter->more() ) continue;
+    SMDS_ElemIteratorPtr aNodesIter;
+    if ( anElem->IsQuadratic() )
+      aNodesIter = static_cast<const SMDS_VtkFace*>(anElem)->
+        interlacedNodesElemIterator();
+    else
+      aNodesIter = anElem->nodesIterator();
     long aNodeId[2] = {0,0};
-    aNodeId[0] = anElem->GetNode( anElem->NbNodes()-1 )->GetID();
-    for ( ; aNodesIter->more(); )
-    {
-      aNodeId[1] = aNodesIter->next()->GetID();
-      Border aBorder( anElemId, aNodeId[0], aNodeId[1] );
-      UpdateBorders( aBorder, aRegistry, theBorders );
-      aNodeId[0] = aNodeId[1];
+    const SMDS_MeshElement* aNode;
+    if(aNodesIter->more()){
+      aNode = aNodesIter->next();
+      aNodeId[0] = aNodeId[1] = aNode->GetID();
     }
+    for(; aNodesIter->more(); ){
+      aNode = aNodesIter->next();
+      long anId = aNode->GetID();
+      Border aBorder(anElemId,aNodeId[1],anId);
+      aNodeId[1] = anId;
+      UpdateBorders(aBorder,aRegistry,theBorders);
+    }
+    Border aBorder(anElemId,aNodeId[0],aNodeId[1]);
+    UpdateBorders(aBorder,aRegistry,theBorders);
   }
 }
 
@@ -3939,20 +4008,24 @@ void ManifoldPart::expandBoundary
 void ManifoldPart::getFacesByLink( const ManifoldPart::Link& theLink,
                                    ManifoldPart::TVectorOfFacePtr& theFaces ) const
 {
-
+  std::set<SMDS_MeshCell *> aSetOfFaces;
   // take all faces that shared first node
-  SMDS_ElemIteratorPtr anItr = theLink.myNode1->GetInverseElementIterator( SMDSAbs_Face );
-  SMDS_StdIterator< const SMDS_MeshElement*, SMDS_ElemIteratorPtr > faces( anItr ), facesEnd;
-  std::set<const SMDS_MeshElement *> aSetOfFaces( faces, facesEnd );
-
+  SMDS_ElemIteratorPtr anItr = theLink.myNode1->facesIterator();
+  for ( ; anItr->more(); )
+  {
+    SMDS_MeshFace* aFace = (SMDS_MeshFace*)anItr->next();
+    if ( !aFace )
+      continue;
+    aSetOfFaces.insert( aFace );
+  }
   // take all faces that shared second node
-  anItr = theLink.myNode2->GetInverseElementIterator( SMDSAbs_Face );
+  anItr = theLink.myNode2->facesIterator();
   // find the common part of two sets
   for ( ; anItr->more(); )
   {
-    const SMDS_MeshElement* aFace = anItr->next();
-    if ( aSetOfFaces.count( aFace ))
-      theFaces.push_back( (SMDS_MeshFace*) aFace );
+    SMDS_MeshFace* aFace = (SMDS_MeshFace*)anItr->next();
+    if ( aSetOfFaces.count( aFace ) )
+      theFaces.push_back( aFace );
   }
 }
 
index d4a1d5c0a21dc4b13b5eae866fb43e80f11e1a44..40d69423cd3aee45a9aa47d5d17c899893ae9bb0 100644 (file)
@@ -25,7 +25,6 @@ INCLUDE_DIRECTORIES(
   ${KERNEL_INCLUDE_DIRS}
   ${PROJECT_SOURCE_DIR}/src/SMESHUtils
   ${PROJECT_SOURCE_DIR}/src/SMESHDS
-  ${PROJECT_SOURCE_DIR}/src/SMDS
 )
 
 # additional preprocessor / compiler flags
index ba8daa44a34ad8415e73020a85f4e492b220c72b..c784acc9fa2f598f15b1f79eb8cca26a483025f2 100644 (file)
@@ -884,7 +884,7 @@ Driver_Mesh::Status DriverCGNS_Read::Perform()
                 {
                   const bool reverse = ( elemData[ pos-1 ] < 0 );
                   const int    iQuad = face->IsQuadratic() ? 1 : 0;
-                  SMDS_NodeIteratorPtr nIter = face->interlacedNodesIterator();
+                  SMDS_ElemIteratorPtr nIter = face->interlacedNodesElemIterator();
                   faceNodes.assign( SMDS_MeshElement::iterator( nIter ),
                                     SMDS_MeshElement::iterator());
                   if ( iQuad && reverse )
@@ -1184,9 +1184,6 @@ Driver_Mesh::Status DriverCGNS_Read::Perform()
 
   aResult = myErrorMessages.empty() ? DRS_OK : DRS_WARN_SKIP_ELEM;
 
-  myMesh->Modified();
-  myMesh->CompactMesh();
-
   return aResult;
 }
 
index 25dab65b638b33fd8f35903656d0bcc613279e57..4d79e0f7cca78c3a0b275f5c1ce2735b09e3eb5a 100644 (file)
@@ -301,26 +301,26 @@ Driver_Mesh::Status DriverCGNS_Write::Perform()
     vector< double > coords( myMesh->NbNodes() );
     int iC;
     // X
-    SMDS_NodeIteratorPtr nIt = myMesh->nodesIterator();
+    SMDS_NodeIteratorPtr nIt = myMesh->nodesIterator( /*idInceasingOrder=*/true );
     for ( int i = 0; nIt->more(); ++i ) coords[i] = nIt->next()->X();
     if ( cg_coord_write( _fn, iBase, iZone, CGNS_ENUMV(RealDouble),
                           "CoordinateX", &coords[0], &iC) != CG_OK )
       return addMessage( cg_get_error(), /*fatal = */true );
     // Y
-    nIt = myMesh->nodesIterator();
+    nIt = myMesh->nodesIterator( /*idInceasingOrder=*/true );
     for ( int i = 0; nIt->more(); ++i ) coords[i] = nIt->next()->Y();
     if ( cg_coord_write( _fn, iBase, iZone, CGNS_ENUMV(RealDouble),
                           "CoordinateY", &coords[0], &iC) != CG_OK )
       return addMessage( cg_get_error(), /*fatal = */true );
     // Z
-    nIt = myMesh->nodesIterator();
+    nIt = myMesh->nodesIterator( /*idInceasingOrder=*/true );
     for ( int i = 0; nIt->more(); ++i ) coords[i] = nIt->next()->Z();
     if ( cg_coord_write( _fn, iBase, iZone, CGNS_ENUMV(RealDouble),
                           "CoordinateZ", &coords[0], &iC) != CG_OK )
       return addMessage( cg_get_error(), /*fatal = */true );
 
     // store CGNS ids of nodes
-    nIt = myMesh->nodesIterator();
+    nIt = myMesh->nodesIterator( /*idInceasingOrder=*/true );
     for ( int i = 0; nIt->more(); ++i )
     {
       const SMDS_MeshElement* n = nIt->next();
index 403dad4f5634748cf6a0d38af896efa95deb158b..7ab288f86783fbf2ee439b4a2530f4a57cee52de 100644 (file)
@@ -117,7 +117,7 @@ Driver_Mesh::Status DriverDAT_W_SMDS_Mesh::Perform()
   }
 
   SMDS_VolumeIteratorPtr itVolumes=myMesh->volumesIterator();
-  const SMDS_MeshVolume* v;
+  const SMDS_VtkVolume* v;
   while(itVolumes->more())
   {
     const SMDS_MeshElement * elem = itVolumes->next();
@@ -125,7 +125,7 @@ Driver_Mesh::Status DriverDAT_W_SMDS_Mesh::Perform()
     {
       fprintf(aFileId, "%d %d ", elem->GetID(), 500+elem->NbNodes());
 
-      if (( v = myMesh->DownCast< SMDS_MeshVolume >( elem )))
+      if (( v = dynamic_cast< const SMDS_VtkVolume*>( elem )))
       {
         std::vector<int> quant = v->GetQuantities();
         if ( !quant.empty() )
@@ -146,7 +146,7 @@ Driver_Mesh::Status DriverDAT_W_SMDS_Mesh::Perform()
 
     fprintf(aFileId, "\n");
   }
-
+  
   fclose(aFileId);
 
   return aResult;
index 420b1495b246e9e3f43919ba6f1968ddcb68c698..54edf6a9c8413a0ab6f1e40bd62caa89026769f3 100644 (file)
@@ -444,9 +444,6 @@ Driver_Mesh::Status DriverGMF_Read::Perform()
     }
   }
 
-  myMesh->Modified();
-  myMesh->CompactMesh();
-
   return status;
 }
 
index a31488e4aabfe6b0287371869bf63df76c9dd874..a11ba4860bc88e09e8ef0f58ee1213ca38189fca 100644 (file)
@@ -574,21 +574,3 @@ void DriverMED_Family::Split (DriverMED_FamilyPtr by,
     common->myType = myType;
   }
 }
-
-//================================================================================
-/*!
- * \brief Return a number of elements of a given type
- */
-//================================================================================
-
-size_t DriverMED_Family::NbElements( SMDSAbs_ElementType theType ) const
-{
-  if ( myTypes.size() < 2 )
-    return myElements.size();
-
-  int nb = 0;
-  for ( ElementsSet::iterator e = myElements.begin(); e != myElements.end(); ++e )
-    nb += ( theType == (*e)->GetType() );
-
-  return nb;
-}
index 97157a2a3b710599921f3121fea393a0e77d9af4..c71ea7254622a777ad0336c91831083a5d965db3 100644 (file)
@@ -119,11 +119,9 @@ class MESHDRIVERMED_EXPORT DriverMED_Family
 
   bool MemberOf(std::string theGroupName) const;
 
-  int  GetGroupAttributVal() const;
+  int GetGroupAttributVal() const;
   void SetGroupAttributVal( int theValue);
 
-  size_t NbElements( SMDSAbs_ElementType ) const;
-
  private:
   //! Initialize the tool by SMESHDS_GroupBase
   void Init (SMESHDS_GroupBase* group);
index 14a648c8a1843b5dc6fe80d6d232ba3840e6842d..000316955a73241fe05852f971e80d25461f14b6 100644 (file)
@@ -273,7 +273,7 @@ Driver_Mesh::Status DriverMED_R_SMESHDS_Mesh::Perform()
             if ( anIsElemNum && !aBallInfo->myElemNum->empty() )
               maxID = *std::max_element( aBallInfo->myElemNum->begin(),
                                          aBallInfo->myElemNum->end() );
-            myMesh->GetGrid()->AllocateDiameters( maxID ); // performance optimization
+            myMesh->getGrid()->AllocateDiameters( maxID ); // performance optimization
 
             // create balls
             SMDS_MeshElement* anElement;
@@ -1038,6 +1038,8 @@ Driver_Mesh::Status DriverMED_R_SMESHDS_Mesh::Perform()
     aResult = addMessage( "Unknown exception", /*isFatal=*/true );
   }
 #endif
+  if (myMesh)
+    myMesh->compactMesh();
 
   // Mantis issue 0020483
   if (aResult == DRS_OK && isDescConn) {
@@ -1135,14 +1137,6 @@ void DriverMED_R_SMESHDS_Mesh::GetGroup(SMESHDS_Group* theGroup)
 
   if (( famVecPtr = myGroups2FamiliesMap.ChangeSeek( aGroupName )))
   {
-    size_t groupSize = 0;
-    for ( size_t i = 0; i < famVecPtr->size(); ++i )
-    {
-      DriverMED_FamilyPtr aFamily = (*famVecPtr)[i];
-      groupSize += aFamily->NbElements( theGroup->GetType() );
-    }
-    theGroup->SMDSGroup().Reserve( groupSize );
-
     for ( size_t i = 0; i < famVecPtr->size(); ++i )
     {
       DriverMED_FamilyPtr aFamily = (*famVecPtr)[i];
index 8317ae96b4cbe1ea23e76303f96db593a3035f7c..57e8edf19482b6db36f39ebea2646fcad0a6d9e5 100644 (file)
@@ -33,6 +33,7 @@
 #include "MED_Wrapper.hxx"
 #include "SMDS_IteratorOnIterators.hxx"
 #include "SMDS_MeshElement.hxx"
+#include "SMDS_PolyhedralVolumeOfNodes.hxx"
 #include "SMDS_SetIterator.hxx"
 #include "SMESHDS_Mesh.hxx"
 
@@ -100,7 +101,7 @@ bool DriverMED_W_Field::Set(SMESHDS_Mesh *      mesh,
     for ( int iG = 0; iG < SMDSEntity_Last; ++iG )
     {
       SMDSAbs_EntityType  geom = (SMDSAbs_EntityType) iG;
-      SMDSAbs_ElementType    t = SMDS_MeshCell::ElemType( geom );
+      SMDSAbs_ElementType t = SMDS_MeshCell::toSmdsType( geom );
       if ( t != _elemType ) continue;
 
       nbElems = mesh->GetMeshInfo().NbElements( geom );
index c33517ca0c009f8f13e9f290388df08dad7d73c3..75ebf667aef77b4fd8a0999a6abb512c48e3385a 100644 (file)
@@ -31,7 +31,9 @@
 #include "MED_Factory.hxx"
 #include "MED_Utilities.hxx"
 #include "SMDS_IteratorOnIterators.hxx"
+#include "SMDS_MeshElement.hxx"
 #include "SMDS_MeshNode.hxx"
+#include "SMDS_PolyhedralVolumeOfNodes.hxx"
 #include "SMDS_SetIterator.hxx"
 #include "SMESHDS_Mesh.hxx"
 
@@ -358,6 +360,10 @@ namespace
 Driver_Mesh::Status DriverMED_W_SMESHDS_Mesh::Perform()
 {
   Status aResult = DRS_OK;
+  if (myMesh->hasConstructionEdges() || myMesh->hasConstructionFaces()) {
+    INFOS("SMDS_MESH with hasConstructionEdges() or hasConstructionFaces() do not supports!!!");
+    return DRS_FAIL;
+  }
   try {
     //MESSAGE("Perform - myFile : "<<myFile);
 
@@ -402,7 +408,7 @@ Driver_Mesh::Status DriverMED_W_SMESHDS_Mesh::Perform()
           const SMDS_MeshNode* aNode = aNodesIter->next();
           aBounds[0] = min(aBounds[0],aNode->X());
           aBounds[1] = max(aBounds[1],aNode->X());
-
+          
           aBounds[2] = min(aBounds[2],aNode->Y());
           aBounds[3] = max(aBounds[3],aNode->Y());
 
@@ -448,7 +454,7 @@ Driver_Mesh::Status DriverMED_W_SMESHDS_Mesh::Perform()
         }
       }
 
-      SMDS_NodeIteratorPtr aNodesIter = myMesh->nodesIterator();
+      SMDS_NodeIteratorPtr aNodesIter = myMesh->nodesIterator(/*idInceasingOrder=*/true);
       switch ( aSpaceDimension ) {
       case 3:
         aCoordHelperPtr.reset(new TCoordHelper(aNodesIter,aXYZGetCoord,aXYZName));
@@ -851,7 +857,7 @@ Driver_Mesh::Status DriverMED_W_SMESHDS_Mesh::Perform()
 
       // Treat POLYEDREs
       // ----------------
-      else if ( aElemTypeData->_geomType == ePOLYEDRE )
+      else if (aElemTypeData->_geomType == ePOLYEDRE )
       {
         elemIterator = myMesh->elementGeomIterator( SMDSGeom_POLYHEDRA );
 
@@ -859,8 +865,10 @@ Driver_Mesh::Status DriverMED_W_SMESHDS_Mesh::Perform()
           // Count nb of nodes
           while ( elemIterator->more() ) {
             const SMDS_MeshElement*  anElem = elemIterator->next();
-            nbPolyhedronNodes += anElem->NbNodes();
-            nbPolyhedronFaces += anElem->NbFaces();
+            const SMDS_VtkVolume *aPolyedre = dynamic_cast<const SMDS_VtkVolume*>(anElem);
+            if ( !aPolyedre ) continue;
+            nbPolyhedronNodes += aPolyedre->NbNodes();
+            nbPolyhedronFaces += aPolyedre->NbFaces();
             if ( ++iElem == aElemTypeData->_nbElems )
               break;
           }
@@ -885,8 +893,8 @@ Driver_Mesh::Status DriverMED_W_SMESHDS_Mesh::Perform()
           TInt iFace = 0, iNode = 0;
           while ( elemIterator->more() )
           {
-            const SMDS_MeshElement* anElem = elemIterator->next();
-            const SMDS_MeshVolume *aPolyedre = myMesh->DownCast< SMDS_MeshVolume >( anElem );
+            const SMDS_MeshElement*  anElem = elemIterator->next();
+            const SMDS_VtkVolume *aPolyedre = dynamic_cast<const SMDS_VtkVolume*>(anElem);
             if ( !aPolyedre ) continue;
             // index
             TInt aNbFaces = aPolyedre->NbFaces();
index 9c24099b47116a9d0845a59c5cadd9b9b4dea5c4..a9539b9e8741fe509dc95803d76eab4d74c5e345 100644 (file)
@@ -40,7 +40,6 @@
 class SMESHDS_Mesh;
 class SMESHDS_GroupBase;
 class SMESHDS_SubMesh;
-class SMDS_MeshElement;
 
 class MESHDRIVERMED_EXPORT DriverMED_W_SMESHDS_Mesh: public Driver_SMESHDS_Mesh
 {
index f1e1ea6ac7448e88fe4bb87138951043810e9eba..ae7e48cca98a1d0b25af2faae85e51dca1d9962b 100644 (file)
@@ -142,9 +142,6 @@ Driver_Mesh::Status DriverSTL_R_SMDS_Mesh::Perform()
   else
     aResult = readBinary( file );
 
-  myMesh->Modified();
-  myMesh->CompactMesh();
-
   return aResult;
 }
 
index 10f7567f090aa9eae82d642ff298266f53ccc0aa..27576a613eaaf6abc26b65c4685a65a9c4613a9f 100644 (file)
@@ -93,11 +93,11 @@ namespace
 
 DriverUNV_R_SMDS_Mesh::~DriverUNV_R_SMDS_Mesh()
 {
-  TGroupNamesMap::iterator grp2name = myGroupNames.begin();
-  for ( ; grp2name != myGroupNames.end(); ++grp2name )
-    delete grp2name->first;
+  if (myGroup != 0) 
+    delete myGroup;
 }
 
+
 Driver_Mesh::Status DriverUNV_R_SMDS_Mesh::Perform()
 {
   Kernel_Utils::Localizer loc;
@@ -137,7 +137,7 @@ Driver_Mesh::Status DriverUNV_R_SMDS_Mesh::Perform()
         }
       }
       // Move nodes to SI unit system
-      const double lenFactor = aUnitsRecord.factors[ UNV164::LENGTH_FACTOR ];
+      const double lenFactor = aUnitsRecord.factors[ UNV164::LENGTH_FACTOR ]; 
       if ( lenFactor != 1. )
       {
         TDataSet::iterator nodeIter = aDataSet2411.begin(), nodeEnd;
@@ -187,23 +187,23 @@ Driver_Mesh::Status DriverUNV_R_SMDS_Mesh::Perform()
         else if(IsFace(aRec.fe_descriptor_id)) {
           //MESSAGE("add face " << aRec.label);
           switch(aRec.fe_descriptor_id){
-          case 41: // Plane Stress Linear Triangle
-          case 51: // Plane Strain Linear Triangle
-          case 61: // Plate Linear Triangle
-          case 74: // Membrane Linear Triangle
-          case 81: // Axisymetric Solid Linear Triangle
-          case 91: // Thin Shell Linear Triangle
+          case 41: // Plane Stress Linear Triangle      
+          case 51: // Plane Strain Linear Triangle      
+          case 61: // Plate Linear Triangle             
+          case 74: // Membrane Linear Triangle          
+          case 81: // Axisymetric Solid Linear Triangle 
+          case 91: // Thin Shell Linear Triangle        
             anElement = myMesh->AddFaceWithID(aRec.node_labels[0],
                                               aRec.node_labels[1],
                                               aRec.node_labels[2],
                                               aRec.label);
             break;
 
-          case 42: //  Plane Stress Parabolic Triangle
-          case 52: //  Plane Strain Parabolic Triangle
-          case 62: //  Plate Parabolic Triangle
-          case 72: //  Membrane Parabolic Triangle
-          case 82: //  Axisymetric Solid Parabolic Triangle
+          case 42: //  Plane Stress Parabolic Triangle       
+          case 52: //  Plane Strain Parabolic Triangle       
+          case 62: //  Plate Parabolic Triangle              
+          case 72: //  Membrane Parabolic Triangle           
+          case 82: //  Axisymetric Solid Parabolic Triangle  
           case 92: //  Thin Shell Parabolic Triangle
             if ( aRec.node_labels.size() == 7 )
               anElement = myMesh->AddFaceWithID(aRec.node_labels[0],
@@ -224,12 +224,12 @@ Driver_Mesh::Status DriverUNV_R_SMDS_Mesh::Perform()
                                                 aRec.label);
             break;
 
-          case 44: // Plane Stress Linear Quadrilateral
-          case 54: // Plane Strain Linear Quadrilateral
-          case 64: // Plate Linear Quadrilateral
-          case 71: // Membrane Linear Quadrilateral
+          case 44: // Plane Stress Linear Quadrilateral     
+          case 54: // Plane Strain Linear Quadrilateral     
+          case 64: // Plate Linear Quadrilateral            
+          case 71: // Membrane Linear Quadrilateral         
           case 84: // Axisymetric Solid Linear Quadrilateral
-          case 94: // Thin Shell Linear Quadrilateral
+          case 94: // Thin Shell Linear Quadrilateral       
             anElement = myMesh->AddFaceWithID(aRec.node_labels[0],
                                               aRec.node_labels[1],
                                               aRec.node_labels[2],
@@ -237,12 +237,12 @@ Driver_Mesh::Status DriverUNV_R_SMDS_Mesh::Perform()
                                               aRec.label);
             break;
 
-          case 45: // Plane Stress Parabolic Quadrilateral
-          case 55: // Plane Strain Parabolic Quadrilateral
-          case 65: // Plate Parabolic Quadrilateral
-          case 75: // Membrane Parabolic Quadrilateral
-          case 85: // Axisymetric Solid Parabolic Quadrilateral
-          case 95: // Thin Shell Parabolic Quadrilateral
+          case 45: // Plane Stress Parabolic Quadrilateral      
+          case 55: // Plane Strain Parabolic Quadrilateral      
+          case 65: // Plate Parabolic Quadrilateral             
+          case 75: // Membrane Parabolic Quadrilateral          
+          case 85: // Axisymetric Solid Parabolic Quadrilateral 
+          case 95: // Thin Shell Parabolic Quadrilateral        
             if ( aRec.node_labels.size() == 9 )
               anElement = myMesh->AddFaceWithID(aRec.node_labels[0],
                                                 aRec.node_labels[2],
@@ -295,7 +295,7 @@ Driver_Mesh::Status DriverUNV_R_SMDS_Mesh::Perform()
                                                 aRec.node_labels[7],
                                                 aRec.label);
             break;
-
+            
           case 112: // Solid Linear Prism - PRISM6
             anElement = myMesh->AddVolumeWithID(aRec.node_labels[0],
                                                 aRec.node_labels[2],
@@ -305,7 +305,7 @@ Driver_Mesh::Status DriverUNV_R_SMDS_Mesh::Perform()
                                                 aRec.node_labels[4],
                                                 aRec.label);
             break;
-
+            
           case 113: // Solid Quadratic Prism - PRISM15
             anElement = myMesh->AddVolumeWithID(aRec.node_labels[0],
                                                 aRec.node_labels[4],
@@ -328,7 +328,7 @@ Driver_Mesh::Status DriverUNV_R_SMDS_Mesh::Perform()
                                                 aRec.node_labels[7],
                                                 aRec.label);
             break;
-
+            
           case 115: // Solid Linear Brick - HEX8
             anElement = myMesh->AddVolumeWithID(aRec.node_labels[0],
                                                 aRec.node_labels[3],
@@ -396,63 +396,101 @@ Driver_Mesh::Status DriverUNV_R_SMDS_Mesh::Perform()
       }
     }
     {
-      using namespace UNV2417;
+      using namespace UNV2417;      
       TDataSet aDataSet2417;
       UNV2417::Read(in_stream,aDataSet2417);
       if(MYDEBUG) MESSAGE("Perform - aDataSet2417.size() = "<<aDataSet2417.size());
-      if (aDataSet2417.size() > 0)
-      {
+      if  (aDataSet2417.size() > 0) {
+        myGroup = new SMDS_MeshGroup(myMesh);
         TDataSet::const_iterator anIter = aDataSet2417.begin();
-        for ( ; anIter != aDataSet2417.end(); anIter++ )
-        {
+        for(; anIter != aDataSet2417.end(); anIter++){
+          const TGroupId& aLabel = anIter->first;
           const TRecord& aRec = anIter->second;
-          int        aNodesNb = aRec.NodeList.size();
-          int     aElementsNb = aRec.ElementList.size();
+
+          int aNodesNb = aRec.NodeList.size();
+          int aElementsNb = aRec.ElementList.size();
 
           bool useSuffix = ((aNodesNb > 0) && (aElementsNb > 0));
-          if ( aNodesNb > 0 )
-          {
-            SMDS_MeshGroup* aNodesGroup = new SMDS_MeshGroup( myMesh );
+          int i;
+          if (aNodesNb > 0) {
+            SMDS_MeshGroup* aNodesGroup = (SMDS_MeshGroup*) myGroup->AddSubGroup(SMDSAbs_Node);
             std::string aGrName = (useSuffix) ? aRec.GroupName + "_Nodes" : aRec.GroupName;
             int i = aGrName.find( "\r" );
             if (i > 0)
               aGrName.erase (i, 2);
-            myGroupNames.insert( std::make_pair( aNodesGroup, aGrName ));
+            myGroupNames.insert(TGroupNamesMap::value_type(aNodesGroup, aGrName));
+            myGroupId.insert(TGroupIdMap::value_type(aNodesGroup, aLabel));
 
-            for ( int i = 0; i < aNodesNb; i++ )
-              if ( const SMDS_MeshNode* aNode = myMesh->FindNode( aRec.NodeList[i] ))
-                aNodesGroup->Add( aNode );
+            for (i = 0; i < aNodesNb; i++) {
+              const SMDS_MeshNode* aNode = myMesh->FindNode(aRec.NodeList[i]);
+              if (aNode)
+                aNodesGroup->Add(aNode);
+            }
           }
-          if ( aElementsNb > 0 )
-          {
-            std::vector< SMDS_MeshGroup* > aGroupVec( SMDSAbs_NbElementTypes, (SMDS_MeshGroup*)0 );
-            const char* aSuffix[] = { "", "", "_Edges", "_Faces", "_Volumes", "_0D", "_Balls" };
+          if (aElementsNb > 0){
+            SMDS_MeshGroup* aEdgesGroup = 0;
+            SMDS_MeshGroup* aFacesGroup = 0;
+            SMDS_MeshGroup* aVolumeGroup = 0;
             bool createdGroup = false;
-            for ( int i = 0; i < aElementsNb; i++)
-            {
-              const SMDS_MeshElement* aElement = myMesh->FindElement( aRec.ElementList[i] );
-              if ( !aElement ) continue;
-
-              SMDS_MeshGroup * & aGroup = aGroupVec[ aElement->GetType() ];
-              if ( !aGroup )
-              {
-                aGroup = new SMDS_MeshGroup( myMesh );
-                if (!useSuffix && createdGroup) useSuffix = true;
-                std::string aGrName = aRec.GroupName;
-                int i = aGrName.find( "\r" );
-                if ( i > 0 )
-                  aGrName.erase (i, 2);
-                if ( useSuffix )
-                  aGrName += aSuffix[ aElement->GetType() ];
-                myGroupNames.insert( std::make_pair( aGroup, aGrName ));
-                createdGroup = true;
-              }
-              aGroup->Add(aElement);
+
+            for (i = 0; i < aElementsNb; i++) {
+              const SMDS_MeshElement* aElement = myMesh->FindElement(aRec.ElementList[i]);
+              if (aElement) {
+                switch (aElement->GetType()) {
+
+                case SMDSAbs_Edge:
+                  if (!aEdgesGroup) {
+                    aEdgesGroup = (SMDS_MeshGroup*) myGroup->AddSubGroup(SMDSAbs_Edge);
+                    if (!useSuffix && createdGroup) useSuffix = true;
+                    std::string aEdgesGrName = (useSuffix) ? aRec.GroupName + "_Edges" : aRec.GroupName;
+                    int i = aEdgesGrName.find( "\r" );
+                    if (i > 0)
+                      aEdgesGrName.erase (i, 2);
+                    myGroupNames.insert(TGroupNamesMap::value_type(aEdgesGroup, aEdgesGrName));
+                    myGroupId.insert(TGroupIdMap::value_type(aEdgesGroup, aLabel));
+                    createdGroup = true;
+                  }
+                  aEdgesGroup->Add(aElement);
+                  break;
+
+                case SMDSAbs_Face:
+                  if (!aFacesGroup) {
+                    aFacesGroup = (SMDS_MeshGroup*) myGroup->AddSubGroup(SMDSAbs_Face);
+                    if (!useSuffix && createdGroup) useSuffix = true;
+                    std::string aFacesGrName = (useSuffix) ? aRec.GroupName + "_Faces" : aRec.GroupName;
+                    int i = aFacesGrName.find( "\r" );
+                    if (i > 0)
+                      aFacesGrName.erase (i, 2);
+                    myGroupNames.insert(TGroupNamesMap::value_type(aFacesGroup, aFacesGrName));
+                    myGroupId.insert(TGroupIdMap::value_type(aFacesGroup, aLabel));
+                    createdGroup = true;
+                  }
+                  aFacesGroup->Add(aElement);
+                  break;
+
+                case SMDSAbs_Volume:
+                  if (!aVolumeGroup) {
+                    aVolumeGroup = (SMDS_MeshGroup*) myGroup->AddSubGroup(SMDSAbs_Volume);
+                    if (!useSuffix && createdGroup) useSuffix = true;
+                    std::string aVolumeGrName = (useSuffix) ? aRec.GroupName + "_Volumes" : aRec.GroupName;
+                    int i = aVolumeGrName.find( "\r" );
+                    if (i > 0)
+                      aVolumeGrName.erase (i, 2);
+                    myGroupNames.insert(TGroupNamesMap::value_type(aVolumeGroup, aVolumeGrName));
+                    myGroupId.insert(TGroupIdMap::value_type(aVolumeGroup, aLabel));
+                    createdGroup = true;
+                  }
+                  aVolumeGroup->Add(aElement);
+                  break;
+
+                default:;
+                }
+              } 
             }
           }
         }
       }
-    }
+    } 
   }
   catch(const std::exception& exc){
     INFOS("Follow exception was cought:\n\t"<<exc.what());
@@ -461,9 +499,6 @@ Driver_Mesh::Status DriverUNV_R_SMDS_Mesh::Perform()
     INFOS("Unknown exception was cought !!!");
   }
   if (myMesh)
-  {
-    myMesh->Modified();
-    myMesh->CompactMesh();
-  }
+    myMesh->compactMesh();
   return aResult;
 }
index 42de629ca5ca5b3b72397244c16cf386d6b0591a..4f7407dbb1704bdda2894a96e9ab2e5dcd8e26b0 100644 (file)
 #include <string>
 
 
+class SMDS_Mesh;
 class SMDS_MeshGroup;
 
+
+typedef std::map<SMDS_MeshGroup*, std::string> TGroupNamesMap;
+typedef std::map<SMDS_MeshGroup*, int> TGroupIdMap;
+
 typedef std::map<SMDS_MeshGroup*, std::string> TGroupNamesMap;
+typedef std::map<SMDS_MeshGroup*, int> TGroupIdMap;
 
 class MESHDRIVERUNV_EXPORT DriverUNV_R_SMDS_Mesh: public Driver_SMDS_Mesh
 {
  public:
-  DriverUNV_R_SMDS_Mesh():Driver_SMDS_Mesh() {};
+  DriverUNV_R_SMDS_Mesh():Driver_SMDS_Mesh(),myGroup(0) {};
   ~DriverUNV_R_SMDS_Mesh();
-
   virtual Status Perform();
 
-  TGroupNamesMap& GetGroupNamesMap() { return myGroupNames; }
+  const SMDS_MeshGroup* GetGroup()         const { return myGroup;}
+  const TGroupNamesMap& GetGroupNamesMap() const { return myGroupNames; }
+  const TGroupIdMap&    GetGroupIdMap() const { return myGroupId; }
 
  private:
+  SMDS_MeshGroup* myGroup;
   TGroupNamesMap myGroupNames;
+  TGroupIdMap    myGroupId;
 };
 
 #endif
index 02ec7588ba394e0240ddb864feb2e4cbc98e75d8..d8bca84a0a723dc6827813ef0e10f9939baaddaa 100644 (file)
@@ -25,6 +25,9 @@
 #include "DriverUNV_W_SMDS_Mesh.h"
 
 #include "SMDS_Mesh.hxx"
+#include "SMDS_QuadraticEdge.hxx"
+#include "SMDS_QuadraticFaceOfNodes.hxx"
+#include "SMDS_PolyhedralVolumeOfNodes.hxx"
 #include "SMESHDS_GroupBase.hxx"
 
 #include "utilities.h"
index 183c0e4dc273c09e989c01f30585c7197cde2a8e..c2868486b7b05cc2a31a7e4e1fc7776b3bcf0831 100644 (file)
@@ -25,8 +25,8 @@
 
 #include <map>
 #include <vector>
-#include <fstream>
-#include <string>
+#include <fstream>      
+#include <string>       
 
 
 namespace UNV2417{
@@ -34,9 +34,9 @@ namespace UNV2417{
   typedef std::vector<int> TListOfId; // Nodal connectivitiesList of Id
 
   struct TRecord{
-    std::string GroupName;
-    TListOfId   NodeList;
-    TListOfId   ElementList;
+    std::string    GroupName;
+    TListOfId NodeList;
+    TListOfId ElementList;
   };
 
   typedef int TGroupId; // type of element label
index 3f64bf4abc6d3ace5af52b849b606ef11f5686c2..a1a69ff3fc4e4df79c066ceeaedf55cb468b1c94 100644 (file)
@@ -31,6 +31,7 @@
 #include "SMDS_BallElement.hxx"
 #include "SMDS_Mesh.hxx"
 #include "SMDS_MeshCell.hxx"
+#include "SMDS_PolyhedralVolumeOfNodes.hxx"
 #include "SMESHDS_Mesh.hxx"
 #include "SMESHDS_Script.hxx"
 #include "SMESH_Actor.h"
@@ -80,6 +81,54 @@ static int MYDEBUGWITHFILES = 0;
   Class       : SMESH_VisualObjDef
   Description : Base class for all mesh objects to be visuilised
 */
+
+//=================================================================================
+// function : getCellType
+// purpose  : Get type of VTK cell
+//=================================================================================
+// static inline vtkIdType getCellType( const SMDSAbs_ElementType theType,
+//                                      const bool                thePoly,
+//                                      const int                 theNbNodes )
+// {
+//   switch( theType )
+//   {
+//     case SMDSAbs_0DElement:         return VTK_VERTEX;
+
+//     case SMDSAbs_Ball:              return VTK_POLY_VERTEX;
+
+//     case SMDSAbs_Edge: 
+//       if( theNbNodes == 2 )         return VTK_LINE;
+//       else if ( theNbNodes == 3 )   return VTK_QUADRATIC_EDGE;
+//       else return VTK_EMPTY_CELL;
+
+//     case SMDSAbs_Face  :
+//       if (thePoly && theNbNodes>2 ) return VTK_POLYGON;
+//       else if ( theNbNodes == 3 )   return VTK_TRIANGLE;
+//       else if ( theNbNodes == 4 )   return VTK_QUAD;
+//       else if ( theNbNodes == 6 )   return VTK_QUADRATIC_TRIANGLE;
+//       else if ( theNbNodes == 8 )   return VTK_QUADRATIC_QUAD;
+//       else if ( theNbNodes == 9 )   return VTK_BIQUADRATIC_QUAD;
+//       else if ( theNbNodes == 7 )   return VTK_BIQUADRATIC_TRIANGLE;
+//       else return VTK_EMPTY_CELL;
+      
+//     case SMDSAbs_Volume:
+//       if (thePoly && theNbNodes>3 ) return VTK_POLYHEDRON; //VTK_CONVEX_POINT_SET;
+//       else if ( theNbNodes == 4 )   return VTK_TETRA;
+//       else if ( theNbNodes == 5 )   return VTK_PYRAMID;
+//       else if ( theNbNodes == 6 )   return VTK_WEDGE;
+//       else if ( theNbNodes == 8 )   return VTK_HEXAHEDRON;
+//       else if ( theNbNodes == 12 )  return VTK_HEXAGONAL_PRISM;
+//       else if ( theNbNodes == 10 )  return VTK_QUADRATIC_TETRA;
+//       else if ( theNbNodes == 20 )  return VTK_QUADRATIC_HEXAHEDRON;
+//       else if ( theNbNodes == 27 )  return VTK_TRIQUADRATIC_HEXAHEDRON;
+//       else if ( theNbNodes == 15 )  return VTK_QUADRATIC_WEDGE;
+//       else if ( theNbNodes == 13 )  return VTK_QUADRATIC_PYRAMID; //VTK_CONVEX_POINT_SET;
+//       else return VTK_EMPTY_CELL;
+
+//     default: return VTK_EMPTY_CELL;
+//   }
+// }
+
 //=================================================================================
 // functions : SMESH_VisualObjDef
 // purpose   : Constructor
@@ -129,7 +178,7 @@ vtkIdType SMESH_VisualObjDef::GetNodeVTKId( int theObjID )
   if( this->GetMesh() ) {
     aNode = this->GetMesh()->FindNode(theObjID);
   }
-  return aNode ? aNode->GetVtkID() : -1;
+  return aNode ? aNode->getVtkId() : -1;
 }
 
 vtkIdType SMESH_VisualObjDef::GetElemObjId( int theVTKID )
@@ -139,7 +188,7 @@ vtkIdType SMESH_VisualObjDef::GetElemObjId( int theVTKID )
     TMapOfIds::const_iterator i = myVTK2SMDSElems.find(theVTKID);
     return i == myVTK2SMDSElems.end() ? -1 : i->second;
   }
-  return this->GetMesh()->FromVtkToSmds(theVTKID);
+  return this->GetMesh()->fromVtkToSmds(theVTKID);
 }
 
 vtkIdType SMESH_VisualObjDef::GetElemVTKId( int theObjID )
@@ -154,7 +203,7 @@ vtkIdType SMESH_VisualObjDef::GetElemVTKId( int theObjID )
   if ( this->GetMesh() )
     e = this->GetMesh()->FindElement(theObjID);
 
-  return e ? e->GetVtkID() : -1;
+  return e ? e->getVtkId() : -1;
 }
 
 //=================================================================================
@@ -231,15 +280,15 @@ void SMESH_VisualObjDef::buildPrs(bool buildGrid)
   else
   {
     myLocalGrid = false;
-    if (!GetMesh()->IsCompacted())
+    if (!GetMesh()->isCompacted())
     {
       NulData(); // detach from the SMDS grid to allow immediate memory de-allocation in compactMesh()
       if ( MYDEBUG ) MESSAGE("*** buildPrs ==> compactMesh!");
-      GetMesh()->CompactMesh();
+      GetMesh()->compactMesh();
       if ( SMESHDS_Mesh* m = dynamic_cast<SMESHDS_Mesh*>( GetMesh() )) // IPAL53915
         m->GetScript()->SetModified(false); // drop IsModified set in compactMesh()
     }
-    vtkUnstructuredGrid *theGrid = GetMesh()->GetGrid();
+    vtkUnstructuredGrid *theGrid = GetMesh()->getGrid();
     updateEntitiesFlags();
     myGrid->ShallowCopy(theGrid);
     //MESSAGE(myGrid->GetReferenceCount());
@@ -346,16 +395,17 @@ void SMESH_VisualObjDef::buildElemPrs()
         if((*anIter)->GetEntityType() != SMDSEntity_Polyhedra &&
            (*anIter)->GetEntityType() != SMDSEntity_Quad_Polyhedra) {
           aCellsSize += (*anIter)->NbNodes() + 1;
-        }
+        } 
         // Special case for the VTK_POLYHEDRON:
         // itsinput cellArray is of special format.
-        //  [nCellFaces, nFace0Pts, i, j, k, nFace1Pts, i, j, k, ...]
+        //  [nCellFaces, nFace0Pts, i, j, k, nFace1Pts, i, j, k, ...]   
         else {
-          if ( const SMDS_MeshVolume* ph = SMDS_Mesh::DownCast<SMDS_MeshVolume>( *anIter )) {
+          if( const SMDS_VtkVolume* ph = dynamic_cast<const SMDS_VtkVolume*>(*anIter) ) {
             int nbFaces = ph->NbFaces();
             aCellsSize += (1 + ph->NbFaces());
-            for( int i = 1; i <= nbFaces; i++ )
+            for( int i = 1; i <= nbFaces; i++ ) {
               aCellsSize += ph->NbFaceNodes(i);
+            }
           }
         }
       }
@@ -417,14 +467,16 @@ void SMESH_VisualObjDef::buildElemPrs()
 
           if (aType == SMDSAbs_Volume && anElem->IsPoly() && aNbNodes > 3) { // POLYEDRE
             anIdList->Reset();
-            if ( const SMDS_MeshVolume* ph = SMDS_Mesh::DownCast<SMDS_MeshVolume>( anElem )) {
+            if ( const SMDS_VtkVolume* ph = dynamic_cast<const SMDS_VtkVolume*>(anElem) ) {
               int nbFaces = ph->NbFaces();
               anIdList->InsertNextId(nbFaces);
               for( int i = 1; i <= nbFaces; i++ ) {
                 anIdList->InsertNextId(ph->NbFaceNodes(i));
                 for(int j = 1; j <= ph->NbFaceNodes(i); j++) {
-                  if ( const SMDS_MeshNode* n = ph->GetFaceNode( i, j ))
-                    anIdList->InsertNextId( mySMDS2VTKNodes[ n->GetID() ]);
+                  const SMDS_MeshNode* n = ph->GetFaceNode(i,j);
+                  if(n) {
+                    anIdList->InsertNextId(mySMDS2VTKNodes[n->GetID()]);
+                  }
                 }
               }
             }
@@ -452,8 +504,11 @@ void SMESH_VisualObjDef::buildElemPrs()
         //Store diameters of the balls
         if(aScalars) {
           double aDiam = 0;
-          if (const SMDS_BallElement* ball = SMDS_Mesh::DownCast<SMDS_BallElement>(anElem) )
-            aDiam = ball->GetDiameter();
+          if(aType == SMDSAbs_Ball) {
+            if (const SMDS_BallElement* ball = dynamic_cast<const SMDS_BallElement*>(anElem) ) {
+              aDiam = ball->GetDiameter();
+            }
+          }
           aScalars->SetTuple(aCurId,&aDiam);
         }
 
@@ -518,14 +573,14 @@ bool SMESH_VisualObjDef::GetEdgeNodes( const int theElemId,
 
 vtkUnstructuredGrid* SMESH_VisualObjDef::GetUnstructuredGrid()
 {
-  if ( !myLocalGrid && !GetMesh()->IsCompacted() )
+  if ( !myLocalGrid && !GetMesh()->isCompacted() )
   {
-    NulData(); // detach from the SMDS grid to allow immediate memory de-allocation in CompactMesh()
-    GetMesh()->CompactMesh();
+    NulData(); // detach from the SMDS grid to allow immediate memory de-allocation in compactMesh()
+    GetMesh()->compactMesh();
     if ( SMESHDS_Mesh* m = dynamic_cast<SMESHDS_Mesh*>( GetMesh() )) // IPAL53915
-      m->GetScript()->SetModified(false); // drop IsModified set in CompactMesh()
+      m->GetScript()->SetModified(false); // drop IsModified set in compactMesh()
     updateEntitiesFlags();
-    vtkUnstructuredGrid *theGrid = GetMesh()->GetGrid();
+    vtkUnstructuredGrid *theGrid = GetMesh()->getGrid();
     myGrid->ShallowCopy(theGrid);
   }
   return myGrid;
index d05091e4e4586f31ca9a559754cb5e0c0d88a03f..e46dbf829cb501b18f4084da3e4765805c44a6b5 100644 (file)
@@ -42,72 +42,96 @@ SET(_link_LIBRARIES
 # header files / no moc processing
 SET(SMDS_HEADERS
   ObjectPool.hxx
+  SMDS_TypeOfPosition.hxx
   SMDSAbs_ElementType.hxx
-  SMDS_BallElement.hxx
-  SMDS_CellOfNodes.hxx
-  SMDS_Downward.hxx
   SMDS_EdgePosition.hxx
   SMDS_ElemIterator.hxx
-  SMDS_ElementFactory.hxx
-  SMDS_FaceOfNodes.hxx
   SMDS_FacePosition.hxx
-  SMDS_Iterator.hxx
-  SMDS_IteratorOnIterators.hxx
-  SMDS_LinearEdge.hxx
   SMDS_Mesh.hxx
   SMDS_Mesh0DElement.hxx
-  SMDS_MeshCell.hxx
+  SMDS_LinearEdge.hxx
   SMDS_MeshEdge.hxx
   SMDS_MeshElement.hxx
+  SMDS_MeshElementIDFactory.hxx
+  SMDS_MeshCell.hxx
   SMDS_MeshFace.hxx
   SMDS_MeshGroup.hxx
-  SMDS_MeshInfo.hxx
+  SMDS_MeshIDFactory.hxx
   SMDS_MeshNode.hxx
+  SMDS_MeshNodeIDFactory.hxx
   SMDS_MeshObject.hxx
   SMDS_MeshVolume.hxx
-  SMDS_PolygonalFaceOfNodes.hxx
   SMDS_Position.hxx
-  SMDS_SetIterator.hxx
   SMDS_SpacePosition.hxx
-  SMDS_StdIterator.hxx
-  SMDS_TypeOfPosition.hxx
-  SMDS_UnstructuredGrid.hxx
   SMDS_VertexPosition.hxx
+  SMDS_Iterator.hxx
+  SMDS_IteratorOfElements.hxx
+  SMDS_VolumeOfFaces.hxx
   SMDS_VolumeOfNodes.hxx
-  SMDS_VolumeTool.hxx
+  SMDS_VtkEdge.hxx
+  SMDS_VtkFace.hxx
+  SMDS_VtkVolume.hxx
   SMDS_VtkCellIterator.hxx
-  SMDS_ElementHolder.hxx
+  SMDS_PolyhedralVolumeOfNodes.hxx
+  SMDS_FaceOfEdges.hxx
+  SMDS_FaceOfNodes.hxx
+  SMDS_PolygonalFaceOfNodes.hxx
+  SMDS_VolumeTool.hxx
+  SMDS_QuadraticEdge.hxx
+  SMDS_QuadraticFaceOfNodes.hxx
+  SMDS_QuadraticVolumeOfNodes.hxx
+  SMDS_SetIterator.hxx
   SMESH_SMDS.hxx
-  chrono.hxx
-  )
+  SMDS_MeshInfo.hxx
+  SMDS_UnstructuredGrid.hxx
+  SMDS_Downward.hxx
+  SMDS_StdIterator.hxx
+  SMDS_IteratorOnIterators.hxx
+  SMDS_BallElement.hxx
+)
 
 # --- sources ---
 
 # sources / static
 SET(SMDS_SOURCES
-  SMDS_BallElement.cxx
-  SMDS_Downward.cxx
-  SMDS_CellOfNodes.cxx
-  SMDS_ElementFactory.cxx
-  SMDS_FaceOfNodes.cxx
-  SMDS_FacePosition.cxx
-  SMDS_LinearEdge.cxx
-  SMDS_MemoryLimit.cxx
-  SMDS_Mesh.cxx
-  SMDS_MeshCell.cxx
+  chrono.cxx
+  SMDS_MeshObject.cxx
   SMDS_MeshElement.cxx
-  SMDS_MeshGroup.cxx
+  SMDS_MeshCell.cxx
+  SMDS_Position.cxx
+  SMDS_EdgePosition.cxx
+  SMDS_FacePosition.cxx
+  SMDS_SpacePosition.cxx
+  SMDS_VertexPosition.cxx
   SMDS_MeshNode.cxx
-  SMDS_MeshObject.cxx
+  SMDS_Mesh0DElement.cxx
+  SMDS_LinearEdge.cxx
+  SMDS_MeshEdge.cxx
+  SMDS_MeshFace.cxx
   SMDS_MeshVolume.cxx
-  SMDS_PolygonalFaceOfNodes.cxx
-  SMDS_SpacePosition.cxx
-  SMDS_UnstructuredGrid.cxx
+  SMDS_MeshNodeIDFactory.cxx
+  SMDS_MeshElementIDFactory.cxx
+  SMDS_MeshGroup.cxx
+  SMDS_MeshIDFactory.cxx
+  SMDS_Mesh.cxx
+  SMDS_IteratorOfElements.cxx
+  SMDS_VolumeOfFaces.cxx
   SMDS_VolumeOfNodes.cxx
-  SMDS_VolumeTool.cxx
+  SMDS_VtkEdge.cxx
+  SMDS_VtkFace.cxx
+  SMDS_VtkVolume.cxx
   SMDS_VtkCellIterator.cxx
-  SMDS_ElementHolder.cxx
-  chrono.cxx
+  SMDS_PolyhedralVolumeOfNodes.cxx
+  SMDS_FaceOfEdges.cxx
+  SMDS_FaceOfNodes.cxx
+  SMDS_PolygonalFaceOfNodes.cxx
+  SMDS_VolumeTool.cxx
+  SMDS_QuadraticEdge.cxx
+  SMDS_QuadraticFaceOfNodes.cxx
+  SMDS_QuadraticVolumeOfNodes.cxx
+  SMDS_UnstructuredGrid.cxx
+  SMDS_Downward.cxx
+  SMDS_BallElement.cxx 
 )
 
 # bin programs
diff --git a/src/SMDS/Notes b/src/SMDS/Notes
new file mode 100644 (file)
index 0000000..830ffb5
--- /dev/null
@@ -0,0 +1,235 @@
+--> Branche V6_main
+
+Problemes en cours
+==================
+- a faire
++ en cours, OK mais perfectible
+* OK
+
++ visualisation de groupe (type d'element): on voit tout le maillage, mais le groupe est OK
+  creation d'une structure vtkUnstructuredGrid locale : iteration un peu lourde, et pas de partage avec la structure du maillage (pas evident)
+- inversion d'un volume (tetra): exception
+- script de creation de noeuds et d'elements: OK, mais pas compatible avec version precedente (numerotation noeuds differente)
++ affichage numeros noeuds: numeros en trop sur (O,0,0) pas systematique, trouver la condition (enlever dans vtkUnstructuredGrid ?)
+  ==> purge systematique noeuds et cellules en trop dans compactage grid.
++ gestion du mode embedded mal faite lors d'un script python : journal commandes intempestif
+- affichage des noeuds apres changement lineaire <--> quadratique à l'IHM : pas pris en compte, alors que maillage OK,
+  mais script OK
+  ==> cassé apres mode embedded ou elimination noeuds en trop ?
+- extrusion elements 2D along a path : affichage apres calcul pas toujours OK (filaire)
+- branche git a ouvrir pour merge avec V5_1_4_BR tag V5_1_4rc1
+
+A tester, non pris en compte
+============================
+- engine standalone
+- polyedres (attendre vtk)
+
+
+=============================== Hypothese de refonte de l'API de SMDS
+
+n'utiliser que vtkUnstructuredGrid, ne pas avor d'objets SMDS_MeshElement mais seulement des index de vtkUnstructuredGrid.
+2987 usages de SMDS_MeshNodes
+810            SMDS_MeshElement
+...
+==> en dernier ressort, lourd
+================================================================================
+
+Essai a API SMDS a peu pres constante
+=====================================
+
+SMDS_Mesh
+  static vector<SMDS_Mesh*> _meshList;     --> retrouver un SMDS_Mesh
+  vtkUnstructuredGrid*      myGrid;
+
+  vector<SMDS_MeshNode *>   myNodes;       --> meme index que dans le pointSet de myGrid
+  vector<SMDS_MeshCell *>   myCells;       --> index = ID client, pas le meme index que dans le cellTypes de myGrid (ID vtk)
+
+
+
+SMDS_MeshElement
+  int myID;                                --> index dans la structure geree par SMDS_Mesh
+  int myMeshId;                            --> pour retrouver SMDS_Mesh* dans _meshList
+  int myShapeId;                           --> pour retrouver la subShape
+                                                         
+
+SMDS_MeshNode: SMDS_MeshElement
+  SMDS_PositionPtr myPosition;             -->  A REVOIR : objet position dans la shape geom
+  ##vector<int> myInverseElements;         -->  SUPPRIME : pour retrouver les elements, vtkCellLinks
+
+
+SMDS_MeshCell: SMDS_MeshElement            --> generique pour tous les elements (cells)
+  int myVtkID                              --> A SUPPRIMER
+
+SMDS_MeshVolume: SMDS_MeshCell
+
+SMDS_VolumeOfNodes: SMDS_MeshVolume        --> Garder temporairement, utilisation dans StdMesher et SMDS_VolumeTool
+  const SMDS_MeshNode **myNodes;           --> Couteux
+  int                 myNbNodes;           -->  ""
+
+SMDS_VolumeVtkNodes: SMDS_MeshVolume       --> Utiliser systematiquement dans SMDS,
+                                           --> IMPLEMENTER.
+
+
+SMDS_MeshElementIDFactory: SMDS_MeshNodeIDFactory
+  vector<int> myIDElements; // index = ID client, value = ID vtk  --> A SUPPRIMER, ne sert que dans SMDS_MeshElementIDFactory
+  vector<int> myVtkIndex;   // index = ID vtk, value = ID client  --> A REPORTER dans SMDS_Mesh
+
+
+
+
+========= TODO ============
+
+enlever vtkId de SMDS_MeshCell, utiliser SMDS_MeshElementIDFactory.
+
+ajouter ID dans SMDS_Mesh::createTriangle 
+verifier ID dans SMDS_Mesh::Find*OrCreate
+
+===================================================
+occupation memoire cube 100*100*100 sans affichage
+NOTES:
+- sur Debian Sarge 64 bits, les mesures malloc_stat() semblent coherentes
+  avec une mesure externe globale(recherche du passage en swap du process).
+- sur Ubuntu 9.10 64 bits, les mesures malloc_stat() donnent des resultats bizarres (surestimation ?),
+  mais la mesure avec l'outil KDE de surveillance systeme est OK avec la recherche du swap.
+
+
+Reference : V513 Debian Sarge 64 bits: --> 463 - 33 = 430 Mo
+-------------------------------------
+Total (incl. mmap):
+system bytes     =   43757568
+in use bytes     =   32909584 = 33M
+max mmap regions =         41
+max mmap bytes   =   16371712
+----
+Total (incl. mmap):
+system bytes     =  464670720
+in use bytes     =  463105120 = 463M
+max mmap regions =         47
+max mmap bytes   =   28188672
+
+Debian Sarge 64 bits, vtkUnstructuredGrid nodes et hexa, 4 janvier 2010 --> 512 - 41 = 471M
+-----------------------------------
+
+Total (incl. mmap):
+system bytes     =   52133888
+in use bytes     =   41340320 : 41M
+max mmap regions =         72
+max mmap bytes   =   24625152
+----
+Total (incl. mmap):
+system bytes     =  520560640
+in use bytes     =  518735584 : 512M
+max mmap regions =         88
+max mmap bytes   =  198385664
+
+idem avec pool SMDS_MeshNodes --> 483 -33 = 450M
+-----------------------------
+Total (incl. mmap):
+system bytes     =   43696128
+in use bytes     =   32915184 : 33M 
+max mmap regions =         41
+max mmap bytes   =   16371712
+----
+Total (incl. mmap):
+system bytes     =  484806656
+in use bytes     =  482980992 : 483M
+max mmap regions =         58
+max mmap bytes   =  184557568
+
+idem ci-dessus + pool SMDS_VolumeVtkNodes --> 475 -33 = 442M (git: add ObjectPool.hxx)
+-----------------------------------------
+
+Total (incl. mmap):
+system bytes     =   43200512
+in use bytes     =   32908576 : 33M
+max mmap regions =         41
+max mmap bytes   =   16371712
+----
+Total (incl. mmap):
+system bytes     =  478068736
+in use bytes     =  475144400 : 475M
+max mmap regions =         59
+max mmap bytes   =  184692736
+
+remplacement SMDS_PositionPtr: (boost::shared_ptr<SMDS_Position> --> SMDS_Position*) --> 436 - 35 = 401M (git SMDS_Position)
+------------------------------------------------------------------------------------
+Total (incl. mmap):
+system bytes     =   45408256
+in use bytes     =   35097680 : 35M
+max mmap regions =         47
+max mmap bytes   =   18116608
+----
+Total (incl. mmap):
+system bytes     =  438935552
+in use bytes     =  436116560 : 436M
+max mmap regions =         65
+max mmap bytes   =  186437632
+
+simplification SMDS_SpacePosition (pas de double[3]) --> 418 -33 = 385M (git SMDS_SpacePosition)
+----------------------------------------------------
+Total (incl. mmap):
+system bytes     =   42582016
+in use bytes     =   32883552 : 33M
+max mmap regions =         41
+max mmap bytes   =   16371712
+----
+Total (incl. mmap):
+system bytes     =  421728256
+in use bytes     =  418378000 : 418M
+max mmap regions =         58
+max mmap bytes   =  183640064
+
+sizeof(SMDS_MeshElement) 16
+sizeof(SMDS_MeshNode) 24
+sizeof(SMDS_MeshCell) 24
+sizeof(SMDS_VolumeVtkNodes) 24
+sizeof(SMDS_Position) 16
+sizeof(SMDS_SpacePosition) 16
+
+impact d'un int en plus dans SMDS_MeshElement --> 426 - 33 = 393M
+---------------------------------------------
+
+sizeof(SMDS_MeshElement) 24
+sizeof(SMDS_MeshNode) 32       --> on retrouve bien les 8M
+sizeof(SMDS_MeshCell) 24
+sizeof(SMDS_VolumeVtkNodes) 24
+sizeof(SMDS_Position) 16
+sizeof(SMDS_SpacePosition) 16
+
+Total (incl. mmap):
+system bytes     =   43192320
+in use bytes     =   32681088 : 33M
+max mmap regions =         41
+max mmap bytes   =   16371712
+----
+Total (incl. mmap):
+system bytes     =  429334528
+in use bytes     =  426424576 : 426M
+max mmap regions =         59
+max mmap bytes   =  184692736
+
+remplacement std::set par std::vector dans SMESHDS_SubMesh --> 347 - 35 = 312M
+----------------------------------------------------------
+sizeof(SMDS_MeshElement) 24
+sizeof(SMDS_MeshNode) 32
+sizeof(SMDS_MeshCell) 24
+sizeof(SMDS_VolumeVtkNodes) 24
+sizeof(SMDS_Position) 16
+sizeof(SMDS_SpacePosition) 16
+
+Total (incl. mmap):
+system bytes     =   45404160
+in use bytes     =   35132160 --> 35M
+max mmap regions =         49
+max mmap bytes   =   17723392
+----
+Total (incl. mmap):
+system bytes     =  349831168
+in use bytes     =  346885424 --> 347M
+max mmap regions =         73
+max mmap bytes   =  204148736
+
+Ce resultat est coherent avec une recherche de swap sur une machine a 8Go de memoire:
+Cube a 270**3 mailles (~20M mailles) --> 6.2 Go (idem Debian Sarge et Ubuntu 9.10, 64 bits)
+Le meme avec V5.1.3 --> 14 Go (swap)
+
index d7eea28c32a812a0bcc20774556633d32aba4c83..ef514b353b0388fdcf4b61eb0cb8924a1742327e 100644 (file)
@@ -28,9 +28,9 @@
 namespace
 {
   // assure deallocation of memory of a vector
-  template<class Y> void clearVector(& v )
+  template<class Y> void clearVector(std::vector<Y>& v )
   {
-    Y emptyVec; v.swap( emptyVec );
+    std::vector<Y> emptyVec; v.swap( emptyVec );
   }
 }
 
index 7a10f79d3883050af8d56a9f263abe347224dde3..fd3859681325b9784447cf98be9a954d34516b46 100644 (file)
 
 #include "SMDS_BallElement.hxx"
 
+#include "SMDS_ElemIterator.hxx"
 #include "SMDS_Mesh.hxx"
 #include "SMDS_MeshNode.hxx"
+#include "SMDS_VtkCellIterator.hxx"
 
-void SMDS_BallElement::init(const SMDS_MeshNode * node, double diameter )
+SMDS_BallElement::SMDS_BallElement()
 {
-  int nodeVtkID = node->GetVtkID();
-  int vtkID = getGrid()->InsertNextLinkedCell( toVtkType( SMDSEntity_Ball ), 1, &nodeVtkID );
-  setVtkID( vtkID );
-  getGrid()->SetBallDiameter( GetVtkID(), diameter );
+  SMDS_MeshCell::init();
+}
+
+SMDS_BallElement::SMDS_BallElement (const SMDS_MeshNode * node, double diameter)
+{
+  init( node->getVtkId(), diameter, SMDS_Mesh::_meshList[ node->getMeshId() ] );
+}
+
+SMDS_BallElement::SMDS_BallElement(vtkIdType nodeId, double diameter, SMDS_Mesh* mesh)
+{
+  init( nodeId, diameter, mesh );
+}
+
+void SMDS_BallElement::init(vtkIdType nodeId, double diameter, SMDS_Mesh* mesh)
+{
+  SMDS_MeshCell::init();
+  myMeshId = mesh->getMeshId();
+  myVtkID = mesh->getGrid()->InsertNextLinkedCell( GetVtkType(), 1, &nodeId );
+  mesh->getGrid()->SetBallDiameter( myVtkID, diameter );
+  mesh->setMyModified();
 }
 
 double SMDS_BallElement::GetDiameter() const
 {
-  return getGrid()->GetBallDiameter( GetVtkID() );
+  return SMDS_Mesh::_meshList[myMeshId]->getGrid()->GetBallDiameter( myVtkID );
 }
 
 void SMDS_BallElement::SetDiameter(double diameter)
 {
-  getGrid()->SetBallDiameter( GetVtkID(), diameter );
-  GetMesh()->setMyModified();
+  SMDS_Mesh::_meshList[myMeshId]->getGrid()->SetBallDiameter( myVtkID, diameter );
+}
+
+bool SMDS_BallElement::ChangeNode (const SMDS_MeshNode * node)
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType npts = 0;
+  vtkIdType* pts = 0;
+  grid->GetCellPoints(myVtkID, npts, pts);
+  pts[0] = node->getVtkId();
+  SMDS_Mesh::_meshList[myMeshId]->setMyModified();
+  return true;
+}
+
+void SMDS_BallElement::Print (std::ostream & OS) const
+{
+  OS << "ball<" << GetID() << "> : ";
 }
+
+const SMDS_MeshNode* SMDS_BallElement::GetNode (const int ind) const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType npts, *pts;
+  grid->GetCellPoints( myVtkID, npts, pts );
+  return SMDS_Mesh::_meshList[myMeshId]->FindNodeVtk( pts[ 0 ]);
+}
+
+SMDS_ElemIteratorPtr SMDS_BallElement::elementsIterator (SMDSAbs_ElementType type) const
+{
+  switch (type)
+  {
+    case SMDSAbs_Node:
+      return SMDS_ElemIteratorPtr(new SMDS_VtkCellIterator(SMDS_Mesh::_meshList[myMeshId], myVtkID, GetEntityType()));
+    default:
+      ;
+      return SMDS_ElemIteratorPtr((SMDS_ElemIterator*) NULL);
+  }
+}
+
index 4e7c6346e79b81895b00ee265d5ee665dc64c380..c62034de77527563915e41cf380e8a9dedd19474 100644 (file)
 #include "SMESH_SMDS.hxx"
 #include "SMDS_MeshCell.hxx"
 
-/*!
- * \brief Ball element. This type is not allocated.
- *        It is only used as function argument type to provide more clear semantic
- *        and to provide API specific to ball element
- */
+#include <iostream>
+
 class SMDS_EXPORT SMDS_BallElement: public SMDS_MeshCell
 {
-  void init(const SMDS_MeshNode * node, double diameter);
-
-  friend class SMDS_Mesh;
-
  public:
-
+  SMDS_BallElement();
+  SMDS_BallElement (const SMDS_MeshNode * node, double diameter);
+  SMDS_BallElement(vtkIdType nodeId, double diameter, SMDS_Mesh* mesh);
+  void init(vtkIdType nodeId, double diameter, SMDS_Mesh* mesh);
   double GetDiameter() const;
-  void   SetDiameter(double diameter);
-
-  static SMDSAbs_ElementType Type() { return SMDSAbs_Ball; }
+  void SetDiameter(double diameter);
+  bool ChangeNode (const SMDS_MeshNode * node);
+
+  virtual bool ChangeNodes(const SMDS_MeshNode* nodes[],
+                           const int            nbNodes) { return ChangeNode( nodes[0] ); }
+  virtual void Print (std::ostream & OS) const;
+
+  virtual SMDSAbs_ElementType  GetType()       const { return SMDSAbs_Ball; }
+  virtual vtkIdType            GetVtkType()    const { return VTK_POLY_VERTEX; }
+  virtual SMDSAbs_EntityType   GetEntityType() const { return SMDSEntity_Ball; }
+  virtual SMDSAbs_GeometryType GetGeomType()   const { return SMDSGeom_BALL; }
+  virtual int NbNodes() const { return 1; }
+  virtual int NbEdges() const { return 0; }
+  virtual int NbFaces() const { return 0; }
+  virtual const SMDS_MeshNode* GetNode (const int ind) const;
+
+ protected:
+  SMDS_ElemIteratorPtr elementsIterator (SMDSAbs_ElementType type) const;
 };
 
 #endif
diff --git a/src/SMDS/SMDS_CellOfNodes.cxx b/src/SMDS/SMDS_CellOfNodes.cxx
deleted file mode 100644 (file)
index bea007f..0000000
+++ /dev/null
@@ -1,62 +0,0 @@
-// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
-//
-// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
-// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
-//
-// This library is free software; you can redistribute it and/or
-// modify it under the terms of the GNU Lesser General Public
-// License as published by the Free Software Foundation; either
-// version 2.1 of the License, or (at your option) any later version.
-//
-// This library is distributed in the hope that it will be useful,
-// but WITHOUT ANY WARRANTY; without even the implied warranty of
-// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
-// Lesser General Public License for more details.
-//
-// You should have received a copy of the GNU Lesser General Public
-// License along with this library; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
-//
-// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
-//
-
-//  SMESH SMDS : implementation of Salome mesh data structure
-//
-
-#include "SMDS_CellOfNodes.hxx"
-
-SMDS_CellOfNodes::SMDS_CellOfNodes( int id, int shapeID )
-  : myID( id )
-{
-  setShapeID( shapeID );
-}
-
-void SMDS_CellOfNodes::setID(const int id)
-{
-  myID = id;
-}
-
-int SMDS_CellOfNodes::GetID() const
-{
-  return myID;
-}
-
-void SMDS_CellOfNodes::setShapeID( const int shapeID )
-{
-  myShapeID = ( shapeID << BITS_SHIFT ) | ( myShapeID & BIT_IS_MARKED );
-}
-
-int SMDS_CellOfNodes::GetShapeID() const
-{
-  return myShapeID >> BITS_SHIFT;
-}
-
-void SMDS_CellOfNodes::setIsMarked( bool is ) const
-{
-  const_cast< SMDS_CellOfNodes* >( this )->myShapeID = ( myShapeID & ~BIT_IS_MARKED ) | is;
-}
-
-bool SMDS_CellOfNodes::isMarked() const
-{
-  return myShapeID & BIT_IS_MARKED;
-}
diff --git a/src/SMDS/SMDS_CellOfNodes.hxx b/src/SMDS/SMDS_CellOfNodes.hxx
deleted file mode 100644 (file)
index 4880d07..0000000
+++ /dev/null
@@ -1,68 +0,0 @@
-// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
-//
-// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
-// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
-//
-// This library is free software; you can redistribute it and/or
-// modify it under the terms of the GNU Lesser General Public
-// License as published by the Free Software Foundation; either
-// version 2.1 of the License, or (at your option) any later version.
-//
-// This library is distributed in the hope that it will be useful,
-// but WITHOUT ANY WARRANTY; without even the implied warranty of
-// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
-// Lesser General Public License for more details.
-//
-// You should have received a copy of the GNU Lesser General Public
-// License along with this library; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
-//
-// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
-//
-
-//  SMESH SMDS : implementation of Salome mesh data structure
-//  File   : SMDS_CellOfNodes.hxx
-//  Module : SMESH
-//
-#ifndef _SMDS_CellOfNodes_HeaderFile
-#define _SMDS_CellOfNodes_HeaderFile
-
-#include "SMESH_SMDS.hxx"
-        
-#include "SMDS_MeshElement.hxx"
-
-// ============================================================
-/*!
- * \brief Base class for elements of not contained in the mesh
- */
-// ============================================================
-
-
-class SMDS_EXPORT SMDS_CellOfNodes : public SMDS_MeshElement
-{
-public:
-
-  virtual int GetID() const;
-  virtual int GetShapeID() const;
-
-  virtual void setIsMarked( bool is ) const;
-  virtual bool isMarked() const;
-
-  virtual VTKCellType GetVtkType() const { return VTK_EMPTY_CELL; }
-
- protected:
-
-  SMDS_CellOfNodes( int id = -1, int shapeID = 0);
-
-  virtual void setID( const int id);
-  virtual void setShapeID( const int shapeID );
-
-  int  myID;
-  int  myShapeID;
-
-  enum Bits { // use the 1st right bit of myShapeId to set/unset a mark
-    BIT_IS_MARKED = 1,
-    BITS_SHIFT = 1
-  };
-};
-#endif
index 1955fa892283bd911a8cddc472ac49678245544e..c4ead4dac025f38aa829ce2f1619d621c3e8d2f7 100644 (file)
@@ -1145,7 +1145,7 @@ void SMDS_DownTetra::getOrderedNodesOfFace(int cellId, std::vector<vtkIdType>& o
       return;
     }
   }
-  MESSAGE("=== Problem volume " << _vtkCellIds[cellId] << " " << _grid->_mesh->FromVtkToSmds(_vtkCellIds[cellId]));
+  MESSAGE("=== Problem volume " << _vtkCellIds[cellId] << " " << _grid->_mesh->fromVtkToSmds(_vtkCellIds[cellId]));
   MESSAGE(orderedNodes[0] << " " << orderedNodes[1] << " " << orderedNodes[2]);
   MESSAGE(nodes[0] << " " << nodes[1] << " " << nodes[2] << " " << nodes[3]);
 }
@@ -1253,7 +1253,7 @@ void SMDS_DownQuadTetra::getOrderedNodesOfFace(int cellId, std::vector<vtkIdType
       return;
     }
   }
-  MESSAGE("=== Problem volume " << _vtkCellIds[cellId] << " " << _grid->_mesh->FromVtkToSmds(_vtkCellIds[cellId]));
+  MESSAGE("=== Problem volume " << _vtkCellIds[cellId] << " " << _grid->_mesh->fromVtkToSmds(_vtkCellIds[cellId]));
   MESSAGE(orderedNodes[0] << " " << orderedNodes[1] << " " << orderedNodes[2]);
   MESSAGE(nodes[0] << " " << nodes[1] << " " << nodes[2] << " " << nodes[3]);
 }
@@ -1387,7 +1387,7 @@ void SMDS_DownPyramid::getOrderedNodesOfFace(int cellId, std::vector<vtkIdType>&
       return;
     }
   }
-  MESSAGE("=== Problem volume " << _vtkCellIds[cellId] << " " << _grid->_mesh->FromVtkToSmds(_vtkCellIds[cellId]));
+  MESSAGE("=== Problem volume " << _vtkCellIds[cellId] << " " << _grid->_mesh->fromVtkToSmds(_vtkCellIds[cellId]));
   MESSAGE(orderedNodes[0] << " " << orderedNodes[1] << " " << orderedNodes[2]);
   MESSAGE(nodes[0] << " " << nodes[1] << " " << nodes[2] << " " << nodes[3]);
 }
@@ -1531,7 +1531,7 @@ void SMDS_DownQuadPyramid::getOrderedNodesOfFace(int cellId, std::vector<vtkIdTy
       return;
     }
   }
-  MESSAGE("=== Problem volume " << _vtkCellIds[cellId] << " " << _grid->_mesh->FromVtkToSmds(_vtkCellIds[cellId]));
+  MESSAGE("=== Problem volume " << _vtkCellIds[cellId] << " " << _grid->_mesh->fromVtkToSmds(_vtkCellIds[cellId]));
   MESSAGE(orderedNodes[0] << " " << orderedNodes[1] << " " << orderedNodes[2] << " " << orderedNodes[3]);
   MESSAGE(nodes[0] << " " << nodes[1] << " " << nodes[2] << " " << nodes[3]);
 }
@@ -1694,7 +1694,7 @@ void SMDS_DownPenta::getOrderedNodesOfFace(int cellId, std::vector<vtkIdType>& o
       return;
     }
   }
-  MESSAGE("=== Problem volume " << _vtkCellIds[cellId] << " " << _grid->_mesh->FromVtkToSmds(_vtkCellIds[cellId]));
+  MESSAGE("=== Problem volume " << _vtkCellIds[cellId] << " " << _grid->_mesh->fromVtkToSmds(_vtkCellIds[cellId]));
   MESSAGE(orderedNodes[0] << " " << orderedNodes[1] << " " << orderedNodes[2]);
   MESSAGE(nodes[0] << " " << nodes[1] << " " << nodes[2] << " " << nodes[3]);
 }
@@ -1845,7 +1845,7 @@ void SMDS_DownQuadPenta::getOrderedNodesOfFace(int cellId, std::vector<vtkIdType
       return;
     }
   }
-  MESSAGE("=== Problem volume " << _vtkCellIds[cellId] << " " << _grid->_mesh->FromVtkToSmds(_vtkCellIds[cellId]));
+  MESSAGE("=== Problem volume " << _vtkCellIds[cellId] << " " << _grid->_mesh->fromVtkToSmds(_vtkCellIds[cellId]));
   MESSAGE(orderedNodes[0] << " " << orderedNodes[1] << " " << orderedNodes[2]);
   MESSAGE(nodes[0] << " " << nodes[1] << " " << nodes[2] << " " << nodes[3]);
 }
@@ -2000,7 +2000,7 @@ void SMDS_DownHexa::getOrderedNodesOfFace(int cellId, std::vector<vtkIdType>& or
       return;
     }
   }
-  MESSAGE("=== Problem volume " << _vtkCellIds[cellId] << " " << _grid->_mesh->FromVtkToSmds(_vtkCellIds[cellId]));
+  MESSAGE("=== Problem volume " << _vtkCellIds[cellId] << " " << _grid->_mesh->fromVtkToSmds(_vtkCellIds[cellId]));
   MESSAGE(orderedNodes[0] << " " << orderedNodes[1] << " " << orderedNodes[2] << " " << orderedNodes[3]);
   MESSAGE(nodes[0] << " " << nodes[1] << " " << nodes[2] << " " << nodes[3]);
   MESSAGE(nodes[4] << " " << nodes[5] << " " << nodes[6] << " " << nodes[7]);
@@ -2132,7 +2132,7 @@ void SMDS_DownQuadHexa::getOrderedNodesOfFace(int cellId, std::vector<vtkIdType>
       return;
     }
   }
-  MESSAGE("=== Problem volume " << _vtkCellIds[cellId] << " " << _grid->_mesh->FromVtkToSmds(_vtkCellIds[cellId]));
+  MESSAGE("=== Problem volume " << _vtkCellIds[cellId] << " " << _grid->_mesh->fromVtkToSmds(_vtkCellIds[cellId]));
   MESSAGE(orderedNodes[0] << " " << orderedNodes[1] << " " << orderedNodes[2] << " " << orderedNodes[3]);
   MESSAGE(nodes[0] << " " << nodes[1] << " " << nodes[2] << " " << nodes[3]);
 }
diff --git a/src/SMDS/SMDS_EdgePosition.cxx b/src/SMDS/SMDS_EdgePosition.cxx
new file mode 100644 (file)
index 0000000..9ac728d
--- /dev/null
@@ -0,0 +1,67 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//  File   : SMDS_EdgePosition.cxx
+//  Author : Jean-Michel BOULCOURT
+//  Module : SMESH
+//
+#include "SMDS_EdgePosition.hxx"
+
+#include "utilities.h"
+
+using namespace std;
+
+//=======================================================================
+//function : SMDS_EdgePosition
+//purpose  : 
+//=======================================================================
+
+SMDS_EdgePosition::SMDS_EdgePosition(const double aUParam): myUParameter(aUParam)
+{
+  //MESSAGE("********************************* SMDS_EdgePosition " << myUParameter);
+}
+
+/**
+*/
+SMDS_TypeOfPosition SMDS_EdgePosition::GetTypeOfPosition() const
+{
+  //MESSAGE("###################################### SMDS_EdgePosition::GetTypeOfPosition");
+        return SMDS_TOP_EDGE;
+}
+
+void SMDS_EdgePosition::SetUParameter(double aUparam)
+{
+  //MESSAGE("############################### SMDS_EdgePosition::SetUParameter " << aUparam);
+        myUParameter = aUparam;
+}
+
+//=======================================================================
+//function : GetUParameter
+//purpose  : 
+//=======================================================================
+
+double SMDS_EdgePosition::GetUParameter() const 
+{
+  //MESSAGE("########################## SMDS_EdgePosition::GetUParameter " << myUParameter);
+        return myUParameter;
+}
index e2c9cf19ec37a9cc26e2fff1ed0e0a8bcafff1f3..f0870e9704e720aab24c64b5ea6d73063ec5ed58 100644 (file)
 
 #include "SMDS_Position.hxx"
 
-class SMDS_EXPORT SMDS_EdgePosition : public SMDS_Position
+class SMDS_EXPORT SMDS_EdgePosition:public SMDS_Position
 {
 
- public:
-  SMDS_EdgePosition(const double aUParam=0) : myUParameter( aUParam ) {}
-  virtual SMDS_TypeOfPosition GetTypeOfPosition() const { return SMDS_TOP_EDGE; }
-  virtual void   SetUParameter(double aUparam) { myUParameter = aUparam; }
-  virtual double GetUParameter() const { return myUParameter; }
-  virtual const double* GetParameters() const { return &myUParameter; }
+  public:
+        SMDS_EdgePosition(const double aUParam=0);
+        SMDS_TypeOfPosition GetTypeOfPosition() const;
+        void SetUParameter(double aUparam);
+        double GetUParameter() const;
 
- private:
 private:
 
-  double myUParameter;
+        double myUParameter;
 
 };
 
diff --git a/src/SMDS/SMDS_ElementFactory.cxx b/src/SMDS/SMDS_ElementFactory.cxx
deleted file mode 100644 (file)
index a6d61e8..0000000
+++ /dev/null
@@ -1,880 +0,0 @@
-// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
-//
-// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
-// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
-//
-// This library is free software; you can redistribute it and/or
-// modify it under the terms of the GNU Lesser General Public
-// License as published by the Free Software Foundation; either
-// version 2.1 of the License, or (at your option) any later version.
-//
-// This library is distributed in the hope that it will be useful,
-// but WITHOUT ANY WARRANTY; without even the implied warranty of
-// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
-// Lesser General Public License for more details.
-//
-// You should have received a copy of the GNU Lesser General Public
-// License along with this library; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
-//
-// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
-//
-//  File   : SMDS_ElementFactory.cxx
-//  Module : SMESH
-//
-
-#include "SMDS_ElementFactory.hxx"
-
-#include "ObjectPool.hxx"
-#include "SMDS_EdgePosition.hxx"
-#include "SMDS_FacePosition.hxx"
-#include "SMDS_Mesh.hxx"
-#include "SMDS_SpacePosition.hxx"
-#include "SMDS_VertexPosition.hxx"
-
-namespace
-{
-  // nb of elements allocated by SMDS_ElementChunk at once
-  const int theChunkSize = 1024;
-
-  const int theDefaultShapeDim = 3;
-
-  // classes allowing to modify parameters of SMDS_Position stored in SMDS_ElementFactory
-
-  struct _EdgePosition : public SMDS_EdgePosition
-  {
-    TParam* myUParameter;
-
-    _EdgePosition( TParam* aUParam ) : myUParameter( aUParam )
-    { SMDS_EdgePosition::SetUParameter( aUParam[0]); }
-    virtual void   SetUParameter(double aUparam)
-    { *myUParameter = (TParam) aUparam; SMDS_EdgePosition::SetUParameter( aUparam ); }
-  };
-
-  struct _FacePosition : public SMDS_FacePosition
-  {
-    TParam* myParameter;
-
-    _FacePosition(TParam* aParam) : myParameter( aParam )
-    { SMDS_FacePosition::SetParameters( aParam[0], aParam[1] ); }
-    virtual void SetUParameter(double aUparam)
-    { myParameter[0] = (TParam) aUparam; SMDS_FacePosition::SetUParameter( aUparam ); }
-    virtual void SetVParameter(double aVparam)
-    { myParameter[1] = (TParam) aVparam; SMDS_FacePosition::SetVParameter( aVparam ); }
-    virtual void SetParameters(double aU, double aV)
-    { myParameter[0] = aU; myParameter[1] = aV; SMDS_FacePosition::SetParameters( aU, aV ); }
-  };
-}
-
-//================================================================================
-/*!
- * \brief Create a factory of cells or nodes in a given mesh
- */
-//================================================================================
-
-SMDS_ElementFactory::SMDS_ElementFactory( SMDS_Mesh* mesh, const bool isNodal )
-  : myIsNodal( isNodal ), myMesh( mesh ), myNbUsedElements( 0 )
-{
-}
-
-//================================================================================
-/*!
- * \brief Destructor
- */
-//================================================================================
-
-SMDS_ElementFactory::~SMDS_ElementFactory()
-{
-  myChunksWithUnused.clear();
-  myChunks.clear();
-}
-
-//================================================================================
-/*!
- * \brief Return a number of elements in a chunk
- *  \return int - chunk size
- */
-//================================================================================
-
-int SMDS_ElementFactory::ChunkSize()
-{
-  return theChunkSize;
-}
-
-//================================================================================
-/*!
- * \brief Return minimal ID of a non-used element
- *  \return int - minimal element ID
- */
-//================================================================================
-
-int SMDS_ElementFactory::GetFreeID()
-{
-  if ( myChunksWithUnused.empty() )
-  {
-    int id0 = myChunks.size() * theChunkSize + 1;
-    myChunks.push_back( new SMDS_ElementChunk( this, id0 ));
-  }
-  SMDS_ElementChunk * chunk = (*myChunksWithUnused.begin());
-  return chunk->GetUnusedID();
-}
-
-//================================================================================
-/*!
- * \brief Return maximal ID of an used element
- *  \return int - element ID
- */
-//================================================================================
-
-int SMDS_ElementFactory::GetMaxID()
-{
-  int id = 0;
-  TIndexRanges usedRanges;
-  for ( int i = myChunks.size() - 1; i >= 0; --i )
-    if ( myChunks[i].GetUsedRanges().GetIndices( true, usedRanges ))
-    {
-      int index = usedRanges.back().second-1;
-      id = myChunks[i].Get1stID() + index;
-      break;
-    }
-  return id;
-}
-
-//================================================================================
-/*!
- * \brief Return minimal ID of an used element
- *  \return int - element ID
- */
-//================================================================================
-
-int SMDS_ElementFactory::GetMinID()
-{
-  int id = 0;
-  TIndexRanges usedRanges;
-  for ( size_t i = 0; i < myChunks.size(); ++i )
-    if ( myChunks[i].GetUsedRanges().GetIndices( true, usedRanges ))
-    {
-      int index = usedRanges[0].first;
-      id = myChunks[i].Get1stID() + index;
-      break;
-    }
-  return id;
-}
-
-//================================================================================
-/*!
- * \brief Return an element by ID. NULL if the element with the given ID is already used
- *  \param [in] id - element ID
- *  \return SMDS_MeshElement* - element pointer
- */
-//================================================================================
-
-SMDS_MeshElement* SMDS_ElementFactory::NewElement( const int id )
-{
-  int iChunk = ( id - 1 ) / theChunkSize;
-  int index  = ( id - 1 ) % theChunkSize;
-  while ((int) myChunks.size() <= iChunk )
-  {
-    int id0 = myChunks.size() * theChunkSize + 1;
-    myChunks.push_back( new SMDS_ElementChunk( this, id0 ));
-  }
-  SMDS_MeshElement* e = myChunks[iChunk].Element( index );
-  if ( !e->IsNull() )
-    return 0; // element with given ID already exists
-
-  myChunks[iChunk].UseElement( index );
-  ++myNbUsedElements;
-
-  e->myHolder = & myChunks[iChunk];
-
-  myMesh->setMyModified();
-
-  return e;
-}
-
-//================================================================================
-/*!
- * \brief Return an used element by ID. NULL if the element with the given ID is not yet used
- *  \param [in] id - element ID
- *  \return const SMDS_MeshElement* - element pointer
- */
-//================================================================================
-
-const SMDS_MeshElement* SMDS_ElementFactory::FindElement( const int id ) const
-{
-  if ( id > 0 )
-  {
-    int iChunk = ( id - 1 ) / theChunkSize;
-    int index  = ( id - 1 ) % theChunkSize;
-    if ( iChunk < (int) myChunks.size() )
-    {
-      const SMDS_MeshElement* e = myChunks[iChunk].Element( index );
-      return e->IsNull() ? 0 : e;
-    }
-  }
-  return 0;
-}
-
-//================================================================================
-/*!
- * \brief Return an SMDS ID by a Vtk one
- *  \param [inout] vtkID - Vtk ID
- *  \return int - SMDS ID
- */
-//================================================================================
-
-int SMDS_ElementFactory::FromVtkToSmds( vtkIdType vtkID )
-{
-  if ( vtkID >= 0 && vtkID < (vtkIdType)mySmdsIDs.size() )
-    return mySmdsIDs[vtkID] + 1;
-  return vtkID + 1;
-}
-
-//================================================================================
-/*!
- * \brief Mark the element as non-used
- *  \param [in] e - element
- */
-//================================================================================
-
-void SMDS_ElementFactory::Free( const SMDS_MeshElement* e )
-{
-  if ( !myVtkIDs.empty() )
-  {
-    size_t    id = e->GetID() - 1;
-    size_t vtkID = e->GetVtkID();
-    if ( id < myVtkIDs.size() )
-      myVtkIDs[ id ] = -1;
-    if ( vtkID < mySmdsIDs.size() )
-      mySmdsIDs[ vtkID ] = -1;
-  }
-  e->myHolder->Free( e );
-  const_cast< SMDS_MeshElement*>( e )->myHolder = 0;
-  --myNbUsedElements;
-
-  myMesh->setMyModified();
-}
-
-//================================================================================
-/*!
- * \brief De-allocate all elements
- */
-//================================================================================
-
-void SMDS_ElementFactory::Clear()
-{
-  myChunksWithUnused.clear();
-  clearVector( myChunks );
-  clearVector( myVtkIDs );
-  clearVector( mySmdsIDs );
-  myNbUsedElements = 0;
-}
-
-//================================================================================
-/*!
- * \brief Remove unused elements located not at the end of the last chunk.
- *        Minimize allocated memory
- *  \param [out] theVtkIDsNewToOld - theVtkIDsNewToOld[ new VtkID ] = old VtkID
- */
-//================================================================================
-
-void SMDS_ElementFactory::Compact( std::vector<int>& theVtkIDsNewToOld )
-{
-  int  newNbCells = NbUsedElements();
-  int   maxCellID = GetMaxID();
-  int newNbChunks = newNbCells / theChunkSize + bool ( newNbCells % theChunkSize );
-
-  theVtkIDsNewToOld.resize( newNbCells );
-
-  if ( newNbCells == 0 ) // empty mesh
-  {
-    clearVector( myChunks );
-  }
-  else if ( newNbCells == maxCellID ) // no holes
-  {
-    int newID, minLastID = std::min( myVtkIDs.size(), theVtkIDsNewToOld.size() );
-    for ( newID = 0; newID < minLastID; ++newID )
-      theVtkIDsNewToOld[ newID ] = myVtkIDs[ newID ];
-    for ( ; newID < newNbCells; ++newID )
-      theVtkIDsNewToOld[ newID ] = newID;
-  }
-  else // there are holes in SMDS IDs
-  {
-    int newVtkID = 0; // same as new smds ID (-1)
-    for ( int oldID = 1; oldID <= maxCellID; ++oldID ) // smds IDs
-    {
-      const SMDS_MeshElement* oldElem = FindElement( oldID );
-      if ( !oldElem ) continue;
-      theVtkIDsNewToOld[ newVtkID++ ] = oldElem->GetVtkID(); // now newVtkID == new smds ID
-      if ( oldID != newVtkID )
-      {
-        const SMDS_MeshElement* newElem = FindElement( newVtkID );
-        if ( !newElem )
-          newElem = NewElement( newVtkID );
-        if ( int shapeID = oldElem->GetShapeID() )
-          const_cast< SMDS_MeshElement* >( newElem )->setShapeID( shapeID );
-        if ( oldID > newNbCells )
-          Free( oldElem );
-      }
-    }
-  }
-  myChunks.resize( newNbChunks );
-
-  myChunksWithUnused.clear();
-  if ( !myChunks.empty() && myChunks.back().GetUsedRanges().Size() > 1 )
-    myChunksWithUnused.insert( & myChunks.back() );
-
-  for ( size_t i = 0; i < myChunks.size(); ++i )
-    myChunks[i].Compact();
-
-  clearVector( myVtkIDs );
-  clearVector( mySmdsIDs );
-}
-
-
-//================================================================================
-/*!
- * \brief Return true if Compact() will change IDs of elements
- */
-//================================================================================
-
-bool SMDS_ElementFactory::CompactChangePointers()
-{
-  // there can be VTK_EMPTY_CELL's in the VTK grid as well as "holes" in SMDS numeration
-  return ( NbUsedElements() != GetMaxID() );
-}
-
-//================================================================================
-/*!
- * \brief Create a factory of nodes in a given mesh
- */
-//================================================================================
-
-SMDS_NodeFactory::SMDS_NodeFactory( SMDS_Mesh* mesh )
-  : SMDS_ElementFactory( mesh, /*isNodal=*/true )
-{
-}
-
-//================================================================================
-/*!
- * \brief Destructor
- */
-//================================================================================
-
-SMDS_NodeFactory::~SMDS_NodeFactory()
-{
-  Clear();
-}
-
-//================================================================================
-/*!
- * \brief Remove unused nodes located not at the end of the last chunk.
- *        Minimize allocated memory
- *  \param [out] theVtkIDsOldToNew - vector storing change of vtk IDs
- */
-//================================================================================
-
-void SMDS_NodeFactory::Compact( std::vector<int>& theVtkIDsOldToNew )
-{
-  // IDs of VTK nodes always correspond to SMDS IDs but there can be "holes"
-  // in the chunks. So we remove holes and report relocation in theVtkIDsOldToNew:
-  // theVtkIDsOldToNew[ old VtkID ] = new VtkID
-
-  int  oldNbNodes = myMesh->GetGrid()->GetNumberOfPoints();
-  int  newNbNodes = NbUsedElements();
-  int newNbChunks = newNbNodes / theChunkSize + bool ( newNbNodes % theChunkSize );
-  int   maxNodeID = GetMaxID();
-
-  theVtkIDsOldToNew.resize( oldNbNodes, -1 );
-
-  if ( newNbNodes == 0 ) // empty mesh
-  {
-    clearVector( myChunks );
-  }
-  else if ( maxNodeID > newNbNodes ) // there are holes
-  {
-    size_t newID = 0;
-    for ( size_t oldID = 0; oldID < theVtkIDsOldToNew.size(); ++oldID )
-    {
-      const SMDS_MeshElement* oldNode = FindNode( oldID+1 );
-      if ( !oldNode )
-        continue;
-      theVtkIDsOldToNew[ oldID ] = newID;
-      if ( oldID != newID )
-      {
-        const SMDS_MeshElement* newNode = FindElement( newID+1 );
-        if ( !newNode )
-          newNode = NewElement( newID+1 );
-        int  shapeID = oldNode->GetShapeID();
-        int shapeDim = GetShapeDim( shapeID );
-        int   iChunk = newID / theChunkSize;
-        myChunks[ iChunk ].SetShapeID( newNode, shapeID );
-        if ( shapeDim == 2 || shapeDim == 1 )
-        {
-          int iChunkOld = oldID / theChunkSize;
-          TParam* oldPos = myChunks[ iChunkOld ].GetPositionPtr( oldNode );
-          TParam* newPos = myChunks[ iChunk    ].GetPositionPtr( newNode, /*allocate=*/true );
-          if ( oldPos )
-          {
-            newPos[0] = oldPos[0];
-            newPos[1] = oldPos[1];
-          }
-        }
-        if ( oldNode->GetID() > newNbNodes )
-          Free( oldNode );
-      }
-      ++newID;
-    }
-  }
-  else // no holes
-  {
-    for ( int i = 0; i < newNbNodes; ++i )
-      theVtkIDsOldToNew[ i ] = i;
-  }
-  myChunks.resize( newNbChunks );
-
-  myChunksWithUnused.clear();
-  if ( !myChunks.empty() && myChunks.back().GetUsedRanges().Size() > 1 )
-    myChunksWithUnused.insert( & myChunks.back() );
-
-  for ( size_t i = 0; i < myChunks.size(); ++i )
-    myChunks[i].Compact();
-
-  ASSERT( newNbNodes == GetMaxID() );
-  ASSERT( newNbNodes == NbUsedElements() );
-}
-
-//================================================================================
-/*!
- * \brief Return true if Compact() will change IDs of elements
- */
-//================================================================================
-
-bool SMDS_NodeFactory::CompactChangePointers()
-{
-  // IDs of VTK nodes always correspond to SMDS IDs but there can be "holes" in SMDS numeration
-  return ( NbUsedElements() != GetMaxID() );
-}
-
-//================================================================================
-/*!
- * \brief De-allocate all nodes
- */
-//================================================================================
-
-void SMDS_NodeFactory::Clear()
-{
-  SMDS_ElementFactory::Clear();
-}
-
-//================================================================================
-/*!
- * \brief Set a total number of sub-shapes in the main shape
- */
-//================================================================================
-
-void SMDS_NodeFactory::SetNbShapes( size_t nbShapes )
-{
-  clearVector( myShapeDim );
-  myShapeDim.resize( nbShapes+1, theDefaultShapeDim );
-}
-
-//================================================================================
-/*!
- * \brief Return a dimension of a shape
- */
-//================================================================================
-
-int SMDS_NodeFactory::GetShapeDim( int shapeID ) const
-{
-  return shapeID < (int)myShapeDim.size() ? myShapeDim[ shapeID ] : theDefaultShapeDim;
-}
-
-//================================================================================
-/*!
- * \brief Set a dimension of a shape
- */
-//================================================================================
-
-void SMDS_NodeFactory::SetShapeDim( int shapeID, int dim )
-{
-  if ( shapeID >= (int)myShapeDim.size() )
-    myShapeDim.resize( shapeID + 10, theDefaultShapeDim );
-  myShapeDim[ shapeID ] = dim;
-}
-
-//================================================================================
-/*!
- * \brief SMDS_ElementChunk constructor
- *  \param [in] factory - the factory
- *  \param [in] id0 - ID of the 1st element
- */
-//================================================================================
-
-SMDS_ElementChunk::SMDS_ElementChunk( SMDS_ElementFactory* factory, int id0 ):
-  myFactory( factory ),
-  my1stID( id0 ),
-  myMinSubID( std::numeric_limits<int>::max() ),
-  myMaxSubID( 0 )
-{
-  if ( !myFactory )
-    return;
-  if ( myFactory->myIsNodal )
-    myElements = new SMDS_MeshNode[ theChunkSize ];
-  else
-    myElements = new SMDS_MeshCell[ theChunkSize ];
-
-  myUsedRanges.mySet.reserve(2);
-  mySubIDRanges.mySet.insert( _ShapeIDRange( 0, 0 ));
-  myUsedRanges.mySet.insert( _UsedRange( 0, false ));
-  myFactory->myChunksWithUnused.insert( this );
-}
-
-//================================================================================
-/*!
- * \brief SMDS_ElementChunk destructor
- */
-//================================================================================
-
-SMDS_ElementChunk::~SMDS_ElementChunk()
-{
-  delete [] myElements;
-  myFactory->myChunksWithUnused.erase( this );
-}
-
-//================================================================================
-/*!
- * \brief Mark an element as used
- */
-//================================================================================
-
-void SMDS_ElementChunk::UseElement( const int index )
-{
-  myUsedRanges.SetValue( index, true );
-  if ( myUsedRanges.Size() == 1 ) // all elements used
-    myFactory->myChunksWithUnused.erase( this );
-}
-
-//================================================================================
-/*!
- * \brief Return ID of the first non-used element
- */
-//================================================================================
-
-int SMDS_ElementChunk::GetUnusedID() const
-{
-  TUsedRangeSet::set_iterator r = myUsedRanges.mySet.begin();
-  for ( ; r != myUsedRanges.mySet.end(); ++r )
-    if ( !IsUsed( *r ))
-      break;
-
-  return my1stID + r->my1st;
-}
-
-//================================================================================
-/*!
- * \brief Mark an element as non-used
- */
-//================================================================================
-
-void SMDS_ElementChunk::Free( const SMDS_MeshElement* e )
-{
-  bool hasHoles = ( myUsedRanges.Size() > 1 );
-  myUsedRanges.SetValue( Index( e ), false );
-  SetShapeID( e, 0 ); // sub-mesh must do it?
-  SetIsMarked( e, false );
-  if ( !hasHoles )
-    myFactory->myChunksWithUnused.insert( this );
-
-  if ( myUsedRanges.Size() == 1 )
-  {
-    clearVector( myMarkedSet );
-    clearVector( myPositions );
-  }
-}
-
-//================================================================================
-/*!
- * \brief Return an SMDS ID of an element
- */
-//================================================================================
-
-int SMDS_ElementChunk::GetID( const SMDS_MeshElement* e ) const
-{
-  return my1stID + Index( e );
-}
-
-//================================================================================
-/*!
- * \brief Set a Vtk ID of an element
- */
-//================================================================================
-
-void SMDS_ElementChunk::SetVTKID( const SMDS_MeshElement* e, const vtkIdType vtkID )
-{
-  if ( e->GetID() - 1 != vtkID )
-  {
-    if ((int) myFactory->myVtkIDs.size() <= e->GetID() - 1 )
-    {
-      size_t i = myFactory->myVtkIDs.size();
-      myFactory->myVtkIDs.resize( e->GetID() + 100 );
-      for ( ; i < myFactory->myVtkIDs.size(); ++i )
-        myFactory->myVtkIDs[i] = i;
-    }
-    myFactory->myVtkIDs[ e->GetID() - 1 ] = vtkID;
-
-    if ((vtkIdType) myFactory->mySmdsIDs.size() <= vtkID )
-    {
-      size_t i = myFactory->mySmdsIDs.size();
-      myFactory->mySmdsIDs.resize( vtkID + 100 );
-      for ( ; i < myFactory->mySmdsIDs.size(); ++i )
-        myFactory->mySmdsIDs[i] = i;
-    }
-    myFactory->mySmdsIDs[ vtkID ] = e->GetID() - 1;
-  }
-}
-
-//================================================================================
-/*!
- * \brief Return a Vtk ID of an element
- */
-//================================================================================
-
-int SMDS_ElementChunk::GetVtkID( const SMDS_MeshElement* e ) const
-{
-  size_t dfltVtkID = e->GetID() - 1;
-  return ( dfltVtkID < myFactory->myVtkIDs.size() ) ? myFactory->myVtkIDs[ dfltVtkID ] : dfltVtkID;
-}
-
-//================================================================================
-/*!
- * \brief Return ID of a shape an element is assigned to
- */
-//================================================================================
-
-int SMDS_ElementChunk::GetShapeID( const SMDS_MeshElement* e ) const
-{
-  return mySubIDRanges.GetValue( Index( e ));
-}
-
-//================================================================================
-/*!
- * \brief Set ID of a shape an element is assigned to
- */
-//================================================================================
-
-void SMDS_ElementChunk::SetShapeID( const SMDS_MeshElement* e, int shapeID ) const
-{
-  const size_t nbRanges = mySubIDRanges.Size();
-
-  SMDS_ElementChunk* me = const_cast<SMDS_ElementChunk*>( this );
-  int oldShapeID = me->mySubIDRanges.SetValue( Index( e ), shapeID );
-  if ( oldShapeID == shapeID ) return;
-
-  if ( const SMDS_MeshNode* n = dynamic_cast< const SMDS_MeshNode* >( e ))
-    if ( TParam* uv = me->GetPositionPtr( n ))
-    {
-      uv[0] = 0.;
-      uv[1] = 0.;
-    }
-  // update min/max
-  if (( nbRanges > mySubIDRanges.Size() ) &&
-      ( myMinSubID == oldShapeID || myMaxSubID == oldShapeID ))
-  {
-    me->myMinSubID = ( std::numeric_limits<int>::max() );
-    me->myMaxSubID = 0;
-    TSubIDRangeSet::set_iterator it;
-    for ( it = mySubIDRanges.mySet.begin(); it < mySubIDRanges.mySet.end(); ++it )
-      if ( it->myValue > 0 )
-      {
-        me->myMinSubID = std::min( myMinSubID, it->myValue );
-        me->myMaxSubID = std::max( myMaxSubID, it->myValue );
-      }
-  }
-  else if ( shapeID > 0 )
-  {
-    me->myMinSubID = std::min( myMinSubID, shapeID );
-    me->myMaxSubID = std::max( myMaxSubID, shapeID );
-  }
-}
-
-//================================================================================
-/*!
- * \brief Set isMarked flag of an element
- */
-//================================================================================
-
-bool SMDS_ElementChunk::IsMarked( const SMDS_MeshElement* e ) const
-{
-  return ( !myMarkedSet.empty() && myMarkedSet[ Index( e )]);
-}
-
-//================================================================================
-/*!
- * \brief Return isMarked flag of an element
- */
-//================================================================================
-
-void SMDS_ElementChunk::SetIsMarked( const SMDS_MeshElement* e, bool is )
-{
-  if ( !is && myMarkedSet.empty() ) return;
-  if ( myMarkedSet.empty() ) myMarkedSet.resize( theChunkSize, false );
-  myMarkedSet[ Index( e )] = is;
-}
-
-//================================================================================
-/*!
- * \brief Return SMDS_Position of a node on a shape
- */
-//================================================================================
-
-SMDS_PositionPtr SMDS_ElementChunk::GetPosition( const SMDS_MeshNode* n ) const
-{
-  int  shapeID = GetShapeID( n );
-  int shapeDim = static_cast< SMDS_NodeFactory* >( myFactory )->GetShapeDim( shapeID );
-
-  SMDS_ElementChunk* me = const_cast< SMDS_ElementChunk* >( this );
-
-  switch ( shapeDim ) {
-  case 2:
-  {
-    return SMDS_PositionPtr( new _FacePosition( me->GetPositionPtr( n )));
-  }
-  case 1:
-  {
-    return SMDS_PositionPtr( new _EdgePosition( me->GetPositionPtr( n )));
-  }
-  case 0:
-    return SMDS_VertexPosition::StaticPosition();
-  }
-
-  return SMDS_SpacePosition::originSpacePosition();
-}
-
-//================================================================================
-/*!
- * \brief Set SMDS_Position of a node on a shape
- */
-//================================================================================
-
-void SMDS_ElementChunk::SetPosition( const SMDS_MeshNode* n, const SMDS_PositionPtr& pos, int shapeID )
-{
-  int shapeDim = pos ? pos->GetDim() : theDefaultShapeDim;
-  if ( shapeID < 1 )
-  {
-    if ( shapeDim == theDefaultShapeDim )
-      return;
-    shapeID = GetShapeID( n );
-    if ( shapeID < 1 )
-      throw SALOME_Exception("SetPosition() No shape ID provided");
-  }
-
-  static_cast< SMDS_NodeFactory* >( myFactory )->SetShapeDim( shapeID, shapeDim );
-
-  switch ( shapeDim ) {
-  case 2:
-  {
-    TParam* uv = GetPositionPtr( n, /*allocate=*/true );
-    uv[0] = (TParam) pos->GetParameters()[0];
-    uv[1] = (TParam) pos->GetParameters()[1];
-    break;
-  }
-  case 1:
-  {
-    GetPositionPtr( n, /*allocate=*/true )[0] = (TParam) pos->GetParameters()[0];
-    break;
-  }
-  }
-}
-
-//================================================================================
-/*!
- * \brief Return pointer to on-shape-parameters of a node
- */
-//================================================================================
-
-TParam* SMDS_ElementChunk::GetPositionPtr( const SMDS_MeshElement* n, bool allocate )
-{
-  if ( myPositions.empty() && !allocate )
-    return 0;
-
-  myPositions.resize( theChunkSize * 2 );
-  return myPositions.data() + 2 * Index( n );
-}
-
-//================================================================================
-/*!
- * \brief Minimize allocated memory
- */
-//================================================================================
-
-void SMDS_ElementChunk::Compact()
-{
-  mySubIDRanges.mySet.shrink_to_fit();
-  if ( myUsedRanges.mySet.capacity() > 2 )
-    myUsedRanges.mySet.shrink_to_fit();
-
-  clearVector( myMarkedSet );
-
-  if ( !myPositions.empty() )
-  {
-    // look for the last position that must be kept
-    TSubIDRangeSet::set_t::reverse_iterator it;
-    for ( it = mySubIDRanges.mySet.rbegin(); it != mySubIDRanges.mySet.rend(); ++it )
-    {
-      int shapeDim = static_cast< SMDS_NodeFactory* >( myFactory )->GetShapeDim( it->myValue );
-      if ( shapeDim == 1 || shapeDim == 2 )
-        break;
-    }
-    if ( it == mySubIDRanges.mySet.rend() )
-    {
-      clearVector( myPositions );
-    }
-    else if ( it != mySubIDRanges.mySet.rbegin() )
-    {
-      int nbNodes = (it-1)->my1st;
-      myPositions.resize( nbNodes * 2 );
-      std::vector<TParam> newPos( myPositions.begin(), myPositions.end() );
-      myPositions.swap( newPos );
-    }
-  }
-}
-
-//================================================================================
-/*!
- * \brief Print some data for debug purposes
- */
-//================================================================================
-
-void SMDS_ElementChunk::Dump() const
-{
-  std::cout << "1stID: " << my1stID << std::endl;
-
-  std::cout << "SubID min/max: " << myMinSubID << ", " << myMaxSubID << std::endl;
-  std::cout << "SubIDRanges: " << mySubIDRanges.Size() << " ";
-  {
-    TSubIDRangeSet::set_iterator i = mySubIDRanges.mySet.begin();
-    for ( int cnt = 0; i != mySubIDRanges.mySet.end(); ++i, ++cnt )
-      std::cout << "|" << cnt << " - (" << i->my1st << ", " << i->myValue << ") ";
-    std::cout << std::endl;
-  }
-  {
-    std::cout << "UsedRanges: " << myUsedRanges.Size() << " ";
-    TUsedRangeSet::set_iterator i = myUsedRanges.mySet.begin();
-    for ( int cnt = 0; i != myUsedRanges.mySet.end(); ++i, ++cnt )
-      std::cout << cnt << " - (" << i->my1st << ", " << i->myValue << ") ";
-    std::cout << std::endl;
-  }
-}
-
-//================================================================================
-/*!
- * \brief Compare SMDS_ElementChunk's
- */
-//================================================================================
-
-bool _ChunkCompare::operator () (const SMDS_ElementChunk* e1, const SMDS_ElementChunk* e2) const
-{
-  return e1->Get1stID() < e2->Get1stID();
-}
-
diff --git a/src/SMDS/SMDS_ElementFactory.hxx b/src/SMDS/SMDS_ElementFactory.hxx
deleted file mode 100644 (file)
index b25b635..0000000
+++ /dev/null
@@ -1,559 +0,0 @@
-// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
-//
-// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
-// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
-//
-// This library is free software; you can redistribute it and/or
-// modify it under the terms of the GNU Lesser General Public
-// License as published by the Free Software Foundation; either
-// version 2.1 of the License, or (at your option) any later version.
-//
-// This library is distributed in the hope that it will be useful,
-// but WITHOUT ANY WARRANTY; without even the implied warranty of
-// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
-// Lesser General Public License for more details.
-//
-// You should have received a copy of the GNU Lesser General Public
-// License along with this library; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
-//
-// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
-//
-//  File   : SMDS_ElementFactory.hxx
-//  Module : SMESH
-//
-#ifndef _SMDS_ElementFactory_HeaderFile
-#define _SMDS_ElementFactory_HeaderFile
-
-#include "SMDS_MeshCell.hxx"
-#include "SMDS_Position.hxx"
-
-#include <Utils_SALOME_Exception.hxx>
-
-#include <boost/container/flat_set.hpp>
-#include <boost/dynamic_bitset.hpp>
-#include <boost/make_shared.hpp>
-#include <boost/ptr_container/ptr_vector.hpp>
-#include <boost/shared_ptr.hpp>
-
-#include <set>
-
-#include <vtkType.h>
-
-class SMDS_ElementChunk;
-class SMDS_Mesh;
-class SMDS_MeshCell;
-class SMDS_MeshNode;
-
-struct _ChunkCompare {
-  bool operator () (const SMDS_ElementChunk* c1, const SMDS_ElementChunk* c2) const;
-};
-typedef boost::ptr_vector<SMDS_ElementChunk>       TChunkVector;
-typedef std::set<SMDS_ElementChunk*,_ChunkCompare> TChunkPtrSet;
-
-//------------------------------------------------------------------------------------
-/*!
- * \brief Allocate SMDS_MeshElement's (SMDS_MeshCell's or SMDS_MeshNode's )
- *        and bind some attributes to elements:
- *        element ID, element VTK ID, sub-mesh ID, position on shape.
- *
- * Elements are allocated by chunks, so there are used and non-used elements
- */
-class SMDS_ElementFactory
-{
-protected:
-  bool                     myIsNodal;          // what to allocate: nodes or cells
-  SMDS_Mesh*               myMesh;
-  TChunkVector             myChunks;           // array of chunks of elements
-  TChunkPtrSet             myChunksWithUnused; // sorted chunks having unused elements
-  std::vector< vtkIdType > myVtkIDs;           // myVtkIDs[ smdsID-1 ] == vtkID
-  std::vector< int >       mySmdsIDs;          // mySmdsIDs[ vtkID ] == smdsID - 1
-  int                      myNbUsedElements;   // counter of elements
-
-  friend class SMDS_ElementChunk;
-
-public:
-
-  SMDS_ElementFactory( SMDS_Mesh* mesh, const bool isNodal=false );
-  virtual ~SMDS_ElementFactory();
-
-  //! Return minimal ID of a non-used element
-  int GetFreeID();
-
-  //! Return maximal ID of an used element
-  int GetMaxID();
-
-  //! Return minimal ID of an used element
-  int GetMinID();
-
-  //! Return an element by ID. NULL if the element with the given ID is already used
-  SMDS_MeshElement* NewElement( const int id );
-
-  //! Return a SMDS_MeshCell by ID. NULL if the cell with the given ID is already used
-  SMDS_MeshCell* NewCell( const int id ) { return static_cast<SMDS_MeshCell*>( NewElement( id )); }
-
-  //! Return an used element by ID. NULL if the element with the given ID is not yet used
-  const SMDS_MeshElement* FindElement( const int id ) const;
-
-  //! Return a number of used elements
-  int NbUsedElements() const { return myNbUsedElements; }
-
-  //! Return an iterator on all element filtered using a given filter.
-  //  nbElemsToReturn is used to optimize by stopping the iteration as soon as
-  //  all elements satisfying filtering condition encountered.
-  template< class ElemIterator >
-  boost::shared_ptr< ElemIterator > GetIterator( SMDS_MeshElement::Filter* filter,
-                                                 size_t nbElemsToReturn = -1 );
-
-  //! Return an iterator on all element assigned to a given shape.
-  //  nbElemsToReturn is used to optimize by stopping the iteration as soon as
-  //  all elements assigned to the shape encountered.
-  template< class ElemIterator >
-  boost::shared_ptr< ElemIterator > GetShapeIterator( int shapeID, size_t nbElemsToReturn );
-
-  //! Mark the element as non-used
-  void Free( const SMDS_MeshElement* );
-
-  //! Return an SMDS ID by a Vtk one
-  int FromVtkToSmds( vtkIdType vtkID );
-
-  //! De-allocate all elements
-  virtual void Clear();
-
-  //! Remove unused elements located not at the end of the last chunk.
-  //  Minimize allocated memory
-  virtual void Compact(std::vector<int>& idCellsOldToNew);
-
-  //! Return true if Compact() will change IDs of elements
-  virtual bool CompactChangePointers();
-
-  //! Return a number of elements in a chunk
-  static int ChunkSize();
-};
-
-//------------------------------------------------------------------------------------
-/*!
- * \brief Allocate SMDS_MeshNode's
- */
-class SMDS_NodeFactory : public SMDS_ElementFactory
-{
-  std::vector<char> myShapeDim; // dimension of shapes
-
-public:
-
-  SMDS_NodeFactory( SMDS_Mesh* mesh );
-  ~SMDS_NodeFactory();
-
-  //! Return a SMDS_MeshNode by ID. NULL if the node with the given ID is already used
-  SMDS_MeshNode* NewNode( int id ) { return (SMDS_MeshNode*) NewElement(id); }
-
-  //! Return an used node by ID. NULL if the node with the given ID is not yet used
-  const SMDS_MeshNode* FindNode( int id ) { return (const SMDS_MeshNode*) FindElement(id); }
-
-  //! Set a total number of sub-shapes in the main shape
-  void SetNbShapes( size_t nbShapes );
-
-  //! Return a dimension of a shape
-  int  GetShapeDim( int shapeID ) const;
-
-  //! Set a dimension of a shape
-  void SetShapeDim( int shapeID, int dim );
-
-  //! De-allocate all nodes
-  virtual void Clear();
-
-  //! Remove unused nodes located not at the end of the last chunk.
-  //  Minimize allocated memory
-  virtual void Compact(std::vector<int>& idNodesOldToNew);
-
-  //! Return true if Compact() will change IDs of node
-  virtual bool CompactChangePointers();
-};
-
-//------------------------------------------------------------------------------------
-/*!
- * \brief Range of elements in a chunk having the same attribute value
- */
-template< typename ATTR>
-struct _Range
-{
-  typedef ATTR attr_t;
-
-  attr_t myValue; // common attribute value
-  int    my1st;   // index in the chunk of the 1st element 
-  _Range( int i0 = 0, attr_t v = 0 ): myValue( v ), my1st( i0 ) {}
-
-  bool operator < (const _Range& other) const { return my1st < other.my1st; }
-};
-
-typedef std::vector< std::pair< int, int > > TIndexRanges;
-
-//------------------------------------------------------------------------------------
-/*!
- * \brief Sorted set of ranges
- */
-template< class RANGE >
-struct _RangeSet
-{
-  typedef typename RANGE::attr_t              attr_t;
-  typedef boost::container::flat_set< RANGE > set_t;
-  typedef typename set_t::const_iterator      set_iterator;
-
-  set_t mySet;
-
-  _RangeSet() { mySet.insert( RANGE( 0, 0 )); }
-
-  /*!
-   * \brief Return a number of ranges
-   */
-  size_t Size() const { return mySet.size(); }
-
-  /*!
-   * \brief Return a mutable _Range::my1st of a range pointed by an iterator
-   */
-  int&   First( set_iterator rangePtr ) { return const_cast< int& >( rangePtr->my1st ); }
-
-  /*!
-   * \brief Return a number of elements in a range pointed by an iterator
-   */
-  size_t Size( set_iterator rangePtr ) const
-  {
-    int next1st =
-      ( rangePtr + 1 == mySet.end() ) ? SMDS_ElementFactory::ChunkSize() : ( rangePtr + 1 )->my1st;
-    return next1st - rangePtr->my1st;
-  }
-
-  /*!
-   * \brief Return ranges of indices (from,to) of elements having a given value
-   */
-  bool GetIndices( const attr_t theValue, TIndexRanges & theIndices,
-                   const attr_t* theMinValue = 0, const attr_t* theMaxValue = 0) const
-  {
-    bool isFound = false;
-
-    if ( sizeof( attr_t ) == sizeof( int ) && theMinValue )
-      if ( theValue < *theMinValue || theValue > *theMaxValue )
-        return isFound;
-
-    for ( set_iterator it = mySet.begin(); it < mySet.end(); ++it )
-    {
-      if ( it->myValue == theValue )
-      {
-        theIndices.push_back( std::make_pair( it->my1st, it->my1st + Size( it )));
-        isFound = true;
-        ++it; // the next range value differs from theValue
-      }
-    }
-    return isFound;
-  }
-
-  /*!
-   * \brief Return value of an element attribute
-   *  \param [in] theIndex - element index
-   *  \return attr_t - attribute value
-   */
-  attr_t GetValue( int theIndex ) const
-  {
-    set_iterator r = mySet.upper_bound( theIndex ) - 1;
-    return r->myValue;
-  }
-
-  /*!
-   * \brief Change value of an element attribute
-   *  \param [in] theIndex - element index
-   *  \param [in] theValue - attribute value
-   *  \return attr_t - previous value
-   */
-  attr_t SetValue( int theIndex, attr_t theValue )
-  {
-    set_iterator rNext = mySet.upper_bound( theIndex );
-    set_iterator     r = rNext - 1;
-    int          rSize = Size( r ); // range size
-    attr_t      rValue = r->myValue;
-    if ( rValue == theValue )
-      return rValue; // it happens while compacting
-
-    if ( r->my1st == theIndex ) // theIndex is the first in the range
-    {
-      bool joinPrev = // can join theIndex to the previous range
-        ( r->my1st > 0 && ( r-1 )->myValue == theValue );
-
-      if ( rSize == 1 )
-      {
-        bool joinNext = // can join to the next range
-          ( rNext != mySet.end() && rNext->myValue == theValue );
-
-        if ( joinPrev )
-        {
-          if ( joinNext ) // && joinPrev
-          {
-            mySet.erase( r, r + 2 );
-          }
-          else // joinPrev && !joinNext
-          {
-            mySet.erase( r );
-          }
-        }
-        else
-        {
-          if ( joinNext ) // && !joinPrev
-          {
-            r = mySet.erase( r ); // then r points to the next range
-            First( r )--;
-          }
-          else // !joinPrev && !joinNext
-          {
-            const_cast< attr_t & >( r->myValue ) = theValue;
-          }
-        }
-      }
-      else // if rSize > 1
-      {
-        if ( joinPrev )
-        {
-          First( r )++;
-        }
-        else
-        {
-          r = mySet.insert( r, RANGE( theIndex + 1, rValue )) - 1;
-          const_cast< attr_t & >( r->myValue ) = theValue;
-        }
-      }
-    }
-    else if ( r->my1st + rSize - 1 == theIndex ) // theIndex is last in the range
-    {
-      if ( rNext != mySet.end() && rNext->myValue == theValue ) // join to the next
-      {
-        First( rNext )--;
-      }
-      else
-      {
-        mySet.insert( r, RANGE( theIndex, theValue ));
-      }
-    }
-    else // theIndex in the middle of the range
-    {
-      r = mySet.insert( r, RANGE( theIndex,     theValue ));
-      r = mySet.insert( r, RANGE( theIndex + 1, rValue ));
-    }
-    return rValue;
-  }
-}; // struct _RangeSet
-
-
-typedef _Range< int >  _ShapeIDRange; // sub-mesh ID range
-typedef _Range< bool > _UsedRange;    // range of used elements
-
-typedef _RangeSet< _ShapeIDRange > TSubIDRangeSet;
-typedef _RangeSet< _UsedRange >    TUsedRangeSet;
-typedef boost::dynamic_bitset<>    TBitSet;
-typedef float                       TParam;
-
-//------------------------------------------------------------------------------------
-/*!
- * \brief Allocate SMDS_MeshElement's (SMDS_MeshCell's or SMDS_MeshNode's )
- *        and bind some attributes to elements:
- *        element ID, sub-shape ID, isMarked flag, parameters on shape
- */
-class SMDS_ElementChunk
-{
-  SMDS_ElementFactory* myFactory;     // holder of this chunk
-  SMDS_MeshElement*    myElements;    // array of elements
-  int                  my1stID;       // ID of myElements[0]
-  TBitSet              myMarkedSet;   // mark some elements
-  TUsedRangeSet        myUsedRanges;  // ranges of used/unused elements
-  TSubIDRangeSet       mySubIDRanges; // ranges of elements on the same sub-shape
-  int                  myMinSubID;    // min sub-shape ID
-  int                  myMaxSubID;    // max sub-shape ID
-  std::vector<TParam>  myPositions;   // UV parameters on shape: 2*param_t per an element
-
-public:
-
-  SMDS_ElementChunk( SMDS_ElementFactory* factory = 0, int id0 = 0 );
-  ~SMDS_ElementChunk();
-
-  //! Return an element by an index [0,ChunkSize()]
-  SMDS_MeshElement* Element(int index) { return & myElements[index]; }
-
-  //! Return an element by an index [0,ChunkSize()]
-  const SMDS_MeshElement* Element(int index) const { return & myElements[index]; }
-
-  //! Return ID of the first non-used element
-  int  GetUnusedID() const;
-
-  //! Mark an element as used
-  void UseElement( const int index );
-
-  //! Mark an element as non-used
-  void Free( const SMDS_MeshElement* e );
-
-  //! Check if a given range holds used or non-used elements
-  static bool IsUsed( const _UsedRange& r ) { return r.myValue; }
-
-  //! Return index of an element in the chunk
-  int Index( const SMDS_MeshElement* e ) const { return e - myElements; }
-
-  //! Return ID of the 1st element in the chunk
-  int Get1stID() const { return my1stID; }
-
-  //! Return pointer to on-shape-parameters of a node
-  TParam* GetPositionPtr( const SMDS_MeshElement* node, bool allocate=false );
-
-  //! Return ranges of used/non-used elements
-  const TUsedRangeSet&  GetUsedRanges() const { return myUsedRanges; }
-  const TUsedRangeSet&  GetUsedRangesMinMax( bool& min, bool& max ) const
-  { min = false; max = true; return myUsedRanges; }
-
-  //! Return ranges of elements assigned to sub-shapes and min/max of sub-shape IDs
-  const TSubIDRangeSet& GetSubIDRangesMinMax( int& min, int& max ) const
-  { min = myMinSubID; max = myMaxSubID; return mySubIDRanges; }
-
-  //! Minimize allocated memory
-  void Compact();
-
-  //! Print some data
-  void Dump() const; // debug
-
-
-  // Methods called by SMDS_MeshElement
-
-  int  GetID( const SMDS_MeshElement* e ) const;
-
-  int  GetVtkID( const SMDS_MeshElement* e ) const;
-  void SetVTKID( const SMDS_MeshElement* e, const vtkIdType id );
-
-  int  GetShapeID( const SMDS_MeshElement* e ) const;
-  void SetShapeID( const SMDS_MeshElement* e, int shapeID ) const;
-
-  bool IsMarked   ( const SMDS_MeshElement* e ) const;
-  void SetIsMarked( const SMDS_MeshElement* e, bool is );
-
-  SMDS_PositionPtr GetPosition( const SMDS_MeshNode* n ) const;
-  void SetPosition( const SMDS_MeshNode* n, const SMDS_PositionPtr& pos, int shapeID );
-
-  SMDS_Mesh* GetMesh() { return myFactory->myMesh; }
-};
-
-//------------------------------------------------------------------------------------
-/*!
- * \brief Iterator on elements in chunks
- */
-template< class ELEM_ITERATOR, class RANGE_SET >
-struct _ChunkIterator : public ELEM_ITERATOR
-{
-  typedef typename ELEM_ITERATOR::value_type    element_type;
-  typedef SMDS_MeshElement::Filter*             filter_ptr;
-  typedef typename RANGE_SET::attr_t            attr_type;
-  typedef const RANGE_SET& (SMDS_ElementChunk::*get_rangeset_fun)(attr_type&, attr_type&) const;
-
-  const SMDS_MeshElement* myElement;
-  TIndexRanges            myRanges;
-  int                     myRangeIndex;
-  const TChunkVector&     myChunks;
-  int                     myChunkIndex;
-  get_rangeset_fun        myGetRangeSetFun;
-  attr_type               myValue;
-  attr_type               myMinValue;
-  attr_type               myMaxValue;
-  filter_ptr              myFilter;
-  size_t                  myNbElemsToReturn;
-  size_t                  myNbReturned;
-
-  _ChunkIterator( const TChunkVector &      theChunks,
-                  get_rangeset_fun          theGetRangeSetFun,
-                  attr_type                 theAttrValue,
-                  SMDS_MeshElement::Filter* theFilter,
-                  size_t                    theNbElemsToReturn = -1):
-    myElement( 0 ),
-    myRangeIndex( 0 ),
-    myChunks( theChunks ),
-    myChunkIndex( -1 ),
-    myGetRangeSetFun( theGetRangeSetFun ),
-    myValue( theAttrValue ),
-    myFilter( theFilter ),
-    myNbElemsToReturn( theNbElemsToReturn ),
-    myNbReturned( 0 )
-  {
-    next();
-  }
-  ~_ChunkIterator()
-  {
-    delete myFilter;
-  }
-
-  virtual bool more()
-  {
-    return myElement;
-  }
-
-  virtual element_type next()
-  {
-    element_type result = (element_type) myElement;
-    myNbReturned += bool( result );
-
-    myElement = 0;
-    if ( myNbReturned < myNbElemsToReturn )
-      while ( ! nextInRange() )
-      {
-        if ( ++myRangeIndex >= (int)myRanges.size() )
-        {
-          myRanges.clear();
-          myRangeIndex = 0;
-          while ( ++myChunkIndex < (int)myChunks.size() &&
-                  !getRangeSet().GetIndices( myValue, myRanges, &myMinValue, &myMaxValue ))
-            ;
-          if ( myChunkIndex >= (int)myChunks.size() )
-            break;
-        }
-      }
-    return result;
-  }
-
-  bool nextInRange()
-  {
-    if ( myRangeIndex < (int)myRanges.size() )
-    {
-      std::pair< int, int > & range = myRanges[ myRangeIndex ];
-      while ( range.first < range.second && !myElement )
-      {
-        myElement = myChunks[ myChunkIndex ].Element( range.first++ );
-        if ( !(*myFilter)( myElement ))
-          myElement = 0;
-      }
-    }
-    return myElement;
-  }
-
-  const RANGE_SET& getRangeSet()
-  {
-    return ( myChunks[  myChunkIndex ].*myGetRangeSetFun )( myMinValue, myMaxValue );
-  }
-}; // struct _ChunkIterator
-
-
-template< class ElemIterator >
-boost::shared_ptr< ElemIterator >
-SMDS_ElementFactory::GetIterator( SMDS_MeshElement::Filter* filter,
-                                  size_t                    nbElemsToReturn )
-{
-  typedef _ChunkIterator< ElemIterator, TUsedRangeSet > TChuckIterator;
-  return boost::make_shared< TChuckIterator >( myChunks,
-                                               & SMDS_ElementChunk::GetUsedRangesMinMax,
-                                               /*isUsed=*/true,
-                                               filter,
-                                               nbElemsToReturn );
-}
-
-template< class ElemIterator >
-boost::shared_ptr< ElemIterator >
-SMDS_ElementFactory::GetShapeIterator( int shapeID, size_t nbElemsToReturn )
-{
-  typedef _ChunkIterator< ElemIterator, TSubIDRangeSet > TChuckIterator;
-  return boost::make_shared< TChuckIterator >( myChunks,
-                                               & SMDS_ElementChunk::GetSubIDRangesMinMax,
-                                               /*shapeID=*/shapeID,
-                                               new SMDS_MeshElement::NonNullFilter(),
-                                               nbElemsToReturn );
-}
-
-#endif
diff --git a/src/SMDS/SMDS_ElementHolder.cxx b/src/SMDS/SMDS_ElementHolder.cxx
deleted file mode 100644 (file)
index 0913590..0000000
+++ /dev/null
@@ -1,122 +0,0 @@
-// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
-//
-// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
-// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
-//
-// This library is free software; you can redistribute it and/or
-// modify it under the terms of the GNU Lesser General Public
-// License as published by the Free Software Foundation; either
-// version 2.1 of the License, or (at your option) any later version.
-//
-// This library is distributed in the hope that it will be useful,
-// but WITHOUT ANY WARRANTY; without even the implied warranty of
-// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
-// Lesser General Public License for more details.
-//
-// You should have received a copy of the GNU Lesser General Public
-// License along with this library; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
-//
-// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
-//
-//  File   : SMDS_ElementHolder.cxx
-//  Module : SMESH
-//
-
-#include "SMDS_ElementHolder.hxx"
-
-#include "ObjectPool.hxx"
-#include "SMDS_CellOfNodes.hxx"
-#include "SMDS_Mesh.hxx"
-
-//=======================================================================
-//function : SMDS_ElementHolder
-//purpose  : register self in the mesh
-//=======================================================================
-
-SMDS_ElementHolder::SMDS_ElementHolder( const SMDS_Mesh* mesh )
-  : myMesh( const_cast< SMDS_Mesh* >( mesh ))
-{
-  myPtrInMesh = myMesh->myElemHolders.insert( this ).first;
-}
-
-//=======================================================================
-//function : ~SMDS_ElementHolder
-//purpose  : un-register self from the mesh
-//=======================================================================
-
-SMDS_ElementHolder::~SMDS_ElementHolder()
-{
-  myMesh->myElemHolders.erase( myPtrInMesh );
-}
-
-//=======================================================================
-//function : beforeCompacting
-//purpose  : store vtkIDs of elements
-//=======================================================================
-
-void SMDS_ElementHolder::beforeCompacting()
-{
-  int i = 0;
-  for ( SMDS_ElemIteratorPtr it = getElements(); it->more(); ++i )
-  {
-    const SMDS_MeshElement* e = it->next();
-    if ( !e ) continue;
-    if ( e->IsNull() && !dynamic_cast<const SMDS_CellOfNodes*>( e ))
-      continue; // removed element
-    myIsNode.push_back( e->GetType() == SMDSAbs_Node );
-    if ( myMesh->Contains( e ))
-    {
-      myVtkIDs.push_back( e->GetVtkID() );
-    }
-    else
-    {
-      myExternalElems.push_back( e );
-      myVtkIDs.push_back( -1 * (int)myExternalElems.size() );
-    }
-  }
-}
-
-//=======================================================================
-//function : restoreElements
-//purpose  : restore pointers to elements
-//=======================================================================
-
-void SMDS_ElementHolder::restoreElements( const std::vector<int>& idNodesOldToNew,
-                                          const std::vector<int>& idCellsOldToNew )
-{
-  tmpClear();
-
-  const SMDS_MeshElement* elem;
-
-  std::vector< bool >::iterator isNode = myIsNode.begin();
-  for ( size_t i = 0; i < myVtkIDs.size(); ++i, ++isNode )
-  {
-    int vtkID = myVtkIDs[i];
-    if ( vtkID < 0 )
-    {
-      elem = myExternalElems[ (-vtkID)-1 ];
-    }
-    else if ( *isNode )
-    {
-      if ( vtkID < (int)idNodesOldToNew.size() )
-        elem = myMesh->FindNodeVtk( idNodesOldToNew[ vtkID ]);
-      else
-        elem = myMesh->FindNodeVtk( vtkID );
-    }
-    else
-    {
-      if ( vtkID < (int)idCellsOldToNew.size() )
-        elem = myMesh->FindElementVtk( idCellsOldToNew[ vtkID ]);
-      else
-        elem = myMesh->FindElementVtk( vtkID );
-    }
-    if ( elem )
-      add( elem );
-  }
-  clearVector( myExternalElems );
-  clearVector( myVtkIDs );
-  clearVector( myIsNode );
-
-  compact();
-}
diff --git a/src/SMDS/SMDS_ElementHolder.hxx b/src/SMDS/SMDS_ElementHolder.hxx
deleted file mode 100644 (file)
index f05774b..0000000
+++ /dev/null
@@ -1,93 +0,0 @@
-// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
-//
-// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
-// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
-//
-// This library is free software; you can redistribute it and/or
-// modify it under the terms of the GNU Lesser General Public
-// License as published by the Free Software Foundation; either
-// version 2.1 of the License, or (at your option) any later version.
-//
-// This library is distributed in the hope that it will be useful,
-// but WITHOUT ANY WARRANTY; without even the implied warranty of
-// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
-// Lesser General Public License for more details.
-//
-// You should have received a copy of the GNU Lesser General Public
-// License along with this library; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
-//
-// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
-//
-//  File   : SMDS_ElementHolder.hxx
-//  Module : SMESH
-//
-#ifndef _SMDS_ElementHolder_HeaderFile
-#define _SMDS_ElementHolder_HeaderFile
-
-#include "SMESH_SMDS.hxx"
-
-#include "SMDS_ElemIterator.hxx"
-
-#include <vector>
-#include <set>
-
-class SMDS_Mesh;
-class SMDS_MeshElement;
-
-//------------------------------------------------------------------------------------
-/*!
- * \brief Base class of object holding SMDS_MeshElement pointers.
- *        Registering such an object in SMDS_Mesh assures that the
- *        pointers remain valid after compacting the mesh
- */
-class SMDS_EXPORT SMDS_ElementHolder
-{
- public:
-
-  //! register self in the mesh
-  SMDS_ElementHolder( const SMDS_Mesh* mesh );
-
-  //! un-register self from the mesh
-  virtual ~SMDS_ElementHolder();
-
-
- protected:
-
-  //!< the descendant object return its elements just before the mesh compacting
-  virtual SMDS_ElemIteratorPtr getElements() = 0;
-
-  //!< the descendant object temporary remove its elements
-  virtual void tmpClear() = 0;
-
-  //!< the descendant object re-add its elements after the mesh compacting
-  virtual void add( const SMDS_MeshElement* element ) = 0;
-
-  //!< the descendant squeeze its element storage after re-adding elements
-  virtual void compact() = 0;
-
-  //!< allow the descendant treat its elements before mesh clearing
-  virtual void clear() {}
-
-  SMDS_Mesh* myMesh;
-
-
- private: // methods called by SMDS_Mesh
-
-  friend class SMDS_Mesh;
-
-  //! store vtkIDs of elements
-  void beforeCompacting();
-
-  //! restore pointers to elements
-  void restoreElements( const std::vector<int>& idNodessOldToNew,
-                        const std::vector<int>& idCellsOldToNew );
-
-
-  std::vector<const SMDS_MeshElement*>      myExternalElems; //!< elements not contained in the mesh
-  std::vector< int >                        myVtkIDs;        //!< vtk IDs of elements
-  std::vector< bool >                       myIsNode;
-  std::set< SMDS_ElementHolder* >::iterator myPtrInMesh;
-};
-
-#endif
diff --git a/src/SMDS/SMDS_FaceOfEdges.cxx b/src/SMDS/SMDS_FaceOfEdges.cxx
new file mode 100644 (file)
index 0000000..67ff4f6
--- /dev/null
@@ -0,0 +1,196 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//
+#ifdef _MSC_VER
+#pragma warning(disable:4786)
+#endif
+
+#include "SMDS_FaceOfEdges.hxx"
+#include "SMDS_IteratorOfElements.hxx"
+#include "SMDS_MeshNode.hxx"
+#include "utilities.h"
+
+using namespace std;
+
+//=======================================================================
+//function : NbEdges
+//purpose  : 
+//=======================================================================
+
+int SMDS_FaceOfEdges::NbEdges() const
+{
+        return myNbEdges;
+}
+
+int SMDS_FaceOfEdges::NbFaces() const
+{
+        return 1;
+}
+//=======================================================================
+//function : Print
+//purpose  : 
+//=======================================================================
+
+void SMDS_FaceOfEdges::Print(ostream & OS) const
+{
+        OS << "face <" << GetID() << " > : ";
+        int i;
+        for (i = 0; i < NbEdges() - 1; i++) OS << myEdges[i] << ",";
+        OS << myEdges[i] << ") " << endl;
+}
+
+SMDSAbs_ElementType SMDS_FaceOfEdges::GetType() const
+{
+        return SMDSAbs_Face;
+}
+
+//=======================================================================
+//function : elementsIterator
+//purpose  : 
+//=======================================================================
+
+class SMDS_FaceOfEdges_MyIterator:public SMDS_ElemIterator
+{
+  const SMDS_MeshEdge* const *mySet;
+  int myLength;
+  int index;
+ public:
+  SMDS_FaceOfEdges_MyIterator(const SMDS_MeshEdge* const *s, int l):
+    mySet(s),myLength(l),index(0) {}
+
+  bool more()
+  {
+    return index<myLength;
+  }
+
+  const SMDS_MeshElement* next()
+  {
+    index++;
+    return mySet[index-1];
+  }     
+};
+
+SMDS_ElemIteratorPtr SMDS_FaceOfEdges::elementsIterator
+                         (SMDSAbs_ElementType type) const
+{
+  switch(type)
+  {
+  case SMDSAbs_Face:
+    return SMDS_MeshElement::elementsIterator(SMDSAbs_Face);
+  case SMDSAbs_Edge:
+    return SMDS_ElemIteratorPtr(new SMDS_FaceOfEdges_MyIterator(myEdges,myNbEdges));
+  default:
+    return SMDS_ElemIteratorPtr
+      (new SMDS_IteratorOfElements
+       (this,type, SMDS_ElemIteratorPtr
+        (new SMDS_FaceOfEdges_MyIterator(myEdges,myNbEdges))));
+  }
+}
+
+SMDS_FaceOfEdges::SMDS_FaceOfEdges(const SMDS_MeshEdge* edge1,
+                                   const SMDS_MeshEdge* edge2,
+                                   const SMDS_MeshEdge* edge3)
+{
+  //MESSAGE("****************************************************** SMDS_FaceOfEdges");
+        myNbEdges = 3;
+        myEdges[0]=edge1;
+        myEdges[1]=edge2;
+        myEdges[2]=edge3;
+        myEdges[3]=0;
+}
+
+SMDS_FaceOfEdges::SMDS_FaceOfEdges(const SMDS_MeshEdge* edge1,
+                                   const SMDS_MeshEdge* edge2,
+                                   const SMDS_MeshEdge* edge3,
+                                   const SMDS_MeshEdge* edge4)
+{
+  //MESSAGE("****************************************************** SMDS_FaceOfEdges");
+        myNbEdges = 4;
+        myEdges[0]=edge1;
+        myEdges[1]=edge2;
+        myEdges[2]=edge3;
+        myEdges[3]=edge4;       
+}
+
+/*bool operator<(const SMDS_FaceOfEdges& f1, const SMDS_FaceOfEdges& f2)
+{
+        set<SMDS_MeshNode> set1,set2;
+        SMDS_ElemIteratorPtr it;
+        const SMDS_MeshNode * n;
+
+        it=f1.nodesIterator();
+
+        while(it->more())
+        {
+                n=static_cast<const SMDS_MeshNode *>(it->next());
+                set1.insert(*n);
+        }
+
+        delete it;
+        it=f2.nodesIterator();
+        
+        while(it->more())
+        {       
+                n=static_cast<const SMDS_MeshNode *>(it->next());
+                set2.insert(*n);
+        }
+
+        delete it;
+        return set1<set2;       
+
+}*/
+
+
+int SMDS_FaceOfEdges::NbNodes() const
+{
+  return myEdges[0]->NbNodes() + myEdges[1]->NbNodes() + myEdges[2]->NbNodes() +
+    ( myNbEdges == 4 ? myEdges[3]->NbNodes() : 0 ) - myNbEdges;
+}
+
+/*!
+ * \brief Return node by its index
+ * \param ind - node index
+ * \retval const SMDS_MeshNode* - the node
+ */
+const SMDS_MeshNode* SMDS_FaceOfEdges::GetNode(const int ind) const
+{
+  int index = ind;
+  for ( int i = 0; i < myNbEdges; ++i ) {
+    if ( index >= myEdges[ i ]->NbNodes() )
+      index -= myEdges[ i ]->NbNodes();
+    else
+      return myEdges[ i ]->GetNode( index );
+  }
+  return 0;
+}
+
+SMDSAbs_EntityType SMDS_FaceOfEdges::GetEntityType() const
+{
+  return myNbEdges == 3 ? SMDSEntity_Triangle : SMDSEntity_Quadrangle;
+}
+
+SMDSAbs_GeometryType SMDS_FaceOfEdges::GetGeomType() const
+{
+  return myNbEdges == 3 ? SMDSGeom_TRIANGLE : SMDSGeom_QUADRANGLE;
+}
diff --git a/src/SMDS/SMDS_FaceOfEdges.hxx b/src/SMDS/SMDS_FaceOfEdges.hxx
new file mode 100644 (file)
index 0000000..8bfc1d3
--- /dev/null
@@ -0,0 +1,68 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//
+#ifndef _SMDS_FaceOfEdges_HeaderFile
+#define _SMDS_FaceOfEdges_HeaderFile
+
+#include "SMESH_SMDS.hxx"
+
+#include "SMDS_MeshFace.hxx"
+#include "SMDS_MeshEdge.hxx"
+#include "SMDS_Iterator.hxx"
+
+#include <iostream>
+
+
+class SMDS_EXPORT SMDS_FaceOfEdges:public SMDS_MeshFace
+{
+  public:
+        void Print(std::ostream & OS) const;
+        SMDS_FaceOfEdges(const SMDS_MeshEdge* edge1,
+                         const SMDS_MeshEdge* edge2,
+                         const SMDS_MeshEdge* edge3);
+        SMDS_FaceOfEdges(const SMDS_MeshEdge* edge1,
+                         const SMDS_MeshEdge* edge2,
+                         const SMDS_MeshEdge* edge3,
+                         const SMDS_MeshEdge* edge4);
+                
+        virtual SMDSAbs_ElementType  GetType() const;
+        virtual SMDSAbs_EntityType   GetEntityType() const;
+        virtual SMDSAbs_GeometryType GetGeomType() const;
+        virtual bool ChangeNodes(const SMDS_MeshNode* nodes[],
+                                 const int            nbNodes) {return false;}
+        virtual int NbNodes() const;
+        virtual int NbEdges() const;
+        virtual int NbFaces() const;
+        virtual const SMDS_MeshNode* GetNode(const int ind) const;
+
+  protected:
+        virtual SMDS_ElemIteratorPtr elementsIterator(SMDSAbs_ElementType type) const;
+
+  private:
+        const SMDS_MeshEdge* myEdges[4];
+        int                  myNbEdges;
+
+};
+
+#endif
index 0b7f9acf989aad783e1ae6a32c6de20c144fceaf..dfd3b7385eb45f424a0e4621fe6b2c1698bd95c2 100644 (file)
 #pragma warning(disable:4786)
 #endif
 
-#include "SMDS_FaceOfNodes.hxx"
-
 #include "SMDS_SetIterator.hxx"
+#include "SMDS_FaceOfNodes.hxx"
+#include "SMDS_IteratorOfElements.hxx"
 #include "SMDS_MeshNode.hxx"
 #include "SMDS_Mesh.hxx"
 
-#include <utilities.h>
+#include "utilities.h"
 
-#include <boost/make_shared.hpp>
+using namespace std;
 
 //=======================================================================
 //function : NbEdges
 
 int SMDS_FaceOfNodes::NbEdges() const
 {
-  return NbNodes();
+        return NbNodes();
 }
 
 int SMDS_FaceOfNodes::NbFaces() const
 {
-  return 1;
+        return 1;
 }
 
 int SMDS_FaceOfNodes::NbNodes() const
 {
-  return myNbNodes;
-}
-
-int SMDS_FaceOfNodes::GetNodeIndex( const SMDS_MeshNode* node ) const
-{
-  for ( int i = 0; i < myNbNodes; ++i )
-    if ( myNodes[i] == node )
-      return i;
-  return -1;
+        return myNbNodes;
 }
 
 //=======================================================================
@@ -71,31 +63,81 @@ int SMDS_FaceOfNodes::GetNodeIndex( const SMDS_MeshNode* node ) const
 
 void SMDS_FaceOfNodes::Print(ostream & OS) const
 {
-  OS << "face <" << GetID() << " > : ";
-  int i;
-  for (i = 0; i < NbNodes() - 1; i++) OS << myNodes[i] << ",";
-  OS << myNodes[i] << ") " << endl;
+        OS << "face <" << GetID() << " > : ";
+        int i;
+        for (i = 0; i < NbNodes() - 1; i++) OS << myNodes[i] << ",";
+        OS << myNodes[i] << ") " << endl;
 }
 
-SMDS_ElemIteratorPtr SMDS_FaceOfNodes::nodesIterator() const
+//=======================================================================
+//function : elementsIterator
+//purpose  : 
+//=======================================================================
+
+class SMDS_FaceOfNodes_MyIterator:public SMDS_NodeArrayElemIterator
 {
-  return boost::make_shared< SMDS_NodeArrayElemIterator >( &myNodes[0], &myNodes[0] + NbNodes() );
-}
+ public:
+  SMDS_FaceOfNodes_MyIterator(const SMDS_MeshNode* const *s, int l):
+    SMDS_NodeArrayElemIterator( s, & s[ l ] ) {}
+};
 
-SMDS_NodeIteratorPtr SMDS_FaceOfNodes::nodeIterator() const
+/// ===================================================================
+/*!
+ * \brief Iterator on edges of face
+ */
+/// ===================================================================
+
+class _MyEdgeIterator : public SMDS_ElemIterator
+{
+  vector< const SMDS_MeshElement* > myElems;
+  size_t                            myIndex;
+public:
+  _MyEdgeIterator(const SMDS_FaceOfNodes* face):myIndex(0) {
+    myElems.reserve( face->NbNodes() );
+    for ( int i = 0; i < face->NbNodes(); ++i ) {
+      const SMDS_MeshElement* edge =
+        SMDS_Mesh::FindEdge( face->GetNode( i ), face->GetNodeWrap( i + 1 ));
+      if ( edge )
+        myElems.push_back( edge );
+    }
+  }
+  /// Return true if and only if there are other object in this iterator
+  virtual bool more() { return myIndex < myElems.size(); }
+
+  /// Return the current object and step to the next one
+  virtual const SMDS_MeshElement* next() { return myElems[ myIndex++ ]; }
+};
+
+SMDS_ElemIteratorPtr SMDS_FaceOfNodes::elementsIterator( SMDSAbs_ElementType type ) const
 {
-  return boost::make_shared< SMDS_NodeArrayIterator >( &myNodes[0], &myNodes[0] + NbNodes() );
+  switch(type)
+  {
+  case SMDSAbs_Face:
+    return SMDS_MeshElement::elementsIterator(SMDSAbs_Face);
+  case SMDSAbs_Node:
+    return SMDS_ElemIteratorPtr(new SMDS_FaceOfNodes_MyIterator(myNodes,myNbNodes));
+  case SMDSAbs_Edge:
+    return SMDS_ElemIteratorPtr(new _MyEdgeIterator( this ));
+    break;
+  default:
+    return SMDS_ElemIteratorPtr
+      (new SMDS_IteratorOfElements
+       (this,type,SMDS_ElemIteratorPtr
+        (new SMDS_FaceOfNodes_MyIterator(myNodes,myNbNodes))));
+  }
+  return SMDS_ElemIteratorPtr();
 }
 
 SMDS_FaceOfNodes::SMDS_FaceOfNodes(const SMDS_MeshNode* node1,
                                    const SMDS_MeshNode* node2,
                                    const SMDS_MeshNode* node3)
 {
-  myNbNodes = 3;
-  myNodes[0]=node1;
-  myNodes[1]=node2;
-  myNodes[2]=node3;
-  myNodes[3]=0;
+  //MESSAGE("******************************************************* SMDS_FaceOfNodes");
+        myNbNodes = 3;
+        myNodes[0]=node1;
+        myNodes[1]=node2;
+        myNodes[2]=node3;
+        myNodes[3]=0;
 }
 
 SMDS_FaceOfNodes::SMDS_FaceOfNodes(const SMDS_MeshNode* node1,
@@ -103,11 +145,12 @@ SMDS_FaceOfNodes::SMDS_FaceOfNodes(const SMDS_MeshNode* node1,
                                    const SMDS_MeshNode* node3,
                                    const SMDS_MeshNode* node4)
 {
-  myNbNodes = 4;
-  myNodes[0]=node1;
-  myNodes[1]=node2;
-  myNodes[2]=node3;
-  myNodes[3]=node4;       
+  //MESSAGE("******************************************************* SMDS_FaceOfNodes");
+        myNbNodes = 4;
+        myNodes[0]=node1;
+        myNodes[1]=node2;
+        myNodes[2]=node3;
+        myNodes[3]=node4;       
 }
 bool SMDS_FaceOfNodes::ChangeNodes(const SMDS_MeshNode* nodes[],
                                    const int            nbNodes)
index 7e25a90f550a342bc97b25d445bef540e38a8883..fec0b09991dfa3ae56e5bc572f8473748ac525b0 100644 (file)
 
 #include "SMESH_SMDS.hxx"
 
-#include "SMDS_CellOfNodes.hxx"
+#include "SMDS_MeshFace.hxx"
+#include "SMDS_MeshNode.hxx"
+#include "SMDS_Iterator.hxx"
 
-class SMDS_EXPORT SMDS_FaceOfNodes: public SMDS_CellOfNodes
-{
- public:
-  void Print(std::ostream & OS) const;
-  SMDS_FaceOfNodes(const SMDS_MeshNode* node1,
-                   const SMDS_MeshNode* node2,
-                   const SMDS_MeshNode* node3);
-  SMDS_FaceOfNodes(const SMDS_MeshNode* node1,
-                   const SMDS_MeshNode* node2,
-                   const SMDS_MeshNode* node3,
-                   const SMDS_MeshNode* node4);
-  virtual bool ChangeNodes(const SMDS_MeshNode* nodes[],
-                           const int            nbNodes);
-  virtual int  NbEdges() const;
-  virtual int  NbFaces() const;
-  virtual int  NbNodes() const;
-
-  virtual int  NbCornerNodes() const { return NbNodes(); }
-  virtual int  GetNodeIndex( const SMDS_MeshNode* node ) const;
-
-  virtual bool IsPoly() const { return false; }
-  virtual bool IsQuadratic() const  { return false; }
+#include <iostream>
 
-  virtual SMDS_ElemIteratorPtr nodesIterator() const;
-  virtual SMDS_NodeIteratorPtr nodeIterator() const;
+class SMDS_EXPORT SMDS_FaceOfNodes:public SMDS_MeshFace
+{
+  public:
+        void Print(std::ostream & OS) const;
+        SMDS_FaceOfNodes(const SMDS_MeshNode* node1,
+                         const SMDS_MeshNode* node2,
+                         const SMDS_MeshNode* node3);
+        SMDS_FaceOfNodes(const SMDS_MeshNode* node1,
+                         const SMDS_MeshNode* node2,
+                         const SMDS_MeshNode* node3,
+                         const SMDS_MeshNode* node4);
+        bool ChangeNodes(const SMDS_MeshNode* nodes[],
+                         const int            nbNodes);
+        int NbEdges() const;
+        int NbFaces() const;
+        int NbNodes() const;
 
+  /*!
+   * \brief Return node by its index
+    * \param ind - node index
+    * \retval const SMDS_MeshNode* - the node
+   */
   virtual const SMDS_MeshNode* GetNode(const int ind) const;
 
-  virtual SMDSAbs_ElementType  GetType() const { return SMDSAbs_Face; }
   virtual SMDSAbs_EntityType   GetEntityType() const;
   virtual SMDSAbs_GeometryType GetGeomType() const;
 
- private:
-  const SMDS_MeshNode* myNodes[4];
-  int                  myNbNodes;
+  protected:
+        SMDS_ElemIteratorPtr
+                elementsIterator(SMDSAbs_ElementType type) const;
+
+  private:
+        const SMDS_MeshNode* myNodes[4];
+        int                  myNbNodes;
 
 };
 
index 3eb3c16dfc49800608771b3592d481caf928d288..ae12dc313d09ee35e62c0d024be632d7ed01315a 100644 (file)
 //  Module : SMESH
 //
 #include "SMDS_FacePosition.hxx"
-#include "SMDS_EdgePosition.hxx"
+
+#include "utilities.h"
+
+using namespace std;
 
 //=======================================================================
 //function : SMDS_FacePosition
-//purpose  :
+//purpose  : 
 //=======================================================================
 
 SMDS_FacePosition::SMDS_FacePosition(const double aUParam,
                                      const double aVParam)
+   : myUParameter(aUParam),myVParameter(aVParam)
 {
-  SetParameters( aUParam,aVParam );
+  //MESSAGE("******************************************************** SMDS_FacePosition");
 }
 
-//=======================================================================
-//function : GetTypeOfPosition
-//purpose  :
-//=======================================================================
-
+/**
+*/
 SMDS_TypeOfPosition SMDS_FacePosition::GetTypeOfPosition() const
 {
-  return SMDS_TOP_FACE;
+        return SMDS_TOP_FACE;
 }
 
 void SMDS_FacePosition::SetUParameter(double aUparam)
 {
-  myParameter[0] = aUparam;
+        myUParameter = aUparam;
 }
 
 //=======================================================================
 //function : SetVParameter
-//purpose  :
+//purpose  : 
 //=======================================================================
 
 void SMDS_FacePosition::SetVParameter(double aVparam)
 {
-  myParameter[1] = aVparam;
+        myVParameter = aVparam;
 }
 
 //=======================================================================
 //function : GetUParameter
-//purpose  :
+//purpose  : 
 //=======================================================================
 
-double SMDS_FacePosition::GetUParameter() const
+double SMDS_FacePosition::GetUParameter() const 
 {
-  return myParameter[0];
+        return myUParameter;
 }
 
 //=======================================================================
 //function : GetVParameter
-//purpose  :
+//purpose  : 
 //=======================================================================
 
-double SMDS_FacePosition::GetVParameter() const
+double SMDS_FacePosition::GetVParameter() const 
 {
-  return myParameter[1];
+        return myVParameter;
 }
 
 //=======================================================================
@@ -91,6 +92,6 @@ double SMDS_FacePosition::GetVParameter() const
 
 void SMDS_FacePosition::SetParameters(double aUparam, double aVparam)
 {
-  myParameter[0] = aUparam;
-  myParameter[1] = aVparam;
+  myUParameter = aUparam;
+  myVParameter = aVparam;
 }
index a36e300ade2127b7f659ed1897b36528b105dec4..45015887d5ad49aefa20ff071f9a780ae96aad7e 100644 (file)
 
 class SMDS_EXPORT SMDS_FacePosition:public SMDS_Position
 {
- public:
-  SMDS_FacePosition(double aUParam=0, double aVParam=0);
-  SMDS_TypeOfPosition GetTypeOfPosition() const;
-  virtual void SetUParameter(double aUparam);
-  virtual void SetVParameter(double aVparam);
-  virtual void SetParameters(double aUparam, double aVparam);
-  virtual double GetUParameter() const;
-  virtual double GetVParameter() const;
-  virtual const double* GetParameters() const { return &myParameter[0]; }
 
- private:
-  double myParameter[2];
+  public:
+        SMDS_FacePosition(double aUParam=0, double aVParam=0);
+        SMDS_TypeOfPosition GetTypeOfPosition() const;
+        void SetUParameter(double aUparam);
+        void SetVParameter(double aVparam);
+        void SetParameters(double aUparam, double aVparam);
+        double GetUParameter() const;
+        double GetVParameter() const;
+
+  private:
+        double myUParameter;
+        double myVParameter;
 };
 #endif
index 56132493035065dcd9c8851aaa03b6119d44585a..f20d7062ed8c26f18e516ee3819f81bc70474c3a 100644 (file)
 #ifndef _SMDS_Iterator_HeaderFile
 #define _SMDS_Iterator_HeaderFile
 
+#include "SMESH_SMDS.hxx"
+
 ///////////////////////////////////////////////////////////////////////////////
 ///Abstract class for iterators
 ///@author Jerome Robert
 ///////////////////////////////////////////////////////////////////////////////
 template<typename VALUE> class SMDS_Iterator
 {
-public:
-
-  typedef VALUE value_type;
-
-  /// Return true if and only if there are other object in this iterator
-  virtual bool more()=0;
-
-  /// Return the current object and step to the next one
-  virtual VALUE next()=0;
+  public:
+        /// Return true if and only if there are other object in this iterator
+          virtual bool more()=0;
+        
+        /// Return the current object and step to the next one
+          virtual VALUE next()=0;
         
-  /// Delete the current element and step to the next one
-  virtual void remove(){}
+        /// Delete the current element and step to the next one
+        virtual void remove(){}
         
-  /// Provide virtual destructor just for case if some derived iterator
-  /// must have a destructor
-  virtual ~SMDS_Iterator(){}
+        /// Provide virtual destructor just for case if some derived iterator
+        /// must have a destructor
+        virtual ~SMDS_Iterator(){}
 };
 
 #endif
diff --git a/src/SMDS/SMDS_IteratorOfElements.cxx b/src/SMDS/SMDS_IteratorOfElements.cxx
new file mode 100644 (file)
index 0000000..3d125fc
--- /dev/null
@@ -0,0 +1,109 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//
+#ifdef _MSC_VER
+#pragma warning(disable:4786)
+#endif
+
+#include "SMDS_IteratorOfElements.hxx"
+
+bool SMDS_IteratorOfElements::subMore()
+{
+        if((t2Iterator.get()==NULL)||(!t2Iterator->more()))
+        {
+                if(t1Iterator->more())
+                {
+                        t2Iterator=t1Iterator->next()->elementsIterator(myType);
+                        return subMore();
+                }
+                else return false;
+        }
+        else return true;
+}
+
+const SMDS_MeshElement * SMDS_IteratorOfElements::subNext()
+{
+        if((t2Iterator.get()==NULL)||(!t2Iterator->more()))
+                if(t1Iterator->more())
+                        t2Iterator=t1Iterator->next()->elementsIterator(myType);
+        return t2Iterator->next();
+}
+
+/////////////////////////////////////////////////////////////////////////////
+/// Create an iterator which look for elements of type type which are linked 
+/// to the element element. it is the iterator to get connectivity of element
+//////////////////////////////////////////////////////////////////////////////
+SMDS_IteratorOfElements::SMDS_IteratorOfElements(const SMDS_MeshElement *    element,
+                                                 SMDSAbs_ElementType         type,
+                                                 const SMDS_ElemIteratorPtr& it)
+  : t1Iterator(it),
+    t2Iterator(SMDS_ElemIteratorPtr((SMDS_ElemIterator*)NULL)),
+    myType(type), myElement(element),
+    myProxyElement(NULL)
+{
+  while(subMore())
+    alreadyReturnedElements.insert(subNext());
+  itAlreadyReturned= alreadyReturnedElements.begin();
+  switch(myElement->GetType())
+  {
+  case SMDSAbs_Node:
+  case SMDSAbs_Edge: myReverseIteration=true; break;
+  case SMDSAbs_Face: myReverseIteration=(type==SMDSAbs_Volume); break;
+  default: myReverseIteration=false;
+  }
+}
+
+bool SMDS_IteratorOfElements::more()
+{
+        if(myProxyElement==NULL)
+        {
+                while(itAlreadyReturned!=alreadyReturnedElements.end())
+                {
+                        myProxyElement=*itAlreadyReturned;
+                        itAlreadyReturned++;    
+
+                        if(myReverseIteration)
+                        {
+                                SMDS_ElemIteratorPtr it=
+                                        myProxyElement->elementsIterator(myElement->GetType());
+                                while(it->more())
+                                {                               
+                                        if(it->next()==myElement) return true;
+                                }
+                        }
+                        else return true;
+                }
+                myProxyElement=NULL;
+                return false;
+        }
+        else return true;
+}
+
+const SMDS_MeshElement * SMDS_IteratorOfElements::next()
+{
+        more();
+        const SMDS_MeshElement *e=myProxyElement;
+        myProxyElement=NULL;
+        return e;
+}
diff --git a/src/SMDS/SMDS_IteratorOfElements.hxx b/src/SMDS/SMDS_IteratorOfElements.hxx
new file mode 100644 (file)
index 0000000..f2d73d8
--- /dev/null
@@ -0,0 +1,57 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//
+#include "SMESH_SMDS.hxx"
+
+#include "SMDS_Iterator.hxx"
+#include "SMDS_MeshElement.hxx"
+#include <set>
+
+
+class SMDS_EXPORT SMDS_IteratorOfElements:public SMDS_ElemIterator
+{
+  public:
+/////////////////////////////////////////////////////////////////////////////
+/// Create an iterator which look for elements of type type which are linked 
+/// to the element element. it is the iterator to get connectivity of element
+//////////////////////////////////////////////////////////////////////////////
+        SMDS_IteratorOfElements(const SMDS_MeshElement * element,
+                                SMDSAbs_ElementType type,
+                                const SMDS_ElemIteratorPtr& it);
+        bool more();
+        const SMDS_MeshElement * next();
+
+  private:
+        SMDS_ElemIteratorPtr t1Iterator;
+        SMDS_ElemIteratorPtr t2Iterator;
+        SMDSAbs_ElementType myType;     
+        const SMDS_MeshElement * myElement;             
+        const SMDS_MeshElement * myProxyElement;
+        bool myReverseIteration;
+
+        std::set<const SMDS_MeshElement*> alreadyReturnedElements;
+        std::set<const SMDS_MeshElement*>::iterator itAlreadyReturned;  
+        bool subMore();
+        const SMDS_MeshElement * subNext();
+};
index 1d58368d426263a16f74037bddc22475403586ec..8b87a9a44f406d90ce366492a04c82e63f1d143a 100644 (file)
 #endif
 
 #include "SMDS_LinearEdge.hxx"
+#include "SMDS_IteratorOfElements.hxx"
 #include "SMDS_MeshNode.hxx"
-#include "SMDS_SetIterator.hxx"
+#include "utilities.h"
 
-#include <boost/make_shared.hpp>
+using namespace std;
 
 //=======================================================================
 //function : SMDS_LinearEdge
 SMDS_LinearEdge::SMDS_LinearEdge(const SMDS_MeshNode * node1,
                                  const SMDS_MeshNode * node2)
 {
+  //MESSAGE("SMDS_LinearEdge " << GetID());
   myNodes[0] = node1;
   myNodes[1] = node2;
 }
 
+//=======================================================================
+//function : Print
+//purpose  : 
+//=======================================================================
+
+void SMDS_LinearEdge::Print(ostream & OS) const
+{
+  OS << "edge <" << GetID() << "> : (" << myNodes[0] << " , " << myNodes[1]
+      << ") " << endl;
+}
+
 int SMDS_LinearEdge::NbNodes() const
 {
   return 2;
@@ -55,29 +68,75 @@ int SMDS_LinearEdge::NbEdges() const
   return 1;
 }
 
-int SMDS_LinearEdge::NbFaces() const
+class SMDS_LinearEdge_MyNodeIterator: public SMDS_ElemIterator
 {
-  return 0;
-}
+  const SMDS_MeshNode * const * myNodes;
+  int myIndex;
+public:
+  SMDS_LinearEdge_MyNodeIterator(const SMDS_MeshNode * const * nodes) :
+    myNodes(nodes), myIndex(0)
+  {
+  }
 
-int SMDS_LinearEdge::GetNodeIndex( const SMDS_MeshNode* node ) const
-{
-  if ( node == myNodes[0] ) return 0;
-  if ( node == myNodes[1] ) return 1;
-  return -1;
-}
+  bool more()
+  {
+    return myIndex < 2;
+  }
 
-SMDS_ElemIteratorPtr SMDS_LinearEdge::nodesIterator() const
+  const SMDS_MeshElement* next()
+  {
+    myIndex++;
+    return myNodes[myIndex - 1];
+  }
+};
+
+SMDS_ElemIteratorPtr SMDS_LinearEdge::elementsIterator(SMDSAbs_ElementType type) const
 {
-  return boost::make_shared< SMDS_NodeArrayElemIterator >( &myNodes[0], &myNodes[0] + NbNodes() );
+  switch (type)
+  {
+    case SMDSAbs_Edge:
+      return SMDS_MeshElement::elementsIterator(SMDSAbs_Edge);
+    case SMDSAbs_Node:
+      return SMDS_ElemIteratorPtr(new SMDS_LinearEdge_MyNodeIterator(myNodes));
+    default:
+      return SMDS_ElemIteratorPtr
+        (new SMDS_IteratorOfElements(this,
+                                     type,
+                                     SMDS_ElemIteratorPtr
+                                     (new SMDS_LinearEdge_MyNodeIterator(myNodes))));
+  }
 }
 
-SMDS_NodeIteratorPtr SMDS_LinearEdge::nodeIterator() const
+bool operator<(const SMDS_LinearEdge & e1, const SMDS_LinearEdge & e2)
 {
-  return boost::make_shared< SMDS_NodeArrayIterator >( &myNodes[0], &myNodes[0] + NbNodes() );
+  int id11 = e1.myNodes[0]->getVtkId();
+  int id21 = e2.myNodes[0]->getVtkId();
+  int id12 = e1.myNodes[1]->getVtkId();
+  int id22 = e2.myNodes[1]->getVtkId();
+  int tmp;
+
+  if (id11 >= id12)
+    {
+      tmp = id11;
+      id11 = id12;
+      id12 = tmp;
+    }
+  if (id21 >= id22)
+    {
+      tmp = id21;
+      id21 = id22;
+      id22 = tmp;
+    }
+
+  if (id11 < id21)
+    return true;
+  else if (id11 == id21)
+    return (id21 < id22);
+  else
+    return false;
 }
 
-/*
+/*!
  * \brief Return node by its index
  * \param ind - node index
  * \retval const SMDS_MeshNode* - the node
@@ -92,9 +151,10 @@ const SMDS_MeshNode* SMDS_LinearEdge::GetNode(const int ind) const
 //purpose  : 
 //=======================================================================
 
-bool SMDS_LinearEdge::ChangeNodes(const SMDS_MeshNode* nodes[], const int nbNodes)
+bool SMDS_LinearEdge::ChangeNodes(const SMDS_MeshNode * node1,
+                                  const SMDS_MeshNode * node2)
 {
-  myNodes[0] = nodes[0];
-  myNodes[1] = nodes[1];
-  return nbNodes == 2;
+  myNodes[0] = node1;
+  myNodes[1] = node2;
+  return true;
 }
index 75d984e3fd0b61f3de1ef255ba88caaa68f9e0ef..1ac80ee8a52b8c8f129df2af5a2196f152214ebf 100644 (file)
 
 #include "SMESH_SMDS.hxx"
 
-#include "SMDS_CellOfNodes.hxx"
+#include "SMDS_MeshEdge.hxx"
+#include <iostream>
 
-class SMDS_EXPORT SMDS_LinearEdge: public SMDS_CellOfNodes
+class SMDS_EXPORT SMDS_LinearEdge: public SMDS_MeshEdge
 {
+
 public:
   SMDS_LinearEdge(const SMDS_MeshNode * node1, const SMDS_MeshNode * node2);
+  bool ChangeNodes(const SMDS_MeshNode * node1, const SMDS_MeshNode * node2);
+  void Print(std::ostream & OS) const;
 
-  virtual SMDSAbs_ElementType  GetType()       const { return SMDSAbs_Edge; }
-  virtual SMDSAbs_GeometryType GetGeomType()   const { return SMDSGeom_EDGE; }
-  virtual SMDSAbs_EntityType   GetEntityType() const { return SMDSEntity_Edge; }
-  virtual bool ChangeNodes(const SMDS_MeshNode* nodes[], const int nbNodes);
-  virtual int  NbNodes() const;
-  virtual int  NbEdges() const;
-  virtual int  NbFaces() const;
-
-  virtual int  NbCornerNodes() const { return NbNodes(); }
-  virtual int  GetNodeIndex( const SMDS_MeshNode* node ) const;
-
-  virtual bool IsPoly() const { return false; }
-  virtual bool IsQuadratic() const  { return false; }
-
-  virtual SMDS_ElemIteratorPtr nodesIterator() const;
-  virtual SMDS_NodeIteratorPtr nodeIterator() const;
+  virtual SMDSAbs_EntityType GetEntityType() const
+  {
+    return SMDSEntity_Edge;
+  }
+  virtual bool ChangeNodes(const SMDS_MeshNode* nodes[], const int nbNodes)
+  {
+    return false;
+  }
+  int NbNodes() const;
+  int NbEdges() const;
+  friend bool operator<(const SMDS_LinearEdge& e1, const SMDS_LinearEdge& e2);
 
+  /*!
+   * \brief Return node by its index
+   * \param ind - node index
+   * \retval const SMDS_MeshNode* - the node
+   */
   virtual const SMDS_MeshNode* GetNode(const int ind) const;
 
 protected:
-  const SMDS_MeshNode* myNodes[2];
+  SMDS_ElemIteratorPtr
+  elementsIterator(SMDSAbs_ElementType type) const;
+
+protected:
+  const SMDS_MeshNode* myNodes[3];
 
 };
 #endif
index 1d7ba140b7005d9644b21af7cd56d99a6eac3bb0..40caa2c8854d51f04cbb99b91ba3f5943a34f8cd 100644 (file)
 #pragma warning(disable:4786)
 #endif
 
+#include "SMDS_FaceOfEdges.hxx"
+#include "SMDS_FaceOfNodes.hxx"
 #include "SMDS_Mesh.hxx"
-
-#include "SMDS_ElementFactory.hxx"
-#include "SMDS_ElementHolder.hxx"
+#include "SMDS_PolygonalFaceOfNodes.hxx"
+#include "SMDS_PolyhedralVolumeOfNodes.hxx"
+#include "SMDS_QuadraticEdge.hxx"
+#include "SMDS_QuadraticFaceOfNodes.hxx"
+#include "SMDS_QuadraticVolumeOfNodes.hxx"
 #include "SMDS_SetIterator.hxx"
 #include "SMDS_SpacePosition.hxx"
 #include "SMDS_UnstructuredGrid.hxx"
+#include "SMDS_VolumeOfFaces.hxx"
+#include "SMDS_VolumeOfNodes.hxx"
 
-#include <utilities.h>
+#include "utilities.h"
 
 #include <vtkUnstructuredGrid.h>
-//#include <vtkUnstructuredGridWriter.h>
-#include <vtkCell.h>
+#include <vtkUnstructuredGridWriter.h>
 #include <vtkUnsignedCharArray.h>
+#include <vtkCell.h>
 #include <vtkCellLinks.h>
 #include <vtkIdList.h>
 
 #include <algorithm>
+#include <map>
 #include <iostream>
 #include <fstream>
-
-#include <boost/make_shared.hpp>
+#include <iterator>
+using namespace std;
 
 #if !defined WIN32 && !defined __APPLE__
 #include <sys/sysinfo.h>
 // number of added entities to check memory after
 #define CHECKMEMORY_INTERVAL 100000
 
-#define MYASSERT(val) if (!(val)) throw SALOME_Exception(LOCALIZED("assertion not verified"));
-
+vector<SMDS_Mesh*> SMDS_Mesh::_meshList = vector<SMDS_Mesh*>();
 int SMDS_Mesh::chunkSize = 1024;
 
+
 //================================================================================
 /*!
  * \brief Raise an exception if free memory (ram+swap) too low
@@ -70,7 +77,6 @@ int SMDS_Mesh::chunkSize = 1024;
 
 int SMDS_Mesh::CheckMemory(const bool doNotRaise) throw (std::bad_alloc)
 {
-  return -1;
 #if !defined WIN32 && !defined __APPLE__
   struct sysinfo si;
   int err = sysinfo( &si );
@@ -81,16 +87,13 @@ int SMDS_Mesh::CheckMemory(const bool doNotRaise) throw (std::bad_alloc)
 
   static int limit = -1;
   if ( limit < 0 ) {
-    if ( si.totalswap == 0 )
-    {
-      int status = system("SMDS_MemoryLimit"); // it returns lower limit of free RAM
-      if (status >= 0 ) {
-        limit = WEXITSTATUS(status);
-      }
-      else {
-        double factor = ( si.totalswap == 0 ) ? 0.1 : 0.2;
-        limit = int(( factor * si.totalram * si.mem_unit ) / Mbyte );
-      }
+    int status = system("SMDS_MemoryLimit"); // it returns lower limit of free RAM
+    if (status >= 0 ) {
+      limit = WEXITSTATUS(status);
+    }
+    else {
+      double factor = ( si.totalswap == 0 ) ? 0.1 : 0.2;
+      limit = int(( factor * si.totalram * si.mem_unit ) / Mbyte );
     }
     if ( limit < 20 )
       limit = 20;
@@ -103,6 +106,7 @@ int SMDS_Mesh::CheckMemory(const bool doNotRaise) throw (std::bad_alloc)
   int freeMb =
     ( si.freeram  * si.mem_unit ) / Mbyte +
     ( si.freeswap * si.mem_unit ) / Mbyte;
+  //cout << "freeMb = " << freeMb << " limit = " << limit << endl;
 
   if ( freeMb > limit )
     return freeMb - limit;
@@ -121,12 +125,29 @@ int SMDS_Mesh::CheckMemory(const bool doNotRaise) throw (std::bad_alloc)
 /// Create a new mesh object
 ///////////////////////////////////////////////////////////////////////////////
 SMDS_Mesh::SMDS_Mesh():
-  myNodeFactory( new SMDS_NodeFactory( this )),
-  myCellFactory( new SMDS_ElementFactory( this )),
+  myNodePool(0), myVolumePool(0), myFacePool(0), myEdgePool(0), myBallPool(0),
   myParent(NULL),
+  myNodeIDFactory(new SMDS_MeshNodeIDFactory()),
+  myElementIDFactory(new SMDS_MeshElementIDFactory()),
   myModified(false), myModifTime(0), myCompactTime(0),
+  myHasConstructionEdges(false), myHasConstructionFaces(false),
+  myHasInverseElements(true),
   xmin(0), xmax(0), ymin(0), ymax(0), zmin(0), zmax(0)
 {
+  myMeshId = _meshList.size();         // --- index of the mesh to push back in the vector
+  myNodeIDFactory->SetMesh(this);
+  myElementIDFactory->SetMesh(this);
+  _meshList.push_back(this);
+  myNodePool = new ObjectPool<SMDS_MeshNode>(SMDS_Mesh::chunkSize);
+  myEdgePool = new ObjectPool<SMDS_VtkEdge>(SMDS_Mesh::chunkSize);
+  myFacePool = new ObjectPool<SMDS_VtkFace>(SMDS_Mesh::chunkSize);
+  myVolumePool = new ObjectPool<SMDS_VtkVolume>(SMDS_Mesh::chunkSize);
+  myBallPool = new ObjectPool<SMDS_BallElement>(SMDS_Mesh::chunkSize);
+
+  myNodes.clear();
+  myCells.clear();
+  //myCellIdSmdsToVtk.clear();
+  myCellIdVtkToSmds.clear();
   myGrid = SMDS_UnstructuredGrid::New();
   myGrid->setSMDS_mesh(this);
   myGrid->Initialize();
@@ -135,13 +156,22 @@ SMDS_Mesh::SMDS_Mesh():
   // bug "21125: EDF 1233 SMESH: Degrardation of precision in a test case for quadratic conversion"
   // Use double type for storing coordinates of nodes instead of float.
   points->SetDataType(VTK_DOUBLE);
-  points->SetNumberOfPoints( 0 );
+  points->SetNumberOfPoints(0 /*SMDS_Mesh::chunkSize*/);
   myGrid->SetPoints( points );
   points->Delete();
+  //myGrid->BuildLinks();
   this->Modified();
 
   // initialize static maps in SMDS_MeshCell, to be thread-safe
-  SMDS_MeshCell::InitStaticMembers();
+  if ( myMeshId == 0 )
+  {
+    SMDS_MeshCell::toVtkType( SMDSEntity_Node );
+    SMDS_MeshCell::toVtkOrder( SMDSEntity_Node );
+    SMDS_MeshCell::reverseSmdsOrder( SMDSEntity_Node );
+    SMDS_MeshCell::interlacedSmdsOrder( SMDSEntity_Node );
+    SMDS_MeshCell::toSmdsType( VTK_VERTEX );
+    SMDS_MeshCell::fromVtkOrder( SMDSEntity_Node );
+  }
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -150,9 +180,15 @@ SMDS_Mesh::SMDS_Mesh():
 /// (2003-09-08) of SMESH
 ///////////////////////////////////////////////////////////////////////////////
 SMDS_Mesh::SMDS_Mesh(SMDS_Mesh * parent):
-  myNodeFactory( new SMDS_NodeFactory( this )),
-  myCellFactory( new SMDS_ElementFactory( this )),
-  myParent(parent)
+  myNodePool(parent->myNodePool),
+  myVolumePool(parent->myVolumePool),
+  myFacePool(parent->myFacePool),
+  myEdgePool(parent->myEdgePool),
+  myBallPool(parent->myBallPool),
+  myParent(parent), myNodeIDFactory(parent->myNodeIDFactory),
+  myElementIDFactory(parent->myElementIDFactory),
+  myHasConstructionEdges(false), myHasConstructionFaces(false),
+  myHasInverseElements(true)
 {
 }
 
@@ -175,7 +211,7 @@ SMDS_Mesh *SMDS_Mesh::AddSubMesh()
 
 SMDS_MeshNode * SMDS_Mesh::AddNode(double x, double y, double z)
 {
-  return SMDS_Mesh::AddNodeWithID( x,y,z, myNodeFactory->GetFreeID() );
+  return SMDS_Mesh::AddNodeWithID(x,y,z,myNodeIDFactory->GetFreeID());
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -183,18 +219,33 @@ SMDS_MeshNode * SMDS_Mesh::AddNode(double x, double y, double z)
 ///@param ID : The ID of the MeshNode to create
 ///@return : The created node or NULL if a node with this ID already exists
 ///////////////////////////////////////////////////////////////////////////////
-SMDS_MeshNode * SMDS_Mesh::AddNodeWithID( double x, double y, double z, int ID )
+SMDS_MeshNode * SMDS_Mesh::AddNodeWithID(double x, double y, double z, int ID)
 {
   // find the MeshNode corresponding to ID
-  SMDS_MeshNode *node = myNodeFactory->NewNode( ID );
-  if ( node )
-  {
-    node->init( x, y, z );
+  const SMDS_MeshElement *node = myNodeIDFactory->MeshElement(ID);
+  if(!node){
+    if (ID < 1)
+      {
+        MESSAGE("=============>  Bad Node Id: " << ID);
+        ID = myNodeIDFactory->GetFreeID();
+      }
+    myNodeIDFactory->adjustMaxId(ID);
+    SMDS_MeshNode * node = myNodePool->getNew();
+    node->init(ID, myMeshId, 0, x, y, z);
+
+    if (ID >= (int)myNodes.size())
+    {
+        myNodes.resize(ID+SMDS_Mesh::chunkSize, 0);
+//         MESSAGE(" ------------------ myNodes resize " << ID << " --> " << ID+SMDS_Mesh::chunkSize);
+    }
+    myNodes[ID] = node;
+    myNodeIDFactory->BindID(ID,node);
     myInfo.myNbNodes++;
     myModified = true;
     this->adjustBoundingBox(x, y, z);
-  }
-  return node;
+    return node;
+  }else
+    return NULL;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -203,7 +254,7 @@ SMDS_MeshNode * SMDS_Mesh::AddNodeWithID( double x, double y, double z, int ID )
 ///////////////////////////////////////////////////////////////////////////////
 SMDS_Mesh0DElement* SMDS_Mesh::Add0DElementWithID(int idnode, int ID)
 {
-  const SMDS_MeshNode * node = myNodeFactory->FindNode(idnode);
+  SMDS_MeshNode * node = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode);
   if (!node) return NULL;
   return SMDS_Mesh::Add0DElementWithID(node, ID);
 }
@@ -214,7 +265,7 @@ SMDS_Mesh0DElement* SMDS_Mesh::Add0DElementWithID(int idnode, int ID)
 ///////////////////////////////////////////////////////////////////////////////
 SMDS_Mesh0DElement* SMDS_Mesh::Add0DElement(const SMDS_MeshNode * node)
 {
-  return SMDS_Mesh::Add0DElementWithID( node, myCellFactory->GetFreeID() );
+  return SMDS_Mesh::Add0DElementWithID(node, myElementIDFactory->GetFreeID());
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -229,26 +280,30 @@ SMDS_Mesh0DElement* SMDS_Mesh::Add0DElementWithID(const SMDS_MeshNode * n, int I
   if (!n) return 0;
 
   if (Nb0DElements() % CHECKMEMORY_INTERVAL == 0) CheckMemory();
-
-  if ( SMDS_MeshCell * cell = myCellFactory->NewCell( ID ))
-  {
-    cell->init( SMDSEntity_0D, /*nbNodes=*/1, n );
+  //MESSAGE("Add0DElementWithID" << ID)
+  SMDS_Mesh0DElement * el0d = new SMDS_Mesh0DElement(n);
+  if (myElementIDFactory->BindID(ID, el0d)) {
+    //SMDS_MeshNode *node = const_cast<SMDS_MeshNode*>(n);
+    //node->AddInverseElement(el0d);// --- fait avec BindID
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = el0d;
     myInfo.myNb0DElements++;
-    return static_cast< SMDS_Mesh0DElement*> ( cell );
+    return el0d;
   }
 
-  return 0;
+  delete el0d;
+  return NULL;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
 /// create a Ball and add it to the current Mesh
 /// @return : The created Ball
 ///////////////////////////////////////////////////////////////////////////////
-SMDS_BallElement* SMDS_Mesh::AddBallWithID( int idnode, double diameter, int ID )
+SMDS_BallElement* SMDS_Mesh::AddBallWithID(int idnode, double diameter, int ID)
 {
-  const SMDS_MeshNode * node = myNodeFactory->FindNode( idnode );
+  SMDS_MeshNode * node = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode);
   if (!node) return NULL;
-  return SMDS_Mesh::AddBallWithID( node, diameter, ID );
+  return SMDS_Mesh::AddBallWithID(node, diameter, ID);
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -257,7 +312,7 @@ SMDS_BallElement* SMDS_Mesh::AddBallWithID( int idnode, double diameter, int ID
 ///////////////////////////////////////////////////////////////////////////////
 SMDS_BallElement* SMDS_Mesh::AddBall(const SMDS_MeshNode * node, double diameter)
 {
-  return SMDS_Mesh::AddBallWithID(node, diameter, myCellFactory->GetFreeID());
+  return SMDS_Mesh::AddBallWithID(node, diameter, myElementIDFactory->GetFreeID());
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -274,12 +329,17 @@ SMDS_BallElement* SMDS_Mesh::AddBallWithID(const SMDS_MeshNode * n, double diame
 
   if (NbBalls() % CHECKMEMORY_INTERVAL == 0) CheckMemory();
 
-  SMDS_BallElement* ball = static_cast< SMDS_BallElement*>( myCellFactory->NewElement( ID ));
-  if ( ball )
+  SMDS_BallElement *ball = myBallPool->getNew();
+  ball->init(n->getVtkId(), diameter, this);
+  if (!this->registerElement(ID,ball))
   {
-    ball->init( n, diameter );
-    myInfo.myNbBalls++;
+    this->myGrid->GetCellTypesArray()->SetValue(ball->getVtkId(), VTK_EMPTY_CELL);
+    myBallPool->destroy(ball);
+    return 0;
   }
+  adjustmyCellsCapacity(ID);
+  myCells[ID] = ball;
+  myInfo.myNbBalls++;
   return ball;
 }
 
@@ -290,8 +350,8 @@ SMDS_BallElement* SMDS_Mesh::AddBallWithID(const SMDS_MeshNode * n, double diame
 
 SMDS_MeshEdge* SMDS_Mesh::AddEdgeWithID(int idnode1, int idnode2, int ID)
 {
-  const SMDS_MeshNode * node1 = myNodeFactory->FindNode(idnode1);
-  const SMDS_MeshNode * node2 = myNodeFactory->FindNode(idnode2);
+  SMDS_MeshNode * node1 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode1);
+  SMDS_MeshNode * node2 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode2);
   if(!node1 || !node2) return NULL;
   return SMDS_Mesh::AddEdgeWithID(node1, node2, ID);
 }
@@ -304,7 +364,7 @@ SMDS_MeshEdge* SMDS_Mesh::AddEdgeWithID(int idnode1, int idnode2, int ID)
 SMDS_MeshEdge* SMDS_Mesh::AddEdge(const SMDS_MeshNode * node1,
                                   const SMDS_MeshNode * node2)
 {
-  return SMDS_Mesh::AddEdgeWithID(node1, node2, myCellFactory->GetFreeID());
+  return SMDS_Mesh::AddEdgeWithID(node1, node2, myElementIDFactory->GetFreeID());
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -318,17 +378,36 @@ SMDS_MeshEdge* SMDS_Mesh::AddEdge(const SMDS_MeshNode * node1,
 
 SMDS_MeshEdge* SMDS_Mesh::AddEdgeWithID(const SMDS_MeshNode * n1,
                                         const SMDS_MeshNode * n2,
-                                        int                   ID)
+                                        int ID)
 {
   if ( !n1 || !n2 ) return 0;
+  SMDS_MeshEdge * edge = 0;
 
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
-  {
-    cell->init( SMDSEntity_Edge, /*nbNodes=*/2, n1, n2 );
-    myInfo.myNbEdges++;
-    return static_cast<SMDS_MeshEdge*>( cell );
-  }
-  return 0;
+  // --- retrieve nodes ID
+  vector<vtkIdType> nodeIds;
+  nodeIds.clear();
+  nodeIds.push_back(n1->getVtkId());
+  nodeIds.push_back(n2->getVtkId());
+
+  SMDS_VtkEdge *edgevtk = myEdgePool->getNew();
+  edgevtk->init(nodeIds, this);
+  if (!this->registerElement(ID,edgevtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(edgevtk->getVtkId(), VTK_EMPTY_CELL);
+      myEdgePool->destroy(edgevtk);
+      return 0;
+    }
+  edge = edgevtk;
+  adjustmyCellsCapacity(ID);
+  myCells[ID] = edge;
+  myInfo.myNbEdges++;
+
+//  if (edge && !registerElement(ID, edge))
+//  {
+//    RemoveElement(edge, false);
+//    edge = NULL;
+//  }
+  return edge;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -340,7 +419,7 @@ SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshNode * n1,
                                   const SMDS_MeshNode * n2,
                                   const SMDS_MeshNode * n3)
 {
-  return SMDS_Mesh::AddFaceWithID(n1,n2,n3, myCellFactory->GetFreeID());
+  return SMDS_Mesh::AddFaceWithID(n1,n2,n3, myElementIDFactory->GetFreeID());
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -349,9 +428,9 @@ SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshNode * n1,
 
 SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(int idnode1, int idnode2, int idnode3, int ID)
 {
-  const SMDS_MeshNode * node1 = myNodeFactory->FindNode(idnode1);
-  const SMDS_MeshNode * node2 = myNodeFactory->FindNode(idnode2);
-  const SMDS_MeshNode * node3 = myNodeFactory->FindNode(idnode3);
+  SMDS_MeshNode * node1 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode1);
+  SMDS_MeshNode * node2 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode2);
+  SMDS_MeshNode * node3 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode3);
   if(!node1 || !node2 || !node3) return NULL;
   return SMDS_Mesh::AddFaceWithID(node1, node2, node3, ID);
 }
@@ -365,16 +444,14 @@ SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(const SMDS_MeshNode * n1,
                                         const SMDS_MeshNode * n3,
                                         int ID)
 {
-  if ( !n1 || !n2 || !n3 ) return 0;
-  if ( NbFaces() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
+  //MESSAGE("AddFaceWithID " << ID)
+  SMDS_MeshFace * face=createTriangle(n1, n2, n3, ID);
 
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
-  {
-    cell->init( SMDSEntity_Triangle, /*nbNodes=*/3, n1, n2, n3 );
-    myInfo.myNbTriangles++;
-    return static_cast<SMDS_MeshFace*>( cell );
-  }
-  return 0;
+//  if (face && !registerElement(ID, face)) {
+//    RemoveElement(face, false);
+//    face = NULL;
+//  }
+  return face;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -387,7 +464,7 @@ SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshNode * n1,
                                   const SMDS_MeshNode * n3,
                                   const SMDS_MeshNode * n4)
 {
-  return SMDS_Mesh::AddFaceWithID(n1,n2,n3, n4, myCellFactory->GetFreeID());
+  return SMDS_Mesh::AddFaceWithID(n1,n2,n3, n4, myElementIDFactory->GetFreeID());
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -400,12 +477,12 @@ SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(int idnode1,
                                         int idnode4,
                                         int ID)
 {
-  const SMDS_MeshNode *node1, *node2, *node3, *node4;
-  node1 = myNodeFactory->FindNode(idnode1);
-  node2 = myNodeFactory->FindNode(idnode2);
-  node3 = myNodeFactory->FindNode(idnode3);
-  node4 = myNodeFactory->FindNode(idnode4);
-  if ( !node1 || !node2 || !node3 || !node4 ) return NULL;
+  SMDS_MeshNode *node1, *node2, *node3, *node4;
+  node1 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode1);
+  node2 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode2);
+  node3 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode3);
+  node4 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode4);
+  if(!node1 || !node2 || !node3 || !node4) return NULL;
   return SMDS_Mesh::AddFaceWithID(node1, node2, node3, node4, ID);
 }
 
@@ -419,16 +496,100 @@ SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(const SMDS_MeshNode * n1,
                                         const SMDS_MeshNode * n4,
                                         int ID)
 {
-  if ( !n1 || !n2 || !n3 || !n4 ) return 0;
+  //MESSAGE("AddFaceWithID " << ID);
+  SMDS_MeshFace * face=createQuadrangle(n1, n2, n3, n4, ID);
+
+//  if (face && !registerElement(ID, face)) {
+//    RemoveElement(face, false);
+//    face = NULL;
+//  }
+  return face;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+/// Add a triangle defined by its edges. An ID is automatically assigned to the
+/// Created face
+///////////////////////////////////////////////////////////////////////////////
+
+SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshEdge * e1,
+                                  const SMDS_MeshEdge * e2,
+                                  const SMDS_MeshEdge * e3)
+{
+  if (!hasConstructionEdges())
+    return NULL;
+     //MESSAGE("AddFaceWithID");
+ return AddFaceWithID(e1,e2,e3, myElementIDFactory->GetFreeID());
+}
+
+///////////////////////////////////////////////////////////////////////////////
+/// Add a triangle defined by its edges
+///////////////////////////////////////////////////////////////////////////////
+
+SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(const SMDS_MeshEdge * e1,
+                                        const SMDS_MeshEdge * e2,
+                                        const SMDS_MeshEdge * e3,
+                                        int ID)
+{
+  if (!hasConstructionEdges())
+    return NULL;
+  if ( !e1 || !e2 || !e3 ) return 0;
+
+  if ( NbFaces() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
+
+  SMDS_MeshFace * face = new SMDS_FaceOfEdges(e1,e2,e3);
+  adjustmyCellsCapacity(ID);
+  myCells[ID] = face;
+  myInfo.myNbTriangles++;
+
+  if (!registerElement(ID, face)) {
+    registerElement(myElementIDFactory->GetFreeID(), face);
+    //RemoveElement(face, false);
+    //face = NULL;
+  }
+  return face;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+/// Add a quadrangle defined by its edges. An ID is automatically assigned to the
+/// Created face
+///////////////////////////////////////////////////////////////////////////////
+
+SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshEdge * e1,
+                                  const SMDS_MeshEdge * e2,
+                                  const SMDS_MeshEdge * e3,
+                                  const SMDS_MeshEdge * e4)
+{
+  if (!hasConstructionEdges())
+    return NULL;
+ return AddFaceWithID(e1,e2,e3,e4, myElementIDFactory->GetFreeID());
+}
+
+///////////////////////////////////////////////////////////////////////////////
+/// Add a quadrangle defined by its edges
+///////////////////////////////////////////////////////////////////////////////
+
+SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(const SMDS_MeshEdge * e1,
+                                        const SMDS_MeshEdge * e2,
+                                        const SMDS_MeshEdge * e3,
+                                        const SMDS_MeshEdge * e4,
+                                        int ID)
+{
+  if (!hasConstructionEdges())
+    return NULL;
+  if ( !e1 || !e2 || !e3 || !e4 ) return 0;
   if ( NbFaces() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
+  SMDS_MeshFace * face = new SMDS_FaceOfEdges(e1,e2,e3,e4);
+  adjustmyCellsCapacity(ID);
+  myCells[ID] = face;
+  myInfo.myNbQuadrangles++;
 
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
+  if (!registerElement(ID, face))
   {
-    cell->init( SMDSEntity_Quadrangle, /*nbNodes=*/4, n1, n2, n3, n4 );
-    myInfo.myNbQuadrangles++;
-    return static_cast<SMDS_MeshFace*>( cell );
+    registerElement(myElementIDFactory->GetFreeID(), face);
+    //RemoveElement(face, false);
+    //face = NULL;
   }
-  return 0;
+  return face;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -441,7 +602,10 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
                                       const SMDS_MeshNode * n3,
                                       const SMDS_MeshNode * n4)
 {
-  return SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, myCellFactory->GetFreeID() );
+  int ID = myElementIDFactory->GetFreeID();
+  SMDS_MeshVolume * v = SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, ID);
+  if(v==NULL) myElementIDFactory->ReleaseID(ID);
+  return v;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -457,11 +621,11 @@ SMDS_MeshVolume * SMDS_Mesh::AddVolumeWithID(int idnode1,
                                              int idnode4,
                                              int ID)
 {
-  const SMDS_MeshNode *node1, *node2, *node3, *node4;
-  node1 = myNodeFactory->FindNode(idnode1);
-  node2 = myNodeFactory->FindNode(idnode2);
-  node3 = myNodeFactory->FindNode(idnode3);
-  node4 = myNodeFactory->FindNode(idnode4);
+  SMDS_MeshNode *node1, *node2, *node3, *node4;
+  node1 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode1);
+  node2 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode2);
+  node3 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode3);
+  node4 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode4);
   if(!node1 || !node2 || !node3 || !node4) return NULL;
   return SMDS_Mesh::AddVolumeWithID(node1, node2, node3, node4, ID);
 }
@@ -478,16 +642,49 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
                                             const SMDS_MeshNode * n4,
                                             int ID)
 {
-  if ( !n1 || !n2 || !n3 || !n4 ) return 0;
+  SMDS_MeshVolume* volume = 0;
+  if ( !n1 || !n2 || !n3 || !n4) return volume;
   if ( NbVolumes() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
-  {
-    cell->init( SMDSEntity_Tetra, /*nbNodes=*/4, n1, n2, n3, n4 );
+  if(hasConstructionFaces()) {
+    SMDS_MeshFace * f1=FindFaceOrCreate(n1,n2,n3);
+    SMDS_MeshFace * f2=FindFaceOrCreate(n1,n2,n4);
+    SMDS_MeshFace * f3=FindFaceOrCreate(n1,n3,n4);
+    SMDS_MeshFace * f4=FindFaceOrCreate(n2,n3,n4);
+    volume=new SMDS_VolumeOfFaces(f1,f2,f3,f4);
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = volume;
     myInfo.myNbTetras++;
-    return static_cast<SMDS_MeshVolume*>( cell );
   }
-  return 0;
+  else if(hasConstructionEdges()) {
+    return NULL;
+  }
+  else {
+    // --- retrieve nodes ID
+    myNodeIds.resize(4);
+    myNodeIds[0] = n1->getVtkId();
+    myNodeIds[1] = n3->getVtkId(); // order SMDS-->VTK
+    myNodeIds[2] = n2->getVtkId();
+    myNodeIds[3] = n4->getVtkId();
+
+    SMDS_VtkVolume *volvtk = myVolumePool->getNew();
+    volvtk->init(myNodeIds, this);
+    if (!this->registerElement(ID,volvtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(volvtk->getVtkId(), VTK_EMPTY_CELL);
+      myVolumePool->destroy(volvtk);
+      return 0;
+    }
+    volume = volvtk;
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = volume;
+    myInfo.myNbTetras++;
+  }
+
+  //  if (!registerElement(ID, volume)) {
+  //    RemoveElement(volume, false);
+  //    volume = NULL;
+  //  }
+  return volume;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -502,7 +699,10 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
                                       const SMDS_MeshNode * n4,
                                       const SMDS_MeshNode * n5)
 {
-  return SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, myCellFactory->GetFreeID() );
+  int ID = myElementIDFactory->GetFreeID();
+  SMDS_MeshVolume * v = SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, ID);
+  if(v==NULL) myElementIDFactory->ReleaseID(ID);
+  return v;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -520,12 +720,12 @@ SMDS_MeshVolume * SMDS_Mesh::AddVolumeWithID(int idnode1,
                                              int idnode5,
                                              int ID)
 {
-  const SMDS_MeshNode *node1, *node2, *node3, *node4, *node5;
-  node1 = myNodeFactory->FindNode(idnode1);
-  node2 = myNodeFactory->FindNode(idnode2);
-  node3 = myNodeFactory->FindNode(idnode3);
-  node4 = myNodeFactory->FindNode(idnode4);
-  node5 = myNodeFactory->FindNode(idnode5);
+  SMDS_MeshNode *node1, *node2, *node3, *node4, *node5;
+  node1 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode1);
+  node2 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode2);
+  node3 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode3);
+  node4 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode4);
+  node5 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode5);
   if(!node1 || !node2 || !node3 || !node4 || !node5) return NULL;
   return SMDS_Mesh::AddVolumeWithID(node1, node2, node3, node4, node5, ID);
 }
@@ -544,16 +744,50 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
                                             const SMDS_MeshNode * n5,
                                             int ID)
 {
-  if ( !n1 || !n2 || !n3 || !n4 || !n5 ) return 0;
+  SMDS_MeshVolume* volume = 0;
+  if ( !n1 || !n2 || !n3 || !n4 || !n5) return volume;
   if ( NbVolumes() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
-  {
-    cell->init( SMDSEntity_Pyramid, /*nbNodes=*/5, n1, n2, n3, n4, n5 );
+  if(hasConstructionFaces()) {
+    SMDS_MeshFace * f1=FindFaceOrCreate(n1,n2,n3,n4);
+    SMDS_MeshFace * f2=FindFaceOrCreate(n1,n2,n5);
+    SMDS_MeshFace * f3=FindFaceOrCreate(n2,n3,n5);
+    SMDS_MeshFace * f4=FindFaceOrCreate(n3,n4,n5);
+    volume=new SMDS_VolumeOfFaces(f1,f2,f3,f4);
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = volume;
     myInfo.myNbPyramids++;
-    return static_cast<SMDS_MeshVolume*>( cell );
   }
-  return 0;
+  else if(hasConstructionEdges()) {
+    return NULL;
+  }
+  else {
+    // --- retrieve nodes ID
+    myNodeIds.resize(5);
+    myNodeIds[0] = n1->getVtkId();
+    myNodeIds[1] = n4->getVtkId();
+    myNodeIds[2] = n3->getVtkId();
+    myNodeIds[3] = n2->getVtkId();
+    myNodeIds[4] = n5->getVtkId();
+
+    SMDS_VtkVolume *volvtk = myVolumePool->getNew();
+    volvtk->init(myNodeIds, this);
+    if (!this->registerElement(ID,volvtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(volvtk->getVtkId(), VTK_EMPTY_CELL);
+      myVolumePool->destroy(volvtk);
+      return 0;
+    }
+    volume = volvtk;
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = volume;
+    myInfo.myNbPyramids++;
+  }
+
+  //  if (!registerElement(ID, volume)) {
+  //    RemoveElement(volume, false);
+  //    volume = NULL;
+  //  }
+  return volume;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -569,8 +803,10 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
                                       const SMDS_MeshNode * n5,
                                       const SMDS_MeshNode * n6)
 {
-  int ID = myCellFactory->GetFreeID();
-  return SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6, ID);
+  int ID = myElementIDFactory->GetFreeID();
+  SMDS_MeshVolume * v = SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6, ID);
+  if(v==NULL) myElementIDFactory->ReleaseID(ID);
+  return v;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -589,13 +825,14 @@ SMDS_MeshVolume * SMDS_Mesh::AddVolumeWithID(int idnode1,
                                              int idnode6,
                                              int ID)
 {
-  const SMDS_MeshNode *node1, *node2, *node3, *node4, *node5, *node6;
-  node1 = myNodeFactory->FindNode(idnode1);
-  node2 = myNodeFactory->FindNode(idnode2);
-  node3 = myNodeFactory->FindNode(idnode3);
-  node4 = myNodeFactory->FindNode(idnode4);
-  node5 = myNodeFactory->FindNode(idnode5);
-  node6 = myNodeFactory->FindNode(idnode6);
+  SMDS_MeshNode *node1, *node2, *node3, *node4, *node5, *node6;
+  node1 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode1);
+  node2 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode2);
+  node3 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode3);
+  node4 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode4);
+  node5 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode5);
+  node6 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode6);
+  if(!node1 || !node2 || !node3 || !node4 || !node5 || !node6) return NULL;
   return SMDS_Mesh::AddVolumeWithID(node1, node2, node3, node4, node5, node6, ID);
 }
 
@@ -614,16 +851,52 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
                                             const SMDS_MeshNode * n6,
                                             int ID)
 {
-  if ( !n1 || !n2 || !n3 || !n4 || !n5 || !n6 ) return 0;
+  SMDS_MeshVolume* volume = 0;
+  if ( !n1 || !n2 || !n3 || !n4 || !n5 || !n6) return volume;
   if ( NbVolumes() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
-  {
-    cell->init( SMDSEntity_Penta, /*nbNodes=*/6, n1, n2, n3, n4, n5, n6 );
+  if(hasConstructionFaces()) {
+    SMDS_MeshFace * f1=FindFaceOrCreate(n1,n2,n3);
+    SMDS_MeshFace * f2=FindFaceOrCreate(n4,n5,n6);
+    SMDS_MeshFace * f3=FindFaceOrCreate(n1,n4,n5,n2);
+    SMDS_MeshFace * f4=FindFaceOrCreate(n2,n5,n6,n3);
+    SMDS_MeshFace * f5=FindFaceOrCreate(n3,n6,n4,n1);
+    volume=new SMDS_VolumeOfFaces(f1,f2,f3,f4,f5);
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = volume;
     myInfo.myNbPrisms++;
-    return static_cast<SMDS_MeshVolume*>( cell );
   }
-  return 0;
+  else if(hasConstructionEdges()) {
+    return NULL;
+  }
+  else {
+    // --- retrieve nodes ID
+    myNodeIds.resize(6);
+    myNodeIds[0] = n1->getVtkId();
+    myNodeIds[1] = n2->getVtkId();
+    myNodeIds[2] = n3->getVtkId();
+    myNodeIds[3] = n4->getVtkId();
+    myNodeIds[4] = n5->getVtkId();
+    myNodeIds[5] = n6->getVtkId();
+
+    SMDS_VtkVolume *volvtk = myVolumePool->getNew();
+    volvtk->init(myNodeIds, this);
+    if (!this->registerElement(ID,volvtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(volvtk->getVtkId(), VTK_EMPTY_CELL);
+      myVolumePool->destroy(volvtk);
+      return 0;
+    }
+    volume = volvtk;
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = volume;
+    myInfo.myNbPrisms++;
+  }
+
+  //  if (!registerElement(ID, volume)) {
+  //    RemoveElement(volume, false);
+  //    volume = NULL;
+  //  }
+  return volume;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -644,9 +917,12 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
                                       const SMDS_MeshNode * n11,
                                       const SMDS_MeshNode * n12)
 {
-  return SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6,
-                                    n7, n8, n9, n10, n11, n12,
-                                    myCellFactory->GetFreeID() );
+  int ID = myElementIDFactory->GetFreeID();
+  SMDS_MeshVolume * v = SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6,
+                                                   n7, n8, n9, n10, n11, n12,
+                                                   ID);
+  if(v==NULL) myElementIDFactory->ReleaseID(ID);
+  return v;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -670,18 +946,18 @@ SMDS_MeshVolume * SMDS_Mesh::AddVolumeWithID(int idnode1,
                                              int idnode12,
                                              int ID)
 {
-  const SMDS_MeshNode *node1 = myNodeFactory->FindNode(idnode1);
-  const SMDS_MeshNode *node2 = myNodeFactory->FindNode(idnode2);
-  const SMDS_MeshNode *node3 = myNodeFactory->FindNode(idnode3);
-  const SMDS_MeshNode *node4 = myNodeFactory->FindNode(idnode4);
-  const SMDS_MeshNode *node5 = myNodeFactory->FindNode(idnode5);
-  const SMDS_MeshNode *node6 = myNodeFactory->FindNode(idnode6);
-  const SMDS_MeshNode *node7 = myNodeFactory->FindNode(idnode7);
-  const SMDS_MeshNode *node8 = myNodeFactory->FindNode(idnode8);
-  const SMDS_MeshNode *node9 = myNodeFactory->FindNode(idnode9);
-  const SMDS_MeshNode *node10 = myNodeFactory->FindNode(idnode10);
-  const SMDS_MeshNode *node11 = myNodeFactory->FindNode(idnode11);
-  const SMDS_MeshNode *node12 = myNodeFactory->FindNode(idnode12);
+  SMDS_MeshNode *node1 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode1);
+  SMDS_MeshNode *node2 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode2);
+  SMDS_MeshNode *node3 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode3);
+  SMDS_MeshNode *node4 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode4);
+  SMDS_MeshNode *node5 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode5);
+  SMDS_MeshNode *node6 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode6);
+  SMDS_MeshNode *node7 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode7);
+  SMDS_MeshNode *node8 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode8);
+  SMDS_MeshNode *node9 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode9);
+  SMDS_MeshNode *node10 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode10);
+  SMDS_MeshNode *node11 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode11);
+  SMDS_MeshNode *node12 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode12);
   return SMDS_Mesh::AddVolumeWithID(node1, node2, node3, node4, node5, node6,
                                     node7, node8, node9, node10, node11, node12,
                                     ID);
@@ -712,15 +988,44 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
      !n7 || !n8 || !n9 || !n10 || !n11 || !n12 )
     return volume;
   if ( NbVolumes() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
-  {
-    cell->init( SMDSEntity_Hexagonal_Prism,
-                /*nbNodes=*/12, n1, n2, n3, n4, n5, n6, n7, n8, n9, n10, n11, n12 );
+  if(hasConstructionFaces()) {
+    return NULL;
+  }
+  else if(hasConstructionEdges()) {
+    return NULL;
+  }
+  else {
+    // --- retrieve nodes ID
+    myNodeIds.resize(12);
+    myNodeIds[0] = n1->getVtkId();
+    myNodeIds[1] = n6->getVtkId();
+    myNodeIds[2] = n5->getVtkId();
+    myNodeIds[3] = n4->getVtkId();
+    myNodeIds[4] = n3->getVtkId();
+    myNodeIds[5] = n2->getVtkId();
+
+    myNodeIds[6] = n7->getVtkId();
+    myNodeIds[7] = n12->getVtkId();
+    myNodeIds[8] = n11->getVtkId();
+    myNodeIds[9] = n10->getVtkId();
+    myNodeIds[10] = n9->getVtkId();
+    myNodeIds[11] = n8->getVtkId();
+
+    SMDS_VtkVolume *volvtk = myVolumePool->getNew();
+    volvtk->init(myNodeIds, this);
+    if (!this->registerElement(ID,volvtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(volvtk->getVtkId(), VTK_EMPTY_CELL);
+      myVolumePool->destroy(volvtk);
+      return 0;
+    }
+    volume = volvtk;
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = volume;
     myInfo.myNbHexPrism++;
-    return static_cast<SMDS_MeshVolume*>( cell );
   }
-  return 0;
+
+  return volume;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -738,8 +1043,10 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
                                       const SMDS_MeshNode * n7,
                                       const SMDS_MeshNode * n8)
 {
-  int ID = myCellFactory->GetFreeID();
-  return SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6, n7, n8, ID);
+  int ID = myElementIDFactory->GetFreeID();
+ SMDS_MeshVolume * v = SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6, n7, n8, ID);
+  if(v==NULL) myElementIDFactory->ReleaseID(ID);
+  return v;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -760,15 +1067,17 @@ SMDS_MeshVolume * SMDS_Mesh::AddVolumeWithID(int idnode1,
                                              int idnode8,
                                              int ID)
 {
-  const SMDS_MeshNode *node1, *node2, *node3, *node4, *node5, *node6, *node7, *node8;
-  node1 = myNodeFactory->FindNode(idnode1);
-  node2 = myNodeFactory->FindNode(idnode2);
-  node3 = myNodeFactory->FindNode(idnode3);
-  node4 = myNodeFactory->FindNode(idnode4);
-  node5 = myNodeFactory->FindNode(idnode5);
-  node6 = myNodeFactory->FindNode(idnode6);
-  node7 = myNodeFactory->FindNode(idnode7);
-  node8 = myNodeFactory->FindNode(idnode8);
+  SMDS_MeshNode *node1, *node2, *node3, *node4, *node5, *node6, *node7, *node8;
+  node1 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode1);
+  node2 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode2);
+  node3 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode3);
+  node4 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode4);
+  node5 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode5);
+  node6 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode6);
+  node7 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode7);
+  node8 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode8);
+  if(!node1 || !node2 || !node3 || !node4 || !node5 || !node6 || !node7 || !node8)
+    return NULL;
   return SMDS_Mesh::AddVolumeWithID(node1, node2, node3, node4, node5, node6,
                                     node7, node8, ID);
 }
@@ -794,28 +1103,203 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
   SMDS_MeshVolume* volume = 0;
   if ( !n1 || !n2 || !n3 || !n4 || !n5 || !n6 || !n7 || !n8) return volume;
   if ( NbVolumes() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
-  {
-    cell->init( SMDSEntity_Hexa,
-                /*nbNodes=*/8, n1, n2, n3, n4, n5, n6, n7, n8 );
+  if(hasConstructionFaces()) {
+    SMDS_MeshFace * f1=FindFaceOrCreate(n1,n2,n3,n4);
+    SMDS_MeshFace * f2=FindFaceOrCreate(n5,n6,n7,n8);
+    SMDS_MeshFace * f3=FindFaceOrCreate(n1,n4,n8,n5);
+    SMDS_MeshFace * f4=FindFaceOrCreate(n1,n2,n6,n5);
+    SMDS_MeshFace * f5=FindFaceOrCreate(n2,n3,n7,n6);
+    SMDS_MeshFace * f6=FindFaceOrCreate(n3,n4,n8,n7);
+    volume=new SMDS_VolumeOfFaces(f1,f2,f3,f4,f5,f6);
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = volume;
     myInfo.myNbHexas++;
-    return static_cast<SMDS_MeshVolume*>( cell );
   }
-  return 0;
+  else if(hasConstructionEdges()) {
+    return NULL;
+  }
+  else {
+    // --- retrieve nodes ID
+    myNodeIds.resize(8);
+    myNodeIds[0] = n1->getVtkId();
+    myNodeIds[1] = n4->getVtkId();
+    myNodeIds[2] = n3->getVtkId();
+    myNodeIds[3] = n2->getVtkId();
+    myNodeIds[4] = n5->getVtkId();
+    myNodeIds[5] = n8->getVtkId();
+    myNodeIds[6] = n7->getVtkId();
+    myNodeIds[7] = n6->getVtkId();
+
+    SMDS_VtkVolume *volvtk = myVolumePool->getNew();
+    volvtk->init(myNodeIds, this);
+    if (!this->registerElement(ID,volvtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(volvtk->getVtkId(), VTK_EMPTY_CELL);
+      myVolumePool->destroy(volvtk);
+      return 0;
+    }
+    volume = volvtk;
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = volume;
+    myInfo.myNbHexas++;
+  }
+
+  //  if (!registerElement(ID, volume)) {
+  //    RemoveElement(volume, false);
+  //    volume = NULL;
+  //  }
+  return volume;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+///Create a new tetrahedron defined by its faces and add it to the mesh.
+///@return The created tetrahedron
+///////////////////////////////////////////////////////////////////////////////
+
+SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshFace * f1,
+                                      const SMDS_MeshFace * f2,
+                                      const SMDS_MeshFace * f3,
+                                      const SMDS_MeshFace * f4)
+{
+  if (!hasConstructionFaces())
+    return NULL;
+  return AddVolumeWithID(f1,f2,f3,f4, myElementIDFactory->GetFreeID());
+}
+
+///////////////////////////////////////////////////////////////////////////////
+///Create a new tetrahedron defined by its faces and add it to the mesh.
+///@param ID The ID of the new volume
+///@return The created tetrahedron
+///////////////////////////////////////////////////////////////////////////////
+
+SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshFace * f1,
+                                            const SMDS_MeshFace * f2,
+                                            const SMDS_MeshFace * f3,
+                                            const SMDS_MeshFace * f4,
+                                            int ID)
+{
+  if (!hasConstructionFaces())
+    return NULL;
+  if ( !f1 || !f2 || !f3 || !f4) return 0;
+  if ( NbVolumes() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
+  SMDS_MeshVolume * volume = new SMDS_VolumeOfFaces(f1,f2,f3,f4);
+  adjustmyCellsCapacity(ID);
+  myCells[ID] = volume;
+  myInfo.myNbTetras++;
+
+  if (!registerElement(ID, volume)) {
+    registerElement(myElementIDFactory->GetFreeID(), volume);
+    //RemoveElement(volume, false);
+    //volume = NULL;
+  }
+  return volume;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+///Create a new pyramid defined by its faces and add it to the mesh.
+///@return The created pyramid
+///////////////////////////////////////////////////////////////////////////////
+
+SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshFace * f1,
+                                      const SMDS_MeshFace * f2,
+                                      const SMDS_MeshFace * f3,
+                                      const SMDS_MeshFace * f4,
+                                      const SMDS_MeshFace * f5)
+{
+ if (!hasConstructionFaces())
+    return NULL;
+  return AddVolumeWithID(f1,f2,f3,f4,f5, myElementIDFactory->GetFreeID());
+}
+
+///////////////////////////////////////////////////////////////////////////////
+///Create a new pyramid defined by its faces and add it to the mesh.
+///@param ID The ID of the new volume
+///@return The created pyramid
+///////////////////////////////////////////////////////////////////////////////
+
+SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshFace * f1,
+                                            const SMDS_MeshFace * f2,
+                                            const SMDS_MeshFace * f3,
+                                            const SMDS_MeshFace * f4,
+                                            const SMDS_MeshFace * f5,
+                                            int ID)
+{
+  if (!hasConstructionFaces())
+    return NULL;
+  if ( !f1 || !f2 || !f3 || !f4 || !f5) return 0;
+  if ( NbVolumes() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
+  SMDS_MeshVolume * volume = new SMDS_VolumeOfFaces(f1,f2,f3,f4,f5);
+  adjustmyCellsCapacity(ID);
+  myCells[ID] = volume;
+  myInfo.myNbPyramids++;
+
+  if (!registerElement(ID, volume)) {
+    registerElement(myElementIDFactory->GetFreeID(), volume);
+    //RemoveElement(volume, false);
+    //volume = NULL;
+  }
+  return volume;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+///Create a new prism defined by its faces and add it to the mesh.
+///@return The created prism
+///////////////////////////////////////////////////////////////////////////////
+
+SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshFace * f1,
+                                      const SMDS_MeshFace * f2,
+                                      const SMDS_MeshFace * f3,
+                                      const SMDS_MeshFace * f4,
+                                      const SMDS_MeshFace * f5,
+                                      const SMDS_MeshFace * f6)
+{
+ if (!hasConstructionFaces())
+    return NULL;
+  return AddVolumeWithID(f1,f2,f3,f4,f5,f6, myElementIDFactory->GetFreeID());
+}
+
+///////////////////////////////////////////////////////////////////////////////
+///Create a new prism defined by its faces and add it to the mesh.
+///@param ID The ID of the new volume
+///@return The created prism
+///////////////////////////////////////////////////////////////////////////////
+
+SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshFace * f1,
+                                            const SMDS_MeshFace * f2,
+                                            const SMDS_MeshFace * f3,
+                                            const SMDS_MeshFace * f4,
+                                            const SMDS_MeshFace * f5,
+                                            const SMDS_MeshFace * f6,
+                                            int ID)
+{
+  if (!hasConstructionFaces())
+    return NULL;
+  if ( !f1 || !f2 || !f3 || !f4 || !f5 || !f6) return 0;
+  if ( NbVolumes() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
+  SMDS_MeshVolume * volume = new SMDS_VolumeOfFaces(f1,f2,f3,f4,f5,f6);
+  adjustmyCellsCapacity(ID);
+  myCells[ID] = volume;
+  myInfo.myNbPrisms++;
+
+  if (!registerElement(ID, volume)) {
+    registerElement(myElementIDFactory->GetFreeID(), volume);
+    //RemoveElement(volume, false);
+    //volume = NULL;
+  }
+  return volume;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
 /// Add a polygon defined by its nodes IDs
 ///////////////////////////////////////////////////////////////////////////////
 
-SMDS_MeshFace* SMDS_Mesh::AddPolygonalFaceWithID (const std::vector<int> & nodes_ids,
-                                                  const int               ID)
+SMDS_MeshFace* SMDS_Mesh::AddPolygonalFaceWithID (const vector<int> & nodes_ids,
+                                                  const int           ID)
 {
   int nbNodes = nodes_ids.size();
-  std::vector<const SMDS_MeshNode*> nodes (nbNodes);
+  vector<const SMDS_MeshNode*> nodes (nbNodes);
   for (int i = 0; i < nbNodes; i++) {
-    nodes[i] = myNodeFactory->FindNode( nodes_ids[i] );
+    nodes[i] = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(nodes_ids[i]);
     if (!nodes[i]) return NULL;
   }
   return SMDS_Mesh::AddPolygonalFaceWithID(nodes, ID);
@@ -826,18 +1310,38 @@ SMDS_MeshFace* SMDS_Mesh::AddPolygonalFaceWithID (const std::vector<int> & nodes
 ///////////////////////////////////////////////////////////////////////////////
 
 SMDS_MeshFace*
-SMDS_Mesh::AddPolygonalFaceWithID (const std::vector<const SMDS_MeshNode*> & nodes,
-                                   const int                                 ID)
+SMDS_Mesh::AddPolygonalFaceWithID (const vector<const SMDS_MeshNode*> & nodes,
+                                   const int                            ID)
 {
-  if ( NbFaces() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
+  SMDS_MeshFace * face;
 
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
+  if ( NbFaces() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
+  if (hasConstructionEdges())
+  {
+    return NULL;
+  }
+  else
   {
-    cell->init( SMDSEntity_Polygon, nodes );
+    myNodeIds.resize( nodes.size() );
+    for ( size_t i = 0; i < nodes.size(); ++i )
+      myNodeIds[i] = nodes[i]->getVtkId();
+
+    SMDS_VtkFace *facevtk = myFacePool->getNew();
+    facevtk->initPoly(myNodeIds, this);
+    if (!this->registerElement(ID,facevtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(facevtk->getVtkId(), VTK_EMPTY_CELL);
+      myFacePool->destroy(facevtk);
+      return 0;
+    }
+    face = facevtk;
+
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = face;
     myInfo.myNbPolygons++;
-    return static_cast<SMDS_MeshFace*>( cell );
   }
-  return 0;
+
+  return face;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -845,21 +1349,21 @@ SMDS_Mesh::AddPolygonalFaceWithID (const std::vector<const SMDS_MeshNode*> & nod
 /// An ID is automatically affected to the created face.
 ///////////////////////////////////////////////////////////////////////////////
 
-SMDS_MeshFace* SMDS_Mesh::AddPolygonalFace (const std::vector<const SMDS_MeshNode*> & nodes)
+SMDS_MeshFace* SMDS_Mesh::AddPolygonalFace (const vector<const SMDS_MeshNode*> & nodes)
 {
-  return SMDS_Mesh::AddPolygonalFaceWithID(nodes, myCellFactory->GetFreeID());
+  return SMDS_Mesh::AddPolygonalFaceWithID(nodes, myElementIDFactory->GetFreeID());
 }
 
 ///////////////////////////////////////////////////////////////////////////////
 /// Add a quadratic polygon defined by its nodes IDs
 ///////////////////////////////////////////////////////////////////////////////
 
-SMDS_MeshFace* SMDS_Mesh::AddQuadPolygonalFaceWithID (const std::vector<int> & nodes_ids,
-                                                      const int                ID)
+SMDS_MeshFace* SMDS_Mesh::AddQuadPolygonalFaceWithID (const vector<int> & nodes_ids,
+                                                      const int           ID)
 {
-  std::vector<const SMDS_MeshNode*> nodes( nodes_ids.size() );
+  vector<const SMDS_MeshNode*> nodes( nodes_ids.size() );
   for ( size_t i = 0; i < nodes.size(); i++) {
-    nodes[i] = myNodeFactory->FindNode(nodes_ids[i]);
+    nodes[i] = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(nodes_ids[i]);
     if (!nodes[i]) return NULL;
   }
   return SMDS_Mesh::AddQuadPolygonalFaceWithID(nodes, ID);
@@ -870,17 +1374,36 @@ SMDS_MeshFace* SMDS_Mesh::AddQuadPolygonalFaceWithID (const std::vector<int> & n
 ///////////////////////////////////////////////////////////////////////////////
 
 SMDS_MeshFace*
-SMDS_Mesh::AddQuadPolygonalFaceWithID (const std::vector<const SMDS_MeshNode*> & nodes,
-                                       const int                                 ID)
+SMDS_Mesh::AddQuadPolygonalFaceWithID (const vector<const SMDS_MeshNode*> & nodes,
+                                       const int                            ID)
 {
+  SMDS_MeshFace * face;
+
   if ( NbFaces() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
+  if (hasConstructionEdges())
+  {
+    return NULL;
+  }
+  else
   {
-    cell->init( SMDSEntity_Quad_Polygon, nodes );
+    myNodeIds.resize( nodes.size() );
+    for ( size_t i = 0; i < nodes.size(); ++i )
+      myNodeIds[i] = nodes[i]->getVtkId();
+
+    SMDS_VtkFace *facevtk = myFacePool->getNew();
+    facevtk->initQuadPoly(myNodeIds, this);
+    if (!this->registerElement(ID,facevtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(facevtk->getVtkId(), VTK_EMPTY_CELL);
+      myFacePool->destroy(facevtk);
+      return 0;
+    }
+    face = facevtk;
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = face;
     myInfo.myNbQuadPolygons++;
-    return static_cast<SMDS_MeshFace*>( cell );
   }
-  return 0;
+  return face;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -888,9 +1411,9 @@ SMDS_Mesh::AddQuadPolygonalFaceWithID (const std::vector<const SMDS_MeshNode*> &
 /// An ID is automatically affected to the created face.
 ///////////////////////////////////////////////////////////////////////////////
 
-SMDS_MeshFace* SMDS_Mesh::AddQuadPolygonalFace (const std::vector<const SMDS_MeshNode*> & nodes)
+SMDS_MeshFace* SMDS_Mesh::AddQuadPolygonalFace (const vector<const SMDS_MeshNode*> & nodes)
 {
-  return SMDS_Mesh::AddQuadPolygonalFaceWithID(nodes, myCellFactory->GetFreeID());
+  return SMDS_Mesh::AddQuadPolygonalFaceWithID(nodes, myElementIDFactory->GetFreeID());
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -900,14 +1423,15 @@ SMDS_MeshFace* SMDS_Mesh::AddQuadPolygonalFace (const std::vector<const SMDS_Mes
 /// or if input nodes are not found.
 ///////////////////////////////////////////////////////////////////////////////
 
-SMDS_MeshVolume * SMDS_Mesh::AddPolyhedralVolumeWithID (const std::vector<int> & nodes_ids,
-                                                        const std::vector<int> & quantities,
-                                                        const int                ID)
+SMDS_MeshVolume * SMDS_Mesh::AddPolyhedralVolumeWithID
+                             (const vector<int> & nodes_ids,
+                              const vector<int> & quantities,
+                              const int           ID)
 {
   int nbNodes = nodes_ids.size();
-  std::vector<const SMDS_MeshNode*> nodes (nbNodes);
+  vector<const SMDS_MeshNode*> nodes (nbNodes);
   for (int i = 0; i < nbNodes; i++) {
-    nodes[i] = myNodeFactory->FindNode(nodes_ids[i]);
+    nodes[i] = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(nodes_ids[i]);
     if (!nodes[i]) return NULL;
   }
   return SMDS_Mesh::AddPolyhedralVolumeWithID(nodes, quantities, ID);
@@ -920,22 +1444,57 @@ SMDS_MeshVolume * SMDS_Mesh::AddPolyhedralVolumeWithID (const std::vector<int> &
 ///////////////////////////////////////////////////////////////////////////////
 
 SMDS_MeshVolume*
-SMDS_Mesh::AddPolyhedralVolumeWithID (const std::vector<const SMDS_MeshNode*>& nodes,
-                                      const std::vector<int>                 & quantities,
+SMDS_Mesh::AddPolyhedralVolumeWithID (const vector<const SMDS_MeshNode*>& nodes,
+                                      const vector<int>                 & quantities,
                                       const int                           ID)
 {
+  SMDS_MeshVolume* volume = 0;
   if ( nodes.empty() || quantities.empty() )
     return NULL;
   if ( NbVolumes() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
+  if (hasConstructionFaces())
+  {
+    return NULL;
+  }
+  else if (hasConstructionEdges())
+  {
+    return NULL;
+  }
+  else
   {
-    SMDS_MeshVolume* volume = static_cast<SMDS_MeshVolume*>( cell );
-    volume->init( nodes, quantities );
+    //#ifdef VTK_HAVE_POLYHEDRON
+    myNodeIds.resize( nodes.size() );
+    for ( size_t i = 0; i < nodes.size(); ++i )
+      myNodeIds[i] = nodes[i]->getVtkId();
+
+    SMDS_VtkVolume *volvtk = myVolumePool->getNew();
+    volvtk->initPoly(myNodeIds, quantities, this);
+    if (!this->registerElement(ID, volvtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(volvtk->getVtkId(), VTK_EMPTY_CELL);
+      myVolumePool->destroy(volvtk);
+      return 0;
+    }
+    volume = volvtk;
+    //#else
+    //      for ( int i = 0; i < nodes.size(); ++i )
+    //      if ( !nodes[ i ] ) return 0;
+    //      volume = new SMDS_PolyhedralVolumeOfNodes(nodes, quantities);
+    //#endif
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = volume;
     myInfo.myNbPolyhedrons++;
-    return volume;
   }
-  return 0;
+
+  //#ifndef VTK_HAVE_POLYHEDRON
+  //  if (!registerElement(ID, volume))
+  //    {
+  //      registerElement(myElementIDFactory->GetFreeID(), volume);
+  //      //RemoveElement(volume, false);
+  //      //volume = NULL;
+  //    }
+  //#endif
+  return volume;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -944,32 +1503,161 @@ SMDS_Mesh::AddPolyhedralVolumeWithID (const std::vector<const SMDS_MeshNode*>& n
 ///////////////////////////////////////////////////////////////////////////////
 
 SMDS_MeshVolume* SMDS_Mesh::AddPolyhedralVolume
-(const std::vector<const SMDS_MeshNode*> & nodes,
const std::vector<int>                  & quantities)
+                            (const vector<const SMDS_MeshNode*> & nodes,
                            const vector<int>                  & quantities)
 {
-  int ID = myCellFactory->GetFreeID();
-  return SMDS_Mesh::AddPolyhedralVolumeWithID(nodes, quantities, ID);
+  int ID = myElementIDFactory->GetFreeID();
+  SMDS_MeshVolume * v = SMDS_Mesh::AddPolyhedralVolumeWithID(nodes, quantities, ID);
+  if (v == NULL) myElementIDFactory->ReleaseID(ID);
+  return v;
 }
 
 SMDS_MeshVolume* SMDS_Mesh::AddVolumeFromVtkIds(const std::vector<vtkIdType>& vtkNodeIds)
 {
-  SMDS_MeshCell*   cell = myCellFactory->NewCell( myCellFactory->GetFreeID() );
-  SMDS_MeshVolume * vol = static_cast<SMDS_MeshVolume*>( cell );
-  vol->init( vtkNodeIds );
-  myInfo.add( cell );
-  return vol;
+  int ID = myElementIDFactory->GetFreeID();
+  SMDS_MeshVolume * v = SMDS_Mesh::AddVolumeFromVtkIdsWithID(vtkNodeIds, ID);
+  if (v == NULL) myElementIDFactory->ReleaseID(ID);
+  return v;
+}
+
+SMDS_MeshVolume* SMDS_Mesh::AddVolumeFromVtkIdsWithID(const std::vector<vtkIdType>& vtkNodeIds, const int ID)
+{
+  SMDS_VtkVolume *volvtk = myVolumePool->getNew();
+  volvtk->init(vtkNodeIds, this);
+  if (!this->registerElement(ID,volvtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(volvtk->getVtkId(), VTK_EMPTY_CELL);
+      myVolumePool->destroy(volvtk);
+      return 0;
+    }
+  adjustmyCellsCapacity(ID);
+  myCells[ID] = volvtk;
+  vtkIdType aVtkType = volvtk->GetVtkType();
+  switch (aVtkType)
+  {
+    case VTK_TETRA:
+      myInfo.myNbTetras++;
+      break;
+    case VTK_PYRAMID:
+      myInfo.myNbPyramids++;
+      break;
+    case VTK_WEDGE:
+      myInfo.myNbPrisms++;
+      break;
+    case VTK_HEXAHEDRON:
+      myInfo.myNbHexas++;
+      break;
+    case VTK_QUADRATIC_TETRA:
+      myInfo.myNbQuadTetras++;
+      break;
+    case VTK_QUADRATIC_PYRAMID:
+      myInfo.myNbQuadPyramids++;
+      break;
+    case VTK_QUADRATIC_WEDGE:
+      myInfo.myNbQuadPrisms++;
+      break;
+    case VTK_BIQUADRATIC_QUADRATIC_WEDGE:
+      myInfo.myNbBiQuadPrisms++;
+      break;
+    case VTK_QUADRATIC_HEXAHEDRON:
+      myInfo.myNbQuadHexas++;
+      break;
+    case VTK_TRIQUADRATIC_HEXAHEDRON:
+      myInfo.myNbTriQuadHexas++;
+      break;
+//#ifdef VTK_HAVE_POLYHEDRON
+    case VTK_POLYHEDRON:
+      myInfo.myNbPolyhedrons++;
+      break;
+//#endif
+    default:
+      myInfo.myNbPolyhedrons++;
+      break;
+  }
+  return volvtk;
 }
 
 SMDS_MeshFace* SMDS_Mesh::AddFaceFromVtkIds(const std::vector<vtkIdType>& vtkNodeIds)
 {
-  SMDS_MeshCell* cell = myCellFactory->NewCell( myCellFactory->GetFreeID() );
-  SMDS_MeshFace *   f = static_cast<SMDS_MeshFace*>( cell );
-  f->init( vtkNodeIds );
-  myInfo.add( cell );
+  int ID = myElementIDFactory->GetFreeID();
+  SMDS_MeshFace * f = SMDS_Mesh::AddFaceFromVtkIdsWithID(vtkNodeIds, ID);
+  if (f == NULL) myElementIDFactory->ReleaseID(ID);
   return f;
 }
 
-//=======================================================================
+SMDS_MeshFace* SMDS_Mesh::AddFaceFromVtkIdsWithID(const std::vector<vtkIdType>& vtkNodeIds, const int ID)
+{
+  SMDS_VtkFace *facevtk = myFacePool->getNew();
+  facevtk->init(vtkNodeIds, this);
+  if (!this->registerElement(ID,facevtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(facevtk->getVtkId(), VTK_EMPTY_CELL);
+      myFacePool->destroy(facevtk);
+      return 0;
+    }
+  adjustmyCellsCapacity(ID);
+  myCells[ID] = facevtk;
+  vtkIdType aVtkType = facevtk->GetVtkType();
+  switch (aVtkType)
+  {
+    case VTK_TRIANGLE:
+      myInfo.myNbTriangles++;
+      break;
+    case VTK_QUAD:
+      myInfo.myNbQuadrangles++;
+      break;
+    case VTK_QUADRATIC_TRIANGLE:
+      myInfo.myNbQuadTriangles++;
+      break;
+    case VTK_QUADRATIC_QUAD:
+      myInfo.myNbQuadQuadrangles++;
+      break;
+    case VTK_BIQUADRATIC_QUAD:
+      myInfo.myNbBiQuadQuadrangles++;
+      break;
+    case VTK_BIQUADRATIC_TRIANGLE:
+      myInfo.myNbBiQuadTriangles++;
+      break;
+    case VTK_POLYGON:
+      myInfo.myNbPolygons++;
+      break;
+     default:
+      myInfo.myNbPolygons++;
+  }
+  return facevtk;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+/// Registers element with the given ID, maintains inverse connections
+///////////////////////////////////////////////////////////////////////////////
+bool SMDS_Mesh::registerElement(int ID, SMDS_MeshElement* element)
+{
+  if ((ID >=0) && (ID < (int)myCells.size()) && myCells[ID]) // --- already bound
+  {
+    MESSAGE(" ------------------ already bound "<< ID << " " << myCells[ID]->getVtkId());
+    return false;
+  }
+
+  element->myID = ID;
+  element->myMeshId = myMeshId;
+
+  SMDS_MeshCell *cell = dynamic_cast<SMDS_MeshCell*>(element);
+  MYASSERT(cell);
+  int vtkId = cell->getVtkId();  
+  if (vtkId == -1)
+    vtkId = myElementIDFactory->SetInVtkGrid(element);
+
+  if (vtkId >= (int)myCellIdVtkToSmds.size()) // --- resize local vector
+  {
+    myCellIdVtkToSmds.resize(vtkId + SMDS_Mesh::chunkSize, -1);
+  }
+  myCellIdVtkToSmds[vtkId] = ID;
+
+  myElementIDFactory->updateMinMax(ID);
+  return true;
+}
+
+//=======================================================================
 //function : MoveNode
 //purpose  : 
 //=======================================================================
@@ -985,7 +1673,11 @@ void SMDS_Mesh::MoveNode(const SMDS_MeshNode *n, double x, double y, double z)
 ///////////////////////////////////////////////////////////////////////////////
 const SMDS_MeshNode * SMDS_Mesh::FindNode(int ID) const
 {
-  return myNodeFactory->FindNode( ID );
+  if (ID < 1 || ID >= (int)myNodes.size())
+  {
+    return 0;
+  }
+  return (const SMDS_MeshNode *)myNodes[ID];
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -993,12 +1685,117 @@ const SMDS_MeshNode * SMDS_Mesh::FindNode(int ID) const
 ///////////////////////////////////////////////////////////////////////////////
 const SMDS_MeshNode * SMDS_Mesh::FindNodeVtk(int vtkId) const
 {
-  return myNodeFactory->FindNode( vtkId + 1 );
+  // TODO if needed use mesh->nodeIdFromVtkToSmds
+  if ( vtkId < 0 || vtkId+1 >= (int) myNodes.size() )
+  {
+    MESSAGE("------------------------------------------------------------------------- ");
+    MESSAGE("---------------------------- bad VTK ID " << vtkId << " " << myNodes.size());
+    MESSAGE("------------------------------------------------------------------------- ");
+    return 0;
+  }
+  return (const SMDS_MeshNode *)myNodes[vtkId+1];
+}
+
+//////////////////////////////////////////////////////////////////////////////
+///Create a triangle and add it to the current mesh. This method does not bind
+///an ID to the create triangle.
+//////////////////////////////////////////////////////////////////////////////
+SMDS_MeshFace * SMDS_Mesh::createTriangle(const SMDS_MeshNode * node1,
+                                          const SMDS_MeshNode * node2,
+                                          const SMDS_MeshNode * node3,
+                                          int ID)
+{
+  if ( !node1 || !node2 || !node3) return 0;
+  if ( NbFaces() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
+  if(hasConstructionEdges())
+  {
+    SMDS_MeshEdge *edge1, *edge2, *edge3;
+    edge1=FindEdgeOrCreate(node1,node2);
+    edge2=FindEdgeOrCreate(node2,node3);
+    edge3=FindEdgeOrCreate(node3,node1);
+
+    //int ID = myElementIDFactory->GetFreeID(); // -PR- voir si on range cet element
+    SMDS_MeshFace * face = new SMDS_FaceOfEdges(edge1,edge2,edge3);
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = face;
+    myInfo.myNbTriangles++;
+    return face;
+  }
+  else
+  {
+    // --- retrieve nodes ID
+    myNodeIds.resize(3);
+    myNodeIds[0] = node1->getVtkId();
+    myNodeIds[1] = node2->getVtkId();
+    myNodeIds[2] = node3->getVtkId();
+
+    SMDS_MeshFace * face = 0;
+    SMDS_VtkFace *facevtk = myFacePool->getNew();
+    facevtk->init(myNodeIds, this); // put in vtkUnstructuredGrid
+    if (!this->registerElement(ID,facevtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(facevtk->getVtkId(), VTK_EMPTY_CELL);
+      myFacePool->destroy(facevtk);
+      return 0;
+    }
+    face = facevtk;
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = face;
+    myInfo.myNbTriangles++;
+    return face;
+  }
 }
 
-const SMDS_MeshElement * SMDS_Mesh::FindElementVtk(int IDelem) const
+////////////////////////////////////////////////////////////////////////////////
+///Create a quadrangle and add it to the current mesh. This method does not bind
+///an ID to the create triangle.
+////////////////////////////////////////////////////////////////////////////////
+SMDS_MeshFace * SMDS_Mesh::createQuadrangle(const SMDS_MeshNode * node1,
+                                            const SMDS_MeshNode * node2,
+                                            const SMDS_MeshNode * node3,
+                                            const SMDS_MeshNode * node4,
+                                            int ID)
 {
-  return myCellFactory->FindElement( FromVtkToSmds( IDelem ));
+  if ( !node1 || !node2 || !node3 || !node4 ) return 0;
+  if ( NbFaces() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
+  if(hasConstructionEdges())
+  {
+    SMDS_MeshEdge *edge1, *edge2, *edge3, *edge4;
+    edge1=FindEdgeOrCreate(node1,node2);
+    edge2=FindEdgeOrCreate(node2,node3);
+    edge3=FindEdgeOrCreate(node3,node4);
+    edge4=FindEdgeOrCreate(node4,node1);
+
+    SMDS_MeshFace * face = new SMDS_FaceOfEdges(edge1,edge2,edge3,edge4);
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = face;
+    myInfo.myNbQuadrangles++;
+    return face;
+  }
+  else
+  {
+    // --- retrieve nodes ID
+    myNodeIds.resize(4);
+    myNodeIds[0] = node1->getVtkId();
+    myNodeIds[1] = node2->getVtkId();
+    myNodeIds[2] = node3->getVtkId();
+    myNodeIds[3] = node4->getVtkId();
+
+    SMDS_MeshFace * face = 0;
+    SMDS_VtkFace *facevtk = myFacePool->getNew();
+    facevtk->init(myNodeIds, this);
+    if (!this->registerElement(ID,facevtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(facevtk->getVtkId(), VTK_EMPTY_CELL);
+      myFacePool->destroy(facevtk);
+      return 0;
+    }
+    face = facevtk;
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = face;
+    myInfo.myNbQuadrangles++;
+    return face;
+  }
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -1010,6 +1807,42 @@ void SMDS_Mesh::RemoveNode(const SMDS_MeshNode * node)
   RemoveElement(node, true);
 }
 
+///////////////////////////////////////////////////////////////////////////////
+/// Remove an edge and all the elements which own this edge
+///////////////////////////////////////////////////////////////////////////////
+
+void SMDS_Mesh::Remove0DElement(const SMDS_Mesh0DElement * elem0d)
+{
+  RemoveElement(elem0d,true);
+}
+
+///////////////////////////////////////////////////////////////////////////////
+/// Remove an edge and all the elements which own this edge
+///////////////////////////////////////////////////////////////////////////////
+
+void SMDS_Mesh::RemoveEdge(const SMDS_MeshEdge * edge)
+{
+  RemoveElement(edge,true);
+}
+
+///////////////////////////////////////////////////////////////////////////////
+/// Remove an face and all the elements which own this face
+///////////////////////////////////////////////////////////////////////////////
+
+void SMDS_Mesh::RemoveFace(const SMDS_MeshFace * face)
+{
+  RemoveElement(face, true);
+}
+
+///////////////////////////////////////////////////////////////////////////////
+/// Remove a volume
+///////////////////////////////////////////////////////////////////////////////
+
+void SMDS_Mesh::RemoveVolume(const SMDS_MeshVolume * volume)
+{
+  RemoveElement(volume, true);
+}
+
 //=======================================================================
 //function : RemoveFromParent
 //purpose  :
@@ -1030,7 +1863,7 @@ bool SMDS_Mesh::RemoveSubMesh(const SMDS_Mesh * aMesh)
 {
   bool found = false;
 
-  std::list<SMDS_Mesh *>::iterator itmsh=myChildren.begin();
+  list<SMDS_Mesh *>::iterator itmsh=myChildren.begin();
   for (; itmsh!=myChildren.end() && !found; itmsh++)
   {
     SMDS_Mesh * submesh = *itmsh;
@@ -1053,27 +1886,28 @@ bool SMDS_Mesh::ChangeElementNodes(const SMDS_MeshElement * element,
                                    const SMDS_MeshNode    * nodes[],
                                    const int                nbnodes)
 {
-  // keep current nodes of element
-  std::set<const SMDS_MeshNode*> oldNodes( element->begin_nodes(), element->end_nodes() );
+  // keep current nodes of elem
+  set<const SMDS_MeshNode*> oldNodes( element->begin_nodes(), element->end_nodes() );
 
   // change nodes
   bool Ok = false;
-  if ( SMDS_MeshCell* cell = dynamic_cast<SMDS_MeshCell*>((SMDS_MeshElement*) element))
+  SMDS_MeshCell* cell = dynamic_cast<SMDS_MeshCell*>((SMDS_MeshElement*) element);
+  if (cell)
+  {
+    Ok = cell->vtkOrder(nodes, nbnodes);
     Ok = cell->ChangeNodes(nodes, nbnodes);
+  }
 
-  if ( Ok )
-    setMyModified();
+  if ( Ok ) { // update InverseElements
 
-  if ( Ok && GetGrid()->HasLinks() ) // update InverseElements
-  {
-    std::set<const SMDS_MeshNode*>::iterator it;
+    set<const SMDS_MeshNode*>::iterator it;
 
     // AddInverseElement to new nodes
     for ( int i = 0; i < nbnodes; i++ ) {
       it = oldNodes.find( nodes[i] );
       if ( it == oldNodes.end() )
         // new node
-        const_cast<SMDS_MeshNode*>( nodes[i] )->AddInverseElement( element );
+        const_cast<SMDS_MeshNode*>( nodes[i] )->AddInverseElement( cell );
       else
         // remove from oldNodes a node that remains in elem
         oldNodes.erase( it );
@@ -1082,13 +1916,84 @@ bool SMDS_Mesh::ChangeElementNodes(const SMDS_MeshElement * element,
     for ( it = oldNodes.begin(); it != oldNodes.end(); it++ )
     {
       SMDS_MeshNode * n = const_cast<SMDS_MeshNode *>( *it );
-      n->RemoveInverseElement( element );
+      n->RemoveInverseElement( cell );
     }
   }
 
   return Ok;
 }
 
+//=======================================================================
+//function : ChangePolyhedronNodes
+//purpose  : to change nodes of polyhedral volume
+//=======================================================================
+bool SMDS_Mesh::ChangePolyhedronNodes (const SMDS_MeshElement *            elem,
+                                       const vector<const SMDS_MeshNode*>& nodes,
+                                       const vector<int>                 & quantities)
+{
+  if (elem->GetType() != SMDSAbs_Volume) {
+    MESSAGE("WRONG ELEM TYPE");
+    return false;
+  }
+
+  const SMDS_VtkVolume* vol = dynamic_cast<const SMDS_VtkVolume*>(elem);
+  if (!vol) {
+    return false;
+  }
+
+  // keep current nodes of elem
+  set<const SMDS_MeshElement*> oldNodes;
+  SMDS_ElemIteratorPtr itn = elem->nodesIterator();
+  while (itn->more()) {
+    oldNodes.insert(itn->next());
+  }
+
+  // change nodes
+  // TODO remove this function
+  //bool Ok = const_cast<SMDS_VtkVolume*>(vol)->ChangeNodes(nodes, quantities);
+  bool Ok = false;
+  if (!Ok) {
+    return false;
+  }
+
+  // update InverseElements
+
+  // AddInverseElement to new nodes
+  int nbnodes = nodes.size();
+  set<const SMDS_MeshElement*>::iterator it;
+  for (int i = 0; i < nbnodes; i++) {
+    it = oldNodes.find(nodes[i]);
+    if (it == oldNodes.end()) {
+      // new node
+      const_cast<SMDS_MeshNode*>(nodes[i])->AddInverseElement(elem);
+    } else {
+      // remove from oldNodes a node that remains in elem
+      oldNodes.erase(it);
+    }
+  }
+
+  // RemoveInverseElement from the nodes removed from elem
+  for (it = oldNodes.begin(); it != oldNodes.end(); it++) {
+    SMDS_MeshNode * n = static_cast<SMDS_MeshNode *>
+      (const_cast<SMDS_MeshElement *>( *it ));
+    n->RemoveInverseElement(elem);
+  }
+
+  return Ok;
+}
+
+
+//=======================================================================
+//function : Find0DElement
+//purpose  :
+//=======================================================================
+const SMDS_Mesh0DElement* SMDS_Mesh::Find0DElement(int idnode) const
+{
+  const SMDS_MeshNode * node = FindNode(idnode);
+  if(node == NULL) return NULL;
+  return Find0DElement(node);
+}
+
 const SMDS_Mesh0DElement* SMDS_Mesh::Find0DElement(const SMDS_MeshNode * node)
 {
   if (!node) return 0;
@@ -1103,6 +2008,18 @@ const SMDS_Mesh0DElement* SMDS_Mesh::Find0DElement(const SMDS_MeshNode * node)
   return toReturn;
 }
 
+//=======================================================================
+//function : FindBall
+//purpose  :
+//=======================================================================
+
+const SMDS_BallElement* SMDS_Mesh::FindBall(int idnode) const
+{
+  const SMDS_MeshNode * node = FindNode(idnode);
+  if(node == NULL) return NULL;
+  return FindBall(node);
+}
+
 const SMDS_BallElement* SMDS_Mesh::FindBall(const SMDS_MeshNode * node)
 {
   if (!node) return 0;
@@ -1116,12 +2033,49 @@ const SMDS_BallElement* SMDS_Mesh::FindBall(const SMDS_MeshNode * node)
   return toReturn;
 }
 
+//=======================================================================
+//function : Find0DElementOrCreate
+//purpose  :
+//=======================================================================
+//SMDS_Mesh0DElement* SMDS_Mesh::Find0DElementOrCreate(const SMDS_MeshNode * node)
+//{
+//  if (!node) return 0;
+//  SMDS_Mesh0DElement * toReturn = NULL;
+//  toReturn = const_cast<SMDS_Mesh0DElement*>(Find0DElement(node));
+//  if (toReturn == NULL) {
+//    //if (my0DElements.Extent() % CHECKMEMORY_INTERVAL == 0) CheckMemory();
+//    toReturn = new SMDS_Mesh0DElement(node);
+//    my0DElements.Add(toReturn);
+//    myInfo.myNb0DElements++;
+//  }
+//  return toReturn;
+//}
+
+
+//=======================================================================
+//function : FindEdge
+//purpose  :
+//=======================================================================
+
+const SMDS_MeshEdge* SMDS_Mesh::FindEdge(int idnode1, int idnode2) const
+{
+  const SMDS_MeshNode * node1=FindNode(idnode1);
+  const SMDS_MeshNode * node2=FindNode(idnode2);
+  if((node1==NULL)||(node2==NULL)) return NULL;
+  return FindEdge(node1,node2);
+}
+
+//#include "Profiler.h"
 const SMDS_MeshEdge* SMDS_Mesh::FindEdge(const SMDS_MeshNode * node1,
                                          const SMDS_MeshNode * node2)
 {
   if ( !node1 ) return 0;
   const SMDS_MeshEdge * toReturn=NULL;
+  //PROFILER_Init();
+  //PROFILER_Set();
   SMDS_ElemIteratorPtr it1=node1->GetInverseElementIterator(SMDSAbs_Edge);
+  //PROFILER_Get(0);
+  //PROFILER_Set();
   while(it1->more()) {
     const SMDS_MeshElement * e = it1->next();
     if ( e->NbNodes() == 2 && e->GetNodeIndex( node2 ) >= 0 ) {
@@ -1129,9 +2083,60 @@ const SMDS_MeshEdge* SMDS_Mesh::FindEdge(const SMDS_MeshNode * node1,
       break;
     }
   }
+  //PROFILER_Get(1);
   return toReturn;
 }
 
+
+//=======================================================================
+//function : FindEdgeOrCreate
+//purpose  :
+//=======================================================================
+
+SMDS_MeshEdge* SMDS_Mesh::FindEdgeOrCreate(const SMDS_MeshNode * node1,
+                                           const SMDS_MeshNode * node2)
+{
+  if ( !node1 || !node2) return 0;
+  SMDS_MeshEdge * toReturn=NULL;
+  toReturn=const_cast<SMDS_MeshEdge*>(FindEdge(node1,node2));
+  if(toReturn==NULL) {
+    if ( NbEdges() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
+    int ID = myElementIDFactory->GetFreeID(); // -PR- voir si on range cet element
+    adjustmyCellsCapacity(ID);
+    myNodeIds.resize(2);
+    myNodeIds[0] = node1->getVtkId();
+    myNodeIds[1] = node2->getVtkId();
+
+    SMDS_VtkEdge *edgevtk = myEdgePool->getNew();
+    edgevtk->init(myNodeIds, this);
+    if (!this->registerElement(ID,edgevtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(edgevtk->getVtkId(), VTK_EMPTY_CELL);
+      myEdgePool->destroy(edgevtk);
+      return 0;
+    }
+    toReturn = edgevtk;
+    myCells[ID] = toReturn;
+    myInfo.myNbEdges++;
+  }
+  return toReturn;
+}
+
+
+//=======================================================================
+//function : FindEdge
+//purpose  :
+//=======================================================================
+
+const SMDS_MeshEdge* SMDS_Mesh::FindEdge(int idnode1, int idnode2,
+                                         int idnode3) const
+{
+  const SMDS_MeshNode * node1=FindNode(idnode1);
+  const SMDS_MeshNode * node2=FindNode(idnode2);
+  const SMDS_MeshNode * node3=FindNode(idnode3);
+  return FindEdge(node1,node2,node3);
+}
+
 const SMDS_MeshEdge* SMDS_Mesh::FindEdge(const SMDS_MeshNode * node1,
                                          const SMDS_MeshNode * node2,
                                          const SMDS_MeshNode * node3)
@@ -1159,11 +2164,21 @@ const SMDS_MeshEdge* SMDS_Mesh::FindEdge(const SMDS_MeshNode * node1,
   return 0;
 }
 
+
 //=======================================================================
 //function : FindFace
 //purpose  :
 //=======================================================================
 
+const SMDS_MeshFace* SMDS_Mesh::FindFace(int idnode1, int idnode2,
+        int idnode3) const
+{
+  const SMDS_MeshNode * node1=FindNode(idnode1);
+  const SMDS_MeshNode * node2=FindNode(idnode2);
+  const SMDS_MeshNode * node3=FindNode(idnode3);
+  return FindFace(node1, node2, node3);
+}
+
 const SMDS_MeshFace* SMDS_Mesh::FindFace(const SMDS_MeshNode *node1,
                                          const SMDS_MeshNode *node2,
                                          const SMDS_MeshNode *node3)
@@ -1191,11 +2206,35 @@ const SMDS_MeshFace* SMDS_Mesh::FindFace(const SMDS_MeshNode *node1,
   return 0;
 }
 
+SMDS_MeshFace* SMDS_Mesh::FindFaceOrCreate(const SMDS_MeshNode *node1,
+                                           const SMDS_MeshNode *node2,
+                                           const SMDS_MeshNode *node3)
+{
+  SMDS_MeshFace * toReturn=NULL;
+  toReturn = const_cast<SMDS_MeshFace*>(FindFace(node1,node2,node3));
+  if(toReturn==NULL) {
+    int ID = myElementIDFactory->GetFreeID();
+    toReturn = createTriangle(node1,node2,node3, ID);
+  }
+  return toReturn;
+}
+
+
 //=======================================================================
 //function : FindFace
 //purpose  :
 //=======================================================================
 
+const SMDS_MeshFace* SMDS_Mesh::FindFace(int idnode1, int idnode2,
+                                         int idnode3, int idnode4) const
+{
+  const SMDS_MeshNode * node1=FindNode(idnode1);
+  const SMDS_MeshNode * node2=FindNode(idnode2);
+  const SMDS_MeshNode * node3=FindNode(idnode3);
+  const SMDS_MeshNode * node4=FindNode(idnode4);
+  return FindFace(node1, node2, node3, node4);
+}
+
 const SMDS_MeshFace* SMDS_Mesh::FindFace(const SMDS_MeshNode *node1,
                                          const SMDS_MeshNode *node2,
                                          const SMDS_MeshNode *node3,
@@ -1225,11 +2264,39 @@ const SMDS_MeshFace* SMDS_Mesh::FindFace(const SMDS_MeshNode *node1,
   return 0;
 }
 
+SMDS_MeshFace* SMDS_Mesh::FindFaceOrCreate(const SMDS_MeshNode *node1,
+                                           const SMDS_MeshNode *node2,
+                                           const SMDS_MeshNode *node3,
+                                           const SMDS_MeshNode *node4)
+{
+  SMDS_MeshFace * toReturn=NULL;
+  toReturn=const_cast<SMDS_MeshFace*>(FindFace(node1,node2,node3,node4));
+  if(toReturn==NULL) {
+    int ID = myElementIDFactory->GetFreeID();
+    toReturn=createQuadrangle(node1,node2,node3,node4,ID);
+  }
+  return toReturn;
+}
+
+
 //=======================================================================
 //function : FindFace
 //purpose  :quadratic triangle
 //=======================================================================
 
+const SMDS_MeshFace* SMDS_Mesh::FindFace(int idnode1, int idnode2,
+                                         int idnode3, int idnode4,
+                                         int idnode5, int idnode6) const
+{
+  const SMDS_MeshNode * node1 = FindNode(idnode1);
+  const SMDS_MeshNode * node2 = FindNode(idnode2);
+  const SMDS_MeshNode * node3 = FindNode(idnode3);
+  const SMDS_MeshNode * node4 = FindNode(idnode4);
+  const SMDS_MeshNode * node5 = FindNode(idnode5);
+  const SMDS_MeshNode * node6 = FindNode(idnode6);
+  return FindFace(node1, node2, node3, node4, node5, node6);
+}
+
 const SMDS_MeshFace* SMDS_Mesh::FindFace(const SMDS_MeshNode *node1,
                                          const SMDS_MeshNode *node2,
                                          const SMDS_MeshNode *node3,
@@ -1269,6 +2336,22 @@ const SMDS_MeshFace* SMDS_Mesh::FindFace(const SMDS_MeshNode *node1,
 //purpose  : quadratic quadrangle
 //=======================================================================
 
+const SMDS_MeshFace* SMDS_Mesh::FindFace(int idnode1, int idnode2,
+                                         int idnode3, int idnode4,
+                                         int idnode5, int idnode6,
+                                         int idnode7, int idnode8) const
+{
+  const SMDS_MeshNode * node1 = FindNode(idnode1);
+  const SMDS_MeshNode * node2 = FindNode(idnode2);
+  const SMDS_MeshNode * node3 = FindNode(idnode3);
+  const SMDS_MeshNode * node4 = FindNode(idnode4);
+  const SMDS_MeshNode * node5 = FindNode(idnode5);
+  const SMDS_MeshNode * node6 = FindNode(idnode6);
+  const SMDS_MeshNode * node7 = FindNode(idnode7);
+  const SMDS_MeshNode * node8 = FindNode(idnode8);
+  return FindFace(node1, node2, node3, node4, node5, node6, node7, node8);
+}
+
 const SMDS_MeshFace* SMDS_Mesh::FindFace(const SMDS_MeshNode *node1,
                                          const SMDS_MeshNode *node2,
                                          const SMDS_MeshNode *node3,
@@ -1314,7 +2397,11 @@ const SMDS_MeshFace* SMDS_Mesh::FindFace(const SMDS_MeshNode *node1,
 
 const SMDS_MeshElement* SMDS_Mesh::FindElement(int IDelem) const
 {
-  return myCellFactory->FindElement( IDelem );
+  if ( IDelem <= 0 || IDelem >= (int)myCells.size() )
+  {
+    return 0;
+  }
+  return myCells[IDelem];
 }
 
 //=======================================================================
@@ -1322,8 +2409,19 @@ const SMDS_MeshElement* SMDS_Mesh::FindElement(int IDelem) const
 //purpose  : find polygon
 //=======================================================================
 
+const SMDS_MeshFace* SMDS_Mesh::FindFace (const vector<int>& nodes_ids) const
+{
+  int nbnodes = nodes_ids.size();
+  vector<const SMDS_MeshNode *> poly_nodes (nbnodes);
+  for (int inode = 0; inode < nbnodes; inode++) {
+    const SMDS_MeshNode * node = FindNode(nodes_ids[inode]);
+    if (node == NULL) return NULL;
+    poly_nodes[inode] = node;
+  }
+  return FindFace(poly_nodes);
+}
 
-const SMDS_MeshFace* SMDS_Mesh::FindFace (const std::vector<const SMDS_MeshNode *>& nodes)
+const SMDS_MeshFace* SMDS_Mesh::FindFace (const vector<const SMDS_MeshNode *>& nodes)
 {
   return (const SMDS_MeshFace*) FindElement( nodes, SMDSAbs_Face );
 }
@@ -1339,7 +2437,7 @@ const SMDS_MeshFace* SMDS_Mesh::FindFace (const std::vector<const SMDS_MeshNode
  */
 //================================================================================
 
-const SMDS_MeshElement* SMDS_Mesh::FindElement (const std::vector<const SMDS_MeshNode *>& nodes,
+const SMDS_MeshElement* SMDS_Mesh::FindElement (const vector<const SMDS_MeshNode *>& nodes,
                                                 const SMDSAbs_ElementType            type,
                                                 const bool                           noMedium)
 {
@@ -1409,6 +2507,110 @@ int SMDS_Mesh::GetElementsByNodes(const std::vector<const SMDS_MeshNode *>& node
   return foundElems.size();
 }
 
+//=======================================================================
+//function : DumpNodes
+//purpose  :
+//=======================================================================
+
+void SMDS_Mesh::DumpNodes() const
+{
+  SMDS_NodeIteratorPtr itnode=nodesIterator();
+  while(itnode->more()) ; //MESSAGE(itnode->next());
+}
+
+//=======================================================================
+//function : Dump0DElements
+//purpose  :
+//=======================================================================
+void SMDS_Mesh::Dump0DElements() const
+{
+  SMDS_ElemIteratorPtr it0d = elementsIterator(SMDSAbs_0DElement);
+  while(it0d->more()) ; //MESSAGE(it0d->next());
+}
+
+//=======================================================================
+//function : DumpEdges
+//purpose  :
+//=======================================================================
+
+void SMDS_Mesh::DumpEdges() const
+{
+  SMDS_EdgeIteratorPtr itedge=edgesIterator();
+  while(itedge->more()) ; //MESSAGE(itedge->next());
+}
+
+//=======================================================================
+//function : DumpFaces
+//purpose  :
+//=======================================================================
+
+void SMDS_Mesh::DumpFaces() const
+{
+  SMDS_FaceIteratorPtr itface=facesIterator();
+  while(itface->more()) ; //MESSAGE(itface->next());
+}
+
+//=======================================================================
+//function : DumpVolumes
+//purpose  :
+//=======================================================================
+
+void SMDS_Mesh::DumpVolumes() const
+{
+  SMDS_VolumeIteratorPtr itvol=volumesIterator();
+  while(itvol->more()) ; //MESSAGE(itvol->next());
+}
+
+//=======================================================================
+//function : DebugStats
+//purpose  :
+//=======================================================================
+
+void SMDS_Mesh::DebugStats() const
+{
+  MESSAGE("Debug stats of mesh : ");
+
+  MESSAGE("===== NODES ====="<<NbNodes());
+  MESSAGE("===== 0DELEMS ====="<<Nb0DElements());
+  MESSAGE("===== EDGES ====="<<NbEdges());
+  MESSAGE("===== FACES ====="<<NbFaces());
+  MESSAGE("===== VOLUMES ====="<<NbVolumes());
+
+  MESSAGE("End Debug stats of mesh ");
+
+  //#ifdef DEB
+
+  SMDS_NodeIteratorPtr itnode=nodesIterator();
+  int sizeofnodes = 0;
+  int sizeoffaces = 0;
+
+  while(itnode->more())
+  {
+    const SMDS_MeshNode *node = itnode->next();
+
+    sizeofnodes += sizeof(*node);
+
+    SMDS_ElemIteratorPtr it = node->GetInverseElementIterator();
+    while(it->more())
+    {
+      const SMDS_MeshElement *me = it->next();
+      sizeofnodes += sizeof(me);
+    }
+  }
+
+  SMDS_FaceIteratorPtr itface=facesIterator();
+  while(itface->more())
+  {
+    const SMDS_MeshElement *face = itface->next();
+    sizeoffaces += sizeof(*face);
+  }
+
+  MESSAGE("total size of node elements = " << sizeofnodes);;
+  MESSAGE("total size of face elements = " << sizeoffaces);;
+
+  //#endif
+}
+
 ///////////////////////////////////////////////////////////////////////////////
 /// Return the number of nodes
 ///////////////////////////////////////////////////////////////////////////////
@@ -1479,35 +2681,91 @@ int SMDS_Mesh::NbSubMesh() const
 ///////////////////////////////////////////////////////////////////////////////
 SMDS_Mesh::~SMDS_Mesh()
 {
-  std::list<SMDS_Mesh*>::iterator itc=myChildren.begin();
+  list<SMDS_Mesh*>::iterator itc=myChildren.begin();
   while(itc!=myChildren.end())
   {
     delete *itc;
     itc++;
   }
 
-  delete myNodeFactory;
-  delete myCellFactory;
-
+  if(myParent==NULL)
+  {
+    delete myNodeIDFactory;
+    delete myElementIDFactory;
+  }
+  else
+  {
+    SMDS_ElemIteratorPtr eIt = elementsIterator();
+    while ( eIt->more() )
+      {
+        const SMDS_MeshElement *elem = eIt->next();
+        myElementIDFactory->ReleaseID(elem->GetID(), elem->getVtkId());
+      }
+    SMDS_NodeIteratorPtr itn = nodesIterator();
+    while (itn->more())
+      {
+        const SMDS_MeshNode *node = itn->next();
+        ((SMDS_MeshNode*)node)->SetPosition(SMDS_SpacePosition::originSpacePosition());
+        myNodeIDFactory->ReleaseID(node->GetID(), node->getVtkId());
+      }
+  }
   myGrid->Delete();
+
+  delete myNodePool;
+  delete myVolumePool;
+  delete myFacePool;
+  delete myEdgePool;
+  delete myBallPool;
 }
 
-//================================================================================
-/*!
- * \brief Clear all data
- */
-//================================================================================
+//================================================================================
+/*!
+ * \brief Clear all data
+ */
+//================================================================================
+
+void SMDS_Mesh::Clear()
+{
+  if (myParent!=NULL)
+  {
+    SMDS_ElemIteratorPtr eIt = elementsIterator();
+    while ( eIt->more() )
+    {
+      const SMDS_MeshElement *elem = eIt->next();
+      myElementIDFactory->ReleaseID(elem->GetID(), elem->getVtkId());
+    }
+    SMDS_NodeIteratorPtr itn = nodesIterator();
+    while (itn->more())
+    {
+      const SMDS_MeshNode *node = itn->next();
+      myNodeIDFactory->ReleaseID(node->GetID(), node->getVtkId());
+    }
+  }
+  else
+  {
+    myNodeIDFactory->Clear();
+    myElementIDFactory->Clear();
+  }
+
+  myVolumePool->clear();
+  myFacePool->clear();
+  myEdgePool->clear();
+  myBallPool->clear();
 
-void SMDS_Mesh::Clear()
-{
-  std::set< SMDS_ElementHolder* >::iterator holder = myElemHolders.begin();
-  for ( ; holder != myElemHolders.end(); ++holder )
-    (*holder)->clear();
+  clearVector( myCells );
+  clearVector( myCellIdVtkToSmds );
 
-  myNodeFactory->Clear();
-  myCellFactory->Clear();
+  SMDS_NodeIteratorPtr itn = nodesIterator();
+  while (itn->more())
+  {
+    SMDS_MeshNode *node = (SMDS_MeshNode*)(itn->next());
+    node->SetPosition(SMDS_SpacePosition::originSpacePosition());
+    //myNodePool->destroy(node);
+  }
+  myNodePool->clear();
+  clearVector( myNodes );
 
-  std::list<SMDS_Mesh*>::iterator itc=myChildren.begin();
+  list<SMDS_Mesh*>::iterator itc=myChildren.begin();
   while(itc!=myChildren.end())
     (*itc)->Clear();
 
@@ -1531,29 +2789,182 @@ void SMDS_Mesh::Clear()
   myGrid->DeleteLinks();
 }
 
+///////////////////////////////////////////////////////////////////////////////
+/// Return true if this mesh create faces with edges.
+/// A false returned value mean that faces are created with nodes. A concequence
+/// is, iteration on edges (SMDS_Element::edgesIterator) will be unavailable.
+///////////////////////////////////////////////////////////////////////////////
+bool SMDS_Mesh::hasConstructionEdges()
+{
+  return myHasConstructionEdges;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+/// Return true if this mesh create volumes with faces
+/// A false returned value mean that volumes are created with nodes or edges.
+/// (see hasConstructionEdges)
+/// A concequence is, iteration on faces (SMDS_Element::facesIterator) will be
+/// unavailable.
+///////////////////////////////////////////////////////////////////////////////
+bool SMDS_Mesh::hasConstructionFaces()
+{
+  return myHasConstructionFaces;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+/// Return true if nodes are linked to the finit elements, they are belonging to.
+/// Currently, It always return true.
+///////////////////////////////////////////////////////////////////////////////
+bool SMDS_Mesh::hasInverseElements()
+{
+  return myHasInverseElements;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+/// Make this mesh creating construction edges (see hasConstructionEdges)
+/// @param b true to have construction edges, else false.
+///////////////////////////////////////////////////////////////////////////////
+void SMDS_Mesh::setConstructionEdges(bool b)
+{
+  myHasConstructionEdges=b;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+/// Make this mesh creating construction faces (see hasConstructionFaces)
+/// @param b true to have construction faces, else false.
+///////////////////////////////////////////////////////////////////////////////
+void SMDS_Mesh::setConstructionFaces(bool b)
+{
+  myHasConstructionFaces=b;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+/// Make this mesh creating link from nodes to elements (see hasInverseElements)
+/// @param b true to link nodes to elements, else false.
+///////////////////////////////////////////////////////////////////////////////
+void SMDS_Mesh::setInverseElements(bool b)
+{
+  if(!b) MESSAGE("Error : inverseElement=false not implemented");
+  myHasInverseElements=b;
+}
+
+namespace {
+
+  //================================================================================
+  /*!
+   * \brief Iterator on elements in id increasing order
+   */
+  //================================================================================
+
+  template <typename ELEM=const SMDS_MeshElement*>
+  class IdSortedIterator : public SMDS_Iterator<ELEM>
+  {
+    SMDS_MeshElementIDFactory&       myIDFact;
+    int                              myID, myMaxID, myNbFound, myTotalNb;
+    SMDSAbs_ElementType              myType;
+    ELEM                             myElem;
+
+  public:
+    IdSortedIterator(const SMDS_MeshElementIDFactory& fact,
+                     const SMDSAbs_ElementType        type, // SMDSAbs_All NOT allowed!!! 
+                     const int                        totalNb)
+      :myIDFact( const_cast<SMDS_MeshElementIDFactory&>(fact) ),
+       myID(1), myMaxID( myIDFact.GetMaxID() ),myNbFound(0), myTotalNb( totalNb ),
+       myType( type ),
+       myElem(0)
+    {
+      next();
+    }
+    bool more()
+    {
+      return myElem;
+    }
+    ELEM next()
+    {
+      ELEM current = myElem;
+
+      for ( myElem = 0;  !myElem && myNbFound < myTotalNb && myID <= myMaxID; ++myID )
+        if ((myElem = (ELEM) myIDFact.MeshElement( myID ))
+            && myElem->GetType() != myType )
+          myElem = 0;
+
+      myNbFound += bool(myElem);
+
+      return current;
+    }
+  };
+
+  //================================================================================
+  /*!
+   * \brief Iterator on vector of elements, possibly being resized while iteration
+   */
+  //================================================================================
+
+  template<typename RETURN_VALUE,
+           typename VECTOR_VALUE=SMDS_MeshCell*,
+           typename VALUE_FILTER=SMDS::NonNullFilter<VECTOR_VALUE> >
+  class ElemVecIterator: public SMDS_Iterator<RETURN_VALUE>
+  {
+    const std::vector<VECTOR_VALUE>& _vector;
+    size_t                           _index;
+    bool                             _more;
+    VALUE_FILTER                     _filter;
+  public:
+    ElemVecIterator(const std::vector<VECTOR_VALUE>& vec,
+                    const VALUE_FILTER&              filter=VALUE_FILTER() )
+      :_vector( vec ), _index(0), _more( !vec.empty() ), _filter( filter )
+    {
+      if ( _more && !_filter( _vector[ _index ]))
+        next();
+    }
+    virtual bool more()
+    {
+      return _more;
+    }
+    virtual RETURN_VALUE next()
+    {
+      if ( !_more ) return NULL;
+      VECTOR_VALUE current = _vector[ _index ];
+      _more = 0;
+      while ( !_more && ++_index < _vector.size() )
+        _more = _filter( _vector[ _index ]);
+      return (RETURN_VALUE) current;
+    }
+  };
+}
+
 ///////////////////////////////////////////////////////////////////////////////
 /// Return an iterator on nodes of the current mesh factory
 ///////////////////////////////////////////////////////////////////////////////
 
-SMDS_NodeIteratorPtr SMDS_Mesh::nodesIterator() const
+SMDS_NodeIteratorPtr SMDS_Mesh::nodesIterator(bool idInceasingOrder) const
 {
-  return myNodeFactory->GetIterator< SMDS_NodeIterator >( new SMDS_MeshElement::NonNullFilter );
+  // naturally always sorted by ID
+  typedef ElemVecIterator<const SMDS_MeshNode*, SMDS_MeshNode*> TIterator;
+  return SMDS_NodeIteratorPtr( new TIterator(myNodes));
 }
 
 SMDS_ElemIteratorPtr SMDS_Mesh::elementGeomIterator(SMDSAbs_GeometryType type) const
 {
-  return myCellFactory->GetIterator< SMDS_ElemIterator >( new SMDS_MeshElement::GeomFilter( type ),
-                                                          myInfo.NbElements( type ));
+  // naturally always sorted by ID
+  typedef ElemVecIterator
+    < const SMDS_MeshElement*, SMDS_MeshCell*, SMDS_MeshElement::GeomFilter > TIterator;
+  return SMDS_ElemIteratorPtr
+    (new TIterator(myCells, SMDS_MeshElement::GeomFilter( type )));
 }
 
 SMDS_ElemIteratorPtr SMDS_Mesh::elementEntityIterator(SMDSAbs_EntityType type) const
 {
   if ( type == SMDSEntity_Node )
   {
-    return myNodeFactory->GetIterator< SMDS_ElemIterator >( new SMDS_MeshElement::NonNullFilter );
+    typedef ElemVecIterator<const SMDS_MeshElement*, SMDS_MeshNode*> TIterator;
+    return SMDS_ElemIteratorPtr( new TIterator(myNodes));
   }
-  return myCellFactory->GetIterator<SMDS_ElemIterator>( new SMDS_MeshElement::EntityFilter( type ),
-                                                        myInfo.NbElements( type ));
+  // naturally always sorted by ID
+  typedef ElemVecIterator
+    < const SMDS_MeshElement*, SMDS_MeshCell*, SMDS_MeshElement::EntityFilter > TIterator;
+  return SMDS_ElemIteratorPtr
+    (new TIterator(myCells, SMDS_MeshElement::EntityFilter( type )));
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -1561,18 +2972,20 @@ SMDS_ElemIteratorPtr SMDS_Mesh::elementEntityIterator(SMDSAbs_EntityType type) c
 ///////////////////////////////////////////////////////////////////////////////
 SMDS_ElemIteratorPtr SMDS_Mesh::elementsIterator(SMDSAbs_ElementType type) const
 {
-  typedef SMDS_ElemIterator TIterator;
+  // naturally always sorted by ID
   switch ( type ) {
 
   case SMDSAbs_All:
-    return myCellFactory->GetIterator< TIterator >( new SMDS_MeshElement::NonNullFilter );
+    return SMDS_ElemIteratorPtr (new ElemVecIterator<const SMDS_MeshElement*>(myCells));
 
   case SMDSAbs_Node:
-    return myNodeFactory->GetIterator< TIterator >( new SMDS_MeshElement::NonNullFilter );
+    return SMDS_ElemIteratorPtr
+      ( new ElemVecIterator<const SMDS_MeshElement*, SMDS_MeshNode*>( myNodes ));
 
   default:
-    return myCellFactory->GetIterator< TIterator >( new SMDS_MeshElement::TypeFilter( type ),
-                                                    myInfo.NbElements( type ));
+    typedef ElemVecIterator
+      < const SMDS_MeshElement*, SMDS_MeshCell*, SMDS_MeshElement::TypeFilter > TIterator;
+    return SMDS_ElemIteratorPtr (new TIterator(myCells, SMDS_MeshElement::TypeFilter( type )));
   }
   return SMDS_ElemIteratorPtr();
 }
@@ -1581,113 +2994,118 @@ SMDS_ElemIteratorPtr SMDS_Mesh::elementsIterator(SMDSAbs_ElementType type) const
 ///Return an iterator on edges of the current mesh.
 ///////////////////////////////////////////////////////////////////////////////
 
-SMDS_EdgeIteratorPtr SMDS_Mesh::edgesIterator() const
+SMDS_EdgeIteratorPtr SMDS_Mesh::edgesIterator(bool idInceasingOrder) const
 {
-  typedef SMDS_EdgeIterator TIterator;
-  return myCellFactory->GetIterator< TIterator >( new SMDS_MeshElement::TypeFilter( SMDSAbs_Edge ),
-                                                  myInfo.NbEdges());
+  // naturally always sorted by ID
+  typedef ElemVecIterator
+    < const SMDS_MeshEdge*, SMDS_MeshCell*, SMDS_MeshElement::TypeFilter > TIterator;
+  return SMDS_EdgeIteratorPtr
+    (new TIterator(myCells, SMDS_MeshElement::TypeFilter( SMDSAbs_Edge )));
 }
 
 ///////////////////////////////////////////////////////////////////////////////
 ///Return an iterator on faces of the current mesh.
 ///////////////////////////////////////////////////////////////////////////////
 
-SMDS_FaceIteratorPtr SMDS_Mesh::facesIterator() const
+SMDS_FaceIteratorPtr SMDS_Mesh::facesIterator(bool idInceasingOrder) const
 {
-  typedef SMDS_FaceIterator TIterator;
-  return myCellFactory->GetIterator< TIterator >( new SMDS_MeshElement::TypeFilter( SMDSAbs_Face ),
-                                                  myInfo.NbFaces());
+  // naturally always sorted by ID
+  typedef ElemVecIterator
+    < const SMDS_MeshFace*, SMDS_MeshCell*, SMDS_MeshElement::TypeFilter > TIterator;
+  return SMDS_FaceIteratorPtr
+    (new TIterator(myCells, SMDS_MeshElement::TypeFilter( SMDSAbs_Face )));
 }
 
 ///////////////////////////////////////////////////////////////////////////////
 ///Return an iterator on volumes of the current mesh.
 ///////////////////////////////////////////////////////////////////////////////
 
-SMDS_VolumeIteratorPtr SMDS_Mesh::volumesIterator() const
-{
-  typedef SMDS_VolumeIterator TIterator;
-  return
-    myCellFactory->GetIterator< TIterator >( new SMDS_MeshElement::TypeFilter( SMDSAbs_Volume ),
-                                             myInfo.NbVolumes());
-}
-
-SMDS_NodeIteratorPtr SMDS_Mesh::shapeNodesIterator(int shapeID, size_t nbElemsToReturn) const
-{
-  return myNodeFactory->GetShapeIterator< SMDS_NodeIterator >( shapeID, nbElemsToReturn );
-}
-
-SMDS_ElemIteratorPtr SMDS_Mesh::shapeElementsIterator(int shapeID, size_t nbElemsToReturn) const
+SMDS_VolumeIteratorPtr SMDS_Mesh::volumesIterator(bool idInceasingOrder) const
 {
-  return myCellFactory->GetShapeIterator< SMDS_ElemIterator >( shapeID, nbElemsToReturn );
+  // naturally always sorted by ID
+  typedef ElemVecIterator
+    < const SMDS_MeshVolume*, SMDS_MeshCell*, SMDS_MeshElement::TypeFilter > TIterator;
+  return SMDS_VolumeIteratorPtr
+    (new TIterator(myCells, SMDS_MeshElement::TypeFilter( SMDSAbs_Volume )));
 }
 
 ///////////////////////////////////////////////////////////////////////////////
 /// Do intersection of sets (more than 2)
 ///////////////////////////////////////////////////////////////////////////////
-static std::set<const SMDS_MeshElement*> *
-intersectionOfSets( std::set<const SMDS_MeshElement*> vs[], int numberOfSets )
+static set<const SMDS_MeshElement*> * intersectionOfSets(
+        set<const SMDS_MeshElement*> vs[], int numberOfSets)
 {
-  std::set<const SMDS_MeshElement*>* rsetA = new std::set<const SMDS_MeshElement*>(vs[0]);
-  std::set<const SMDS_MeshElement*>* rsetB;
+        set<const SMDS_MeshElement*>* rsetA=new set<const SMDS_MeshElement*>(vs[0]);
+        set<const SMDS_MeshElement*>* rsetB;
 
-  for(int i=0; i<numberOfSets-1; i++)
-  {
-    rsetB = new std::set<const SMDS_MeshElement*>();
-    set_intersection(rsetA->begin(), rsetA->end(),
-                     vs[i+1].begin(), vs[i+1].end(),
-                     inserter(*rsetB, rsetB->begin()));
-    delete rsetA;
-    rsetA=rsetB;
-  }
-  return rsetA;
+        for(int i=0; i<numberOfSets-1; i++)
+        {
+                rsetB=new set<const SMDS_MeshElement*>();
+                set_intersection(
+                        rsetA->begin(), rsetA->end(),
+                        vs[i+1].begin(), vs[i+1].end(),
+                        inserter(*rsetB, rsetB->begin()));
+                delete rsetA;
+                rsetA=rsetB;
+        }
+        return rsetA;
 }
+
 ///////////////////////////////////////////////////////////////////////////////
 /// Return the list of finite elements owning the given element: elements
 /// containing all the nodes of the given element, for instance faces and
 /// volumes containing a given edge.
 ///////////////////////////////////////////////////////////////////////////////
-static std::set<const SMDS_MeshElement*> * getFinitElements(const SMDS_MeshElement * element)
+static set<const SMDS_MeshElement*> * getFinitElements(const SMDS_MeshElement * element)
 {
   int numberOfSets=element->NbNodes();
-  std::set<const SMDS_MeshElement*> *initSet = new std::set<const SMDS_MeshElement*>[numberOfSets];
+  set<const SMDS_MeshElement*> *initSet = new set<const SMDS_MeshElement*>[numberOfSets];
 
-  SMDS_NodeIteratorPtr itNodes = element->nodeIterator();
+  SMDS_ElemIteratorPtr itNodes=element->nodesIterator();
 
   int i = 0;
   while ( itNodes->more() )
   {
-    const SMDS_MeshNode *   n = itNodes->next();
-    for ( SMDS_ElemIteratorPtr itFe = n->GetInverseElementIterator(); itFe->more(); )
-      initSet[i].insert( itFe->next() );
+    const SMDS_MeshElement* node = itNodes->next();
+    MYASSERT(node);
+    const SMDS_MeshNode * n=static_cast<const SMDS_MeshNode*>(node);
+    SMDS_ElemIteratorPtr itFe = n->GetInverseElementIterator();
+
+    while ( itFe->more() )
+    {
+      const SMDS_MeshElement* elem = itFe->next();
+      MYASSERT(elem);
+      initSet[i].insert(elem);
+    }
+
     i++;
   }
-  std::set<const SMDS_MeshElement*> *retSet = intersectionOfSets( initSet, numberOfSets );
+  set<const SMDS_MeshElement*> *retSet = intersectionOfSets( initSet, numberOfSets );
   delete [] initSet;
   return retSet;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
-/// Return the std::list of nodes used only by the given elements
+/// Return the list of nodes used only by the given elements
 ///////////////////////////////////////////////////////////////////////////////
-static
-std::set<const SMDS_MeshElement*> *getExclusiveNodes(std::set<const SMDS_MeshElement*>& elements)
+static set<const SMDS_MeshElement*> * getExclusiveNodes(set<const SMDS_MeshElement*>& elements)
 {
-  std::set<const SMDS_MeshElement*> *           toReturn = new std::set<const SMDS_MeshElement*>();
-  std::set<const SMDS_MeshElement*>::iterator itElements = elements.begin();
+  set<const SMDS_MeshElement*> * toReturn=new set<const SMDS_MeshElement*>();
+  set<const SMDS_MeshElement*>::iterator itElements=elements.begin();
 
-  while( itElements != elements.end() )
+  while(itElements!=elements.end())
   {
-    SMDS_NodeIteratorPtr itNodes = (*itElements)->nodeIterator();
+    SMDS_ElemIteratorPtr itNodes = (*itElements)->nodesIterator();
     itElements++;
 
-    while( itNodes->more() )
+    while(itNodes->more())
     {
-      const SMDS_MeshNode *   n = itNodes->next();
+      const SMDS_MeshNode * n=static_cast<const SMDS_MeshNode*>(itNodes->next());
       SMDS_ElemIteratorPtr itFe = n->GetInverseElementIterator();
-      std::set<const SMDS_MeshElement*> s;
-      while ( itFe->more() )
-        s.insert( itFe->next() );
-      if ( s == elements ) toReturn->insert(n);
+      set<const SMDS_MeshElement*> s;
+      while(itFe->more())
+        s.insert(itFe->next());
+      if(s==elements) toReturn->insert(n);
     }
   }
   return toReturn;
@@ -1699,14 +3117,14 @@ std::set<const SMDS_MeshElement*> *getExclusiveNodes(std::set<const SMDS_MeshEle
 ///@param element The element were to search matching children
 ///@param nodes The nodes that the children must have to be selected
 ///////////////////////////////////////////////////////////////////////////////
-void SMDS_Mesh::addChildrenWithNodes(std::set<const SMDS_MeshElement*>& setOfChildren,
-                                     const SMDS_MeshElement *           element,
-                                     std::set<const SMDS_MeshElement*>& nodes)
+void SMDS_Mesh::addChildrenWithNodes(set<const SMDS_MeshElement*>& setOfChildren,
+                                     const SMDS_MeshElement *      element,
+                                     set<const SMDS_MeshElement*>& nodes)
 {
   switch(element->GetType())
   {
   case SMDSAbs_Node:
-    throw SALOME_Exception("Internal Error: This should not happen");
+    MESSAGE("Internal Error: This should not happen");
     break;
   case SMDSAbs_0DElement:
   case SMDSAbs_Ball:
@@ -1738,8 +3156,28 @@ void SMDS_Mesh::addChildrenWithNodes(std::set<const SMDS_MeshElement*>& setOfChi
         break;
       }
     }
+    if(hasConstructionEdges())
+    {
+      SMDS_ElemIteratorPtr ite=element->edgesIterator();
+      while(ite->more())
+        addChildrenWithNodes(setOfChildren, ite->next(), nodes);
+    }
   } break;
   case SMDSAbs_Volume:
+  {
+    if(hasConstructionFaces())
+    {
+      SMDS_ElemIteratorPtr ite=element->facesIterator();
+      while(ite->more())
+        addChildrenWithNodes(setOfChildren, ite->next(), nodes);
+    }
+    else if(hasConstructionEdges())
+    {
+      SMDS_ElemIteratorPtr ite=element->edgesIterator();
+      while(ite->more())
+        addChildrenWithNodes(setOfChildren, ite->next(), nodes);
+    }
+  }
   case SMDSAbs_NbElementTypes:
   case SMDSAbs_All: break;
   }
@@ -1750,10 +3188,10 @@ void SMDS_Mesh::addChildrenWithNodes(std::set<const SMDS_MeshElement*>& setOfChi
 ///@param removenodes if true remaining nodes will be removed
 ///////////////////////////////////////////////////////////////////////////////
 void SMDS_Mesh::RemoveElement(const SMDS_MeshElement * elem,
-                              const bool               removenodes)
+                              const bool removenodes)
 {
-  std::vector<const SMDS_MeshElement *> removedElems;
-  std::vector<const SMDS_MeshElement *> removedNodes;
+  list<const SMDS_MeshElement *> removedElems;
+  list<const SMDS_MeshElement *> removedNodes;
   RemoveElement( elem, removedElems, removedNodes, removenodes );
 }
 
@@ -1763,91 +3201,169 @@ void SMDS_Mesh::RemoveElement(const SMDS_MeshElement * elem,
 ///@param removedNodes to be filled with all removed nodes
 ///@param removenodes if true remaining nodes will be removed
 ///////////////////////////////////////////////////////////////////////////////
-void SMDS_Mesh::RemoveElement(const SMDS_MeshElement *               elem,
-                              std::vector<const SMDS_MeshElement *>& removedElems,
-                              std::vector<const SMDS_MeshElement *>& removedNodes,
-                              bool                                   removenodes)
+void SMDS_Mesh::RemoveElement(const SMDS_MeshElement *        elem,
+                              list<const SMDS_MeshElement *>& removedElems,
+                              list<const SMDS_MeshElement *>& removedNodes,
+                              bool                            removenodes)
 {
   // get finite elements built on elem
-  std::set<const SMDS_MeshElement*> * s1;
+  set<const SMDS_MeshElement*> * s1;
   if (    (elem->GetType() == SMDSAbs_0DElement)
-          ||  (elem->GetType() == SMDSAbs_Ball)
-          ||  (elem->GetType() == SMDSAbs_Edge)
-          ||  (elem->GetType() == SMDSAbs_Face)
-          ||  (elem->GetType() == SMDSAbs_Volume) )
-  {
-    s1 = new std::set<const SMDS_MeshElement*> ();
-    s1->insert(elem);
-  }
+      || ((elem->GetType() == SMDSAbs_Edge) && !hasConstructionEdges())
+      || ((elem->GetType() == SMDSAbs_Face) && !hasConstructionFaces())
+      ||  (elem->GetType() == SMDSAbs_Volume) )
+    {
+      s1 = new set<const SMDS_MeshElement*> ();
+      s1->insert(elem);
+    }
   else
     s1 = getFinitElements(elem);
 
   // get exclusive nodes (which would become free afterwards)
-  std::set<const SMDS_MeshElement*> * s2;
+  set<const SMDS_MeshElement*> * s2;
   if (elem->GetType() == SMDSAbs_Node) // a node is removed
-  {
-    // do not remove nodes except elem
-    s2 = new std::set<const SMDS_MeshElement*> ();
-    s2->insert(elem);
-    removenodes = true;
-  }
+    {
+      // do not remove nodes except elem
+      s2 = new set<const SMDS_MeshElement*> ();
+      s2->insert(elem);
+      removenodes = true;
+    }
   else
     s2 = getExclusiveNodes(*s1);
 
   // form the set of finite and construction elements to remove
-  std::set<const SMDS_MeshElement*> s3;
-  std::set<const SMDS_MeshElement*>::iterator it = s1->begin();
+  set<const SMDS_MeshElement*> s3;
+  set<const SMDS_MeshElement*>::iterator it = s1->begin();
   while (it != s1->end())
-  {
-    addChildrenWithNodes(s3, *it, *s2);
-    s3.insert(*it);
-    it++;
-  }
+    {
+      addChildrenWithNodes(s3, *it, *s2);
+      s3.insert(*it);
+      it++;
+    }
   if (elem->GetType() != SMDSAbs_Node)
     s3.insert(elem);
 
   // remove finite and construction elements
-  for( it = s3.begin();it != s3.end(); ++it )
-  {
-    // Remove element from <InverseElements> of its nodes
-    SMDS_NodeIteratorPtr itn = (*it)->nodeIterator();
-    while (itn->more())
+  it = s3.begin();
+  while (it != s3.end())
     {
-      SMDS_MeshNode * n = const_cast<SMDS_MeshNode *> (itn->next());
-      n->RemoveInverseElement((*it));
-    }
-
-    int vtkid = (*it)->GetVtkID();
-
-    switch ((*it)->GetType()) {
-    case SMDSAbs_Node:
-      throw SALOME_Exception(LOCALIZED("Internal Error: This should not happen"));
-      break;
-    case SMDSAbs_Edge:      myInfo.RemoveEdge(*it);   break;
-    case SMDSAbs_Face:      myInfo.RemoveFace(*it);   break;
-    case SMDSAbs_Volume:    myInfo.RemoveVolume(*it); break;
-    case SMDSAbs_Ball:      myInfo.myNbBalls--;       break;
-    case SMDSAbs_0DElement: myInfo.myNb0DElements--;  break;
-    case SMDSAbs_All: // avoid compilation warning
-    case SMDSAbs_NbElementTypes: break;
-    }
-
-    myCellFactory->Free( static_cast< const SMDS_MeshCell*>( *it ));
+      // Remove element from <InverseElements> of its nodes
+      SMDS_ElemIteratorPtr itn = (*it)->nodesIterator();
+      while (itn->more())
+      {
+        SMDS_MeshNode * n = static_cast<SMDS_MeshNode *> (const_cast<SMDS_MeshElement *> (itn->next()));
+        n->RemoveInverseElement((*it));
+      }
+      int IdToRemove = (*it)->GetID();
+      int vtkid = (*it)->getVtkId();
+      switch ((*it)->GetType())
+      {
+        case SMDSAbs_Node:
+          MYASSERT("Internal Error: This should not happen");
+          break;
+        case SMDSAbs_0DElement:
+          if (IdToRemove >= 0)
+            {
+              myCells[IdToRemove] = 0; // -PR- ici ou dans myElementIDFactory->ReleaseID ?
+              myInfo.remove(*it);
+            }
+          removedElems.push_back((*it));
+          myElementIDFactory->ReleaseID(IdToRemove, vtkid);
+          delete (*it);
+          break;
+        case SMDSAbs_Edge:
+          if (IdToRemove >= 0)
+            {
+              myCells[IdToRemove] = 0;
+              myInfo.RemoveEdge(*it);
+            }
+          removedElems.push_back((*it));
+          myElementIDFactory->ReleaseID(IdToRemove, vtkid);
+          if (const SMDS_VtkEdge* vtkElem = dynamic_cast<const SMDS_VtkEdge*>(*it))
+            myEdgePool->destroy((SMDS_VtkEdge*) vtkElem);
+          else {
+            ((SMDS_MeshElement*) *it)->init( 0, -1, -1 ); // avoid reuse
+            delete (*it);
+          }
+          break;
+        case SMDSAbs_Face:
+          if (IdToRemove >= 0)
+            {
+              myCells[IdToRemove] = 0;
+              myInfo.RemoveFace(*it);
+            }
+          removedElems.push_back((*it));
+          myElementIDFactory->ReleaseID(IdToRemove, vtkid);
+          if (const SMDS_VtkFace* vtkElem = dynamic_cast<const SMDS_VtkFace*>(*it))
+            myFacePool->destroy((SMDS_VtkFace*) vtkElem);
+          else {
+            ((SMDS_MeshElement*) *it)->init( 0, -1, -1 ); // avoid reuse
+            delete (*it);
+          }
+          break;
+        case SMDSAbs_Volume:
+          if (IdToRemove >= 0)
+            {
+              myCells[IdToRemove] = 0;
+              myInfo.RemoveVolume(*it);
+            }
+          removedElems.push_back((*it));
+          myElementIDFactory->ReleaseID(IdToRemove, vtkid);
+          if (const SMDS_VtkVolume* vtkElem = dynamic_cast<const SMDS_VtkVolume*>(*it))
+            myVolumePool->destroy((SMDS_VtkVolume*) vtkElem);
+          else {
+            ((SMDS_MeshElement*) *it)->init( 0, -1, -1 ); // avoid reuse
+            delete (*it);
+          }
+          break;
+        case SMDSAbs_Ball:
+          if (IdToRemove >= 0)
+            {
+              myCells[IdToRemove] = 0;
+              myInfo.remove(*it);
+            }
+          removedElems.push_back((*it));
+          myElementIDFactory->ReleaseID(IdToRemove, vtkid);
+          if (const SMDS_BallElement* vtkElem = dynamic_cast<const SMDS_BallElement*>(*it))
+            myBallPool->destroy(const_cast<SMDS_BallElement*>( vtkElem ));
+          else {
+            ((SMDS_MeshElement*) *it)->init( 0, -1, -1 ); // avoid reuse
+            delete (*it);
+          }
+          break;
 
-    if (vtkid >= 0)
-    {
-      this->myGrid->GetCellTypesArray()->SetValue(vtkid, VTK_EMPTY_CELL);
+        case SMDSAbs_All: // avoid compilation warning
+        case SMDSAbs_NbElementTypes: break;
+      }
+      if (vtkid >= 0)
+      {
+        this->myGrid->GetCellTypesArray()->SetValue(vtkid, VTK_EMPTY_CELL);
+      }
+      it++;
     }
-  }
 
   // remove exclusive (free) nodes
   if (removenodes)
   {
-    for ( it = s2->begin(); it != s2->end(); ++it )
+    it = s2->begin();
+    while (it != s2->end())
     {
-      myInfo.myNbNodes--;
-      myNodeFactory->Free( (*it) );
+      int IdToRemove = (*it)->GetID();
+      if (IdToRemove >= 0)
+      {
+        myNodes[IdToRemove] = 0;
+        myInfo.myNbNodes--;
+      }
+      myNodeIDFactory->ReleaseID((*it)->GetID(), (*it)->getVtkId());
       removedNodes.push_back((*it));
+      if (const SMDS_MeshNode* vtkElem = dynamic_cast<const SMDS_MeshNode*>(*it))
+      {
+        ((SMDS_MeshNode*)vtkElem)->SetPosition(SMDS_SpacePosition::originSpacePosition());
+        myNodePool->destroy((SMDS_MeshNode*) vtkElem);
+      }
+      else
+        delete (*it);
+      it++;
     }
   }
 
@@ -1861,60 +3377,95 @@ void SMDS_Mesh::RemoveElement(const SMDS_MeshElement *               elem,
 ///////////////////////////////////////////////////////////////////////////////
 void SMDS_Mesh::RemoveFreeElement(const SMDS_MeshElement * elem)
 {
-  const int           vtkId = elem->GetVtkID();
+  int elemId = elem->GetID();
+  int  vtkId = elem->getVtkId();
   SMDSAbs_ElementType aType = elem->GetType();
+  SMDS_MeshElement*  todest = (SMDS_MeshElement*)(elem);
   if ( aType == SMDSAbs_Node )
   {
     // only free node can be removed by this method
-    const SMDS_MeshNode* n = static_cast<const SMDS_MeshNode*>( elem );
+    const SMDS_MeshNode* n = static_cast<SMDS_MeshNode*>(todest);
     if ( n->NbInverseElements() == 0 ) { // free node
+      myNodes[elemId] = 0;
       myInfo.myNbNodes--;
-      myNodeFactory->Free( n );
-    }
-    else
-    {
-      throw SALOME_Exception( LOCALIZED( "RemoveFreeElement: not a free node" ));
+      ((SMDS_MeshNode*) n)->SetPosition(SMDS_SpacePosition::originSpacePosition());
+      ((SMDS_MeshNode*) n)->SMDS_MeshElement::init( 0, -1, -1 ); // avoid reuse
+      myNodePool->destroy(static_cast<SMDS_MeshNode*>(todest));
+      myNodeIDFactory->ReleaseID(elemId, vtkId);
     }
   }
   else
   {
+    if (hasConstructionEdges() || hasConstructionFaces())
+      // this methods is only for meshes without descendants
+      return;
+
     // Remove element from <InverseElements> of its nodes
-    SMDS_NodeIteratorPtr itn = elem->nodeIterator();
+    SMDS_ElemIteratorPtr itn = elem->nodesIterator();
     while (itn->more()) {
-      SMDS_MeshNode * n = const_cast<SMDS_MeshNode *>(itn->next());
+      SMDS_MeshNode * n = static_cast<SMDS_MeshNode *>
+        (const_cast<SMDS_MeshElement *>(itn->next()));
       n->RemoveInverseElement(elem);
     }
 
     // in meshes without descendants elements are always free
     switch (aType) {
-    case SMDSAbs_0DElement: myInfo.remove(elem);       break;
-    case SMDSAbs_Edge:      myInfo.RemoveEdge(elem);   break;
-    case SMDSAbs_Face:      myInfo.RemoveFace(elem);   break;
-    case SMDSAbs_Volume:    myInfo.RemoveVolume(elem); break;
-    case SMDSAbs_Ball:      myInfo.remove(elem);       break;
-    default: break;
+    case SMDSAbs_0DElement:
+      myCells[elemId] = 0;
+      myInfo.remove(elem);
+      delete elem;
+      elem = 0;
+      break;
+    case SMDSAbs_Edge:
+      myCells[elemId] = 0;
+      myInfo.RemoveEdge(elem);
+      myEdgePool->destroy(static_cast<SMDS_VtkEdge*>(todest));
+      break;
+    case SMDSAbs_Face:
+      myCells[elemId] = 0;
+      myInfo.RemoveFace(elem);
+      myFacePool->destroy(static_cast<SMDS_VtkFace*>(todest));
+      break;
+    case SMDSAbs_Volume:
+      myCells[elemId] = 0;
+      myInfo.RemoveVolume(elem);
+      myVolumePool->destroy(static_cast<SMDS_VtkVolume*>(todest));
+      break;
+    case SMDSAbs_Ball:
+      myCells[elemId] = 0;
+      myInfo.remove(elem);
+      myBallPool->destroy(static_cast<SMDS_BallElement*>(todest));
+      break;
+    default:
+      break;
     }
-    myCellFactory->Free( elem );
+    myElementIDFactory->ReleaseID(elemId, vtkId);
 
     this->myGrid->GetCellTypesArray()->SetValue(vtkId, VTK_EMPTY_CELL);
+    // --- to do: keep vtkid in a list of reusable cells
+
+    if ( elem )
+      ((SMDS_MeshElement*) elem)->init( 0, -1, -1 ); // avoid reuse
   }
 }
 
-//=======================================================================
 /*!
  * Checks if the element is present in mesh.
+ * Useful to determine dead pointers.
  */
-//=======================================================================
-
 bool SMDS_Mesh::Contains (const SMDS_MeshElement* elem) const
 {
-  if ( !elem || elem->IsNull() )
-    return false;
-
-  if ( elem->GetType() == SMDSAbs_Node )
-    return ( elem == myNodeFactory->FindElement( elem->GetID() ));
-
-  return ( elem == myCellFactory->FindElement( elem->GetID() ));
+  // we should not rely on validity of *elem, so iterate on containers
+  // of all types in the hope of finding <elem> somewhere there
+  SMDS_NodeIteratorPtr itn = nodesIterator();
+  while (itn->more())
+    if (elem == itn->next())
+      return true;
+  SMDS_ElemIteratorPtr ite = elementsIterator();
+  while (ite->more())
+    if (elem == ite->next())
+      return true;
+  return false;
 }
 
 //=======================================================================
@@ -1924,7 +3475,7 @@ bool SMDS_Mesh::Contains (const SMDS_MeshElement* elem) const
 
 int SMDS_Mesh::MaxNodeID() const
 {
-  return myNodeFactory->GetMaxID();
+  return myNodeIDFactory->GetMaxID();
 }
 
 //=======================================================================
@@ -1934,7 +3485,7 @@ int SMDS_Mesh::MaxNodeID() const
 
 int SMDS_Mesh::MinNodeID() const
 {
-  return myNodeFactory->GetMinID();
+  return myNodeIDFactory->GetMinID();
 }
 
 //=======================================================================
@@ -1944,7 +3495,7 @@ int SMDS_Mesh::MinNodeID() const
 
 int SMDS_Mesh::MaxElementID() const
 {
-  return myCellFactory->GetMaxID();
+  return myElementIDFactory->GetMaxID();
 }
 
 //=======================================================================
@@ -1954,7 +3505,7 @@ int SMDS_Mesh::MaxElementID() const
 
 int SMDS_Mesh::MinElementID() const
 {
-  return myCellFactory->GetMinID();
+  return myElementIDFactory->GetMinID();
 }
 
 //=======================================================================
@@ -1962,12 +3513,39 @@ int SMDS_Mesh::MinElementID() const
 //purpose  : Renumber all nodes or elements.
 //=======================================================================
 
-// void SMDS_Mesh::Renumber (const bool isNodes, const int  startID, const int  deltaID)
-// {
-//   if ( deltaID == 0 )
-//     return;
+void SMDS_Mesh::Renumber (const bool isNodes, const int  startID, const int  deltaID)
+{
+  if ( deltaID == 0 )
+    return;
 
-// }
+  SMDS_MeshNodeIDFactory * idFactory =
+    isNodes ? myNodeIDFactory : myElementIDFactory;
+
+  // get existing elements in the order of ID increasing
+  map<int,SMDS_MeshElement*> elemMap;
+  SMDS_ElemIteratorPtr idElemIt = idFactory->elementsIterator();
+  while ( idElemIt->more() ) {
+    SMDS_MeshElement* elem = const_cast<SMDS_MeshElement*>(idElemIt->next());
+    int id = elem->GetID();
+    elemMap.insert(map<int,SMDS_MeshElement*>::value_type(id, elem));
+  }
+  // release their ids
+  map<int,SMDS_MeshElement*>::iterator elemIt = elemMap.begin();
+  idFactory->Clear();
+//   for ( ; elemIt != elemMap.end(); elemIt++ )
+//   {
+//     int id = (*elemIt).first;
+//     idFactory->ReleaseID( id );
+//   }
+  // set new IDs
+  int ID = startID;
+  elemIt = elemMap.begin();
+  for ( ; elemIt != elemMap.end(); elemIt++ )
+  {
+    idFactory->BindID( ID, (*elemIt).second );
+    ID += deltaID;
+  }
+}
 
 //=======================================================================
 //function : GetElementType
@@ -1976,13 +3554,19 @@ int SMDS_Mesh::MinElementID() const
 
 SMDSAbs_ElementType SMDS_Mesh::GetElementType( const int id, const bool iselem ) const
 {
-  const SMDS_MeshElement* elem = 0;
+  SMDS_MeshElement* elem = 0;
   if( iselem )
-    elem = myCellFactory->FindElement( id );
+    elem = myElementIDFactory->MeshElement( id );
   else
-    elem = myNodeFactory->FindElement( id );
+    elem = myNodeIDFactory->MeshElement( id );
 
-  return elem ? elem->GetType() : SMDSAbs_All;
+  if( !elem )
+  {
+    //throw SALOME_Exception(LOCALIZED ("this element isn't exist"));
+    return SMDSAbs_All;
+  }
+  else
+    return elem->GetType();
 }
 
 
@@ -2001,10 +3585,11 @@ SMDSAbs_ElementType SMDS_Mesh::GetElementType( const int id, const bool iselem )
 //=======================================================================
 SMDS_MeshEdge* SMDS_Mesh::AddEdgeWithID(int n1, int n2, int n12, int ID)
 {
-  return SMDS_Mesh::AddEdgeWithID (myNodeFactory->FindNode(n1),
-                                   myNodeFactory->FindNode(n2),
-                                   myNodeFactory->FindNode(n12),
-                                   ID);
+  return SMDS_Mesh::AddEdgeWithID
+    ((SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n2),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n12),
+     ID);
 }
 
 //=======================================================================
@@ -2015,7 +3600,7 @@ SMDS_MeshEdge* SMDS_Mesh::AddEdge(const SMDS_MeshNode* n1,
                                   const SMDS_MeshNode* n2,
                                   const SMDS_MeshNode* n12)
 {
-  return SMDS_Mesh::AddEdgeWithID(n1, n2, n12, myCellFactory->GetFreeID());
+  return SMDS_Mesh::AddEdgeWithID(n1, n2, n12, myElementIDFactory->GetFreeID());
 }
 
 //=======================================================================
@@ -2025,17 +3610,36 @@ SMDS_MeshEdge* SMDS_Mesh::AddEdge(const SMDS_MeshNode* n1,
 SMDS_MeshEdge* SMDS_Mesh::AddEdgeWithID(const SMDS_MeshNode * n1,
                                         const SMDS_MeshNode * n2,
                                         const SMDS_MeshNode * n12,
-                                        int                   ID)
+                                        int ID)
 {
   if ( !n1 || !n2 || !n12 ) return 0;
 
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
+  // --- retrieve nodes ID
+  myNodeIds.resize(3);
+  myNodeIds[0] = n1->getVtkId();
+  myNodeIds[1] = n2->getVtkId();
+  myNodeIds[2] = n12->getVtkId();
+
+  SMDS_MeshEdge * edge = 0;
+  SMDS_VtkEdge *edgevtk = myEdgePool->getNew();
+  edgevtk->init(myNodeIds, this);
+  if (!this->registerElement(ID,edgevtk))
   {
-    cell->init( SMDSEntity_Quad_Edge, /*nbNodes=*/3, n1, n2, n12 );
-    myInfo.myNbQuadEdges++;
-    return static_cast<SMDS_MeshEdge*>( cell );
+    this->myGrid->GetCellTypesArray()->SetValue(edgevtk->getVtkId(), VTK_EMPTY_CELL);
+    myEdgePool->destroy(edgevtk);
+    return 0;
   }
-  return 0;
+  edge = edgevtk;
+  adjustmyCellsCapacity(ID);
+  myCells[ID] = edge;
+  myInfo.myNbQuadEdges++;
+
+  //  if (!registerElement(ID, edge)) {
+  //        RemoveElement(edge, false);
+  //        edge = NULL;
+  //  }
+  return edge;
+
 }
 
 
@@ -2051,7 +3655,7 @@ SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshNode * n1,
                                   const SMDS_MeshNode * n31)
 {
   return SMDS_Mesh::AddFaceWithID(n1,n2,n3,n12,n23,n31,
-                                  myCellFactory->GetFreeID());
+                                  myElementIDFactory->GetFreeID());
 }
 
 //=======================================================================
@@ -2061,13 +3665,14 @@ SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshNode * n1,
 SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(int n1, int n2, int n3,
                                         int n12,int n23,int n31, int ID)
 {
-  return SMDS_Mesh::AddFaceWithID (myNodeFactory->FindNode(n1) ,
-                                   myNodeFactory->FindNode(n2) ,
-                                   myNodeFactory->FindNode(n3) ,
-                                   myNodeFactory->FindNode(n12),
-                                   myNodeFactory->FindNode(n23),
-                                   myNodeFactory->FindNode(n31),
-                                   ID);
+  return SMDS_Mesh::AddFaceWithID
+    ((SMDS_MeshNode *)myNodeIDFactory->MeshElement(n1) ,
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n2) ,
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n3) ,
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n12),
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n23),
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n31),
+     ID);
 }
 
 //=======================================================================
@@ -2082,16 +3687,42 @@ SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(const SMDS_MeshNode * n1,
                                         const SMDS_MeshNode * n31,
                                         int ID)
 {
-  if ( !n1 || !n2 || !n3 || !n12 || !n23 || !n31 ) return 0;
-  if ( NbFaces() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
+  if ( !n1 || !n2 || !n3 || !n12 || !n23 || !n31) return 0;
+  if(hasConstructionEdges()) {
+    // creation quadratic edges - not implemented
+    return 0;
+  }
+  else
   {
-    cell->init( SMDSEntity_Quad_Triangle, /*nbNodes=*/6, n1, n2, n3, n12, n23, n31 );
+    // --- retrieve nodes ID
+    myNodeIds.resize(6);
+    myNodeIds[0] = n1->getVtkId();
+    myNodeIds[1] = n2->getVtkId();
+    myNodeIds[2] = n3->getVtkId();
+    myNodeIds[3] = n12->getVtkId();
+    myNodeIds[4] = n23->getVtkId();
+    myNodeIds[5] = n31->getVtkId();
+
+    SMDS_MeshFace * face = 0;
+    SMDS_VtkFace *facevtk = myFacePool->getNew();
+    facevtk->init(myNodeIds, this);
+    if (!this->registerElement(ID,facevtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(facevtk->getVtkId(), VTK_EMPTY_CELL);
+      myFacePool->destroy(facevtk);
+      return 0;
+    }
+    face = facevtk;
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = face;
     myInfo.myNbQuadTriangles++;
-    return static_cast<SMDS_MeshFace*>( cell );
+
+    //    if (!registerElement(ID, face)) {
+    //      RemoveElement(face, false);
+    //      face = NULL;
+    //    }
+    return face;
   }
-  return 0;
 }
 
 
@@ -2108,7 +3739,7 @@ SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshNode * n1,
                                   const SMDS_MeshNode * nCenter)
 {
   return SMDS_Mesh::AddFaceWithID(n1,n2,n3,n12,n23,n31,nCenter,
-                                  myCellFactory->GetFreeID());
+                                  myElementIDFactory->GetFreeID());
 }
 
 //=======================================================================
@@ -2118,14 +3749,15 @@ SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshNode * n1,
 SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(int n1, int n2, int n3,
                                         int n12,int n23,int n31, int nCenter, int ID)
 {
-  return SMDS_Mesh::AddFaceWithID (myNodeFactory->FindNode(n1) ,
-                                   myNodeFactory->FindNode(n2) ,
-                                   myNodeFactory->FindNode(n3) ,
-                                   myNodeFactory->FindNode(n12),
-                                   myNodeFactory->FindNode(n23),
-                                   myNodeFactory->FindNode(n31),
-                                   myNodeFactory->FindNode(nCenter),
-                                   ID);
+  return SMDS_Mesh::AddFaceWithID
+    ((SMDS_MeshNode *)myNodeIDFactory->MeshElement(n1) ,
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n2) ,
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n3) ,
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n12),
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n23),
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n31),
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(nCenter),
+     ID);
 }
 
 //=======================================================================
@@ -2142,15 +3774,42 @@ SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(const SMDS_MeshNode * n1,
                                         int ID)
 {
   if ( !n1 || !n2 || !n3 || !n12 || !n23 || !n31 || !nCenter) return 0;
-  if ( NbFaces() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
+  if(hasConstructionEdges()) {
+    // creation quadratic edges - not implemented
+    return 0;
+  }
+  else
   {
-    cell->init( SMDSEntity_BiQuad_Triangle, /*nbNodes=*/7, n1, n2, n3, n12, n23, n31, nCenter );
+    // --- retrieve nodes ID
+    myNodeIds.resize(7);
+    myNodeIds[0] = n1->getVtkId();
+    myNodeIds[1] = n2->getVtkId();
+    myNodeIds[2] = n3->getVtkId();
+    myNodeIds[3] = n12->getVtkId();
+    myNodeIds[4] = n23->getVtkId();
+    myNodeIds[5] = n31->getVtkId();
+    myNodeIds[6] = nCenter->getVtkId();
+
+    SMDS_MeshFace * face = 0;
+    SMDS_VtkFace *facevtk = myFacePool->getNew();
+    facevtk->init(myNodeIds, this);
+    if (!this->registerElement(ID,facevtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(facevtk->getVtkId(), VTK_EMPTY_CELL);
+      myFacePool->destroy(facevtk);
+      return 0;
+    }
+    face = facevtk;
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = face;
     myInfo.myNbBiQuadTriangles++;
-    return static_cast<SMDS_MeshFace*>( cell );
+
+    //    if (!registerElement(ID, face)) {
+    //      RemoveElement(face, false);
+    //      face = NULL;
+    //    }
+    return face;
   }
-  return 0;
 }
 
 
@@ -2168,7 +3827,7 @@ SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshNode * n1,
                                   const SMDS_MeshNode * n41)
 {
   return SMDS_Mesh::AddFaceWithID(n1,n2,n3,n4,n12,n23,n34,n41,
-                                  myCellFactory->GetFreeID());
+                                  myElementIDFactory->GetFreeID());
 }
 
 //=======================================================================
@@ -2178,15 +3837,16 @@ SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshNode * n1,
 SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(int n1, int n2, int n3, int n4,
                                         int n12,int n23,int n34,int n41, int ID)
 {
-  return SMDS_Mesh::AddFaceWithID (myNodeFactory->FindNode(n1) ,
-                                   myNodeFactory->FindNode(n2) ,
-                                   myNodeFactory->FindNode(n3) ,
-                                   myNodeFactory->FindNode(n4) ,
-                                   myNodeFactory->FindNode(n12),
-                                   myNodeFactory->FindNode(n23),
-                                   myNodeFactory->FindNode(n34),
-                                   myNodeFactory->FindNode(n41),
-                                   ID);
+  return SMDS_Mesh::AddFaceWithID
+    ((SMDS_MeshNode *)myNodeIDFactory->MeshElement(n1) ,
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n2) ,
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n3) ,
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n4) ,
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n12),
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n23),
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n34),
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n41),
+     ID);
 }
 
 //=======================================================================
@@ -2204,15 +3864,43 @@ SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(const SMDS_MeshNode * n1,
                                         int ID)
 {
   if ( !n1 || !n2 || !n3 || !n4 || !n12 || !n23 || !n34 || !n41) return 0;
-  if ( NbFaces() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
+  if(hasConstructionEdges()) {
+    // creation quadratic edges - not implemented
+    return 0;
+  }
+  else
   {
-    cell->init( SMDSEntity_Quad_Quadrangle, /*nbNodes=*/8, n1, n2, n3, n4, n12, n23, n34, n41 );
+    // --- retrieve nodes ID
+    myNodeIds.resize(8);
+    myNodeIds[0] = n1->getVtkId();
+    myNodeIds[1] = n2->getVtkId();
+    myNodeIds[2] = n3->getVtkId();
+    myNodeIds[3] = n4->getVtkId();
+    myNodeIds[4] = n12->getVtkId();
+    myNodeIds[5] = n23->getVtkId();
+    myNodeIds[6] = n34->getVtkId();
+    myNodeIds[7] = n41->getVtkId();
+
+    SMDS_MeshFace * face = 0;
+    SMDS_VtkFace *facevtk = myFacePool->getNew();
+    facevtk->init(myNodeIds, this);
+    if (!this->registerElement(ID,facevtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(facevtk->getVtkId(), VTK_EMPTY_CELL);
+      myFacePool->destroy(facevtk);
+      return 0;
+    }
+    face = facevtk;
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = face;
     myInfo.myNbQuadQuadrangles++;
-    return static_cast<SMDS_MeshFace*>( cell );
+
+    //    if (!registerElement(ID, face)) {
+    //      RemoveElement(face, false);
+    //      face = NULL;
+    //    }
+    return face;
   }
-  return 0;
 }
 
 //=======================================================================
@@ -2230,7 +3918,7 @@ SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshNode * n1,
                                   const SMDS_MeshNode * nCenter)
 {
   return SMDS_Mesh::AddFaceWithID(n1,n2,n3,n4,n12,n23,n34,n41,nCenter,
-                                  myCellFactory->GetFreeID());
+                                  myElementIDFactory->GetFreeID());
 }
 
 //=======================================================================
@@ -2240,16 +3928,17 @@ SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshNode * n1,
 SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(int n1, int n2, int n3, int n4,
                                         int n12,int n23,int n34,int n41, int nCenter, int ID)
 {
-  return SMDS_Mesh::AddFaceWithID (myNodeFactory->FindNode(n1) ,
-                                   myNodeFactory->FindNode(n2) ,
-                                   myNodeFactory->FindNode(n3) ,
-                                   myNodeFactory->FindNode(n4) ,
-                                   myNodeFactory->FindNode(n12),
-                                   myNodeFactory->FindNode(n23),
-                                   myNodeFactory->FindNode(n34),
-                                   myNodeFactory->FindNode(n41),
-                                   myNodeFactory->FindNode(nCenter),
-                                   ID);
+  return SMDS_Mesh::AddFaceWithID
+    ((SMDS_MeshNode *)myNodeIDFactory->MeshElement(n1) ,
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n2) ,
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n3) ,
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n4) ,
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n12),
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n23),
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n34),
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n41),
+     (SMDS_MeshNode *)myNodeIDFactory->MeshElement(nCenter),
+     ID);
 }
 
 //=======================================================================
@@ -2268,16 +3957,44 @@ SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(const SMDS_MeshNode * n1,
                                         int ID)
 {
   if ( !n1 || !n2 || !n3 || !n4 || !n12 || !n23 || !n34 || !n41 || !nCenter) return 0;
-  if ( NbFaces() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
+  if(hasConstructionEdges()) {
+    // creation quadratic edges - not implemented
+    return 0;
+  }
+  else
   {
-    cell->init( SMDSEntity_BiQuad_Quadrangle,
-                /*nbNodes=*/9, n1, n2, n3, n4, n12, n23, n34, n41, nCenter );
+    // --- retrieve nodes ID
+    myNodeIds.resize(9);
+    myNodeIds[0] = n1->getVtkId();
+    myNodeIds[1] = n2->getVtkId();
+    myNodeIds[2] = n3->getVtkId();
+    myNodeIds[3] = n4->getVtkId();
+    myNodeIds[4] = n12->getVtkId();
+    myNodeIds[5] = n23->getVtkId();
+    myNodeIds[6] = n34->getVtkId();
+    myNodeIds[7] = n41->getVtkId();
+    myNodeIds[8] = nCenter->getVtkId();
+
+    SMDS_MeshFace * face = 0;
+    SMDS_VtkFace *facevtk = myFacePool->getNew();
+    facevtk->init(myNodeIds, this);
+    if (!this->registerElement(ID,facevtk))
+    {
+      this->myGrid->GetCellTypesArray()->SetValue(facevtk->getVtkId(), VTK_EMPTY_CELL);
+      myFacePool->destroy(facevtk);
+      return 0;
+    }
+    face = facevtk;
+    adjustmyCellsCapacity(ID);
+    myCells[ID] = face;
     myInfo.myNbBiQuadQuadrangles++;
-    return static_cast<SMDS_MeshFace*>( cell );
+
+    //    if (!registerElement(ID, face)) {
+    //      RemoveElement(face, false);
+    //      face = NULL;
+    //    }
+    return face;
   }
-  return 0;
 }
 
 
@@ -2296,8 +4013,11 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
                                       const SMDS_MeshNode * n24,
                                       const SMDS_MeshNode * n34)
 {
-  return SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n12, n23,
-                                    n31, n14, n24, n34, myCellFactory->GetFreeID());
+  int ID = myElementIDFactory->GetFreeID();
+  SMDS_MeshVolume * v = SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n12, n23,
+                                                   n31, n14, n24, n34, ID);
+  if(v==NULL) myElementIDFactory->ReleaseID(ID);
+  return v;
 }
 
 //=======================================================================
@@ -2308,17 +4028,18 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(int n1, int n2, int n3, int n4,
                                             int n12,int n23,int n31,
                                             int n14,int n24,int n34, int ID)
 {
-  return SMDS_Mesh::AddVolumeWithID (myNodeFactory->FindNode(n1) ,
-                                     myNodeFactory->FindNode(n2) ,
-                                     myNodeFactory->FindNode(n3) ,
-                                     myNodeFactory->FindNode(n4) ,
-                                     myNodeFactory->FindNode(n12),
-                                     myNodeFactory->FindNode(n23),
-                                     myNodeFactory->FindNode(n31),
-                                     myNodeFactory->FindNode(n14),
-                                     myNodeFactory->FindNode(n24),
-                                     myNodeFactory->FindNode(n34),
-                                     ID);
+  return SMDS_Mesh::AddVolumeWithID
+    ((SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n2) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n3) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n4) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n12),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n23),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n31),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n14),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n24),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n34),
+     ID);
 }
 
 //=======================================================================
@@ -2339,16 +4060,42 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
 {
   if ( !n1 || !n2 || !n3 || !n4 || !n12 || !n23 || !n31 || !n14 || !n24 || !n34)
     return 0;
-  if ( NbVolumes() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
+  if(hasConstructionFaces()) {
+    // creation quadratic faces - not implemented
+    return 0;
+  }
+  // --- retrieve nodes ID
+  myNodeIds.resize(10);
+  myNodeIds[0] = n1->getVtkId();
+  myNodeIds[1] = n3->getVtkId();
+  myNodeIds[2] = n2->getVtkId();
+  myNodeIds[3] = n4->getVtkId();
+
+  myNodeIds[4] = n31->getVtkId();
+  myNodeIds[5] = n23->getVtkId();
+  myNodeIds[6] = n12->getVtkId();
+
+  myNodeIds[7] = n14->getVtkId();
+  myNodeIds[8] = n34->getVtkId();
+  myNodeIds[9] = n24->getVtkId();
+
+  SMDS_VtkVolume *volvtk = myVolumePool->getNew();
+  volvtk->init(myNodeIds, this);
+  if (!this->registerElement(ID,volvtk))
   {
-    cell->init( SMDSEntity_Quad_Tetra,
-                /*nbNodes=*/10, n1, n2, n3, n4, n12, n23, n31, n14, n24, n34 );
-    myInfo.myNbQuadTetras++;
-    return static_cast<SMDS_MeshVolume*>( cell );
+    this->myGrid->GetCellTypesArray()->SetValue(volvtk->getVtkId(), VTK_EMPTY_CELL);
+    myVolumePool->destroy(volvtk);
+    return 0;
   }
-  return 0;
+  adjustmyCellsCapacity(ID);
+  myCells[ID] = volvtk;
+  myInfo.myNbQuadTetras++;
+
+  //  if (!registerElement(ID, volvtk)) {
+  //    RemoveElement(volvtk, false);
+  //    volvtk = NULL;
+  //  }
+  return volvtk;
 }
 
 
@@ -2370,8 +4117,12 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
                                       const SMDS_MeshNode * n35,
                                       const SMDS_MeshNode * n45)
 {
-  return SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n12, n23, n34, n41,
-                                    n15, n25, n35, n45, myCellFactory->GetFreeID());
+  int ID = myElementIDFactory->GetFreeID();
+  SMDS_MeshVolume * v =
+    SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n12, n23, n34, n41,
+                               n15, n25, n35, n45, ID);
+  if(v==NULL) myElementIDFactory->ReleaseID(ID);
+  return v;
 }
 
 //=======================================================================
@@ -2382,20 +4133,21 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(int n1, int n2, int n3, int n4, int
                                             int n12,int n23,int n34,int n41,
                                             int n15,int n25,int n35,int n45, int ID)
 {
-  return SMDS_Mesh::AddVolumeWithID (myNodeFactory->FindNode(n1) ,
-                                     myNodeFactory->FindNode(n2) ,
-                                     myNodeFactory->FindNode(n3) ,
-                                     myNodeFactory->FindNode(n4) ,
-                                     myNodeFactory->FindNode(n5) ,
-                                     myNodeFactory->FindNode(n12),
-                                     myNodeFactory->FindNode(n23),
-                                     myNodeFactory->FindNode(n34),
-                                     myNodeFactory->FindNode(n41),
-                                     myNodeFactory->FindNode(n15),
-                                     myNodeFactory->FindNode(n25),
-                                     myNodeFactory->FindNode(n35),
-                                     myNodeFactory->FindNode(n45),
-                                     ID);
+  return SMDS_Mesh::AddVolumeWithID
+    ((SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n2) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n3) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n4) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n5) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n12),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n23),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n34),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n41),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n15),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n25),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n35),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n45),
+     ID);
 }
 
 //=======================================================================
@@ -2420,16 +4172,45 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
   if (!n1 || !n2 || !n3 || !n4 || !n5 || !n12 || !n23 ||
       !n34 || !n41 || !n15 || !n25 || !n35 || !n45)
     return 0;
-  if ( NbVolumes() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
+  if(hasConstructionFaces()) {
+    // creation quadratic faces - not implemented
+    return 0;
+  }
+  // --- retrieve nodes ID
+  myNodeIds.resize(13);
+  myNodeIds[0] = n1->getVtkId();
+  myNodeIds[1] = n4->getVtkId();
+  myNodeIds[2] = n3->getVtkId();
+  myNodeIds[3] = n2->getVtkId();
+  myNodeIds[4] = n5->getVtkId();
+
+  myNodeIds[5] = n41->getVtkId();
+  myNodeIds[6] = n34->getVtkId();
+  myNodeIds[7] = n23->getVtkId();
+  myNodeIds[8] = n12->getVtkId();
+
+  myNodeIds[9] = n15->getVtkId();
+  myNodeIds[10] = n45->getVtkId();
+  myNodeIds[11] = n35->getVtkId();
+  myNodeIds[12] = n25->getVtkId();
+
+  SMDS_VtkVolume *volvtk = myVolumePool->getNew();
+  volvtk->init(myNodeIds, this);
+  if (!this->registerElement(ID,volvtk))
   {
-    cell->init( SMDSEntity_Quad_Pyramid,
-                /*nbNodes=*/13, n1, n2, n3, n4, n5, n12, n23, n34, n41, n15, n25, n35, n45);
-    myInfo.myNbQuadPyramids++;
-    return static_cast<SMDS_MeshVolume*>( cell );
+    this->myGrid->GetCellTypesArray()->SetValue(volvtk->getVtkId(), VTK_EMPTY_CELL);
+    myVolumePool->destroy(volvtk);
+    return 0;
   }
-  return 0;
+  adjustmyCellsCapacity(ID);
+  myCells[ID] = volvtk;
+  myInfo.myNbQuadPyramids++;
+
+  //  if (!registerElement(ID, volvtk)) {
+  //    RemoveElement(volvtk, false);
+  //    volvtk = NULL;
+  //  }
+  return volvtk;
 }
 
 
@@ -2453,8 +4234,12 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
                                       const SMDS_MeshNode * n25,
                                       const SMDS_MeshNode * n36)
 {
-  return SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6, n12, n23, n31,
-                                    n45, n56, n64, n14, n25, n36, myCellFactory->GetFreeID());
+  int ID = myElementIDFactory->GetFreeID();
+  SMDS_MeshVolume * v =
+    SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6, n12, n23, n31,
+                               n45, n56, n64, n14, n25, n36, ID);
+  if(v==NULL) myElementIDFactory->ReleaseID(ID);
+  return v;
 }
 
 //=======================================================================
@@ -2467,22 +4252,23 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(int n1, int n2, int n3,
                                             int n45,int n56,int n64,
                                             int n14,int n25,int n36, int ID)
 {
-  return SMDS_Mesh::AddVolumeWithID (myNodeFactory->FindNode(n1) ,
-                                     myNodeFactory->FindNode(n2) ,
-                                     myNodeFactory->FindNode(n3) ,
-                                     myNodeFactory->FindNode(n4) ,
-                                     myNodeFactory->FindNode(n5) ,
-                                     myNodeFactory->FindNode(n6) ,
-                                     myNodeFactory->FindNode(n12),
-                                     myNodeFactory->FindNode(n23),
-                                     myNodeFactory->FindNode(n31),
-                                     myNodeFactory->FindNode(n45),
-                                     myNodeFactory->FindNode(n56),
-                                     myNodeFactory->FindNode(n64),
-                                     myNodeFactory->FindNode(n14),
-                                     myNodeFactory->FindNode(n25),
-                                     myNodeFactory->FindNode(n36),
-                                     ID);
+  return SMDS_Mesh::AddVolumeWithID
+    ((SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n2) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n3) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n4) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n5) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n6) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n12),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n23),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n31),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n45),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n56),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n64),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n14),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n25),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n36),
+     ID);
 }
 
 //=======================================================================
@@ -2509,16 +4295,49 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
   if (!n1 || !n2 || !n3 || !n4 || !n5 || !n6 || !n12 || !n23 ||
       !n31 || !n45 || !n56 || !n64 || !n14 || !n25 || !n36)
     return 0;
-  if ( NbVolumes() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
+  if(hasConstructionFaces()) {
+    // creation quadratic faces - not implemented
+    return 0;
+  }
+  // --- retrieve nodes ID
+  myNodeIds.resize(15);
+  myNodeIds[0] = n1->getVtkId();
+  myNodeIds[1] = n2->getVtkId();
+  myNodeIds[2] = n3->getVtkId();
+
+  myNodeIds[3] = n4->getVtkId();
+  myNodeIds[4] = n5->getVtkId();
+  myNodeIds[5] = n6->getVtkId();
+
+  myNodeIds[6] = n12->getVtkId();
+  myNodeIds[7] = n23->getVtkId();
+  myNodeIds[8] = n31->getVtkId();
+
+  myNodeIds[9] = n45->getVtkId();
+  myNodeIds[10] = n56->getVtkId();
+  myNodeIds[11] = n64->getVtkId();
+
+  myNodeIds[12] = n14->getVtkId();
+  myNodeIds[13] = n25->getVtkId();
+  myNodeIds[14] = n36->getVtkId();
+
+  SMDS_VtkVolume *volvtk = myVolumePool->getNew();
+  volvtk->init(myNodeIds, this);
+  if (!this->registerElement(ID,volvtk))
   {
-    cell->init( SMDSEntity_Quad_Penta, /*nbNodes=*/15,
-                n1, n2, n3, n4, n5, n6, n12, n23, n31, n45, n56, n64, n14, n25, n36 );
-    myInfo.myNbQuadPrisms++;
-    return static_cast<SMDS_MeshVolume*>( cell );
+    this->myGrid->GetCellTypesArray()->SetValue(volvtk->getVtkId(), VTK_EMPTY_CELL);
+    myVolumePool->destroy(volvtk);
+    return 0;
   }
-  return 0;
+  adjustmyCellsCapacity(ID);
+  myCells[ID] = volvtk;
+  myInfo.myNbQuadPrisms++;
+
+  //  if (!registerElement(ID, volvtk)) {
+  //    RemoveElement(volvtk, false);
+  //    volvtk = NULL;
+  //  }
+  return volvtk;
 }
 
 //=======================================================================
@@ -2544,9 +4363,13 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
                                       const SMDS_MeshNode * n2356,
                                       const SMDS_MeshNode * n1346)
 {
-  return SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6, n12, n23, n31,
-                                    n45, n56, n64, n14, n25, n36, n1245, n2356, n1346,
-                                    myCellFactory->GetFreeID());
+  //MESSAGE("AddVolume penta18");
+  int ID = myElementIDFactory->GetFreeID();
+  SMDS_MeshVolume * v =
+    SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6, n12, n23, n31,
+                               n45, n56, n64, n14, n25, n36, n1245, n2356, n1346, ID);
+  if(v==NULL) myElementIDFactory->ReleaseID(ID);
+  return v;
 }
 
 //=======================================================================
@@ -2560,25 +4383,27 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(int n1, int n2, int n3,
                                             int n14,int n25,int n36,
                                             int n1245, int n2356, int n1346, int ID)
 {
-  return SMDS_Mesh::AddVolumeWithID (myNodeFactory->FindNode(n1) ,
-                                     myNodeFactory->FindNode(n2) ,
-                                     myNodeFactory->FindNode(n3) ,
-                                     myNodeFactory->FindNode(n4) ,
-                                     myNodeFactory->FindNode(n5) ,
-                                     myNodeFactory->FindNode(n6) ,
-                                     myNodeFactory->FindNode(n12),
-                                     myNodeFactory->FindNode(n23),
-                                     myNodeFactory->FindNode(n31),
-                                     myNodeFactory->FindNode(n45),
-                                     myNodeFactory->FindNode(n56),
-                                     myNodeFactory->FindNode(n64),
-                                     myNodeFactory->FindNode(n14),
-                                     myNodeFactory->FindNode(n25),
-                                     myNodeFactory->FindNode(n36),
-                                     myNodeFactory->FindNode(n1245),
-                                     myNodeFactory->FindNode(n2356),
-                                     myNodeFactory->FindNode(n1346),
-                                     ID);
+  //MESSAGE("AddVolumeWithID penta18 " << ID);
+  return SMDS_Mesh::AddVolumeWithID
+    ((SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n2) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n3) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n4) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n5) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n6) ,
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n12),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n23),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n31),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n45),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n56),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n64),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n14),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n25),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n36),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1245),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n2356),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1346),
+     ID);
 }
 
 //=======================================================================
@@ -2609,16 +4434,53 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
   if (!n1 || !n2 || !n3 || !n4 || !n5 || !n6 || !n12 || !n23 ||
       !n31 || !n45 || !n56 || !n64 || !n14 || !n25 || !n36 || !n1245 || !n2356 || !n1346)
     return 0;
-  if ( NbVolumes() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
+  if(hasConstructionFaces()) {
+    // creation quadratic faces - not implemented
+    return 0;
+  }
+  // --- retrieve nodes ID
+  myNodeIds.resize(18);
+  myNodeIds[0] = n1->getVtkId();
+  myNodeIds[1] = n2->getVtkId();
+  myNodeIds[2] = n3->getVtkId();
+
+  myNodeIds[3] = n4->getVtkId();
+  myNodeIds[4] = n5->getVtkId();
+  myNodeIds[5] = n6->getVtkId();
+
+  myNodeIds[6] = n12->getVtkId();
+  myNodeIds[7] = n23->getVtkId();
+  myNodeIds[8] = n31->getVtkId();
+
+  myNodeIds[9] = n45->getVtkId();
+  myNodeIds[10] = n56->getVtkId();
+  myNodeIds[11] = n64->getVtkId();
+
+  myNodeIds[12] = n14->getVtkId();
+  myNodeIds[13] = n25->getVtkId();
+  myNodeIds[14] = n36->getVtkId();
+
+  myNodeIds[15] = n1245->getVtkId();
+  myNodeIds[16] = n2356->getVtkId();
+  myNodeIds[17] = n1346->getVtkId();
+
+  SMDS_VtkVolume *volvtk = myVolumePool->getNew();
+  volvtk->init(myNodeIds, this);
+  if (!this->registerElement(ID,volvtk))
   {
-    cell->init( SMDSEntity_BiQuad_Penta, /*nbNodes=*/18, n1, n2, n3, n4, n5, n6,
-                n12, n23, n31, n45, n56, n64, n14, n25, n36, n1245, n2356, n1346 );
-    myInfo.myNbBiQuadPrisms++;
-    return static_cast<SMDS_MeshVolume*>( cell );
+    this->myGrid->GetCellTypesArray()->SetValue(volvtk->getVtkId(), VTK_EMPTY_CELL);
+    myVolumePool->destroy(volvtk);
+    return 0;
   }
-  return 0;
+  adjustmyCellsCapacity(ID);
+  myCells[ID] = volvtk;
+  myInfo.myNbBiQuadPrisms++;
+
+  //  if (!registerElement(ID, volvtk)) {
+  //    RemoveElement(volvtk, false);
+  //    volvtk = NULL;
+  //  }
+  return volvtk;
 }
 
 
@@ -2647,9 +4509,12 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
                                       const SMDS_MeshNode * n37,
                                       const SMDS_MeshNode * n48)
 {
-  return SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6, n7, n8, n12, n23, n34, n41,
-                                    n56, n67, n78, n85, n15, n26, n37, n48,
-                                    myCellFactory->GetFreeID());
+  int ID = myElementIDFactory->GetFreeID();
+  SMDS_MeshVolume * v =
+    SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6, n7, n8, n12, n23, n34, n41,
+                               n56, n67, n78, n85, n15, n26, n37, n48, ID);
+  if(v==NULL) myElementIDFactory->ReleaseID(ID);
+  return v;
 }
 
 //=======================================================================
@@ -2662,27 +4527,28 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(int n1, int n2, int n3, int n4,
                                             int n56,int n67,int n78,int n85,
                                             int n15,int n26,int n37,int n48, int ID)
 {
-  return SMDS_Mesh::AddVolumeWithID (myNodeFactory->FindNode(n1),
-                                     myNodeFactory->FindNode(n2),
-                                     myNodeFactory->FindNode(n3),
-                                     myNodeFactory->FindNode(n4),
-                                     myNodeFactory->FindNode(n5),
-                                     myNodeFactory->FindNode(n6),
-                                     myNodeFactory->FindNode(n7),
-                                     myNodeFactory->FindNode(n8),
-                                     myNodeFactory->FindNode(n12),
-                                     myNodeFactory->FindNode(n23),
-                                     myNodeFactory->FindNode(n34),
-                                     myNodeFactory->FindNode(n41),
-                                     myNodeFactory->FindNode(n56),
-                                     myNodeFactory->FindNode(n67),
-                                     myNodeFactory->FindNode(n78),
-                                     myNodeFactory->FindNode(n85),
-                                     myNodeFactory->FindNode(n15),
-                                     myNodeFactory->FindNode(n26),
-                                     myNodeFactory->FindNode(n37),
-                                     myNodeFactory->FindNode(n48),
-                                     ID);
+  return SMDS_Mesh::AddVolumeWithID
+    ((SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n2),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n3),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n4),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n5),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n6),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n7),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n8),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n12),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n23),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n34),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n41),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n56),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n67),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n78),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n85),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n15),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n26),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n37),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n48),
+     ID);
 }
 
 //=======================================================================
@@ -2714,16 +4580,54 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
   if (!n1 || !n2 || !n3 || !n4 || !n5 || !n6 || !n7 || !n8 || !n12 || !n23 ||
       !n34 || !n41 || !n56 || !n67 || !n78 || !n85 || !n15 || !n26 || !n37 || !n48)
     return 0;
-  if ( NbVolumes() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
+  if(hasConstructionFaces()) {
+    return 0;
+    // creation quadratic faces - not implemented
+  }
+  // --- retrieve nodes ID
+  myNodeIds.resize(20);
+  myNodeIds[0] = n1->getVtkId();
+  myNodeIds[1] = n4->getVtkId();
+  myNodeIds[2] = n3->getVtkId();
+  myNodeIds[3] = n2->getVtkId();
+
+  myNodeIds[4] = n5->getVtkId();
+  myNodeIds[5] = n8->getVtkId();
+  myNodeIds[6] = n7->getVtkId();
+  myNodeIds[7] = n6->getVtkId();
+
+  myNodeIds[8] = n41->getVtkId();
+  myNodeIds[9] = n34->getVtkId();
+  myNodeIds[10] = n23->getVtkId();
+  myNodeIds[11] = n12->getVtkId();
+
+  myNodeIds[12] = n85->getVtkId();
+  myNodeIds[13] = n78->getVtkId();
+  myNodeIds[14] = n67->getVtkId();
+  myNodeIds[15] = n56->getVtkId();
+
+  myNodeIds[16] = n15->getVtkId();
+  myNodeIds[17] = n48->getVtkId();
+  myNodeIds[18] = n37->getVtkId();
+  myNodeIds[19] = n26->getVtkId();
+
+  SMDS_VtkVolume *volvtk = myVolumePool->getNew();
+  volvtk->init(myNodeIds, this);
+  if (!this->registerElement(ID,volvtk))
   {
-    cell->init( SMDSEntity_Quad_Hexa, /*nbNodes=*/20, n1, n2, n3, n4, n5, n6, n7, n8,
-                n12, n23, n34, n41, n56, n67, n78, n85, n15, n26, n37, n48 );
-    myInfo.myNbQuadHexas++;
-    return static_cast<SMDS_MeshVolume*>( cell );
+    this->myGrid->GetCellTypesArray()->SetValue(volvtk->getVtkId(), VTK_EMPTY_CELL);
+    myVolumePool->destroy(volvtk);
+    return 0;
   }
-  return 0;
+  adjustmyCellsCapacity(ID);
+  myCells[ID] = volvtk;
+  myInfo.myNbQuadHexas++;
+
+  //  if (!registerElement(ID, volvtk)) {
+  //    RemoveElement(volvtk, false);
+  //    volvtk = NULL;
+  //  }
+  return volvtk;
 }
 
 //=======================================================================
@@ -2758,10 +4662,14 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
                                       const SMDS_MeshNode * n5678,
                                       const SMDS_MeshNode * nCenter)
 {
-  return SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6, n7, n8, n12, n23, n34, n41,
-                                    n56, n67, n78, n85, n15, n26, n37, n48,
-                                    n1234, n1256, n2367, n3478, n1458, n5678, nCenter,
-                                    myCellFactory->GetFreeID());
+  int ID = myElementIDFactory->GetFreeID();
+  SMDS_MeshVolume * v =
+    SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6, n7, n8, n12, n23, n34, n41,
+                               n56, n67, n78, n85, n15, n26, n37, n48,
+                               n1234, n1256, n2367, n3478, n1458, n5678, nCenter,
+                               ID);
+  if(v==NULL) myElementIDFactory->ReleaseID(ID);
+  return v;
 }
 
 //=======================================================================
@@ -2776,39 +4684,40 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(int n1, int n2, int n3, int n4,
                                             int n1234,int n1256,int n2367,int n3478,
                                             int n1458,int n5678,int nCenter, int ID)
 {
-  return SMDS_Mesh::AddVolumeWithID (myNodeFactory->FindNode(n1),
-                                     myNodeFactory->FindNode(n2),
-                                     myNodeFactory->FindNode(n3),
-                                     myNodeFactory->FindNode(n4),
-                                     myNodeFactory->FindNode(n5),
-                                     myNodeFactory->FindNode(n6),
-                                     myNodeFactory->FindNode(n7),
-                                     myNodeFactory->FindNode(n8),
-                                     myNodeFactory->FindNode(n12),
-                                     myNodeFactory->FindNode(n23),
-                                     myNodeFactory->FindNode(n34),
-                                     myNodeFactory->FindNode(n41),
-                                     myNodeFactory->FindNode(n56),
-                                     myNodeFactory->FindNode(n67),
-                                     myNodeFactory->FindNode(n78),
-                                     myNodeFactory->FindNode(n85),
-                                     myNodeFactory->FindNode(n15),
-                                     myNodeFactory->FindNode(n26),
-                                     myNodeFactory->FindNode(n37),
-                                     myNodeFactory->FindNode(n48),
-                                     myNodeFactory->FindNode(n1234),
-                                     myNodeFactory->FindNode(n1256),
-                                     myNodeFactory->FindNode(n2367),
-                                     myNodeFactory->FindNode(n3478),
-                                     myNodeFactory->FindNode(n1458),
-                                     myNodeFactory->FindNode(n5678),
-                                     myNodeFactory->FindNode(nCenter),
-                                     ID);
+  return SMDS_Mesh::AddVolumeWithID
+    ((SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n2),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n3),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n4),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n5),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n6),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n7),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n8),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n12),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n23),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n34),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n41),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n56),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n67),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n78),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n85),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n15),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n26),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n37),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n48),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1234),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1256),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n2367),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n3478),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1458),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n5678),
+     (SMDS_MeshNode*) myNodeIDFactory->MeshElement(nCenter),
+     ID);
 }
 
 //=======================================================================
 //function : AddVolumeWithID
-//purpose  : 2d order Hexahedrons with 27 nodes
+//purpose  : 2d order Hexahedrons with 20 nodes
 //=======================================================================
 SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
                                             const SMDS_MeshNode * n2,
@@ -2843,20 +4752,61 @@ SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
       !n34 || !n41 || !n56 || !n67 || !n78 || !n85 || !n15 || !n26 || !n37 || !n48 ||
       !n1234 || !n1256 || !n2367 || !n3478 || !n1458 || !n5678 || !nCenter )
     return 0;
-  if ( NbVolumes() % CHECKMEMORY_INTERVAL == 0 ) CheckMemory();
-
-  if ( SMDS_MeshCell* cell = myCellFactory->NewCell( ID ))
+  if(hasConstructionFaces()) {
+    return 0;
+    // creation quadratic faces - not implemented
+  }
+  // --- retrieve nodes ID
+  myNodeIds.resize(27);
+  myNodeIds[0] = n1->getVtkId();
+  myNodeIds[1] = n4->getVtkId();
+  myNodeIds[2] = n3->getVtkId();
+  myNodeIds[3] = n2->getVtkId();
+
+  myNodeIds[4] = n5->getVtkId();
+  myNodeIds[5] = n8->getVtkId();
+  myNodeIds[6] = n7->getVtkId();
+  myNodeIds[7] = n6->getVtkId();
+
+  myNodeIds[8] = n41->getVtkId();
+  myNodeIds[9] = n34->getVtkId();
+  myNodeIds[10] = n23->getVtkId();
+  myNodeIds[11] = n12->getVtkId();
+
+  myNodeIds[12] = n85->getVtkId();
+  myNodeIds[13] = n78->getVtkId();
+  myNodeIds[14] = n67->getVtkId();
+  myNodeIds[15] = n56->getVtkId();
+
+  myNodeIds[16] = n15->getVtkId();
+  myNodeIds[17] = n48->getVtkId();
+  myNodeIds[18] = n37->getVtkId();
+  myNodeIds[19] = n26->getVtkId();
+
+  myNodeIds[20] = n1256->getVtkId();
+  myNodeIds[21] = n3478->getVtkId();
+  myNodeIds[22] = n1458->getVtkId();
+  myNodeIds[23] = n2367->getVtkId();
+  myNodeIds[24] = n1234->getVtkId();
+  myNodeIds[25] = n5678->getVtkId();
+  myNodeIds[26] = nCenter->getVtkId();
+
+  SMDS_VtkVolume *volvtk = myVolumePool->getNew();
+  volvtk->init(myNodeIds, this);
+  if (!this->registerElement(ID,volvtk))
   {
-    cell->init( SMDSEntity_TriQuad_Hexa, /*nbNodes=*/27, n1, n2, n3, n4, n5, n6, n7, n8,
-                n12, n23, n34, n41, n56, n67, n78, n85, n15, n26, n37, n48,
-                n1234, n1256, n2367, n3478, n1458, n5678, nCenter);
-    myInfo.myNbTriQuadHexas++;
-    return static_cast<SMDS_MeshVolume*>( cell );
+    this->myGrid->GetCellTypesArray()->SetValue(volvtk->getVtkId(), VTK_EMPTY_CELL);
+    myVolumePool->destroy(volvtk);
+    return 0;
   }
-  return 0;
+  adjustmyCellsCapacity(ID);
+  myCells[ID] = volvtk;
+  myInfo.myNbTriQuadHexas++;
+
+  return volvtk;
 }
 
-void SMDS_Mesh::dumpGrid(std::string ficdump)
+void SMDS_Mesh::dumpGrid(string ficdump)
 {
   //  vtkUnstructuredGridWriter* aWriter = vtkUnstructuredGridWriter::New();
   //  aWriter->SetFileName(ficdump.c_str());
@@ -2867,7 +4817,7 @@ void SMDS_Mesh::dumpGrid(std::string ficdump)
   //  }
   //  aWriter->Delete();
   ficdump = ficdump + "_connectivity";
-  std::ofstream ficcon(ficdump.c_str(), ios::out);
+  ofstream ficcon(ficdump.c_str(), ios::out);
   int nbPoints = myGrid->GetNumberOfPoints();
   ficcon << "-------------------------------- points " <<  nbPoints << endl;
   for (int i=0; i<nbPoints; i++)
@@ -2904,44 +4854,41 @@ void SMDS_Mesh::dumpGrid(std::string ficdump)
 
 }
 
-void SMDS_Mesh::CompactMesh()
+void SMDS_Mesh::compactMesh()
 {
   this->myCompactTime = this->myModifTime;
-
-  bool idsChange = ( myNodeFactory->CompactChangePointers() ||
-                     myCellFactory->CompactChangePointers() );
-  if ( idsChange )
-  {
-    std::set< SMDS_ElementHolder* >::iterator holder = myElemHolders.begin();
-    for ( ; holder != myElemHolders.end(); ++holder )
-      (*holder)->beforeCompacting();
-  }
-
-  // remove "holes" in SMDS numeration
-  std::vector<int> idNodesOldToNew, idCellsNewToOld;
-  myNodeFactory->Compact( idNodesOldToNew );
-  myCellFactory->Compact( idCellsNewToOld );
-
-  // make VTK IDs correspond to SMDS IDs
-  int newNodeSize = myNodeFactory->NbUsedElements();
-  int newCellSize = myCellFactory->NbUsedElements();
-  myGrid->compactGrid( idNodesOldToNew, newNodeSize, idCellsNewToOld, newCellSize );
-
-  std::set< SMDS_ElementHolder* >::iterator holder = myElemHolders.begin();
-  for ( ; holder != myElemHolders.end(); ++holder )
-    if ( idsChange )
-      (*holder)->restoreElements( idNodesOldToNew, idCellsNewToOld );
-    else
-      (*holder)->compact();
-
-  return;
 }
 
-int SMDS_Mesh::FromVtkToSmds( int vtkid ) const
+int SMDS_Mesh::fromVtkToSmds(int vtkid)
 {
-  return myCellFactory->FromVtkToSmds( vtkid );
+  if (vtkid >= 0 && vtkid < (int)myCellIdVtkToSmds.size())
+    return myCellIdVtkToSmds[vtkid];
+  throw SALOME_Exception(LOCALIZED ("vtk id out of bounds"));
 }
 
+// void SMDS_Mesh::updateBoundingBox()
+// {
+//   xmin = 0; xmax = 0;
+//   ymin = 0; ymax = 0;
+//   zmin = 0; zmax = 0;
+//   vtkPoints *points = myGrid->GetPoints();
+//   int myNodesSize = this->myNodes.size();
+//   for (int i = 0; i < myNodesSize; i++)
+//     {
+//       if (SMDS_MeshNode *n = myNodes[i])
+//         {
+//           double coords[3];
+//           points->GetPoint(n->myVtkID, coords);
+//           if (coords[0] < xmin) xmin = coords[0];
+//           else if (coords[0] > xmax) xmax = coords[0];
+//           if (coords[1] < ymin) ymin = coords[1];
+//           else if (coords[1] > ymax) ymax = coords[1];
+//           if (coords[2] < zmin) zmin = coords[2];
+//           else if (coords[2] > zmax) zmax = coords[2];
+//         }
+//     }
+// }
+
 double SMDS_Mesh::getMaxDim()
 {
   double dmax = 1.e-3;
@@ -2967,12 +4914,7 @@ vtkMTimeType SMDS_Mesh::GetMTime() const
   return this->myModifTime;
 }
 
-bool SMDS_Mesh::IsCompacted()
-{
-  return ( this->myCompactTime == this->myModifTime );
-}
-
-void SMDS_Mesh::setNbShapes( size_t nbShapes )
+bool SMDS_Mesh::isCompacted()
 {
-  myNodeFactory->SetNbShapes( nbShapes );
+  return this->myCompactTime == this->myModifTime;
 }
index 38952f78cb5bcb17d540b1952418f3fc98078ff5..00b31a33c782c31ceda7e1a775c41362040af6ee 100644 (file)
 
 #include "SMESH_SMDS.hxx"
 
-#include "SMDS_BallElement.hxx"
-#include "SMDS_ElemIterator.hxx"
-#include "SMDS_Mesh0DElement.hxx"
+#include "SMDS_MeshNode.hxx"
 #include "SMDS_MeshCell.hxx"
+#include "SMDS_Mesh0DElement.hxx"
 #include "SMDS_MeshEdge.hxx"
 #include "SMDS_MeshFace.hxx"
-#include "SMDS_MeshInfo.hxx"
-#include "SMDS_MeshNode.hxx"
 #include "SMDS_MeshVolume.hxx"
+#include "SMDS_MeshNodeIDFactory.hxx"
+#include "SMDS_MeshElementIDFactory.hxx"
+#include "SMDS_MeshInfo.hxx"
+#include "SMDS_ElemIterator.hxx"
+#include "SMDS_VolumeOfNodes.hxx"
+#include "SMDS_VtkEdge.hxx"
+#include "SMDS_VtkFace.hxx"
+#include "SMDS_VtkVolume.hxx"
+#include "ObjectPool.hxx"
 #include "SMDS_UnstructuredGrid.hxx"
+#include "SMDS_BallElement.hxx"
 
+#include <boost/shared_ptr.hpp>
 #include <set>
 #include <list>
 #include <vector>
+#include <vtkSystemIncludes.h>
+#include <cassert>
 
-class SMDS_ElementHolder;
-class SMDS_ElementFactory;
-class SMDS_NodeFactory;
+#include "Utils_SALOME_Exception.hxx"
+
+#define MYASSERT(val) if (!(val)) throw SALOME_Exception(LOCALIZED("assertion not verified"));
 
 class SMDS_EXPORT SMDS_Mesh : public SMDS_MeshObject
 {
 public:
+  friend class SMDS_MeshIDFactory;
+  friend class SMDS_MeshNodeIDFactory;
+  friend class SMDS_MeshElementIDFactory;
+  friend class SMDS_MeshVolumeVtkNodes;
+  friend class SMDS_MeshNode;
 
   SMDS_Mesh();
   
+  //! to retrieve this SMDS_Mesh instance from its elements (index stored in SMDS_Elements)
+  static std::vector<SMDS_Mesh*> _meshList;
+
   //! actual nodes coordinates, cells definition and reverse connectivity are stored in a vtkUnstructuredGrid
-  inline SMDS_UnstructuredGrid* GetGrid() { return myGrid; }
+  inline SMDS_UnstructuredGrid* getGrid() { return myGrid; }
+  inline int getMeshId() { return myMeshId; }
 
-  virtual SMDS_NodeIteratorPtr   nodesIterator  () const;
-  virtual SMDS_EdgeIteratorPtr   edgesIterator  () const;
-  virtual SMDS_FaceIteratorPtr   facesIterator  () const;
-  virtual SMDS_VolumeIteratorPtr volumesIterator() const;
+  virtual SMDS_NodeIteratorPtr   nodesIterator     (bool idInceasingOrder=false) const;
+  virtual SMDS_EdgeIteratorPtr   edgesIterator     (bool idInceasingOrder=false) const;
+  virtual SMDS_FaceIteratorPtr   facesIterator     (bool idInceasingOrder=false) const;
+  virtual SMDS_VolumeIteratorPtr volumesIterator   (bool idInceasingOrder=false) const;
 
   virtual SMDS_ElemIteratorPtr elementsIterator(SMDSAbs_ElementType type=SMDSAbs_All) const;
   virtual SMDS_ElemIteratorPtr elementGeomIterator(SMDSAbs_GeometryType type) const;
   virtual SMDS_ElemIteratorPtr elementEntityIterator(SMDSAbs_EntityType type) const;
 
-  virtual SMDS_NodeIteratorPtr shapeNodesIterator   (int shapeID, size_t nbElemsToReturn=-1) const;
-  virtual SMDS_ElemIteratorPtr shapeElementsIterator(int shapeID, size_t nbElemsToReturn=-1) const;
-
   SMDSAbs_ElementType GetElementType( const int id, const bool iselem ) const;
 
   SMDS_Mesh *AddSubMesh();
@@ -121,6 +137,21 @@ public:
                                  const SMDS_MeshNode * n3,
                                  const SMDS_MeshNode * n4);
 
+  virtual SMDS_MeshFace* AddFaceWithID(const SMDS_MeshEdge * e1,
+                                       const SMDS_MeshEdge * e2,
+                                       const SMDS_MeshEdge * e3, int ID);
+  virtual SMDS_MeshFace* AddFace(const SMDS_MeshEdge * e1,
+                                 const SMDS_MeshEdge * e2,
+                                 const SMDS_MeshEdge * e3);
+
+  virtual SMDS_MeshFace* AddFaceWithID(const SMDS_MeshEdge * e1,
+                                       const SMDS_MeshEdge * e2,
+                                       const SMDS_MeshEdge * e3,
+                                       const SMDS_MeshEdge * e4, int ID);
+  virtual SMDS_MeshFace* AddFace(const SMDS_MeshEdge * e1,
+                                 const SMDS_MeshEdge * e2,
+                                 const SMDS_MeshEdge * e3,
+                                 const SMDS_MeshEdge * e4);
 
   // 2d order triangle of 6 nodes
   virtual SMDS_MeshFace* AddFaceWithID(int n1, int n2, int n3,
@@ -262,6 +293,38 @@ public:
                                      const SMDS_MeshNode * n7,
                                      const SMDS_MeshNode * n8);
 
+  virtual SMDS_MeshVolume* AddVolumeWithID(const SMDS_MeshFace * f1,
+                                           const SMDS_MeshFace * f2,
+                                           const SMDS_MeshFace * f3,
+                                           const SMDS_MeshFace * f4, int ID);
+  virtual SMDS_MeshVolume* AddVolume(const SMDS_MeshFace * f1,
+                                     const SMDS_MeshFace * f2,
+                                     const SMDS_MeshFace * f3,
+                                     const SMDS_MeshFace * f4);
+
+  virtual SMDS_MeshVolume* AddVolumeWithID(const SMDS_MeshFace * f1,
+                                           const SMDS_MeshFace * f2,
+                                           const SMDS_MeshFace * f3,
+                                           const SMDS_MeshFace * f4,
+                                           const SMDS_MeshFace * f5, int ID);
+  virtual SMDS_MeshVolume* AddVolume(const SMDS_MeshFace * f1,
+                                     const SMDS_MeshFace * f2,
+                                     const SMDS_MeshFace * f3,
+                                     const SMDS_MeshFace * f4,
+                                     const SMDS_MeshFace * f5);
+
+  virtual SMDS_MeshVolume* AddVolumeWithID(const SMDS_MeshFace * f1,
+                                           const SMDS_MeshFace * f2,
+                                           const SMDS_MeshFace * f3,
+                                           const SMDS_MeshFace * f4,
+                                           const SMDS_MeshFace * f5,
+                                           const SMDS_MeshFace * f6, int ID);
+  virtual SMDS_MeshVolume* AddVolume(const SMDS_MeshFace * f1,
+                                     const SMDS_MeshFace * f2,
+                                     const SMDS_MeshFace * f3,
+                                     const SMDS_MeshFace * f4,
+                                     const SMDS_MeshFace * f5,
+                                     const SMDS_MeshFace * f6);
 
   // hexagonal prism
   virtual SMDS_MeshVolume* AddVolumeWithID(int n1, int n2, int n3, int n4, int n5, int n6,
@@ -576,24 +639,33 @@ public:
   virtual SMDS_MeshVolume* AddPolyhedralVolumeWithID
     (const std::vector<const SMDS_MeshNode*> & nodes,
      const std::vector<int>                  & quantities,
-     const int                                 ID);
+                            const int                                 ID);
 
   virtual SMDS_MeshVolume* AddPolyhedralVolume
-    (const std::vector<const SMDS_MeshNode*> & nodes,
-     const std::vector<int>                  & quantities);
+                           (const std::vector<const SMDS_MeshNode*> & nodes,
+                            const std::vector<int>                  & quantities);
 
   virtual SMDS_MeshVolume* AddVolumeFromVtkIds(const std::vector<vtkIdType>& vtkNodeIds);
 
+  virtual SMDS_MeshVolume* AddVolumeFromVtkIdsWithID(const std::vector<vtkIdType>& vtkNodeIds,
+                                                     const int ID);
+
   virtual SMDS_MeshFace* AddFaceFromVtkIds(const std::vector<vtkIdType>& vtkNodeIds);
 
+  virtual SMDS_MeshFace* AddFaceFromVtkIdsWithID(const std::vector<vtkIdType>& vtkNodeIds,
+                                                     const int ID);
   virtual void MoveNode(const SMDS_MeshNode *n, double x, double y, double z);
 
-  virtual void RemoveElement(const SMDS_MeshElement *               elem,
-                             std::vector<const SMDS_MeshElement *>& removedElems,
-                             std::vector<const SMDS_MeshElement *>& removedNodes,
-                             const bool                             removenodes = false);
+  virtual void RemoveElement(const SMDS_MeshElement *        elem,
+                             std::list<const SMDS_MeshElement *>& removedElems,
+                             std::list<const SMDS_MeshElement *>& removedNodes,
+                             const bool                      removenodes = false);
   virtual void RemoveElement(const SMDS_MeshElement * elem, bool removenodes = false);
   virtual void RemoveNode(const SMDS_MeshNode * node);
+  virtual void Remove0DElement(const SMDS_Mesh0DElement * elem0d);
+  virtual void RemoveEdge(const SMDS_MeshEdge * edge);
+  virtual void RemoveFace(const SMDS_MeshFace * face);
+  virtual void RemoveVolume(const SMDS_MeshVolume * volume);
 
   /*! Remove only the given element and only if it is free.
    *  Method does not work for meshes with descendants.
@@ -609,23 +681,27 @@ public:
   bool ChangeElementNodes(const SMDS_MeshElement * elem,
                           const SMDS_MeshNode    * nodes[],
                           const int                nbnodes);
+  bool ChangePolyhedronNodes(const SMDS_MeshElement *                 elem,
+                             const std::vector<const SMDS_MeshNode*>& nodes,
+                             const std::vector<int> &                 quantities);
 
-  //virtual void Renumber (const bool isNodes, const int startID = 1, const int deltaID = 1);
+  virtual void Renumber (const bool isNodes, const int startID = 1, const int deltaID = 1);
   // Renumber all nodes or elements.
-
-  virtual void CompactMesh();
-  bool IsCompacted();
-
-  template<class ELEMTYPE>
-    static const ELEMTYPE* DownCast( const SMDS_MeshElement* e )
-  {
-    return (( e && !e->IsNull() && ELEMTYPE::Type() == e->GetType() ) ?
-            static_cast<const ELEMTYPE*>(e) : 0 );
-  }
+  virtual void compactMesh();
+  virtual void CompactMesh() { compactMesh(); }
 
   const SMDS_MeshNode *FindNode(int idnode) const;
   const SMDS_MeshNode *FindNodeVtk(int idnode) const;
-  const SMDS_MeshElement *FindElementVtk(int IDelem) const;
+  const SMDS_Mesh0DElement* Find0DElement(int idnode) const;
+  const SMDS_BallElement* FindBall(int idnode) const;
+  const SMDS_MeshEdge *FindEdge(int idnode1, int idnode2) const;
+  const SMDS_MeshEdge *FindEdge(int idnode1, int idnode2, int idnode3) const;
+  const SMDS_MeshFace *FindFace(int idnode1, int idnode2, int idnode3) const;
+  const SMDS_MeshFace *FindFace(int idnode1, int idnode2, int idnode3, int idnode4) const;
+  const SMDS_MeshFace *FindFace(int idnode1, int idnode2, int idnode3,
+                                int idnode4, int idnode5, int idnode6) const;
+  const SMDS_MeshFace *FindFace(int idnode1, int idnode2, int idnode3, int idnode4,
+                                int idnode5, int idnode6, int idnode7, int idnode8) const;
   virtual const SMDS_MeshElement * FindElement(int IDelem) const;
   static const SMDS_Mesh0DElement* Find0DElement(const SMDS_MeshNode * n);
   static const SMDS_BallElement* FindBall(const SMDS_MeshNode * n);
@@ -656,7 +732,8 @@ public:
                                        const SMDS_MeshNode *n7,
                                        const SMDS_MeshNode *n8);
 
-  static const SMDS_MeshFace*    FindFace   (const std::vector<const SMDS_MeshNode *>& nodes);
+  const SMDS_MeshFace *FindFace(const std::vector<int>& nodes_ids) const;
+  static const SMDS_MeshFace* FindFace(const std::vector<const SMDS_MeshNode *>& nodes);
   static const SMDS_MeshElement* FindElement(const std::vector<const SMDS_MeshNode *>& nodes,
                                              const SMDSAbs_ElementType                 type=SMDSAbs_All,
                                              const bool                                noMedium=true);
@@ -664,8 +741,6 @@ public:
                                 std::vector<const SMDS_MeshElement *>&    foundElems,
                                 const SMDSAbs_ElementType                 type=SMDSAbs_All);
 
-  virtual bool Contains( const SMDS_MeshElement* elem ) const;
-
   /*!
    * \brief Raise an exception if free memory (ram+swap) too low
     * \param doNotRaise - if true, suppres exception, just return free memory size
@@ -689,10 +764,36 @@ public:
   virtual int NbVolumes() const;
   virtual int NbSubMesh() const;
 
+  void DumpNodes() const;
+  void Dump0DElements() const;
+  void DumpEdges() const;
+  void DumpFaces() const;
+  void DumpVolumes() const;
+  void DebugStats() const;
+
   virtual ~SMDS_Mesh();
 
+  bool hasConstructionEdges();
+  bool hasConstructionFaces();
+  bool hasInverseElements();
+  void setConstructionEdges(bool);
+  void setConstructionFaces(bool);
+  void setInverseElements(bool);
+
+  /*!
+   * Checks if the element is present in mesh.
+   * Useful to determine dead pointers.
+   * Use this function for debug purpose only! Do not check in the code
+   * using it even in _DEBUG_ mode
+   */
+  bool Contains (const SMDS_MeshElement* elem) const;
+
+  typedef std::vector<SMDS_MeshNode *> SetOfNodes;
+  typedef std::vector<SMDS_MeshCell *> SetOfCells;
+
+  //void updateBoundingBox();
   double getMaxDim();
-  int FromVtkToSmds(int vtkid) const;
+  int fromVtkToSmds(int vtkid);
 
   void dumpGrid(std::string ficdump="dumpGrid");
   static int chunkSize;
@@ -702,14 +803,44 @@ public:
 
   void Modified();
   vtkMTimeType GetMTime() const;
+  bool isCompacted();
 
 protected:
   SMDS_Mesh(SMDS_Mesh * parent);
 
+  SMDS_MeshFace * createTriangle(const SMDS_MeshNode * node1,
+                                 const SMDS_MeshNode * node2,
+                                 const SMDS_MeshNode * node3,
+                                 int ID);
+  SMDS_MeshFace * createQuadrangle(const SMDS_MeshNode * node1,
+                                   const SMDS_MeshNode * node2,
+                                   const SMDS_MeshNode * node3,
+                                   const SMDS_MeshNode * node4,
+                                   int ID);
+  SMDS_MeshEdge* FindEdgeOrCreate(const SMDS_MeshNode * n1,
+                                  const SMDS_MeshNode * n2);
+  SMDS_MeshFace* FindFaceOrCreate(const SMDS_MeshNode *n1,
+                                  const SMDS_MeshNode *n2,
+                                  const SMDS_MeshNode *n3);
+  SMDS_MeshFace* FindFaceOrCreate(const SMDS_MeshNode *n1,
+                                  const SMDS_MeshNode *n2,
+                                  const SMDS_MeshNode *n3,
+                                  const SMDS_MeshNode *n4);
+
+  bool registerElement(int ID, SMDS_MeshElement * element);
+
   void addChildrenWithNodes(std::set<const SMDS_MeshElement*>& setOfChildren,
                             const SMDS_MeshElement *           element,
                             std::set<const SMDS_MeshElement*>& nodes);
 
+  inline void adjustmyCellsCapacity(int ID)
+  {
+    assert(ID >= 0);
+    myElementIDFactory->adjustMaxId(ID);
+    if (ID >= (int)myCells.size())
+      myCells.resize(ID+SMDS_Mesh::chunkSize,0);
+  }
+
   inline void adjustBoundingBox(double x, double y, double z)
   {
     if (x > xmax) xmax = x;
@@ -720,29 +851,47 @@ protected:
     else if (z < zmin) zmin = z;
   }
 
-  void setNbShapes( size_t nbShapes );
-
-
   // Fields PRIVATE
 
+  //! index of this SMDS_mesh in the static vector<SMDS_Mesh*> _meshList
+  int myMeshId;
+
   //! actual nodes coordinates, cells definition and reverse connectivity are stored in a vtkUnstructuredGrid
-  SMDS_UnstructuredGrid* myGrid;
+  SMDS_UnstructuredGrid*        myGrid;
 
   //! Small objects like SMDS_MeshNode are allocated by chunks to limit memory costs of new
-  SMDS_NodeFactory*      myNodeFactory;
-  SMDS_ElementFactory*   myCellFactory;
+  ObjectPool<SMDS_MeshNode>*    myNodePool;
+
+  //! Small objects like SMDS_VtkVolume are allocated by chunks to limit memory costs of new
+  ObjectPool<SMDS_VtkVolume>*   myVolumePool;
+  ObjectPool<SMDS_VtkFace>*     myFacePool;
+  ObjectPool<SMDS_VtkEdge>*     myEdgePool;
+  ObjectPool<SMDS_BallElement>* myBallPool;
+
+  //! SMDS_MeshNodes refer to vtk nodes (vtk id != index in myNodes),store reference to this mesh, and sub-shape
+  SetOfNodes                    myNodes;
+  SetOfCells                    myCells;
+
+  //! a buffer to speed up elements addition by excluding some memory allocation
+  std::vector<vtkIdType>        myNodeIds;
+
+  //! for cells only: index = ID in vtkUnstructuredGrid, value = ID for SMDS users
+  std::vector<int>              myCellIdVtkToSmds;
 
-  SMDS_Mesh *            myParent;
-  std::list<SMDS_Mesh *> myChildren;
-  SMDS_MeshInfo          myInfo;
+  SMDS_Mesh *                   myParent;
+  std::list<SMDS_Mesh *>        myChildren;
+  SMDS_MeshNodeIDFactory *      myNodeIDFactory;
+  SMDS_MeshElementIDFactory *   myElementIDFactory;
+  SMDS_MeshInfo                 myInfo;
 
   //! any add, remove or change of node or cell
-  bool                   myModified;
+  bool myModified;
   //! use a counter to keep track of modifications
-  unsigned long          myModifTime, myCompactTime;
+  unsigned long myModifTime, myCompactTime;
 
-  friend class SMDS_ElementHolder;
-  std::set< SMDS_ElementHolder* > myElemHolders;
+  bool myHasConstructionEdges;
+  bool myHasConstructionFaces;
+  bool myHasInverseElements;
 
   double xmin;
   double xmax;
diff --git a/src/SMDS/SMDS_Mesh0DElement.cxx b/src/SMDS/SMDS_Mesh0DElement.cxx
new file mode 100644 (file)
index 0000000..8ac7bcc
--- /dev/null
@@ -0,0 +1,164 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//  File   : SMDS_Mesh0DElement.cxx
+//  Module : SMESH
+//
+#ifdef _MSC_VER
+#pragma warning(disable:4786)
+#endif
+
+#include "SMDS_Mesh0DElement.hxx"
+#include "SMDS_IteratorOfElements.hxx"
+#include "SMDS_MeshNode.hxx"
+#include "SMDS_Mesh.hxx"
+
+#include "utilities.h"
+
+using namespace std;
+
+//=======================================================================
+//function : SMDS_Mesh0DElement
+//purpose  :
+//=======================================================================
+SMDS_Mesh0DElement::SMDS_Mesh0DElement (const SMDS_MeshNode * node)
+{
+  myNode = node;
+}
+
+//=======================================================================
+//function : Print
+//purpose  :
+//=======================================================================
+void SMDS_Mesh0DElement::Print (ostream & OS) const
+{
+  OS << "0D Element <" << GetID() << "> : (" << myNode << ") " << endl;
+}
+
+//=======================================================================
+//function : NbNodes
+//purpose  :
+//=======================================================================
+int SMDS_Mesh0DElement::NbNodes() const
+{
+  return 1;
+}
+
+//=======================================================================
+//function : NbEdges
+//purpose  :
+//=======================================================================
+int SMDS_Mesh0DElement::NbEdges() const
+{
+  return 0;
+}
+
+//=======================================================================
+//function : GetType
+//purpose  :
+//=======================================================================
+SMDSAbs_ElementType SMDS_Mesh0DElement::GetType() const
+{
+  return SMDSAbs_0DElement;
+}
+
+vtkIdType SMDS_Mesh0DElement::GetVtkType() const
+{
+  return VTK_VERTEX;
+}
+
+//=======================================================================
+//function : elementsIterator
+//purpose  :
+//=======================================================================
+class SMDS_Mesh0DElement_MyNodeIterator: public SMDS_ElemIterator
+{
+  const SMDS_MeshNode * myNode;
+  int myIndex;
+ public:
+  SMDS_Mesh0DElement_MyNodeIterator(const SMDS_MeshNode * node):
+    myNode(node),myIndex(0) {}
+
+  bool more()
+  {
+    return myIndex < 1;
+  }
+
+  const SMDS_MeshElement* next()
+  {
+    myIndex++;
+    if (myIndex == 1)
+      return myNode;
+    return NULL;
+  }
+};
+
+SMDS_ElemIteratorPtr SMDS_Mesh0DElement::elementsIterator (SMDSAbs_ElementType type) const
+{
+  switch(type)
+  {
+  case SMDSAbs_0DElement:
+    return SMDS_MeshElement::elementsIterator(SMDSAbs_0DElement);
+  case SMDSAbs_Node:
+    return SMDS_ElemIteratorPtr(new SMDS_Mesh0DElement_MyNodeIterator(myNode));
+  default:
+    return SMDS_ElemIteratorPtr
+      (new SMDS_IteratorOfElements
+       (this,type, SMDS_ElemIteratorPtr(new SMDS_Mesh0DElement_MyNodeIterator(myNode))));
+  }
+}
+
+/*!
+ * \brief Return node by its index
+ * \param ind - node index
+ * \retval const SMDS_MeshNode* - the node
+ */
+const SMDS_MeshNode* SMDS_Mesh0DElement::GetNode(const int ind) const
+{
+  if (ind == 0)
+    return myNode;
+  return NULL;
+}
+
+//=======================================================================
+//function : ChangeNode
+//purpose  :
+//=======================================================================
+bool SMDS_Mesh0DElement::ChangeNodes(const SMDS_MeshNode* nodes[], const int nbNodes)
+{
+  if ( nbNodes == 1 )
+  {
+    vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+    vtkIdType npts = 0;
+    vtkIdType* pts = 0;
+    grid->GetCellPoints(myVtkID, npts, pts);
+    if (nbNodes != npts)
+    {
+      MESSAGE("ChangeNodes problem: not the same number of nodes " << npts << " -> " << nbNodes);
+      return false;
+    }
+    myNode = nodes[0];
+    pts[0] = myNode->getVtkId();
+
+    SMDS_Mesh::_meshList[myMeshId]->setMyModified();
+    return true;
+  }
+  return false;
+}
index 1ba4d4b5791bf8ae3b058c7a07ad59db48e67d75..f4b9fa2dd756a2917bd1caffa0ba7e65e5109ee1 100644 (file)
 
 #include "SMDS_MeshCell.hxx"
 
-/*!
- * \brief 0D mesh element. This type is not allocated.
- *        It is only used as function argument type to provide more clear semantic.
- */
+#include <iostream>
+
 class SMDS_EXPORT SMDS_Mesh0DElement: public SMDS_MeshCell
 {
  public:
+  SMDS_Mesh0DElement (const SMDS_MeshNode * node);
+  virtual bool ChangeNodes(const SMDS_MeshNode* nodes[], const int nbNodes);
+  virtual void Print (std::ostream & OS) const;
+
+  virtual SMDSAbs_ElementType  GetType() const;
+  virtual vtkIdType            GetVtkType() const;
+  virtual SMDSAbs_EntityType   GetEntityType() const {return SMDSEntity_0D;}
+  virtual SMDSAbs_GeometryType GetGeomType() const { return SMDSGeom_POINT; }
+  virtual const SMDS_MeshNode* GetNode (const int ind) const;
+  virtual int NbNodes() const;
+  virtual int NbEdges() const;
+
+ protected:
+  virtual SMDS_ElemIteratorPtr elementsIterator (SMDSAbs_ElementType type) const;
 
-  static SMDSAbs_ElementType Type() { return SMDSAbs_0DElement; }
+ protected:
+  const SMDS_MeshNode* myNode;
 };
 
 #endif
index ae6d99fad98b3b3fbcfe4c2f77213fa993cdd619..7175ae5d457c3cd80695fcea22172c7f9845942e 100644 (file)
 //
 
 #include "SMDS_MeshCell.hxx"
+#include "utilities.h"
 
-#include "SMDS_Mesh.hxx"
-#include "SMDS_VtkCellIterator.hxx"
+int SMDS_MeshCell::nbCells = 0;
 
-#include <utilities.h>
-
-#include <vtkCell.h>
-
-#include <cstdarg>
-
-#include <boost/make_shared.hpp>
-
-namespace
-{
-  /*!
-   * \brief Cell type features
-   */
-  struct CellProps
-  {
-    SMDSAbs_EntityType   myEntity;
-    SMDSAbs_ElementType  myType;
-    SMDSAbs_GeometryType myGeom;
-    bool                 myIsPoly;
-    int                  myNbCornerNodes;
-    int                  myNbNodes;
-    int                  myNbEdges;
-    int                  myNbFaces;
-
-    CellProps() :
-      myEntity( SMDSEntity_Last ), myType( SMDSAbs_All ), myGeom( SMDSGeom_NONE ),
-      myIsPoly( 0 ), myNbCornerNodes( 0 ),
-      myNbNodes( 0 ), myNbEdges( 0 ), myNbFaces ( 0 )
-    {
-    }
-    void Set( SMDSAbs_EntityType   Entity,
-              SMDSAbs_ElementType  Type,
-              SMDSAbs_GeometryType Geom,
-              bool                 IsPoly,
-              int                  NbCornerNodes,
-              int                  NbNodes,
-              int                  NbEdges,
-              int                  NbFaces)
-    {
-      myEntity        = Entity;
-      myType          = Type;
-      myGeom          = Geom;
-      myIsPoly        = IsPoly;
-      myNbCornerNodes = NbCornerNodes;
-      myNbNodes       = NbNodes;
-      myNbEdges       = NbEdges;
-      myNbFaces       = NbFaces;
-    }
-    bool IsQuadratic() const { return myNbNodes > myNbCornerNodes; }
-  };
-
-  //! return vector a CellProps
-  const CellProps& getCellProps( VTKCellType vtkType )
-  {
-    static std::vector< CellProps > theCellProps;
-    if ( theCellProps.empty() )
-    {
-      theCellProps.resize( VTK_NUMBER_OF_CELL_TYPES );
-      CellProps* p = & theCellProps[0];
-      p[ VTK_VERTEX ].
-        Set( SMDSEntity_0D, SMDSAbs_0DElement, SMDSGeom_POINT,
-             /*isPoly=*/0,/*nbCN=*/1,/*nbN=*/1,/*nbE=*/0,/*nbF=*/0 );
-      p[ VTK_LINE ].
-        Set( SMDSEntity_Edge, SMDSAbs_Edge, SMDSGeom_EDGE,
-             /*isPoly=*/0,/*nbCN=*/2,/*nbN=*/2,/*nbE=*/1,/*nbF=*/0 );
-      p[ VTK_QUADRATIC_EDGE ].
-        Set( SMDSEntity_Quad_Edge, SMDSAbs_Edge, SMDSGeom_EDGE,
-             /*isPoly=*/0,/*nbCN=*/2,/*nbN=*/3,/*nbE=*/1,/*nbF=*/0 );
-      p[ VTK_TRIANGLE ].
-        Set( SMDSEntity_Triangle, SMDSAbs_Face, SMDSGeom_TRIANGLE,
-             /*isPoly=*/0,/*nbCN=*/3,/*nbN=*/3,/*nbE=*/3,/*nbF=*/1 );
-      p[ VTK_QUADRATIC_TRIANGLE ].
-        Set( SMDSEntity_Quad_Triangle, SMDSAbs_Face, SMDSGeom_TRIANGLE,
-             /*isPoly=*/0,/*nbCN=*/3,/*nbN=*/6,/*nbE=*/3,/*nbF=*/1 );
-      p[ VTK_BIQUADRATIC_TRIANGLE ].
-        Set( SMDSEntity_BiQuad_Triangle, SMDSAbs_Face, SMDSGeom_TRIANGLE,
-             /*isPoly=*/0,/*nbCN=*/3,/*nbN=*/7,/*nbE=*/3,/*nbF=*/1 );
-      p[ VTK_QUAD].
-        Set( SMDSEntity_Quadrangle, SMDSAbs_Face, SMDSGeom_QUADRANGLE,
-             /*isPoly=*/0,/*nbCN=*/4,/*nbN=*/4,/*nbE=*/4,/*nbF=*/1 );
-      p[ VTK_QUADRATIC_QUAD].
-        Set( SMDSEntity_Quad_Quadrangle, SMDSAbs_Face, SMDSGeom_QUADRANGLE,
-             /*isPoly=*/0,/*nbCN=*/4,/*nbN=*/8,/*nbE=*/4,/*nbF=*/1 );
-      p[ VTK_BIQUADRATIC_QUAD].
-        Set( SMDSEntity_BiQuad_Quadrangle, SMDSAbs_Face, SMDSGeom_QUADRANGLE,
-             /*isPoly=*/0,/*nbCN=*/4,/*nbN=*/9,/*nbE=*/4,/*nbF=*/1 );
-      p[ VTK_POLYGON ].
-        Set( SMDSEntity_Polygon, SMDSAbs_Face, SMDSGeom_POLYGON,
-             /*isPoly=*/1,/*nbCN=*/-1,/*nbN=*/-1,/*nbE=*/-1,/*nbF=*/1 );
-      p[ VTK_QUADRATIC_POLYGON ].
-        Set( SMDSEntity_Quad_Polygon, SMDSAbs_Face, SMDSGeom_POLYGON,
-             /*isPoly=*/1,/*nbCN=*/-2,/*nbN=*/-1,/*nbE=*/-1,/*nbF=*/1 );
-      p[ VTK_TETRA ].
-        Set( SMDSEntity_Tetra, SMDSAbs_Volume, SMDSGeom_TETRA,
-             /*isPoly=*/0,/*nbCN=*/4,/*nbN=*/4,/*nbE=*/6,/*nbF=*/4 );
-      p[ VTK_QUADRATIC_TETRA ].
-        Set( SMDSEntity_Quad_Tetra, SMDSAbs_Volume, SMDSGeom_TETRA,
-             /*isPoly=*/0,/*nbCN=*/4,/*nbN=*/10,/*nbE=*/6,/*nbF=*/4 );
-      p[ VTK_PYRAMID ].
-        Set( SMDSEntity_Pyramid, SMDSAbs_Volume, SMDSGeom_PYRAMID,
-             /*isPoly=*/0,/*nbCN=*/5,/*nbN=*/5,/*nbE=*/8,/*nbF=*/5 );
-      p[ VTK_QUADRATIC_PYRAMID].
-        Set( SMDSEntity_Quad_Pyramid, SMDSAbs_Volume, SMDSGeom_PYRAMID,
-             /*isPoly=*/0,/*nbCN=*/5,/*nbN=*/13,/*nbE=*/8,/*nbF=*/5 );
-      p[ VTK_HEXAHEDRON ].
-        Set( SMDSEntity_Hexa, SMDSAbs_Volume, SMDSGeom_HEXA,
-             /*isPoly=*/0,/*nbCN=*/8,/*nbN=*/8,/*nbE=*/12,/*nbF=*/6 );
-      p[ VTK_QUADRATIC_HEXAHEDRON ].
-        Set( SMDSEntity_Quad_Hexa, SMDSAbs_Volume, SMDSGeom_HEXA,
-             /*isPoly=*/0,/*nbCN=*/8,/*nbN=*/20,/*nbE=*/12,/*nbF=*/6 );
-      p[ VTK_TRIQUADRATIC_HEXAHEDRON ].
-        Set( SMDSEntity_TriQuad_Hexa, SMDSAbs_Volume, SMDSGeom_HEXA,
-             /*isPoly=*/0,/*nbCN=*/8,/*nbN=*/27,/*nbE=*/12,/*nbF=*/6 );
-      p[ VTK_WEDGE ].
-        Set( SMDSEntity_Penta, SMDSAbs_Volume, SMDSGeom_PENTA,
-             /*isPoly=*/0,/*nbCN=*/6,/*nbN=*/6,/*nbE=*/9,/*nbF=*/5 );
-      p[ VTK_QUADRATIC_WEDGE ].
-        Set( SMDSEntity_Quad_Penta, SMDSAbs_Volume, SMDSGeom_PENTA,
-             /*isPoly=*/0,/*nbCN=*/6,/*nbN=*/15,/*nbE=*/9,/*nbF=*/5 );
-      p[ VTK_BIQUADRATIC_QUADRATIC_WEDGE ].
-        Set( SMDSEntity_BiQuad_Penta, SMDSAbs_Volume, SMDSGeom_PENTA,
-             /*isPoly=*/0,/*nbCN=*/6,/*nbN=*/21,/*nbE=*/9,/*nbF=*/5 );
-      p[ VTK_HEXAGONAL_PRISM].
-        Set( SMDSEntity_Hexagonal_Prism, SMDSAbs_Volume, SMDSGeom_HEXAGONAL_PRISM,
-             /*isPoly=*/0,/*nbCN=*/12,/*nbN=*/12,/*nbE=*/18,/*nbF=*/8 );
-      p[ VTK_POLYHEDRON ].
-        Set( SMDSEntity_Polyhedra, SMDSAbs_Volume, SMDSGeom_POLYHEDRA,
-             /*isPoly=*/1,/*nbCN=*/-1,/*nbN=*/-1,/*nbE=*/-1,/*nbF=*/-1 );
-      p[ VTK_POLY_VERTEX].
-        Set( SMDSEntity_Ball, SMDSAbs_Ball, SMDSGeom_BALL,
-             /*isPoly=*/0,/*nbCN=*/1,/*nbN=*/1,/*nbE=*/0,/*nbF=*/0 );
-    }
-    return theCellProps[ vtkType ];
-
-  } // getCellProps()
-
-  //! return vector a CellProps
-  const CellProps& getCellProps( SMDSAbs_EntityType entity )
-  {
-    return getCellProps( SMDS_MeshCell::toVtkType( entity ));
-  }
-  
-} // namespace
-
-void SMDS_MeshCell::InitStaticMembers()
-{
-  getCellProps( SMDSEntity_Ball );
-  toVtkOrder( SMDSEntity_Ball );
-  reverseSmdsOrder( SMDSEntity_Ball, 1 );
-  interlacedSmdsOrder( SMDSEntity_Ball, 1 );
-  fromVtkOrder( SMDSEntity_Ball );
-}
-
-void SMDS_MeshCell::init( SMDSAbs_EntityType theEntity, int theNbNodes, ... )
-{
-  ASSERT( getCellProps( theEntity ).myNbNodes == theNbNodes ||
-          getCellProps( theEntity ).myIsPoly);
-
-  va_list vl;
-  va_start( vl, theNbNodes );
-
-  vtkIdType vtkIds[ VTK_CELL_SIZE ];
-  typedef const SMDS_MeshNode* node_t;
-
-  const std::vector<int>& interlace = toVtkOrder( theEntity );
-  if ((int) interlace.size() == theNbNodes )
-  {
-    const SMDS_MeshNode* nodes[ VTK_CELL_SIZE ];
-    for ( int i = 0; i < theNbNodes; i++ )
-      nodes[i] = va_arg( vl, node_t );
-
-    for ( int i = 0; i < theNbNodes; i++ )
-      vtkIds[i] = nodes[ interlace[i] ]->GetVtkID();
-  }
-  else
-  {
-    for ( int i = 0; i < theNbNodes; i++ )
-      vtkIds[i] = va_arg( vl, node_t )->GetVtkID();
-  }
-  va_end( vl );
-
-  int vtkType = toVtkType( theEntity );
-  int   vtkID = getGrid()->InsertNextLinkedCell( vtkType, theNbNodes, vtkIds );
-  setVtkID( vtkID );
-}
-
-void SMDS_MeshCell::init( SMDSAbs_EntityType                       theEntity,
-                          const std::vector<const SMDS_MeshNode*>& nodes )
-{
-  std::vector< vtkIdType > vtkIds( nodes.size() );
-  for ( size_t i = 0; i < nodes.size(); ++i )
-    vtkIds[i] = nodes[i]->GetVtkID();
-
-  int vtkType = toVtkType( theEntity );
-  int   vtkID = getGrid()->InsertNextLinkedCell( vtkType, nodes.size(), &vtkIds[0] );
-  setVtkID( vtkID );
-}
-
-void SMDS_MeshCell::init( SMDSAbs_EntityType            theEntity,
-                          const std::vector<vtkIdType>& vtkNodeIds )
-{
-  int vtkType = toVtkType( theEntity );
-  int   vtkID = getGrid()->InsertNextLinkedCell( vtkType, vtkNodeIds.size(),
-                                                 const_cast< vtkIdType* > ( &vtkNodeIds[0] ));
-  setVtkID( vtkID );
-}
-
-bool SMDS_MeshCell::ChangeNodes(const SMDS_MeshNode* nodes[], const int theNbNodes)
-{
-  vtkIdType npts = 0;
-  vtkIdType* pts = 0;
-  getGrid()->GetCellPoints( GetVtkID(), npts, pts );
-  if ( theNbNodes != npts )
-  {
-    MESSAGE("ChangeNodes problem: not the same number of nodes " << npts << " -> " << theNbNodes);
-    return false;
-  }
-  const std::vector<int>& interlace = toVtkOrder((VTKCellType) GetVtkType() );
-  if ((int) interlace.size() != theNbNodes )
-    for ( int i = 0; i < theNbNodes; i++ )
-    {
-      pts[i] = nodes[i]->GetVtkID();
-    }
-  else
-    for ( int i = 0; i < theNbNodes; i++ )
-    {
-      pts[i] = nodes[ interlace[i] ]->GetVtkID();
-    }
-
-  return true;
-}
-
-///////////////////////////////////////////////////////////////////////////////
-///Return The number of nodes owned by the current element
-///////////////////////////////////////////////////////////////////////////////
-int SMDS_MeshCell::NbNodes() const
+SMDS_MeshCell::SMDS_MeshCell() :
+  SMDS_MeshElement(-1)
 {
-  if ( GetEntityType() == SMDSEntity_Polyhedra )
-    return static_cast< const SMDS_MeshVolume* >( this )->SMDS_MeshVolume::NbNodes();
-  vtkIdType *pts, npts;
-  getGrid()->GetCellPoints( GetVtkID(), npts, pts );
-  return npts;
+  nbCells++;
+  myVtkID = -1;
 }
 
-int SMDS_MeshCell::NbFaces() const
+SMDS_MeshCell::~SMDS_MeshCell()
 {
-  if ( GetEntityType() == SMDSEntity_Polyhedra )
-    return static_cast< const SMDS_MeshVolume* >( this )->SMDS_MeshVolume::NbFaces();
-  return getCellProps( GetVtkType() ).myNbFaces;
+  nbCells--;
 }
-
-int SMDS_MeshCell::NbEdges() const
-{
-  switch ( GetEntityType() )
-  {
-  case SMDSEntity_Polyhedra:
-    return static_cast< const SMDS_MeshVolume* >( this )->SMDS_MeshVolume::NbEdges();
-  case SMDSEntity_Polygon:
-    return NbNodes();
-  case SMDSEntity_Quad_Polygon:
-    return NbNodes() / 2;
-  default:;
-  }
-  return getCellProps( GetVtkType() ).myNbEdges;
-}
-
-int SMDS_MeshCell::NbCornerNodes() const
-{
-  switch ( GetEntityType() )
-  {
-  case SMDSEntity_Polyhedra:
-    return static_cast< const SMDS_MeshVolume* >( this )->SMDS_MeshVolume::NbCornerNodes();
-  case SMDSEntity_Polygon:
-    return NbNodes();
-  case SMDSEntity_Quad_Polygon:
-    return NbNodes() / 2;
-  default:;
-  }
-  return getCellProps( GetVtkType() ).myNbCornerNodes;
-}
-
-///////////////////////////////////////////////////////////////////////////////
-/// Create an iterator which iterate on nodes owned by the element.
-///////////////////////////////////////////////////////////////////////////////
-SMDS_ElemIteratorPtr SMDS_MeshCell::nodesIterator() const
-{
-  if ( GetEntityType() == SMDSEntity_Polyhedra )
-    return static_cast< const SMDS_MeshVolume* >( this )->SMDS_MeshVolume::nodesIterator();
-
-  return boost::make_shared< SMDS_VtkCellIterator<> >( GetMesh(), GetVtkID(), GetEntityType());
-}
-
-///////////////////////////////////////////////////////////////////////////////
-/// Create an iterator which iterate on nodes owned by the element.
-///////////////////////////////////////////////////////////////////////////////
-SMDS_NodeIteratorPtr SMDS_MeshCell::nodeIterator() const
-{
-  if ( GetEntityType() == SMDSEntity_Polyhedra )
-    return static_cast< const SMDS_MeshVolume* >( this )->SMDS_MeshVolume::nodeIterator();
-
-  return SMDS_NodeIteratorPtr
-    (new SMDS_VtkCellIterator<SMDS_NodeIterator>( GetMesh(), GetVtkID(), GetEntityType()));
-}
-
-SMDS_NodeIteratorPtr SMDS_MeshCell::interlacedNodesIterator() const
-{
-  bool canInterlace = ( GetType() == SMDSAbs_Face || GetType() == SMDSAbs_Edge );
-  return canInterlace ? nodesIteratorToUNV() : nodeIterator();
-}
-
-SMDS_NodeIteratorPtr SMDS_MeshCell::nodesIteratorToUNV() const
-{
-  return SMDS_NodeIteratorPtr
-    (new SMDS_VtkCellIteratorToUNV<SMDS_NodeIterator>( GetMesh(), GetVtkID(), GetEntityType()));
-}
-
-SMDSAbs_ElementType SMDS_MeshCell::GetType() const
-{
-  return ElemType( GetEntityType() );
-}
-
-SMDSAbs_EntityType SMDS_MeshCell::GetEntityType() const
-{
-  return toSmdsType( (VTKCellType) GetVtkType() );
-}
-
-SMDSAbs_GeometryType SMDS_MeshCell::GetGeomType() const
-{
-  return getCellProps( GetVtkType() ).myGeom;
-}
-
-VTKCellType SMDS_MeshCell::GetVtkType() const
-{
-  return (VTKCellType) getGrid()->GetCellType( GetVtkID() );
-}
-
-bool SMDS_MeshCell::IsPoly() const
-{
-  return getCellProps( GetVtkType() ).myIsPoly;
-}
-
-bool SMDS_MeshCell::IsQuadratic() const
-{
-  return getCellProps( GetVtkType() ).IsQuadratic();
-}
-
-const SMDS_MeshNode* SMDS_MeshCell::GetNode(const int ind) const
-{
-  if ( GetEntityType() == SMDSEntity_Polyhedra )
-    return static_cast< const SMDS_MeshVolume* >( this )->SMDS_MeshVolume::GetNode( ind );
-
-  vtkIdType npts, *pts;
-  getGrid()->GetCellPoints( GetVtkID(), npts, pts );
-  const std::vector<int>& interlace = SMDS_MeshCell::fromVtkOrder( VTKCellType( GetVtkType() ));
-  return GetMesh()->FindNodeVtk( pts[ interlace.empty() ? ind : interlace[ ind ]]);
-}
-
-int SMDS_MeshCell::GetNodeIndex( const SMDS_MeshNode* node ) const
-{
-  if ( GetEntityType() == SMDSEntity_Polyhedra )
-    return static_cast< const SMDS_MeshVolume* >( this )->SMDS_MeshVolume::GetNodeIndex( node );
-
-  vtkIdType npts, *pts;
-  getGrid()->GetCellPoints( GetVtkID(), npts, pts );
-  for ( vtkIdType i = 0; i < npts; ++i )
-    if ( pts[i] == node->GetVtkID() )
-    {
-      const std::vector<int>& interlace = SMDS_MeshCell::toVtkOrder( VTKCellType( GetVtkType() ));
-      return interlace.empty() ? i : interlace[i];
-    }
-  return -1;
-}
-
 //================================================================================
 /*!
  * \brief Return VTKCellType corresponding to SMDSAbs_EntityType
@@ -624,7 +262,7 @@ const std::vector<int>& SMDS_MeshCell::reverseSmdsOrder(SMDSAbs_EntityType smdsT
       const int ids[] = {0,2,1,3,5,4, 8,7,6,11,10,9,12,14,13,15,16,17};
       reverseInterlaces[SMDSEntity_BiQuad_Penta].assign( &ids[0], &ids[0]+18 );
     }
-    {
+   {
       const int ids[] = {0,5,4,3,2,1,6,11,10,9,8,7};
       reverseInterlaces[SMDSEntity_Hexagonal_Prism].assign( &ids[0], &ids[0]+12 );
     }
@@ -710,7 +348,14 @@ const std::vector<int>& SMDS_MeshCell::interlacedSmdsOrder(SMDSAbs_EntityType sm
 
 SMDSAbs_EntityType SMDS_MeshCell::toSmdsType(VTKCellType vtkType)
 {
-  return getCellProps( vtkType ).myEntity;
+  static std::vector< SMDSAbs_EntityType > smdsTypes;
+  if ( smdsTypes.empty() )
+  {
+    smdsTypes.resize( VTK_NUMBER_OF_CELL_TYPES, SMDSEntity_Last );
+    for ( int iSMDS = 0; iSMDS < SMDSEntity_Last; ++iSMDS )
+      smdsTypes[ toVtkType( SMDSAbs_EntityType( iSMDS ))] = SMDSAbs_EntityType( iSMDS );
+  }
+  return smdsTypes[ vtkType ];
 }
 
 //================================================================================
@@ -719,7 +364,7 @@ SMDSAbs_EntityType SMDS_MeshCell::toSmdsType(VTKCellType vtkType)
  */
 //================================================================================
 
-SMDSAbs_ElementType SMDS_MeshCell::ElemType(SMDSAbs_GeometryType geomType)
+SMDSAbs_ElementType SMDS_MeshCell::toSmdsType(SMDSAbs_GeometryType geomType)
 {
   switch ( geomType ) {
   case SMDSGeom_POINT:     return SMDSAbs_0DElement;
@@ -750,45 +395,46 @@ SMDSAbs_ElementType SMDS_MeshCell::ElemType(SMDSAbs_GeometryType geomType)
  */
 //================================================================================
 
-SMDSAbs_ElementType SMDS_MeshCell::ElemType(SMDSAbs_EntityType entityType)
+SMDSAbs_ElementType SMDS_MeshCell::toSmdsType(SMDSAbs_EntityType entityType)
 {
-  return getCellProps( entityType ).myType;
-}
-
-SMDSAbs_GeometryType SMDS_MeshCell::GeomType( SMDSAbs_EntityType entityType )
-{
-  return getCellProps( entityType ).myGeom;
-}
+  switch ( entityType ) {
+  case SMDSEntity_Node:           return SMDSAbs_Node;
 
-bool SMDS_MeshCell::IsPoly( SMDSAbs_EntityType entityType )
-{
-  return getCellProps( entityType ).myIsPoly;
-}
+  case SMDSEntity_0D:             return SMDSAbs_0DElement;
 
-bool SMDS_MeshCell::IsQuadratic( SMDSAbs_EntityType entityType )
-{
-  return getCellProps( entityType ).IsQuadratic();
-}
+  case SMDSEntity_Edge:
+  case SMDSEntity_Quad_Edge:      return SMDSAbs_Edge;
 
-int SMDS_MeshCell::NbCornerNodes( SMDSAbs_EntityType entityType )
-{
-  return getCellProps( entityType ).myNbCornerNodes;
-}
+  case SMDSEntity_Triangle:
+  case SMDSEntity_Quad_Triangle:
+  case SMDSEntity_BiQuad_Triangle:
+  case SMDSEntity_Quadrangle:
+  case SMDSEntity_Quad_Quadrangle:
+  case SMDSEntity_BiQuad_Quadrangle:
+  case SMDSEntity_Polygon:
+  case SMDSEntity_Quad_Polygon:   return SMDSAbs_Face;
+
+  case SMDSEntity_Tetra:
+  case SMDSEntity_Quad_Tetra:
+  case SMDSEntity_Pyramid:
+  case SMDSEntity_Quad_Pyramid:
+  case SMDSEntity_Hexa:
+  case SMDSEntity_Quad_Hexa:
+  case SMDSEntity_TriQuad_Hexa:
+  case SMDSEntity_Penta:
+  case SMDSEntity_Quad_Penta:
+  case SMDSEntity_BiQuad_Penta:
+  case SMDSEntity_Hexagonal_Prism:
+  case SMDSEntity_Polyhedra:
+  case SMDSEntity_Quad_Polyhedra: return SMDSAbs_Volume;
 
-int SMDS_MeshCell::NbNodes( SMDSAbs_EntityType entityType )
-{
-  return getCellProps( entityType ).myNbNodes;
-}
+  case SMDSEntity_Ball:           return SMDSAbs_Ball;
 
-int SMDS_MeshCell::NbEdges( SMDSAbs_EntityType entityType )
-{
-  return getCellProps( entityType ).myNbEdges;
+  case SMDSEntity_Last:;
+  }
+  return SMDSAbs_All;
 }
 
-int SMDS_MeshCell::NbFaces( SMDSAbs_EntityType entityType )
-{
-  return getCellProps( entityType ).myNbFaces;
-}
 
 //================================================================================
 /*!
index 568cbbbc9c9763e462e7e1b01e6cfbb62787c7d6..413b1265ab6e3f729e8f6587a16de5e33e88deb1 100644 (file)
 
 class SMDS_EXPORT SMDS_MeshCell: public SMDS_MeshElement
 {
- protected:
+public:
+  SMDS_MeshCell();
+  virtual ~SMDS_MeshCell();
 
-  void init( SMDSAbs_EntityType entityType, int nbNodes, ... );
+  virtual bool ChangeNodes(const SMDS_MeshNode* nodes[], const int nbNodes)= 0;
+  virtual bool vtkOrder(const SMDS_MeshNode* nodes[], const int nbNodes) { return true; }
 
-  void init( SMDSAbs_EntityType entityType, const std::vector<const SMDS_MeshNode*>& nodes );
-
-  void init( SMDSAbs_EntityType entityType, const std::vector<vtkIdType>& vtkNodeIds );
-
-  friend class SMDS_Mesh;
-
- public:
-
-  virtual int  NbEdges() const;
-  virtual int  NbFaces() const;
-  virtual int  NbNodes() const;
-  virtual int  NbCornerNodes() const;
-  virtual bool ChangeNodes(const SMDS_MeshNode* nodes[], const int nbNodes);
-  virtual int  GetNodeIndex( const SMDS_MeshNode* node ) const;
-  virtual const SMDS_MeshNode* GetNode(const int ind) const;
-
-  virtual SMDSAbs_ElementType  GetType() const;
-  virtual SMDSAbs_EntityType   GetEntityType() const;
-  virtual SMDSAbs_GeometryType GetGeomType() const;
-  virtual VTKCellType          GetVtkType() const;
-
-  virtual bool IsPoly() const;
-  virtual bool IsQuadratic() const;
-
-  virtual SMDS_ElemIteratorPtr nodesIterator() const;
-  virtual SMDS_NodeIteratorPtr nodeIterator() const;
-  virtual SMDS_NodeIteratorPtr interlacedNodesIterator() const;
-  virtual SMDS_NodeIteratorPtr nodesIteratorToUNV() const;
-
-
-  static void InitStaticMembers();
-  static VTKCellType          toVtkType    ( SMDSAbs_EntityType   entityType );
-  static SMDSAbs_EntityType   toSmdsType   ( VTKCellType          vtkType );
-  static SMDSAbs_ElementType  ElemType     ( SMDSAbs_GeometryType geomType );
-  static SMDSAbs_ElementType  ElemType     ( SMDSAbs_EntityType   entityType );
-  static SMDSAbs_GeometryType GeomType     ( SMDSAbs_EntityType   entityType );
-  static bool                 IsPoly       ( SMDSAbs_EntityType   entityType );
-  static bool                 IsQuadratic  ( SMDSAbs_EntityType   entityType );
-  static int                  NbCornerNodes( SMDSAbs_EntityType   entityType );
-  static int                  NbNodes      ( SMDSAbs_EntityType   entityType );
-  static int                  NbEdges      ( SMDSAbs_EntityType   entityType );
-  static int                  NbFaces      ( SMDSAbs_EntityType   entityType );
+  static VTKCellType         toVtkType (SMDSAbs_EntityType vtkType);
+  static SMDSAbs_EntityType  toSmdsType(VTKCellType vtkType);
+  static SMDSAbs_ElementType toSmdsType(SMDSAbs_GeometryType geomType);
+  static SMDSAbs_ElementType toSmdsType(SMDSAbs_EntityType entityType);
 
   static const std::vector<int>& toVtkOrder(VTKCellType vtkType);
   static const std::vector<int>& toVtkOrder(SMDSAbs_EntityType smdsType);
@@ -85,7 +50,6 @@ class SMDS_EXPORT SMDS_MeshCell: public SMDS_MeshElement
   static const std::vector<int>& interlacedSmdsOrder(SMDSAbs_EntityType smdsType,
                                                      const size_t       nbNodes=0);
 
-
   template< class VECT > // interlacedIDs[i] = smdsIDs[ indices[ i ]]
     static void applyInterlace( const std::vector<int>& interlace, VECT & data)
   {
@@ -105,6 +69,15 @@ class SMDS_EXPORT SMDS_MeshCell: public SMDS_MeshElement
     data.swap( tmpData );
   }
 
+  static int nbCells;
+
+protected:
+  inline void exchange(const SMDS_MeshNode* nodes[],int a, int b)
+  {
+    const SMDS_MeshNode* noda = nodes[a];
+    nodes[a] = nodes[b];
+    nodes[b] = noda;
+  }
 };
 
 #endif
diff --git a/src/SMDS/SMDS_MeshEdge.cxx b/src/SMDS/SMDS_MeshEdge.cxx
new file mode 100644 (file)
index 0000000..672adee
--- /dev/null
@@ -0,0 +1,30 @@
+// Copyright (C) 2010-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+#include "SMDS_MeshEdge.hxx"
+
+SMDSAbs_ElementType SMDS_MeshEdge::GetType() const
+{
+        return SMDSAbs_Edge;
+}
+
+vtkIdType SMDS_MeshEdge::GetVtkType() const
+{
+  return VTK_POLY_VERTEX; // --- must be reimplemented in derived classes
+}
index 462028e911091179350e1d86ca90e1c8c3f858c3..423d96241f8e11cadd1cfc0d0df91296e4c7f3a7 100644 (file)
 
 #include "SMDS_MeshCell.hxx"
 
-/*!
- * \brief Edge mesh element. This type is not allocated.
- *        It is only used as function argument type to provide more clear semantic.
- */
 class SMDS_EXPORT SMDS_MeshEdge: public SMDS_MeshCell
 {
+        
  public:
-  virtual SMDSAbs_ElementType  GetType()     const { return SMDSAbs_Edge; }
+  virtual SMDSAbs_ElementType  GetType() const;
+  virtual vtkIdType            GetVtkType() const;
   virtual SMDSAbs_GeometryType GetGeomType() const { return SMDSGeom_EDGE; }
-
-  static SMDSAbs_ElementType Type() { return SMDSAbs_Edge; }
 };
 #endif
index 48221c7c6861dda72d67072bf44434508399b404..31119a8eda8abc03dfd6cb094b9c797cf14bb73c 100644 (file)
 #endif
 
 #include "SMDS_MeshElement.hxx"
-
-#include "SMDS_Mesh.hxx"
-#include "SMDS_ElementFactory.hxx"
-
+#include "SMDS_MeshNode.hxx"
+#include "SMDS_MeshEdge.hxx"
+#include "SMDS_MeshFace.hxx"
+#include "SMDS_MeshVolume.hxx"
 #include "utilities.h"
 
-//================================================================================
-/*!
- * \brief Constructor of a non-used element
- */
-//================================================================================
+using namespace std;
 
-SMDS_MeshElement::SMDS_MeshElement(): myHolder(0)
+SMDS_MeshElement::SMDS_MeshElement(int ID)
 {
+  init(ID);
 }
 
-//================================================================================
-/*!
- * \brief Check if a node is a medium node of a quadratic cell
- */
-//================================================================================
-
-bool SMDS_MeshElement::IsMediumNode(const SMDS_MeshNode* node) const
+SMDS_MeshElement::SMDS_MeshElement(int id, ShortType meshId, LongType shapeId)
 {
-  return !( GetNodeIndex( node ) < NbCornerNodes() );
+  init(id, meshId, shapeId);
 }
 
-//================================================================================
-/*!
- * \brief Return true if index of node is valid (0 <= ind < NbNodes())
- *  \param ind - node index
- *  \retval bool - index check result
- */
-//================================================================================
-
-bool SMDS_MeshElement::IsValidIndex(const int ind) const
+void SMDS_MeshElement::init(int id, ShortType meshId, LongType shapeId )
 {
-  return ( ind>-1 && ind<NbNodes() );
+  myID = id;
+  myMeshId = meshId;
+  myShapeId = shapeId;
+  myIdInShape = -1;
 }
 
-//================================================================================
-/*!
- * \brief Return a valid corner node index, fixing the given one if necessary
- * \param ind - node index
- * \retval int - valid node index
- */
-//================================================================================
-
-int SMDS_MeshElement::WrappedIndex(const int ind) const
+void SMDS_MeshElement::Print(ostream & OS) const
 {
-  if ( ind < 0 ) return NbCornerNodes() + ind % NbCornerNodes();
-  if ( ind >= NbCornerNodes() ) return ind % NbCornerNodes();
-  return ind;
+  OS << "dump of mesh element" << endl;
 }
 
-//================================================================================
-/*!
- * \brief Check if a node belongs to the element
- * \param node - the node to check
- * \retval int - node index within the element, -1 if not found
- */
-//================================================================================
+ostream & operator <<(ostream & OS, const SMDS_MeshElement * ME)
+{
+  ME->Print(OS);
+  return OS;
+}
 
-int SMDS_MeshElement::GetNodeIndex( const SMDS_MeshNode* node ) const
+///////////////////////////////////////////////////////////////////////////////
+/// Create an iterator which iterate on nodes owned by the element.
+/// This method call elementsIterator().
+///////////////////////////////////////////////////////////////////////////////
+SMDS_ElemIteratorPtr SMDS_MeshElement::nodesIterator() const
 {
-  SMDS_ElemIteratorPtr nIt = nodesIterator();
-  for ( int i = 0; nIt->more(); ++i )
-    if ( nIt->next() == node )
-      return i;
-  return -1;
+  return elementsIterator(SMDSAbs_Node);
 }
 
-//================================================================================
-/*!
- * \brief Return ID of an element
- */
-//================================================================================
+///////////////////////////////////////////////////////////////////////////////
+/// Create an iterator which iterate on edges linked with or owned by the element.
+/// This method call elementsIterator().
+///////////////////////////////////////////////////////////////////////////////
+SMDS_ElemIteratorPtr SMDS_MeshElement::edgesIterator() const
+{
+  return elementsIterator(SMDSAbs_Edge);
+}
 
-int SMDS_MeshElement::GetID() const
+///////////////////////////////////////////////////////////////////////////////
+/// Create an iterator which iterate on faces linked with or owned by the element.
+/// This method call elementsIterator().
+///////////////////////////////////////////////////////////////////////////////
+SMDS_ElemIteratorPtr SMDS_MeshElement::facesIterator() const
 {
-  return myHolder ? myHolder->GetID( this ) : -1;
+  return elementsIterator(SMDSAbs_Face);
 }
 
-//================================================================================
-/*!
- * \brief Set ID of a shape this element was generated on
- */
-//================================================================================
+///////////////////////////////////////////////////////////////////////////////
+///Return The number of nodes owned by the current element
+///////////////////////////////////////////////////////////////////////////////
+int SMDS_MeshElement::NbNodes() const
+{
+  int nbnodes=0;
+  SMDS_ElemIteratorPtr it=nodesIterator();
+  while(it->more())
+  {
+    it->next();
+    nbnodes++;
+  }
+  return nbnodes;
+}
 
-void SMDS_MeshElement::setShapeID( const int shapeID ) const
+///////////////////////////////////////////////////////////////////////////////
+///Return the number of edges owned by or linked with the current element
+///////////////////////////////////////////////////////////////////////////////
+int SMDS_MeshElement::NbEdges() const
 {
-  const_cast<SMDS_ElementChunk*>( myHolder )->SetShapeID( this, shapeID );
+  int nbedges=0;
+  SMDS_ElemIteratorPtr it=edgesIterator();
+  while(it->more())
+  {
+    it->next();
+    nbedges++;
+  }
+  return nbedges;
 }
 
-//================================================================================
-/*!
- * \brief Return ID of a shape this element was generated on
- */
-//================================================================================
+///////////////////////////////////////////////////////////////////////////////
+///Return the number of faces owned by or linked with the current element
+///////////////////////////////////////////////////////////////////////////////
+int SMDS_MeshElement::NbFaces() const
+{
+  int nbfaces=0;
+  SMDS_ElemIteratorPtr it=facesIterator();
+  while(it->more())
+  {
+    it->next();
+    nbfaces++;
+  }
+  return nbfaces;
+}
 
-int SMDS_MeshElement::GetShapeID() const
+///////////////////////////////////////////////////////////////////////////////
+///Create an iterator which iterate on elements linked with the current element.
+///@param type The of elements on which you want to iterate
+///@return A smart pointer to iterator, you are not to take care of freeing memory
+///////////////////////////////////////////////////////////////////////////////
+class SMDS_MeshElement_MyIterator:public SMDS_ElemIterator
+{
+  const SMDS_MeshElement * myElement;
+  bool myMore;
+public:
+  SMDS_MeshElement_MyIterator(const SMDS_MeshElement * element):
+    myElement(element),myMore(true) {}
+
+  bool more()
+  {
+    return myMore;
+  }
+
+  const SMDS_MeshElement* next()
+  {
+    myMore=false;
+    return myElement;   
+  }     
+};
+
+SMDS_ElemIteratorPtr
+SMDS_MeshElement::elementsIterator(SMDSAbs_ElementType type) const
 {
-  return myHolder->GetShapeID( this );
+  /** @todo Check that iterator in the child classes return elements
+      in the same order for each different implementation (i.e: SMDS_VolumeOfNodes
+      and SMDS_VolumeOfFaces */
+  if(type==GetType())
+    return SMDS_ElemIteratorPtr(new SMDS_MeshElement_MyIterator(this));
+  else
+  {
+    MESSAGE("Iterator not implemented");
+    return SMDS_ElemIteratorPtr((SMDS_ElemIterator*)NULL);
+  }
 }
 
-//================================================================================
-/*!
- * \brief Return VTK ID of this element
- */
-//================================================================================
+//! virtual, redefined in vtkEdge, vtkFace and vtkVolume classes
+SMDS_NodeIteratorPtr SMDS_MeshElement::nodesIteratorToUNV() const
+{
+  return nodeIterator();
+}
 
-int SMDS_MeshElement::GetVtkID() const
+//! virtual, redefined in vtkEdge, vtkFace and vtkVolume classes
+SMDS_NodeIteratorPtr SMDS_MeshElement::interlacedNodesIterator() const
 {
-  return myHolder->GetVtkID( this );
+  return nodeIterator();
 }
 
-//================================================================================
-/*!
- * \brief Mark this element
- */
-//================================================================================
+namespace
+{
+  //=======================================================================
+  //class : _MyNodeIteratorFromElemIterator
+  //=======================================================================
+  class _MyNodeIteratorFromElemIterator : public SMDS_NodeIterator
+  {
+    SMDS_ElemIteratorPtr myItr;
+  public:
+    _MyNodeIteratorFromElemIterator(SMDS_ElemIteratorPtr elemItr):myItr( elemItr ) {}
+    bool                 more() { return myItr->more(); }
+    const SMDS_MeshNode* next() { return static_cast< const SMDS_MeshNode*>( myItr->next() ); }
+  };
+  //=======================================================================
+  //class : _MyElemIteratorFromNodeIterator
+  //=======================================================================
+  class _MyElemIteratorFromNodeIterator : public SMDS_ElemIterator
+  {
+    SMDS_NodeIteratorPtr myItr;
+  public:
+    _MyElemIteratorFromNodeIterator(SMDS_NodeIteratorPtr nodeItr): myItr( nodeItr ) {}
+    bool more()                    { return myItr->more(); }
+    const SMDS_MeshElement* next() { return myItr->next(); }
+  };
+}
 
-void SMDS_MeshElement::setIsMarked( bool is ) const
+SMDS_ElemIteratorPtr SMDS_MeshElement::interlacedNodesElemIterator() const
 {
-  const_cast<SMDS_ElementChunk*>( myHolder )->SetIsMarked( this, is );
+  return SMDS_ElemIteratorPtr
+    ( new _MyElemIteratorFromNodeIterator( interlacedNodesIterator() ));
 }
 
-//================================================================================
-/*!
- * \brief Check if this element is marked
- */
-//================================================================================
+SMDS_NodeIteratorPtr SMDS_MeshElement::nodeIterator() const
+{
+  return SMDS_NodeIteratorPtr
+    ( new _MyNodeIteratorFromElemIterator( nodesIterator() ));
+}
 
-bool SMDS_MeshElement::isMarked() const
+bool operator<(const SMDS_MeshElement& e1, const SMDS_MeshElement& e2)
 {
-  return myHolder->IsMarked( this );
+  if(e1.GetType()!=e2.GetType()) return false;
+  switch(e1.GetType())
+  {
+  case SMDSAbs_Node:
+    return static_cast<const SMDS_MeshNode &>(e1) <
+    static_cast<const SMDS_MeshNode &>(e2);
+
+  case SMDSAbs_Edge:
+    return static_cast<const SMDS_MeshEdge &>(e1) <
+    static_cast<const SMDS_MeshEdge &>(e2);
+
+  case SMDSAbs_Face:
+    return static_cast<const SMDS_MeshFace &>(e1) <
+    static_cast<const SMDS_MeshFace &>(e2);
+
+  case SMDSAbs_Volume:
+    return static_cast<const SMDS_MeshVolume &>(e1) <
+    static_cast<const SMDS_MeshVolume &>(e2);
+
+  default : MESSAGE("Internal Error");
+  }
+  return false;
 }
 
-//================================================================================
-/*!
- * \brief Store VTK ID
- */
-//================================================================================
+bool SMDS_MeshElement::IsValidIndex(const int ind) const
+{
+  return ( ind>-1 && ind<NbNodes() );
+}
 
-void SMDS_MeshElement::setVtkID( const int vtkID )
+const SMDS_MeshNode* SMDS_MeshElement::GetNode(const int ind) const
 {
-  myHolder->SetVTKID( this, vtkID );
+  if ( ind >= 0 ) {
+    SMDS_ElemIteratorPtr it = nodesIterator();
+    for ( int i = 0; i < ind; ++i )
+      it->next();
+    if ( it->more() )
+      return static_cast<const SMDS_MeshNode*> (it->next());
+  }
+  return 0;
 }
 
-//================================================================================
-/*!
- * \brief Return the mesh this element belongs to
- */
-//================================================================================
+bool SMDS_MeshElement::IsQuadratic() const
+{
+  return false;
+}
 
-SMDS_Mesh* SMDS_MeshElement::GetMesh() const
+bool SMDS_MeshElement::IsMediumNode(const SMDS_MeshNode* node) const
 {
-  return const_cast<SMDS_ElementChunk*>( myHolder )->GetMesh();
+  return false;
 }
 
 //================================================================================
 /*!
- * \brief Return a SMDS_UnstructuredGrid
+ * \brief Return number of nodes excluding medium ones
  */
 //================================================================================
 
-SMDS_UnstructuredGrid* SMDS_MeshElement::getGrid() const
+int SMDS_MeshElement::NbCornerNodes() const
 {
-  return const_cast<SMDS_ElementChunk*>( myHolder )->GetMesh()->GetGrid();
+  return IsQuadratic() ? NbNodes() - NbEdges() : NbNodes();
 }
 
 //================================================================================
 /*!
- * \brief Print self
+ * \brief Check if a node belongs to the element
+ * \param node - the node to check
+ * \retval int - node index within the element, -1 if not found
  */
 //================================================================================
 
-void SMDS_MeshElement::Print(ostream & OS) const
-{
-  OS << "dump of mesh element" << endl;
-}
-
-ostream & operator <<(ostream & OS, const SMDS_MeshElement * e)
+int SMDS_MeshElement::GetNodeIndex( const SMDS_MeshNode* node ) const
 {
-  e->Print(OS);
-  return OS;
+  SMDS_ElemIteratorPtr nIt = nodesIterator();
+  for ( int i = 0; nIt->more(); ++i )
+    if ( nIt->next() == node )
+      return i;
+  return -1;
 }
index 63fc8cecf14b41858a93d74b63e3b6700056c426..4634548aa4f2fa9146bd251edbf23c7300627196 100644 (file)
 #include "SMDSAbs_ElementType.hxx"
 #include "SMDS_MeshObject.hxx"
 #include "SMDS_ElemIterator.hxx"
+#include "SMDS_MeshElementIDFactory.hxx"
 #include "SMDS_StdIterator.hxx"
 
+#include <vector>
 #include <iostream>
 
 #include <vtkType.h>
 #include <vtkCellType.h>
 
-class SMDS_ElementChunk;
-class SMDS_Mesh;
+//typedef unsigned short UShortType;
+typedef short ShortType;
+typedef int   LongType;
+
 class SMDS_MeshNode;
-class SMDS_UnstructuredGrid;
+class SMDS_MeshEdge;
+class SMDS_MeshFace;
+class SMDS_Mesh;
 
 // ============================================================
 /*!
@@ -55,36 +61,43 @@ class SMDS_EXPORT SMDS_MeshElement : public SMDS_MeshObject
 {
 public:
 
-  // ===========================
-  // Access to nodes
-  // ===========================
-  virtual SMDS_ElemIteratorPtr nodesIterator() const = 0;
+  SMDS_ElemIteratorPtr nodesIterator() const;
+  SMDS_ElemIteratorPtr edgesIterator() const;
+  SMDS_ElemIteratorPtr facesIterator() const;
+  virtual SMDS_ElemIteratorPtr elementsIterator(SMDSAbs_ElementType type) const;
+  virtual SMDS_ElemIteratorPtr interlacedNodesElemIterator() const;
 
-  virtual SMDS_NodeIteratorPtr nodeIterator() const = 0;
-  virtual SMDS_NodeIteratorPtr interlacedNodesIterator() const { return nodeIterator(); }
-  virtual SMDS_NodeIteratorPtr nodesIteratorToUNV() const  { return nodeIterator(); }
+  virtual SMDS_NodeIteratorPtr nodeIterator() const;
+  virtual SMDS_NodeIteratorPtr interlacedNodesIterator() const;
+  virtual SMDS_NodeIteratorPtr nodesIteratorToUNV() const;
 
   // std-like iteration on nodes
-  typedef SMDS_StdIterator< const SMDS_MeshNode*, SMDS_NodeIteratorPtr > iterator;
-  iterator begin_nodes() const { return iterator( nodeIterator() ); }
+  typedef SMDS_StdIterator< const SMDS_MeshNode*, SMDS_ElemIteratorPtr > iterator;
+  iterator begin_nodes() const { return iterator( nodesIterator() ); }
   iterator end_nodes()   const { return iterator(); }
 
-  // ===========================
-  // Type of element
-  // ===========================
-  virtual int NbNodes() const = 0;
-  virtual int NbEdges() const = 0;
-  virtual int NbFaces() const = 0;
+  virtual int NbNodes() const;
+  virtual int NbEdges() const;
+  virtual int NbFaces() const;
+  inline int GetID() const { return myID; }
 
+  ///Return the type of the current element
   virtual SMDSAbs_ElementType  GetType() const = 0;
   virtual SMDSAbs_EntityType   GetEntityType() const = 0;
   virtual SMDSAbs_GeometryType GetGeomType() const = 0;
-  virtual VTKCellType          GetVtkType() const = 0;
+  virtual vtkIdType            GetVtkType() const = 0;
 
-  virtual bool IsPoly() const = 0;
-  virtual bool IsQuadratic() const = 0;
+  virtual bool IsPoly() const { return false; }
+  virtual bool IsQuadratic() const;
   virtual bool IsMediumNode(const SMDS_MeshNode* node) const;
-  virtual int  NbCornerNodes() const = 0;
+  virtual int  NbCornerNodes() const;
+
+  friend SMDS_EXPORT std::ostream & operator <<(std::ostream & OS, const SMDS_MeshElement *);
+  friend SMDS_EXPORT bool SMDS_MeshElementIDFactory::BindID(int ID,SMDS_MeshElement* elem);
+  friend class SMDS_Mesh;
+  friend class SMESHDS_Mesh;
+  friend class SMESHDS_SubMesh;
+  friend class SMDS_MeshElementIDFactory;
 
   // ===========================
   //  Access to nodes by index
@@ -94,14 +107,14 @@ public:
     * \param ind - node index
     * \retval const SMDS_MeshNode* - the node
    */
-  virtual const SMDS_MeshNode* GetNode(const int ind) const = 0;
+  virtual const SMDS_MeshNode* GetNode(const int ind) const;
 
   /*!
    * \brief Return node by its index
     * \param ind - node index
     * \retval const SMDS_MeshNode* - the node
    * 
-   * Index is wrapped if it is out of a valid range of corner nodes
+   * Index is wrapped if it is out of a valid range
    */
   const SMDS_MeshNode* GetNodeWrap(const int ind) const { return GetNode( WrappedIndex( ind )); }
 
@@ -113,11 +126,15 @@ public:
   virtual bool IsValidIndex(const int ind) const;
 
   /*!
-   * \brief Return a valid corner node index, fixing the given one if necessary
+   * \brief Return a valid node index, fixing the given one if necessary
     * \param ind - node index
     * \retval int - valid node index
    */
-  int WrappedIndex(const int ind) const;
+  int WrappedIndex(const int ind) const {
+    if ( ind < 0 ) return NbNodes() + ind % NbNodes();
+    if ( ind >= NbNodes() ) return ind % NbNodes();
+    return ind;
+  }
 
   /*!
    * \brief Check if a node belongs to the element
@@ -126,26 +143,14 @@ public:
    */
   virtual int GetNodeIndex( const SMDS_MeshNode* node ) const;
 
-
-  virtual int GetID() const;
-  virtual int GetVtkID()   const;
-  virtual int getshapeId() const { return GetShapeID(); }
-  virtual int GetShapeID() const;
+  inline ShortType getMeshId()    const { return myMeshId; }
+  inline LongType  getshapeId()   const { return myShapeId >> BITS_SHIFT; }
+  inline int       getIdInShape() const { return myIdInShape; }
+  inline int       getVtkId()     const { return myVtkID; }
 
   // mark this element; to be used in algos
-  virtual void setIsMarked( bool is ) const;
-  virtual bool isMarked() const;
-
-  // element can be allocated but "not used"
-  bool IsNull() const { return myHolder == 0; }
-
-  SMDS_Mesh* GetMesh() const;
-
-  void Print(std::ostream & OS) const;
-
-  friend SMDS_EXPORT std::ostream & operator <<(std::ostream & OS, const SMDS_MeshElement *);
-  friend class SMDS_ElementFactory;
-  friend class SMESHDS_SubMesh;
+  inline void setIsMarked( bool is ) const;
+  inline bool isMarked() const;
 
   /*!
    * \brief Filters of elements, to be used with SMDS_SetIterator
@@ -178,20 +183,42 @@ public:
     bool operator()(const SMDS_MeshElement* e) const { return e && e->GetGeomType() == _type; }
   };
 
- protected:
-
-  SMDS_MeshElement();
-
-  void setVtkID(const int vtkID );
-  virtual void setShapeID( const int shapeID ) const;
-
-  SMDS_UnstructuredGrid* getGrid() const;
-
- protected:
-
-  SMDS_ElementChunk* myHolder;
+protected:
+  inline void setId(int id)                { myID = id; }
+  inline void setVtkId(int vtkId)          { myVtkID = vtkId; }
+  inline void setIdInShape(int id)         { myIdInShape = id; }
+  inline void setShapeId(LongType shapeId) { myShapeId = ( shapeId << BITS_SHIFT ) | ( myShapeId & BIT_IS_MARKED ); }
+  SMDS_MeshElement(int ID=-1);
+  SMDS_MeshElement(int id, ShortType meshId, LongType shapeId = 0);
+  virtual void init(int id = -1, ShortType meshId = -1, LongType shapeId = 0);
+  virtual void Print(std::ostream & OS) const;
+
+  //! Element index in vector SMDS_Mesh::myNodes or SMDS_Mesh::myCells
+  int myID;
+  //! index in vtkUnstructuredGrid
+  int myVtkID;
+  //! SMDS_Mesh identification in SMESH
+  ShortType myMeshId;
+  //! SubShape and SubMesh identification in SMESHDS; one bit is used to mark the element
+  LongType myShapeId;
+  //! Element index in SMESHDS_SubMesh vector
+  int myIdInShape;
+
+  enum Bits { // use the 1st right bit of myShapeId to set/unset a mark
+    BIT_IS_MARKED = 1,
+    BITS_SHIFT = 1
+  };
 };
 
+inline void SMDS_MeshElement::setIsMarked( bool is ) const
+{
+  const_cast< SMDS_MeshElement* >( this )->myShapeId = ( myShapeId & ~BIT_IS_MARKED ) | is;
+}
+inline bool SMDS_MeshElement::isMarked() const
+{
+  return myShapeId & BIT_IS_MARKED;
+}
+
 // ============================================================
 /*!
  * \brief Comparator of elements by ID for usage in std containers
diff --git a/src/SMDS/SMDS_MeshElementIDFactory.cxx b/src/SMDS/SMDS_MeshElementIDFactory.cxx
new file mode 100644 (file)
index 0000000..c7fc45e
--- /dev/null
@@ -0,0 +1,176 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//  File   : SMDS_MeshElementIDFactory.cxx
+//  Author : Jean-Michel BOULCOURT
+//  Module : SMESH
+//
+#ifdef _MSC_VER
+#pragma warning(disable:4786)
+#endif
+
+#include "SMDS_MeshElementIDFactory.hxx"
+#include "SMDS_MeshElement.hxx"
+#include "SMDS_Mesh.hxx"
+
+#include "utilities.h"
+
+#include "SMDS_UnstructuredGrid.hxx"
+#include <vtkCellType.h>
+
+#include <climits>
+
+using namespace std;
+
+//=======================================================================
+//function : SMDS_MeshElementIDFactory
+//purpose  : 
+//=======================================================================
+SMDS_MeshElementIDFactory::SMDS_MeshElementIDFactory():
+  SMDS_MeshNodeIDFactory()
+{
+}
+
+int SMDS_MeshElementIDFactory::SetInVtkGrid(SMDS_MeshElement * elem)
+{
+  // --- retrieve nodes ID
+
+  SMDS_MeshCell *cell = dynamic_cast<SMDS_MeshCell*>(elem);
+  assert(cell);
+  vector<vtkIdType> nodeIds( elem->NbNodes() );
+  SMDS_ElemIteratorPtr it = elem->nodesIterator();
+  for( int i = 0; it->more(); ++i )
+  {
+    int nodeId = (static_cast<const SMDS_MeshNode*>(it->next()))->getVtkId();
+    nodeIds[i] = nodeId;
+  }
+
+  // --- insert cell in vtkUnstructuredGrid
+
+  int typ = VTK_VERTEX;
+  int cellId = myMesh->getGrid()->InsertNextLinkedCell(typ, nodeIds.size(), &nodeIds[0]);
+  cell->setVtkId(cellId);
+  return cellId;
+}
+
+//=======================================================================
+//function : BindID
+//purpose  :
+//=======================================================================
+
+bool SMDS_MeshElementIDFactory::BindID(int ID, SMDS_MeshElement * elem)
+{
+  SetInVtkGrid(elem);
+  return myMesh->registerElement(ID, elem);
+}
+
+//=======================================================================
+//function : MeshElement
+//purpose  : 
+//=======================================================================
+SMDS_MeshElement* SMDS_MeshElementIDFactory::MeshElement(int ID)
+{
+  if ( ID<1 || ID >= (int) myMesh->myCells.size() )
+    return NULL;
+  const SMDS_MeshElement* elem = GetMesh()->FindElement(ID);
+  return (SMDS_MeshElement*)(elem);
+}
+
+//=======================================================================
+//function : GetFreeID
+//purpose  : 
+//=======================================================================
+
+int SMDS_MeshElementIDFactory::GetFreeID()
+{
+  int ID;
+  do {
+    ID = SMDS_MeshIDFactory::GetFreeID();
+  } while ( MeshElement( ID ));
+  return ID;
+}
+
+//=======================================================================
+//function : ReleaseID
+//purpose  : 
+//=======================================================================
+void SMDS_MeshElementIDFactory::ReleaseID(int ID, int vtkId)
+{
+  if (ID < 1) // TODO check case ID == O
+  {
+    MESSAGE("~~~~~~~~~~~~~~ SMDS_MeshElementIDFactory::ReleaseID ID = " << ID);
+    return;
+  }
+  if (vtkId >= 0)
+  {
+    assert(vtkId < (int)myMesh->myCellIdVtkToSmds.size());
+    myMesh->myCellIdVtkToSmds[vtkId] = -1;
+    myMesh->setMyModified();
+  }
+  SMDS_MeshIDFactory::ReleaseID(ID);
+  if (ID == myMax)
+    myMax = 0;
+  if (ID == myMin)
+    myMax = 0;
+}
+
+//=======================================================================
+//function : updateMinMax
+//purpose  :
+//=======================================================================
+
+void SMDS_MeshElementIDFactory::updateMinMax() const
+{
+  myMin = INT_MAX;
+  myMax = 0;
+  for (size_t i = 0; i < myMesh->myCells.size(); i++)
+  {
+    if (myMesh->myCells[i])
+    {
+      int id = myMesh->myCells[i]->GetID();
+      if (id > myMax)
+        myMax = id;
+      if (id < myMin)
+        myMin = id;
+    }
+  }
+  if (myMin == INT_MAX)
+    myMin = 0;
+}
+
+//=======================================================================
+//function : elementsIterator
+//purpose  : Return an iterator on elements of the factory
+//=======================================================================
+
+SMDS_ElemIteratorPtr SMDS_MeshElementIDFactory::elementsIterator() const
+{
+  return myMesh->elementsIterator(SMDSAbs_All);
+}
+
+void SMDS_MeshElementIDFactory::Clear()
+{
+  myMesh->myCellIdVtkToSmds.clear();
+  myMin = myMax = 0;
+  SMDS_MeshIDFactory::Clear();
+}
diff --git a/src/SMDS/SMDS_MeshElementIDFactory.hxx b/src/SMDS/SMDS_MeshElementIDFactory.hxx
new file mode 100644 (file)
index 0000000..f75d24f
--- /dev/null
@@ -0,0 +1,62 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//  File   : SMDS_MeshElementIDFactory.hxx
+//  Module : SMESH
+//
+#ifndef _SMDS_MeshElementIDFactory_HeaderFile
+#define _SMDS_MeshElementIDFactory_HeaderFile
+
+#include "SMESH_SMDS.hxx"
+
+#include "SMDS_MeshNodeIDFactory.hxx"
+
+#include <vector>
+
+class SMDS_MeshElement;
+class SMDS_Mesh;
+
+class SMDS_EXPORT SMDS_MeshElementIDFactory:public SMDS_MeshNodeIDFactory
+{
+public:
+  friend class SMDS_Mesh;
+  
+  SMDS_MeshElementIDFactory();
+  bool BindID(int ID, SMDS_MeshElement * elem);
+  int SetInVtkGrid(SMDS_MeshElement * elem);
+  SMDS_MeshElement * MeshElement(int ID);
+  virtual int GetFreeID();
+  virtual void ReleaseID(int ID, int vtkId = -1);
+  SMDS_ElemIteratorPtr elementsIterator() const;
+  virtual void Clear();
+
+protected:
+  virtual void updateMinMax() const;
+  void updateMinMax(int id) const
+  {
+    if (id > myMax) myMax = id;
+    if (id < myMin) myMin = id;
+  }
+};
+
+#endif
diff --git a/src/SMDS/SMDS_MeshFace.cxx b/src/SMDS/SMDS_MeshFace.cxx
new file mode 100644 (file)
index 0000000..1269455
--- /dev/null
@@ -0,0 +1,35 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//
+#include "SMDS_MeshFace.hxx"
+
+SMDSAbs_ElementType SMDS_MeshFace::GetType() const
+{
+        return SMDSAbs_Face;
+}
+
+vtkIdType SMDS_MeshFace::GetVtkType() const
+{
+  return VTK_POLY_LINE;  // --- must be reimplemented in derived classes
+}
index 11e1f32c6ca606ff00858dabe0d93036c8c7eca0..92f2f9b4f64ff2b0a5c4eb93a221568a145990aa 100644 (file)
 
 #include "SMDS_MeshCell.hxx"
 
-#include "Utils_SALOME_Exception.hxx"
-
-/*!
- * \brief Mesh face. This type is not allocated.
- *        It is only used as function argument type to provide more clear semantic.
- */
-class SMDS_EXPORT SMDS_MeshFace : public SMDS_MeshCell
+class SMDS_EXPORT SMDS_MeshFace:public SMDS_MeshCell
 {
-  void init( const std::vector<vtkIdType>& vtkNodeIds )
-  {
-    SMDSAbs_EntityType entity = SMDSEntity_Triangle;
-    switch ( vtkNodeIds.size())
-    {
-    case 3: entity = SMDSEntity_Triangle;          break;
-    case 4: entity = SMDSEntity_Quadrangle;        break;
-    case 6: entity = SMDSEntity_Quad_Triangle;     break;
-    case 8: entity = SMDSEntity_Quad_Quadrangle;   break;
-    case 7: entity = SMDSEntity_BiQuad_Triangle;   break;
-    case 9: entity = SMDSEntity_BiQuad_Quadrangle; break;
-    default: throw SALOME_Exception("wrong face nodes");
-    }
-    SMDS_MeshCell::init( entity, vtkNodeIds );
-  }
-
-  friend class SMDS_Mesh;
-
- public:
-
-  virtual SMDSAbs_ElementType GetType() const { return SMDSAbs_Face; }
-
-  static SMDSAbs_ElementType Type() { return SMDSAbs_Face; }
+  public:
+        SMDSAbs_ElementType GetType() const;
+        virtual vtkIdType GetVtkType() const;
 };
 
 #endif
index 80e7c6080496b14e5f4204a5b896f620095f21d5..4040a3e1d2193e2d205cdc436c7d467a5b1dc19e 100644 (file)
 #endif
 
 #include "SMDS_MeshGroup.hxx"
+#include "utilities.h"
 
-#include "SMDS_SetIterator.hxx"
-#include "ObjectPool.hxx"
+using namespace std;
 
-#include <utilities.h>
+//=======================================================================
+//function : SMDS_MeshGroup
+//purpose  : 
+//=======================================================================
 
-#include <boost/make_shared.hpp>
+SMDS_MeshGroup::SMDS_MeshGroup(const SMDS_Mesh * theMesh,
+                               const SMDSAbs_ElementType theType)
+  :myMesh(theMesh),myType(theType), myParent(NULL), myTic(0)
+{
+}
 
 //=======================================================================
 //function : SMDS_MeshGroup
-//purpose  :
+//purpose  : 
 //=======================================================================
 
-SMDS_MeshGroup::SMDS_MeshGroup(const SMDS_Mesh *         theMesh,
+SMDS_MeshGroup::SMDS_MeshGroup(SMDS_MeshGroup * theParent,
                                const SMDSAbs_ElementType theType)
-  : SMDS_ElementHolder( theMesh ), myType(theType), myTic(0)
+        :myMesh(theParent->myMesh),myType(theType), myParent(theParent)
 {
 }
 
+//=======================================================================
+//function : AddSubGroup
+//purpose  : 
+//=======================================================================
+
+const SMDS_MeshGroup *SMDS_MeshGroup::AddSubGroup
+                (const SMDSAbs_ElementType theType)
+{
+        const SMDS_MeshGroup * subgroup = new SMDS_MeshGroup(this,theType);
+        myChildren.insert(myChildren.end(),subgroup);
+        return subgroup;
+}
+
+//=======================================================================
+//function : RemoveSubGroup
+//purpose  : 
+//=======================================================================
+
+bool SMDS_MeshGroup::RemoveSubGroup(const SMDS_MeshGroup * theGroup)
+{
+        bool found = false;     
+        list<const SMDS_MeshGroup*>::iterator itgroup;
+        for(itgroup=myChildren.begin(); itgroup!=myChildren.end(); itgroup++)
+        {
+                const SMDS_MeshGroup* subgroup=*itgroup;
+                if (subgroup == theGroup)
+                {
+                        found = true;
+                        myChildren.erase(itgroup);
+                }
+        }
+
+        return found;
+}
+
+//=======================================================================
+//function : RemoveFromParent
+//purpose  : 
+//=======================================================================
+
+bool SMDS_MeshGroup::RemoveFromParent()
+{
+        
+        if (myParent==NULL) return false;
+        else
+        {
+                return (myParent->RemoveSubGroup(this));
+        }
+}
 //=======================================================================
 //function : Clear
-//purpose  :
+//purpose  : 
 //=======================================================================
 
 void SMDS_MeshGroup::Clear()
 {
-  clearVector( myElements );
+  myElements.clear();
   myType = SMDSAbs_All;
   ++myTic;
 }
@@ -76,8 +132,8 @@ bool SMDS_MeshGroup::Add(const SMDS_MeshElement * theElem)
     MESSAGE("SMDS_MeshGroup::Add : Type Mismatch "<<theElem->GetType()<<"!="<<myType);
     return false;
   }
-
-  myElements.insert(theElem);
+        
+  myElements.insert(myElements.end(), theElem);
   ++myTic;
 
   return true;
@@ -85,12 +141,12 @@ bool SMDS_MeshGroup::Add(const SMDS_MeshElement * theElem)
 
 //=======================================================================
 //function : Remove
-//purpose  :
+//purpose  : 
 //=======================================================================
 
 bool SMDS_MeshGroup::Remove(const SMDS_MeshElement * theElem)
 {
-  TElementSet::iterator found = myElements.find(theElem);
+  set<const SMDS_MeshElement *>::iterator found = myElements.find(theElem);
   if ( found != myElements.end() ) {
     myElements.erase(found);
     if (myElements.empty()) myType = SMDSAbs_All;
@@ -120,38 +176,3 @@ void SMDS_MeshGroup::SetType(const SMDSAbs_ElementType theType)
   if (IsEmpty())
     myType = theType;
 }
-
-//=======================================================================
-//function : GetElements
-//purpose  : 
-//=======================================================================
-
-SMDS_ElemIteratorPtr SMDS_MeshGroup::GetElements() const
-{
-  typedef SMDS_SetIterator< const SMDS_MeshElement*, TIterator > TSetIterator;
-  return boost::make_shared< TSetIterator >( myElements.begin(), myElements.end() );
-}
-
-//=======================================================================
-//function : Move contents of another group
-//purpose  : 
-//=======================================================================
-
-void SMDS_MeshGroup::operator=( SMDS_MeshGroup && other )
-{
-  myMesh = other.myMesh;
-  myType = other.myType;
-  myElements = std::move( other.myElements );
-  ++myTic;
-}
-
-//=======================================================================
-//function : tmpClear
-//purpose  : temporary remove its elements before mesh compacting
-//=======================================================================
-
-void SMDS_MeshGroup::tmpClear()
-{
-  compact();
-  myElements.clear();
-}
index b605737bfab79d92af4df0b1dc95df4acfda169b..7ba1375ad5b8ce92d96db67f95362b1c0d5d74de 100644 (file)
 
 #include "SMESH_SMDS.hxx"
 
-#include "SMDS_ElementHolder.hxx"
 #include "SMDS_Mesh.hxx"
 #include <set>
 
-#include <boost/container/flat_set.hpp>
-
-class SMDS_EXPORT SMDS_MeshGroup: public SMDS_MeshObject, SMDS_ElementHolder
+class SMDS_EXPORT SMDS_MeshGroup:public SMDS_MeshObject
 {
- public:
-  SMDS_MeshGroup(const SMDS_Mesh *         theMesh,
-                 const SMDSAbs_ElementType theType = SMDSAbs_All);
-
-  void SetType (const SMDSAbs_ElementType theType);
-  void Clear();
-  void Reserve(size_t nbElems) { myElements.reserve( nbElems ); }
-  bool Add(const SMDS_MeshElement * theElem);
-  bool Remove(const SMDS_MeshElement * theElem);
-  bool IsEmpty() const { return myElements.empty(); }
-  int  Extent() const { return myElements.size(); }
-  int  Tic() const { return myTic; }
-  bool Contains(const SMDS_MeshElement * theElem) const;
-
-  const SMDS_Mesh*     GetMesh() const { return myMesh; }
-  SMDSAbs_ElementType  GetType() const { return myType; }
-  SMDS_ElemIteratorPtr GetElements() const; // WARNING: iterator becomes invalid if group changes
-
-  void operator=( SMDS_MeshGroup && other );
-
- protected: // methods of SMDS_ElementHolder
-
-  virtual SMDS_ElemIteratorPtr getElements() { return GetElements(); }
-  virtual void tmpClear();
-  virtual void add( const SMDS_MeshElement* element ) { Add( element ); }
-  virtual void compact() { myElements.shrink_to_fit(); }
-
- private:
-
-  typedef boost::container::flat_set< const SMDS_MeshElement* > TElementSet;
-  typedef TElementSet::const_iterator                           TIterator;
-
-  const SMDS_Mesh *   myMesh;
-  SMDSAbs_ElementType myType;
-  TElementSet         myElements; // not sorted by ID because it can contain deleted elements
-  int                 myTic;      // to track changes
+  public:
+        SMDS_MeshGroup(const SMDS_Mesh * theMesh,
+                       const SMDSAbs_ElementType theType = SMDSAbs_All);
+        const SMDS_MeshGroup * AddSubGroup
+                      (const SMDSAbs_ElementType theType = SMDSAbs_All);
+        virtual bool RemoveSubGroup(const SMDS_MeshGroup* theGroup);
+        virtual bool RemoveFromParent();
+
+        const SMDS_Mesh* GetMesh() const { return myMesh; }
+
+        void SetType (const SMDSAbs_ElementType theType);
+        void Clear();
+        bool Add(const SMDS_MeshElement * theElem);
+        bool Remove(const SMDS_MeshElement * theElem);
+        bool IsEmpty() const { return myElements.empty(); }
+        int Extent() const { return myElements.size(); }
+        int Tic() const { return myTic; }
+
+        int SubGroupsNb() const { return myChildren.size(); }
+
+        SMDSAbs_ElementType GetType() const { return myType; }
+
+        bool Contains(const SMDS_MeshElement * theElem) const;
+
+        void InitIterator() const
+        { const_cast<TIterator&>(myIterator) = myElements.begin(); }
+
+        bool More() const { return myIterator != myElements.end(); }
+
+        const SMDS_MeshElement* Next() const
+        { return *(const_cast<TIterator&>(myIterator))++; }
+
+        void InitSubGroupsIterator() const
+        { const_cast<TGroupIterator&>(myGroupIterator) = myChildren.begin(); }
+
+        bool MoreSubGroups() const { return myGroupIterator != myChildren.end(); }
+
+        const SMDS_MeshGroup* NextSubGroup() const
+        { return *(const_cast<TGroupIterator&>(myGroupIterator))++; }
+
+  private:
+        SMDS_MeshGroup(SMDS_MeshGroup* theParent,
+                       const SMDSAbs_ElementType theType = SMDSAbs_All);
+
+        typedef std::set<const SMDS_MeshElement *>::const_iterator TIterator;
+        typedef std::list<const SMDS_MeshGroup *>::const_iterator TGroupIterator;
+
+        const SMDS_Mesh *                       myMesh;
+        SMDSAbs_ElementType                     myType;
+        std::set<const SMDS_MeshElement*>       myElements; /* - not sorted by ID because it */
+        SMDS_MeshGroup *                        myParent;   /* can contain deleted elements */
+        std::list<const SMDS_MeshGroup*>        myChildren;
+        TIterator                               myIterator;
+        TGroupIterator                          myGroupIterator;
+        int                                     myTic; // to track changes
 };
 #endif
diff --git a/src/SMDS/SMDS_MeshIDFactory.cxx b/src/SMDS/SMDS_MeshIDFactory.cxx
new file mode 100644 (file)
index 0000000..ea74aa5
--- /dev/null
@@ -0,0 +1,113 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//  File   : SMDS_MeshIDFactory.cxx
+//  Author : Jean-Michel BOULCOURT
+//  Module : SMESH
+//
+#include "SMDS_MeshIDFactory.hxx"
+#include "SMDS_Mesh.hxx"
+#include "utilities.h"
+
+using namespace std;
+
+//=======================================================================
+//function : SMDS_MeshIDFactory
+//purpose  : 
+//=======================================================================
+
+SMDS_MeshIDFactory::SMDS_MeshIDFactory():myMaxID(0), myMesh(0)
+{
+}
+
+int SMDS_MeshIDFactory::GetFreeID()
+{
+  int newid;
+  if (myPoolOfID.empty())
+  {
+    newid = ++myMaxID;
+  }
+  else
+  {
+    set<int>::iterator i = myPoolOfID.begin();
+    newid = *i;
+    myPoolOfID.erase( i );
+  }
+  return newid;
+}
+
+//=======================================================================
+//function : ReleaseID
+//purpose  :
+//=======================================================================
+void SMDS_MeshIDFactory::ReleaseID(int ID, int vtkId)
+{
+  if ( ID > 0 )
+  {
+    if ( ID < myMaxID )
+    {
+      myPoolOfID.insert(ID);
+    }
+    else if ( ID == myMaxID )
+    {
+      --myMaxID;
+      if ( !myPoolOfID.empty() ) // assure that myMaxID is not in myPoolOfID
+      {
+        set<int>::iterator i = --myPoolOfID.end();
+        while ( i != myPoolOfID.begin() && myMaxID == *i ) {
+          --myMaxID; --i;
+        }
+        if ( myMaxID == *i ) {
+          --myMaxID; // begin of myPoolOfID reached
+          myPoolOfID.clear();
+        }
+        else if ( myMaxID < ID-1 ) {
+          myPoolOfID.erase( ++i, myPoolOfID.end() );
+        }
+      }
+    }
+  }
+}
+
+void SMDS_MeshIDFactory::Clear()
+{
+  myMaxID = 0;
+  myPoolOfID.clear();
+}
+
+void SMDS_MeshIDFactory::SetMesh(SMDS_Mesh *mesh)
+{
+  myMesh = mesh;
+}
+
+SMDS_Mesh* SMDS_MeshIDFactory::GetMesh()
+{
+  return myMesh;
+}
+
+void SMDS_MeshIDFactory::emptyPool(int maxId)
+{
+  myMaxID = maxId;
+  myPoolOfID.clear();
+}
+
diff --git a/src/SMDS/SMDS_MeshIDFactory.hxx b/src/SMDS/SMDS_MeshIDFactory.hxx
new file mode 100644 (file)
index 0000000..35be69b
--- /dev/null
@@ -0,0 +1,56 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//  File   : SMDS_MeshIDFactory.hxx
+//  Module : SMESH
+//
+#ifndef _SMDS_MeshIDFactory_HeaderFile
+#define _SMDS_MeshIDFactory_HeaderFile
+
+#include "SMESH_SMDS.hxx"
+
+#include "SMDS_MeshObject.hxx"
+#include <set>
+
+class SMDS_Mesh;
+
+class SMDS_EXPORT SMDS_MeshIDFactory:public SMDS_MeshObject
+{
+public:
+  int  GetFreeID();
+  virtual void ReleaseID(int ID, int vtkId = -1);
+  virtual void Clear();
+
+  void SetMesh(SMDS_Mesh *mesh);
+  SMDS_Mesh* GetMesh();
+  inline bool isPoolIdEmpty() { return myPoolOfID.empty(); };
+  virtual void emptyPool(int maxId);
+  inline void adjustMaxId(int ID) { if (ID > myMaxID) myMaxID = ID;};
+protected:
+  SMDS_MeshIDFactory();
+  int myMaxID;
+  std::set<int> myPoolOfID;
+  SMDS_Mesh *myMesh;
+};
+
+#endif
index 542798277413e60557770323318340af367a90b3..554f0fa7115dd75e0e8e021c97be94f90a051694 100644 (file)
 #endif
 
 #include "SMDS_MeshNode.hxx"
-
-#include "SMDS_ElementFactory.hxx"
-#include "SMDS_Mesh.hxx"
-#include "SMDS_SetIterator.hxx"
 #include "SMDS_SpacePosition.hxx"
+#include "SMDS_IteratorOfElements.hxx"
+#include "SMDS_Mesh.hxx"
+#include <vtkUnstructuredGrid.h>
 
-#include <utilities.h>
-#include <Utils_SALOME_Exception.hxx>
+#include "utilities.h"
+#include "Utils_SALOME_Exception.hxx"
 #include <cassert>
 
-#include <boost/make_shared.hpp>
+using namespace std;
+
+int SMDS_MeshNode::nbNodes =0;
+
+//=======================================================================
+//function : SMDS_MeshNode
+//purpose  :
+//=======================================================================
+SMDS_MeshNode::SMDS_MeshNode() :
+  SMDS_MeshElement(-1, -1, 0),
+  myPosition(SMDS_SpacePosition::originSpacePosition())
+{
+  nbNodes++;
+}
+
+SMDS_MeshNode::SMDS_MeshNode(int id, int meshId, int shapeId, double x, double y, double z):
+  SMDS_MeshElement(id, meshId, shapeId),
+  myPosition(SMDS_SpacePosition::originSpacePosition())
+{
+  nbNodes++;
+  init(id, meshId, shapeId, x, y ,z);
+}
 
-void SMDS_MeshNode::init(double x, double y, double z)
+void SMDS_MeshNode::init(int id, int meshId, int shapeId, double x, double y, double z)
 {
-  SMDS_UnstructuredGrid * grid = getGrid();
+  SMDS_MeshElement::init(id, meshId, shapeId);
+  myVtkID = id - 1;
+  assert(myVtkID >= 0);
+  SMDS_UnstructuredGrid * grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
   vtkPoints *points = grid->GetPoints();
-  points->InsertPoint( GetVtkID(), x, y, z );
+  points->InsertPoint(myVtkID, x, y, z);
   if ( grid->HasLinks() )
-    grid->GetLinks()->ResizeForPoint( GetVtkID() );
+    grid->GetLinks()->ResizeForPoint( myVtkID );
+}
+
+SMDS_MeshNode::~SMDS_MeshNode()
+{
+  nbNodes--;
+  if ( myPosition && myPosition != SMDS_SpacePosition::originSpacePosition() )
+    delete myPosition, myPosition = 0;
 }
 
 //=======================================================================
@@ -55,8 +85,8 @@ void SMDS_MeshNode::init(double x, double y, double z)
 
 void SMDS_MeshNode::RemoveInverseElement(const SMDS_MeshElement * elem)
 {
-  if ( getGrid()->HasLinks() )
-    getGrid()->RemoveReferenceToCell( GetVtkID(), elem->GetVtkID());
+  if ( SMDS_Mesh::_meshList[myMeshId]->getGrid()->HasLinks() )
+    SMDS_Mesh::_meshList[myMeshId]->getGrid()->RemoveReferenceToCell(myVtkID, elem->getVtkId());
 }
 
 //=======================================================================
@@ -66,7 +96,7 @@ void SMDS_MeshNode::RemoveInverseElement(const SMDS_MeshElement * elem)
 
 void SMDS_MeshNode::Print(ostream & OS) const
 {
-  OS << "Node <" << GetID() << "> : X = " << X() << " Y = "
+  OS << "Node <" << myID << "> : X = " << X() << " Y = "
      << Y() << " Z = " << Z() << endl;
 }
 
@@ -75,20 +105,23 @@ void SMDS_MeshNode::Print(ostream & OS) const
 //purpose  :
 //=======================================================================
 
-void SMDS_MeshNode::SetPosition(const SMDS_PositionPtr& aPos, int shapeID)
+void SMDS_MeshNode::SetPosition(const SMDS_PositionPtr& aPos)
 {
-  myHolder->SetPosition( this, aPos, shapeID );
+  if ( myPosition &&
+       myPosition != SMDS_SpacePosition::originSpacePosition() &&
+       myPosition != aPos )
+    delete myPosition;
+  myPosition = aPos;
 }
 
 //=======================================================================
 //function : GetPosition
-//purpose  : Return a position of this node on shape
-//warning  : result is std::unique_ptr !
+//purpose  :
 //=======================================================================
 
-SMDS_PositionPtr SMDS_MeshNode::GetPosition() const
+const SMDS_PositionPtr& SMDS_MeshNode::GetPosition() const
 {
-  return myHolder->GetPosition( this );
+  return myPosition;
 }
 
 //=======================================================================
@@ -97,120 +130,94 @@ SMDS_PositionPtr SMDS_MeshNode::GetPosition() const
  */
 //=======================================================================
 
-namespace
+class SMDS_MeshNode_MyInvIterator: public SMDS_ElemIterator
 {
-  struct InverseIterator: public SMDS_ElemIterator
+private:
+  SMDS_Mesh* myMesh;
+  vtkIdType* myCells;
+  int myNcells;
+  SMDSAbs_ElementType myType;
+  int iter;
+  vector<vtkIdType> cellList;
+
+public:
+  SMDS_MeshNode_MyInvIterator(SMDS_Mesh *mesh, vtkIdType* cells, int ncells, SMDSAbs_ElementType type) :
+    myMesh(mesh), myCells(cells), myNcells(ncells), myType(type), iter(0)
   {
-    const SMDS_Mesh*       myMesh;
-    size_t                 myIter;
-    std::vector<vtkIdType> myCellList;
-
-    InverseIterator(const SMDS_Mesh *   mesh = 0,
-                    const vtkIdType*    cells = 0,
-                    const int           ncells = 0,
-                    SMDSAbs_ElementType type = SMDSAbs_All)
-      : myMesh(mesh), myIter(0)
+    if ( ncells )
     {
-      if ( ncells )
+      cellList.reserve( ncells );
+      if (type == SMDSAbs_All)
       {
-        myCellList.reserve( ncells );
-        if (type == SMDSAbs_All)
-        {
-          myCellList.assign( cells, cells + ncells );
-        }
-        else
+        cellList.assign( cells, cells + ncells );
+      }
+      else
+      {
+        for (int i = 0; i < ncells; i++)
         {
-          for (int i = 0; i < ncells; i++)
+          int vtkId = cells[i];
+          int smdsId = myMesh->fromVtkToSmds(vtkId);
+          const SMDS_MeshElement* elem = myMesh->FindElement(smdsId);
+          if (elem->GetType() == type)
           {
-            int  vtkId = cells[i];
-            int smdsId = myMesh->FromVtkToSmds( vtkId );
-            const SMDS_MeshElement* elem = myMesh->FindElement( smdsId );
-            if ( elem->GetType() == type )
-            {
-              myCellList.push_back(vtkId);
-            }
+            cellList.push_back(vtkId);
           }
         }
       }
+      myCells = cellList.empty() ? 0 : &cellList[0];
+      myNcells = cellList.size();
     }
+  }
 
-    bool more()
-    {
-      return ( myIter < myCellList.size() );
-    }
-
-    const SMDS_MeshElement* next()
-    {
-      int vtkId  = myCellList[ myIter++ ];
-      int smdsId = myMesh->FromVtkToSmds( vtkId );
-      const SMDS_MeshElement* elem = myMesh->FindElement(smdsId);
-      if (!elem)
-      {
-        MESSAGE("InverseIterator problem Null element");
-        throw SALOME_Exception("InverseIterator problem Null element");
-      }
-      return elem;
-    }
-  };
-
-  //=======================================================================
-  /*!
-   * \brief Iterator on a node
-   */
-  //=======================================================================
-
-  template< class ELEM_ITERATOR >
-  struct Iterator : public ELEM_ITERATOR
+  bool more()
   {
-    typedef typename ELEM_ITERATOR::value_type element_type;
-    const SMDS_MeshNode* myNode;
-
-    Iterator( const SMDS_MeshNode* n ): myNode( n ) {}
+    return (iter < myNcells);
+  }
 
-    virtual bool more()
-    {
-      return myNode;
-    }
-    virtual element_type next()
+  const SMDS_MeshElement* next()
+  {
+    int vtkId = myCells[iter];
+    int smdsId = myMesh->fromVtkToSmds(vtkId);
+    const SMDS_MeshElement* elem = myMesh->FindElement(smdsId);
+    if (!elem)
     {
-      element_type res = static_cast<element_type>( myNode );
-      myNode = 0;
-      return res;
+      MESSAGE("SMDS_MeshNode_MyInvIterator problem Null element");
+      throw SALOME_Exception("SMDS_MeshNode_MyInvIterator problem Null element");
     }
-  };
-}
+    iter++;
+    return elem;
+  }
+};
 
 SMDS_ElemIteratorPtr SMDS_MeshNode::GetInverseElementIterator(SMDSAbs_ElementType type) const
 {
-  if ( GetMesh()->NbElements() > 0 ) // avoid building links
+  if ( SMDS_Mesh::_meshList[myMeshId]->NbElements() > 0 ) // avoid building links
   {
-    vtkCellLinks::Link& l = getGrid()->GetLinks()->GetLink( GetVtkID() );
-    return boost::make_shared< InverseIterator >( GetMesh(), l.cells, l.ncells, type );
+    vtkCellLinks::Link& l = SMDS_Mesh::_meshList[myMeshId]->getGrid()->GetLinks()->GetLink(myVtkID);
+    return SMDS_ElemIteratorPtr(new SMDS_MeshNode_MyInvIterator(SMDS_Mesh::_meshList[myMeshId], l.cells, l.ncells, type));
   }
   else
   {
-    return boost::make_shared< InverseIterator >();
+    return SMDS_ElemIteratorPtr(new SMDS_MeshNode_MyInvIterator(SMDS_Mesh::_meshList[myMeshId], 0, 0, type));
   }
 }
 
-SMDS_ElemIteratorPtr SMDS_MeshNode::nodesIterator() const
-{
-  return boost::make_shared< Iterator< SMDS_ElemIterator > >( this );
-}
-
-SMDS_NodeIteratorPtr SMDS_MeshNode::nodeIterator() const
+SMDS_ElemIteratorPtr SMDS_MeshNode::elementsIterator(SMDSAbs_ElementType type) const
 {
-  return boost::make_shared< Iterator< SMDS_NodeIterator > >( this );
+  if ( type == SMDSAbs_Node )
+    return SMDS_MeshElement::elementsIterator( SMDSAbs_Node );
+  else
+    return GetInverseElementIterator( type );
 }
 
-const SMDS_MeshNode* SMDS_MeshNode::GetNode(const int ind) const
+int SMDS_MeshNode::NbNodes() const
 {
-  return ind == 0 ? this : 0;
+  return 1;
 }
 
 double* SMDS_MeshNode::getCoord() const
 {
-  return getGrid()->GetPoint( GetVtkID() );
+  return SMDS_Mesh::_meshList[myMeshId]->getGrid()->GetPoint(myVtkID);
 }
 
 double SMDS_MeshNode::X() const
@@ -239,30 +246,41 @@ double SMDS_MeshNode::Z() const
 
 void SMDS_MeshNode::GetXYZ(double xyz[3]) const
 {
-  return getGrid()->GetPoint( GetVtkID(), xyz );
+  return SMDS_Mesh::_meshList[myMeshId]->getGrid()->GetPoint(myVtkID,xyz);
 }
 
 //================================================================================
-void SMDS_MeshNode::setXYZ( double x, double y, double z )
+void SMDS_MeshNode::setXYZ(double x, double y, double z)
+{
+  SMDS_Mesh *mesh = SMDS_Mesh::_meshList[myMeshId];
+  vtkPoints *points = mesh->getGrid()->GetPoints();
+  points->InsertPoint(myVtkID, x, y, z);
+  mesh->adjustBoundingBox(x, y, z);
+  mesh->setMyModified();
+}
+
+SMDSAbs_ElementType SMDS_MeshNode::GetType() const
+{
+  return SMDSAbs_Node;
+}
+
+vtkIdType SMDS_MeshNode::GetVtkType() const
 {
-  vtkPoints *points = getGrid()->GetPoints();
-  points->InsertPoint( GetVtkID(), x, y, z );
-  //GetMesh()->adjustBoundingBox(x, y, z);
-  GetMesh()->setMyModified();
+  return VTK_VERTEX;
 }
 
 //=======================================================================
 //function : AddInverseElement
 //purpose  :
 //=======================================================================
-void SMDS_MeshNode::AddInverseElement( const SMDS_MeshElement* elem )
+void SMDS_MeshNode::AddInverseElement(const SMDS_MeshElement* ME)
 {
-  SMDS_UnstructuredGrid* grid = getGrid();
+  SMDS_UnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
   if ( grid->HasLinks() )
   {
     vtkCellLinks *Links = grid->GetLinks();
-    Links->ResizeCellList( GetVtkID(), 1 );
-    Links->AddCellReference( elem->GetVtkID(), GetVtkID() );
+    Links->ResizeCellList(myVtkID, 1);
+    Links->AddCellReference(ME->getVtkId(), myVtkID);
   }
 }
 
@@ -272,7 +290,7 @@ void SMDS_MeshNode::AddInverseElement( const SMDS_MeshElement* elem )
 //=======================================================================
 void SMDS_MeshNode::ClearInverseElements()
 {
-  getGrid()->ResizeCellList( GetVtkID(), 0);
+  SMDS_Mesh::_meshList[myMeshId]->getGrid()->ResizeCellList(myVtkID, 0);
 }
 
 //================================================================================
@@ -284,17 +302,17 @@ void SMDS_MeshNode::ClearInverseElements()
 int SMDS_MeshNode::NbInverseElements(SMDSAbs_ElementType type) const
 {
   int nb = 0;
-  SMDS_Mesh *mesh = GetMesh();
-  if ( mesh->NbElements() > 0 ) // avoid building links
+  if ( SMDS_Mesh::_meshList[myMeshId]->NbElements() > 0 ) // avoid building links
   {
-    vtkCellLinks::Link& l = mesh->GetGrid()->GetLinks()->GetLink( GetVtkID() );
+    vtkCellLinks::Link& l = SMDS_Mesh::_meshList[myMeshId]->getGrid()->GetLinks()->GetLink(myVtkID);
 
     if ( type == SMDSAbs_All )
       return l.ncells;
 
+    SMDS_Mesh *mesh = SMDS_Mesh::_meshList[myMeshId];
     for ( int i = 0; i < l.ncells; i++ )
     {
-      const SMDS_MeshElement* elem = mesh->FindElement( mesh->FromVtkToSmds( l.cells[i] ));
+      const SMDS_MeshElement* elem = mesh->FindElement( mesh->fromVtkToSmds( l.cells[i] ));
       nb += ( elem->GetType() == type );
     }
   }
index b156b911c7718a46d61402a5f8ed6955a1022a7c..2c8bad7be6927ed5634abcd28e8fa71af9f50998 100644 (file)
 
 #include "SMDS_MeshElement.hxx"
 #include "SMDS_Position.hxx"
+#include "ObjectPool.hxx"
 
 class SMDS_EXPORT SMDS_MeshNode: public SMDS_MeshElement
 {
- public:
+public:
+  friend class SMESHDS_Mesh;
+  friend class SMDS_Mesh;
+  friend class ObjectPool<SMDS_MeshNode>;
+  friend class SMDS_VtkFace;
 
-  void setXYZ(double x, double y, double z);
+  void Print(std::ostream & OS) const;
   double X() const; // ! NOT thread safe methods !
   double Y() const;
   double Z() const;
   void   GetXYZ(double xyz[3]) const; // thread safe getting coords
-
   SMDS_ElemIteratorPtr    GetInverseElementIterator(SMDSAbs_ElementType type=SMDSAbs_All) const;
   int                     NbInverseElements(SMDSAbs_ElementType type=SMDSAbs_All) const;
-
-  SMDS_PositionPtr GetPosition() const; // WARNING result is std::unique_ptr !
-  void SetPosition(const SMDS_PositionPtr& aPos, int shapeID = 0 );
-
-  virtual SMDSAbs_ElementType  GetType() const       { return SMDSAbs_Node; }
-  virtual VTKCellType          GetVtkType() const    { return VTK_VERTEX; }
+  const SMDS_PositionPtr& GetPosition() const;
+  virtual SMDSAbs_ElementType  GetType() const;
+  virtual vtkIdType            GetVtkType() const;
   virtual SMDSAbs_EntityType   GetEntityType() const { return SMDSEntity_Node;}
   virtual SMDSAbs_GeometryType GetGeomType() const   { return SMDSGeom_NONE; }
-  virtual int                  NbNodes() const       { return 1; }
-  virtual int                  NbEdges() const       { return 0; }
-  virtual int                  NbFaces() const       { return 0; }
+  virtual int                  NbNodes() const;
 
-  virtual SMDS_ElemIteratorPtr nodesIterator() const;
-  virtual SMDS_NodeIteratorPtr nodeIterator() const;
-  virtual const SMDS_MeshNode* GetNode(const int ind) const;
-
-  virtual bool IsPoly() const { return false; }
-  virtual bool IsQuadratic() const { return false; }
-  virtual bool IsMediumNode(const SMDS_MeshNode* node) const  { return false; }
-  virtual int  NbCornerNodes() const { return 1; }
-
-  void Print(std::ostream & OS) const;
-
- private:
+  void SetPosition(const SMDS_PositionPtr& aPos);
+  void setXYZ(double x, double y, double z);
 
-  void init(double x=0, double y=0, double z=0);
+  static int nbNodes;
 
+protected:
+  SMDS_MeshNode();
+  SMDS_MeshNode(int id, int meshId, int shapeId = -1, double x=0, double y=0, double z=0);
+  virtual ~SMDS_MeshNode();
+  void init(int id, int meshId, int shapeId = -1, double x=0, double y=0, double z=0);
   double* getCoord() const;
-  void AddInverseElement   (const SMDS_MeshElement * elem);
-  void RemoveInverseElement(const SMDS_MeshElement * elem);
+  void AddInverseElement(const SMDS_MeshElement * ME);
+  void RemoveInverseElement(const SMDS_MeshElement * parent);
   void ClearInverseElements();
 
-  friend class SMDS_Mesh;
+  SMDS_ElemIteratorPtr
+  elementsIterator(SMDSAbs_ElementType type) const;
 
+private:
+  SMDS_PositionPtr myPosition;
 };
 
 #endif
diff --git a/src/SMDS/SMDS_MeshNodeIDFactory.cxx b/src/SMDS/SMDS_MeshNodeIDFactory.cxx
new file mode 100644 (file)
index 0000000..64b7bae
--- /dev/null
@@ -0,0 +1,161 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+//  File   : SMDS_MeshNodeIDFactory.cxx
+//  Author : Jean-Michel BOULCOURT
+//  Module : SMESH
+//
+#ifdef _MSC_VER
+#pragma warning(disable:4786)
+#endif
+
+#include "SMDS_MeshNodeIDFactory.hxx"
+#include "SMDS_MeshElement.hxx"
+#include "SMDS_Mesh.hxx"
+
+#include <vtkUnstructuredGrid.h>
+#include <vtkCellType.h>
+
+using namespace std;
+
+//=======================================================================
+//function : SMDS_MeshNodeIDFactory
+//purpose  : 
+//=======================================================================
+SMDS_MeshNodeIDFactory::SMDS_MeshNodeIDFactory() :
+  SMDS_MeshIDFactory(), myMin(0), myMax(0)
+{
+}
+
+//=======================================================================
+//function : BindID
+//purpose  : 
+//=======================================================================
+bool SMDS_MeshNodeIDFactory::BindID(int ID, SMDS_MeshElement * elem)
+{
+  updateMinMax(ID);
+  return true;
+}
+
+//=======================================================================
+//function : MeshElement
+//purpose  : 
+//=======================================================================
+SMDS_MeshElement* SMDS_MeshNodeIDFactory::MeshElement(int ID)
+{
+  // commented since myMax can be 0 after ReleaseID()
+//   if ((ID < 1) || (ID > myMax))
+//     return NULL;
+  const SMDS_MeshElement* elem = GetMesh()->FindNode(ID);
+  return (SMDS_MeshElement*) (elem);
+}
+
+//=======================================================================
+//function : GetFreeID
+//purpose  : 
+//=======================================================================
+int SMDS_MeshNodeIDFactory::GetFreeID()
+{
+  int ID;
+  do {
+    ID = SMDS_MeshIDFactory::GetFreeID();
+  } while ( MeshElement( ID ));
+  return ID;
+}
+
+//=======================================================================
+//function : ReleaseID
+//purpose  : 
+//=======================================================================
+void SMDS_MeshNodeIDFactory::ReleaseID(const int ID, int vtkId)
+{
+  SMDS_MeshIDFactory::ReleaseID(ID);
+  myMesh->setMyModified();
+  if (ID == myMax)
+    myMax = 0; // --- force updateMinMax
+  if (ID == myMin)
+    myMax = 0; // --- force updateMinMax
+}
+
+//=======================================================================
+//function : GetMaxID
+//purpose  : 
+//=======================================================================
+
+int SMDS_MeshNodeIDFactory::GetMaxID() const
+{
+  if (myMax == 0)
+    updateMinMax();
+  return myMax;
+}
+
+//=======================================================================
+//function : GetMinID
+//purpose  : 
+//=======================================================================
+
+int SMDS_MeshNodeIDFactory::GetMinID() const
+{
+  if (myMax == 0)
+    updateMinMax();
+  return myMin;
+}
+
+//=======================================================================
+//function : updateMinMax
+//purpose  : 
+//=======================================================================
+
+void SMDS_MeshNodeIDFactory::updateMinMax() const
+{
+  myMin = INT_MAX;
+  myMax = 0;
+  for (size_t i = 0; i < myMesh->myNodes.size(); i++)
+  {
+    if (myMesh->myNodes[i])
+    {
+      int id = myMesh->myNodes[i]->GetID();
+      if (id > myMax)
+        myMax = id;
+      if (id < myMin)
+        myMin = id;
+    }
+  }
+  if (myMin == INT_MAX)
+    myMin = 0;
+}
+
+SMDS_ElemIteratorPtr SMDS_MeshNodeIDFactory::elementsIterator() const
+{
+  return myMesh->elementsIterator(SMDSAbs_Node);
+}
+
+void SMDS_MeshNodeIDFactory::Clear()
+{
+  myMin = myMax = 0;
+  SMDS_MeshIDFactory::Clear();
+}
+
+void SMDS_MeshNodeIDFactory::emptyPool(int maxId)
+{
+  SMDS_MeshIDFactory::emptyPool(maxId);
+  myMax = maxId;
+}
diff --git a/src/SMDS/SMDS_MeshNodeIDFactory.hxx b/src/SMDS/SMDS_MeshNodeIDFactory.hxx
new file mode 100644 (file)
index 0000000..80c1271
--- /dev/null
@@ -0,0 +1,65 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+//  File   : SMDS_MeshElementIDFactory.hxx
+//  Module : SMESH
+//
+#ifndef _SMDS_MeshNodeIDFactory_HeaderFile
+#define _SMDS_MeshNodeIDFactory_HeaderFile
+
+#include "SMESH_SMDS.hxx"
+
+#include "SMDS_MeshIDFactory.hxx"
+#include "SMDS_ElemIterator.hxx"
+
+#include <vector>
+
+class SMDS_MeshElement;
+
+class SMDS_EXPORT SMDS_MeshNodeIDFactory: public SMDS_MeshIDFactory
+{
+public:
+  SMDS_MeshNodeIDFactory();
+  bool BindID(int ID, SMDS_MeshElement * elem);
+  SMDS_MeshElement * MeshElement(int ID);
+  virtual int GetFreeID();
+  virtual void ReleaseID(int ID, int vtkId = -1);
+  int GetMaxID() const;
+  int GetMinID() const;
+  SMDS_ElemIteratorPtr elementsIterator() const;
+  virtual void Clear();
+  virtual void emptyPool(int maxId);
+
+protected:
+  virtual void updateMinMax() const;
+  void updateMinMax(int id) const
+  {
+    if (id > myMax)
+      myMax = id;
+    if (id < myMin)
+      myMin = id;
+  }
+
+  mutable int myMin, myMax;
+
+};
+
+#endif
index 755285447cb721d880293adb649e1a32a9fcedea..a56c119b7b0c1e9f650c447689ddde04e3c5c084 100644 (file)
 //  Author : Jean-Michel BOULCOURT
 //  Module : SMESH
 //
-
 #include "SMDS_MeshVolume.hxx"
+//=======================================================================
+//function : Print
+//purpose  : 
+//=======================================================================
 
-#include "SMDS_Mesh.hxx"
-#include "SMDS_VolumeTool.hxx"
-#include "SMDS_VtkCellIterator.hxx"
-
-#include <boost/make_shared.hpp>
-
-// init a polyherdon
-void SMDS_MeshVolume::init( const std::vector<const SMDS_MeshNode*>& nodes,
-                            const std::vector<int>&                  nbNodesPerFace )
-{
-  std::vector<vtkIdType> ptIds;
-  ptIds.reserve( nodes.size() + nbNodesPerFace.size() + 1 );
-
-  size_t nbFaces = nbNodesPerFace.size();
-  for ( size_t iN = 0, iF = 0; iF < nbFaces; iF++ )
-  {
-    int nf = nbNodesPerFace[iF];
-    ptIds.push_back(nf);
-    for (int n = 0; n < nf; n++)
-      ptIds.push_back( nodes[ iN++ ]->GetVtkID() );
-  }
-
-  int vtkID = getGrid()->InsertNextLinkedCell(VTK_POLYHEDRON, nbFaces, &ptIds[0]);
-  setVtkID( vtkID );
-}
-
-void SMDS_MeshVolume::init( const std::vector<vtkIdType>& vtkNodeIds )
-{
-  SMDSAbs_EntityType aType = SMDSEntity_Tetra;
-  switch ( vtkNodeIds.size()) // cases are in order of usage frequency
-  {
-  case 4:  aType = SMDSEntity_Tetra;           break;
-  case 5:  aType = SMDSEntity_Pyramid;         break;
-  case 8:  aType = SMDSEntity_Hexa;            break;
-  case 6:  aType = SMDSEntity_Penta;           break;
-  case 10: aType = SMDSEntity_Quad_Tetra;      break;
-  case 20: aType = SMDSEntity_Quad_Hexa;       break;
-  case 13: aType = SMDSEntity_Quad_Pyramid;    break;
-  case 27: aType = SMDSEntity_TriQuad_Hexa;    break;
-  case 15: aType = SMDSEntity_Quad_Penta;      break;
-  case 18: aType = SMDSEntity_BiQuad_Penta;    break;
-  case 12: aType = SMDSEntity_Hexagonal_Prism; break;
-  default: throw SALOME_Exception("wrong volume nodes");
-  }
-  SMDS_MeshCell::init( aType, vtkNodeIds );
-}
-
-const SMDS_MeshNode* SMDS_MeshVolume::GetNode(const int ind) const
-{
-  if ( !IsPoly() )
-    return SMDS_MeshCell::GetNode( ind );
-
-  vtkIdType nFaces = 0;
-  vtkIdType* ptIds = 0;
-  getGrid()->GetFaceStream( GetVtkID(), nFaces, ptIds );
-  int id = 0, nbPoints = 0;
-  for (int i = 0; i < nFaces; i++)
-  {
-    int nodesInFace = ptIds[id];
-    if ( ind < nbPoints + nodesInFace )
-      return GetMesh()->FindNodeVtk( ptIds[ ind + i ]);
-    nbPoints += nodesInFace;
-    id += (nodesInFace + 1);
-  }
-  return 0;
-}
-int SMDS_MeshVolume::NbNodes() const
-{
-  if ( !IsPoly() )
-    return SMDS_MeshCell::NbNodes();
-
-  vtkIdType nFaces = 0;
-  vtkIdType* ptIds = 0;
-  getGrid()->GetFaceStream( GetVtkID(), nFaces, ptIds );
-  int id = 0, nbPoints = 0;
-  for (int i = 0; i < nFaces; i++)
-  {
-    int nodesInFace = ptIds[id];
-    nbPoints += nodesInFace;
-    id += (nodesInFace + 1);
-  }
-  return nbPoints;
-}
-
-int SMDS_MeshVolume::NbFaces() const
-{
-  if ( !IsPoly() )
-    return SMDS_MeshCell::NbFaces();
-
-  vtkIdType nFaces = 0;
-  vtkIdType* ptIds = 0;
-  getGrid()->GetFaceStream( GetVtkID(), nFaces, ptIds );
-  return nFaces;
-  
-}
-int SMDS_MeshVolume::NbEdges() const
-{
-  if ( !IsPoly() )
-    return SMDS_MeshCell::NbEdges();
-
-  vtkIdType nFaces = 0;
-  vtkIdType* ptIds = 0;
-  getGrid()->GetFaceStream( GetVtkID(), nFaces, ptIds );
-  int id = 0, nbEdges = 0;
-  for (int i = 0; i < nFaces; i++)
-  {
-    int edgesInFace = ptIds[id];
-    id += (edgesInFace + 1);
-    nbEdges += edgesInFace;
-  }
-  nbEdges = nbEdges / 2;
-  return nbEdges;
-}
-
-int SMDS_MeshVolume::GetNodeIndex( const SMDS_MeshNode* node ) const
-{
-  if ( !IsPoly() )
-    return SMDS_MeshCell::GetNodeIndex( node );
-
-  vtkIdType nFaces = 0;
-  vtkIdType* ptIds = 0;
-  getGrid()->GetFaceStream( GetVtkID(), nFaces, ptIds );
-  int id = 0;
-  for (int iF = 0; iF < nFaces; iF++)
-  {
-    int nodesInFace = ptIds[id];
-    for ( vtkIdType i = 0; i < nodesInFace; ++i )
-      if ( ptIds[id+i+1] == node->GetVtkID() )
-        return id+i-iF;
-    id += (nodesInFace + 1);
-  }
-  return -1;
-}
-bool SMDS_MeshVolume::ChangeNodes(const SMDS_MeshNode* nodes[], const int nbNodes)
-{
-  return false;
-}
-
-bool SMDS_MeshVolume::IsMediumNode(const SMDS_MeshNode* node) const
-{
-  if ( !IsPoly() )
-    return SMDS_MeshCell::IsMediumNode( node );
-
-  return false;
-}
-
-int SMDS_MeshVolume::NbCornerNodes() const
-{
-  if ( !IsPoly() )
-    return SMDS_MeshCell::NbCornerNodes();
-
-  return NbNodes();
-}
-
-int SMDS_MeshVolume::NbFaceNodes (const int face_ind) const
+SMDSAbs_ElementType SMDS_MeshVolume::GetType() const
 {
-  if ( !IsPoly() )
-    return SMDS_VolumeTool( this ).NbFaceNodes( face_ind-1 );
-
-  vtkIdType nFaces = 0;
-  vtkIdType* ptIds = 0;
-  getGrid()->GetFaceStream( GetVtkID(), nFaces, ptIds );
-  int id = 0, nbNodes = 0;
-  for (int i = 0; i < nFaces; i++)
-  {
-    int nodesInFace = ptIds[id];
-    id += (nodesInFace + 1);
-    if (i == face_ind - 1)
-    {
-      nbNodes = nodesInFace;
-      break;
-    }
-  }
-  return nbNodes;
+        return SMDSAbs_Volume;
 }
 
-const SMDS_MeshNode* SMDS_MeshVolume::GetFaceNode (const int face_ind, const int node_ind) const
+vtkIdType SMDS_MeshVolume::GetVtkType() const
 {
-  if ( !IsPoly() )
-    return SMDS_VolumeTool( this ).GetFaceNodes( face_ind-1 )[ node_ind - 1 ];
-
-  vtkIdType nFaces = 0;
-  vtkIdType* ptIds = 0;
-  getGrid()->GetFaceStream( GetVtkID(), nFaces, ptIds);
-  int id = 0;
-  for (int i = 0; i < nFaces; i++)
-  {
-    int nodesInFace = ptIds[id]; // nodeIds in ptIds[id+1 .. id+nodesInFace]
-    if (i == face_ind - 1) // first face is number 1
-    {
-      if ((node_ind > 0) && (node_ind <= nodesInFace))
-        return GetMesh()->FindNodeVtk(ptIds[id + node_ind]); // ptIds[id+1] : first node
-    }
-    id += (nodesInFace + 1);
-  }
-  return 0;
-}
-
-std::vector<int> SMDS_MeshVolume::GetQuantities() const
-{
-  std::vector<int> quantities;
-  if ( IsPoly() )
-  {
-    vtkIdType nFaces = 0;
-    vtkIdType* ptIds = 0;
-    getGrid()->GetFaceStream( GetVtkID(), nFaces, ptIds );
-    int id = 0;
-    for (int i = 0; i < nFaces; i++)
-    {
-      int nodesInFace = ptIds[id]; // nodeIds in ptIds[id+1 .. id+nodesInFace]
-      quantities.push_back( nodesInFace );
-      id += (nodesInFace + 1);
-    }
-  }
-  return quantities;
-}
-
-///////////////////////////////////////////////////////////////////////////////
-/// Create an iterator which iterate on nodes owned by the element.
-///////////////////////////////////////////////////////////////////////////////
-SMDS_ElemIteratorPtr SMDS_MeshVolume::nodesIterator() const
-{
-  if ( !IsPoly() )
-    return SMDS_MeshCell::nodesIterator();
-
-  return boost::make_shared< SMDS_VtkCellIteratorPolyH<> >( GetMesh(), GetVtkID(), GetEntityType());
-}
-
-///////////////////////////////////////////////////////////////////////////////
-/// Create an iterator which iterate on nodes owned by the element.
-///////////////////////////////////////////////////////////////////////////////
-SMDS_NodeIteratorPtr SMDS_MeshVolume::nodeIterator() const
-{
-  if ( !IsPoly() )
-    return SMDS_MeshCell::nodeIterator();
-
-  return boost::make_shared< SMDS_VtkCellIteratorPolyH< SMDS_NodeIterator> >( GetMesh(), GetVtkID(), GetEntityType());
+  return VTK_CONVEX_POINT_SET; // --- must be reimplemented in derived classes
 }
index 7a69da0a6cc5fcfbe82e5992786b44a132551613..15887bdcd0778233fc66df31b42354d4a8ed357a 100644 (file)
 
 #include "SMDS_MeshCell.hxx"
 
-/*!
- * \brief Mesh volume. This type is not allocated.
- *        It is only used as function argument type to provide more clear semantic
- *        and to provide API specific to polyherdal volume
- */
-class SMDS_EXPORT SMDS_MeshVolume : public SMDS_MeshCell
+class SMDS_EXPORT SMDS_MeshVolume:public SMDS_MeshCell
 {
-  void init( const std::vector<const SMDS_MeshNode*>& nodes,
-             const std::vector<int>&                  nbNodesPerFace ); // init a polyherdon
-
-  void init( const std::vector<vtkIdType>& vtkNodeIds );
-
-  friend class SMDS_Mesh;
-
- public:
-  virtual SMDSAbs_ElementType  GetType() const { return SMDSAbs_Volume; }
-  virtual const SMDS_MeshNode* GetNode(const int ind) const;
-  virtual int  NbNodes() const;
-  virtual int  NbFaces() const;
-  virtual int  NbEdges() const;
-  virtual int  GetNodeIndex( const SMDS_MeshNode* node ) const;
-  virtual bool ChangeNodes(const SMDS_MeshNode* nodes[], const int nbNodes);
-  virtual bool IsMediumNode(const SMDS_MeshNode* node) const;
-  virtual int  NbCornerNodes() const;
-
-  virtual SMDS_ElemIteratorPtr nodesIterator() const = 0;
-  virtual SMDS_NodeIteratorPtr nodeIterator() const = 0;
-
-  // 1 <= face_ind <= NbFaces()
-  int NbFaceNodes (const int face_ind) const;
-  // 1 <= face_ind <= NbFaces()
-  // 1 <= node_ind <= NbFaceNodes()
-  const SMDS_MeshNode* GetFaceNode (const int face_ind, const int node_ind) const;
-
-  std::vector<int> GetQuantities() const;
-
-  static SMDSAbs_ElementType Type() { return SMDSAbs_Volume; }
+        
+  public:
+        SMDSAbs_ElementType GetType() const;
+  virtual vtkIdType GetVtkType() const;
 };
 #endif
index 2ddc79d87de391a006e7b1b6f0246aafa8aebb67..54ead2af02c79dabbd4dcdf4e0d2ffbfcd0b056e 100644 (file)
 
 #include "SMDS_PolygonalFaceOfNodes.hxx"
 
+#include "SMDS_IteratorOfElements.hxx"
 #include "SMDS_SetIterator.hxx"
 #include "SMDS_Mesh.hxx"
 
-#include <boost/make_shared.hpp>
+#include "utilities.h"
 
-#include <utilities.h>
+using namespace std;
 
 //=======================================================================
 //function : Constructor
 //purpose  : 
 //=======================================================================
-SMDS_PolygonalFaceOfNodes::
-SMDS_PolygonalFaceOfNodes (const std::vector<const SMDS_MeshNode *>& nodes)
+SMDS_PolygonalFaceOfNodes::SMDS_PolygonalFaceOfNodes
+                          (const std::vector<const SMDS_MeshNode *>& nodes)
 {
+  //MESSAGE("******************************************** SMDS_PolygonalFaceOfNodes");
   myNodes = nodes;
 }
 
@@ -52,40 +54,41 @@ SMDS_PolygonalFaceOfNodes (const std::vector<const SMDS_MeshNode *>& nodes)
 SMDSAbs_ElementType SMDS_PolygonalFaceOfNodes::GetType() const
 {
   return SMDSAbs_Face;
+  //return SMDSAbs_PolygonalFace;
 }
 
 //=======================================================================
 //function : ChangeNodes
 //purpose  : 
 //=======================================================================
-// bool SMDS_PolygonalFaceOfNodes::ChangeNodes (std::vector<const SMDS_MeshNode *> nodes)
-// {
-//   if (nodes.size() < 3)
-//     return false;
+bool SMDS_PolygonalFaceOfNodes::ChangeNodes (std::vector<const SMDS_MeshNode *> nodes)
+{
+  if (nodes.size() < 3)
+    return false;
 
-//   myNodes = nodes;
+  myNodes = nodes;
 
-//   return true;
-// }
+  return true;
+}
 
 //=======================================================================
 //function : ChangeNodes
 //purpose  : to support the same interface, as SMDS_FaceOfNodes
 //=======================================================================
-// bool SMDS_PolygonalFaceOfNodes::ChangeNodes (const SMDS_MeshNode* nodes[],
-//                                              const int            nbNodes)
-// {
-//   if (nbNodes < 3)
-//     return false;
+bool SMDS_PolygonalFaceOfNodes::ChangeNodes (const SMDS_MeshNode* nodes[],
+                                             const int            nbNodes)
+{
+  if (nbNodes < 3)
+    return false;
 
-//   myNodes.resize(nbNodes);
-//   int i = 0;
-//   for (; i < nbNodes; i++) {
-//     myNodes[i] = nodes[i];
-//   }
+  myNodes.resize(nbNodes);
+  int i = 0;
+  for (; i < nbNodes; i++) {
+    myNodes[i] = nodes[i];
+  }
 
-//   return true;
-// }
+  return true;
+}
 
 //=======================================================================
 //function : NbNodes
@@ -127,12 +130,65 @@ void SMDS_PolygonalFaceOfNodes::Print(ostream & OS) const
   OS << myNodes[i] << ") " << endl;
 }
 
+//=======================================================================
+//function : elementsIterator
+//purpose  : 
+//=======================================================================
+class SMDS_PolygonalFaceOfNodes_MyIterator:public SMDS_NodeVectorElemIterator
+{
+ public:
+  SMDS_PolygonalFaceOfNodes_MyIterator(const vector<const SMDS_MeshNode *>& s):
+    SMDS_NodeVectorElemIterator( s.begin(), s.end() ) {}
+};
+
 /// ===================================================================
 /*!
  * \brief Iterator on edges of face
  */
 /// ===================================================================
 
+class _MyEdgeIterator : public SMDS_ElemIterator
+{
+  vector< const SMDS_MeshElement* > myElems;
+  size_t                            myIndex;
+public:
+  _MyEdgeIterator(const SMDS_MeshFace* face):myIndex(0) {
+    myElems.reserve( face->NbNodes() );
+    for ( int i = 0; i < face->NbNodes(); ++i ) {
+      const SMDS_MeshElement* edge =
+        SMDS_Mesh::FindEdge( face->GetNode( i ), face->GetNodeWrap( i + 1 ));
+      if ( edge )
+        myElems.push_back( edge );
+    }
+  }
+  /// Return true if and only if there are other object in this iterator
+  virtual bool more() { return myIndex < myElems.size(); }
+
+  /// Return the current object and step to the next one
+  virtual const SMDS_MeshElement* next() { return myElems[ myIndex++ ]; }
+};
+
+SMDS_ElemIteratorPtr SMDS_PolygonalFaceOfNodes::elementsIterator
+                                         (SMDSAbs_ElementType type) const
+{
+  switch(type)
+  {
+  case SMDSAbs_Face:
+    return SMDS_MeshElement::elementsIterator(SMDSAbs_Face);
+  case SMDSAbs_Node:
+    return SMDS_ElemIteratorPtr(new SMDS_PolygonalFaceOfNodes_MyIterator(myNodes));
+  case SMDSAbs_Edge:
+    return SMDS_ElemIteratorPtr(new _MyEdgeIterator( this ));
+    break;
+  default:
+    return SMDS_ElemIteratorPtr
+      (new SMDS_IteratorOfElements
+       (this,type,SMDS_ElemIteratorPtr
+        (new SMDS_PolygonalFaceOfNodes_MyIterator(myNodes))));
+  }
+  return SMDS_ElemIteratorPtr();
+}
+
 /*!
  * \brief Return node by its index
  * \param ind - node index
@@ -142,13 +198,3 @@ const SMDS_MeshNode* SMDS_PolygonalFaceOfNodes::GetNode(const int ind) const
 {
   return myNodes[ WrappedIndex( ind )];
 }
-
-SMDS_ElemIteratorPtr SMDS_PolygonalFaceOfNodes::nodesIterator() const
-{
-  return boost::make_shared< SMDS_NodeArrayElemIterator >( &myNodes[0], &myNodes[0] + NbNodes() );
-}
-
-SMDS_NodeIteratorPtr SMDS_PolygonalFaceOfNodes::nodeIterator() const
-{
-  return boost::make_shared< SMDS_NodeArrayIterator >( &myNodes[0], &myNodes[0] + NbNodes() );
-}
index f06352edee1504c6097c58c3bd2da8268b53afaa..33dd39d0f0cd97483c9be389b468e0bf7fe5bc48 100644 (file)
 
 #include "SMESH_SMDS.hxx"
 
-#include "SMDS_CellOfNodes.hxx"
+#include "SMDS_MeshFace.hxx"
+//#include "SMDS_FaceOfNodes.hxx"
+#include "SMDS_MeshNode.hxx"
+#include "SMDS_Iterator.hxx"
 
-class SMDS_EXPORT SMDS_PolygonalFaceOfNodes : public SMDS_CellOfNodes
+#include <iostream>
+
+//class SMDS_PolygonalFaceOfNodes:public SMDS_FaceOfNodes
+class SMDS_EXPORT SMDS_PolygonalFaceOfNodes:public SMDS_MeshFace
 {
  public:
   SMDS_PolygonalFaceOfNodes (const std::vector<const SMDS_MeshNode *>& nodes);
@@ -37,10 +43,13 @@ class SMDS_EXPORT SMDS_PolygonalFaceOfNodes : public SMDS_CellOfNodes
   virtual SMDSAbs_ElementType GetType() const;
   virtual SMDSAbs_EntityType  GetEntityType() const { return SMDSEntity_Polygon; }
   virtual SMDSAbs_GeometryType GetGeomType()  const { return SMDSGeom_POLYGON; }
-  virtual bool IsPoly() const { return true; }
-  virtual bool IsQuadratic() const { return false; }
-  virtual bool IsMediumNode(const SMDS_MeshNode* node) const { return false; }
-  virtual int  NbCornerNodes() const { return NbNodes(); }
+  virtual bool IsPoly() const { return true; };
+
+  bool ChangeNodes (std::vector<const SMDS_MeshNode *> nodes);
+
+  bool ChangeNodes (const SMDS_MeshNode* nodes[],
+                    const int            nbNodes);
+  // to support the same interface, as SMDS_FaceOfNodes
 
   virtual int NbNodes() const;
   virtual int NbEdges() const;
@@ -48,12 +57,15 @@ class SMDS_EXPORT SMDS_PolygonalFaceOfNodes : public SMDS_CellOfNodes
 
   virtual void Print (std::ostream & OS) const;
 
+  /*!
+   * \brief Return node by its index
+    * \param ind - node index
+    * \retval const SMDS_MeshNode* - the node
+   */
   virtual const SMDS_MeshNode* GetNode(const int ind) const;
 
-  virtual SMDS_ElemIteratorPtr nodesIterator() const;
-  virtual SMDS_NodeIteratorPtr nodeIterator() const;
-
  protected:
+  virtual SMDS_ElemIteratorPtr elementsIterator (SMDSAbs_ElementType type) const;
 
   std::vector<const SMDS_MeshNode *> myNodes;
 };
diff --git a/src/SMDS/SMDS_PolyhedralVolumeOfNodes.cxx b/src/SMDS/SMDS_PolyhedralVolumeOfNodes.cxx
new file mode 100644 (file)
index 0000000..20c948b
--- /dev/null
@@ -0,0 +1,265 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//
+#ifdef _MSC_VER
+#pragma warning(disable:4786)
+#endif
+
+#include "SMDS_PolyhedralVolumeOfNodes.hxx"
+#include "SMDS_MeshNode.hxx"
+#include "SMDS_SetIterator.hxx"
+#include "SMDS_VolumeTool.hxx"
+#include "utilities.h"
+
+#include <set>
+
+using namespace std;
+
+//=======================================================================
+//function : Constructor
+//purpose  : Create a volume of many faces
+//=======================================================================
+SMDS_PolyhedralVolumeOfNodes::SMDS_PolyhedralVolumeOfNodes
+                                (vector<const SMDS_MeshNode *> nodes,
+                                 vector<int>                   quantities)
+: SMDS_VolumeOfNodes(NULL, NULL, NULL, NULL)
+{
+  //MESSAGE("****************************************** SMDS_PolyhedralVolumeOfNodes");
+  ChangeNodes(nodes, quantities);
+}
+
+//=======================================================================
+//function : GetType
+//purpose  : 
+//=======================================================================
+SMDSAbs_ElementType SMDS_PolyhedralVolumeOfNodes::GetType() const
+{
+//  return SMDSAbs_PolyhedralVolume;
+  return SMDSAbs_Volume;
+}
+
+//=======================================================================
+//function : ChangeNodes
+//purpose  : 
+//=======================================================================
+bool SMDS_PolyhedralVolumeOfNodes::ChangeNodes (const vector<const SMDS_MeshNode *>& nodes,
+                                                const vector<int>&                   quantities)
+{
+  myNodesByFaces = nodes;
+  myQuantities = quantities;
+
+  // Init fields of parent class, it allows to get only unique nodes(?)
+
+  set<const SMDS_MeshNode *> aSet;
+  aSet.insert( nodes.begin(), nodes.end());
+  //SMDS_VolumeOfNodes::ChangeNodes(aNodes, aNbNodes);
+  delete [] myNodes;
+  myNbNodes = aSet.size();
+  myNodes = new const SMDS_MeshNode* [myNbNodes];
+  set<const SMDS_MeshNode *>::iterator anIter = aSet.begin();
+  for (int k=0; anIter != aSet.end(); anIter++, k++)
+    myNodes[k] = *anIter;
+
+  return true;
+}
+
+//=======================================================================
+//function : NbEdges
+//purpose  : 
+//=======================================================================
+int SMDS_PolyhedralVolumeOfNodes::NbNodes() const
+{
+  return myNodesByFaces.size();
+}
+
+//=======================================================================
+//function : NbEdges
+//purpose  : 
+//=======================================================================
+int SMDS_PolyhedralVolumeOfNodes::NbEdges() const
+{
+  int nbEdges = 0;
+
+  for ( size_t ifa = 0; ifa < myQuantities.size(); ifa++) {
+    nbEdges += myQuantities[ifa];
+  }
+  nbEdges /= 2;
+
+  return nbEdges;
+}
+
+//=======================================================================
+//function : NbFaces
+//purpose  : 
+//=======================================================================
+int SMDS_PolyhedralVolumeOfNodes::NbFaces() const
+{
+  return myQuantities.size();
+}
+
+//=======================================================================
+//function : NbFaceNodes
+//purpose  : 
+//=======================================================================
+int SMDS_PolyhedralVolumeOfNodes::NbFaceNodes (const int face_ind) const
+{
+  if (face_ind < 1 || (int)myQuantities.size() < face_ind)
+    return 0;
+  return myQuantities[face_ind - 1];
+}
+
+//=======================================================================
+//function : GetFaceNode
+//purpose  : 
+//=======================================================================
+const SMDS_MeshNode* SMDS_PolyhedralVolumeOfNodes::GetFaceNode (const int face_ind,
+                                                                const int node_ind) const
+{
+  if (node_ind < 1 || NbFaceNodes(face_ind) < node_ind)
+    return NULL;
+
+  int i, first_node = 0;
+  for (i = 0; i < face_ind - 1; i++) {
+    first_node += myQuantities[i];
+  }
+
+  return myNodesByFaces[first_node + node_ind - 1];
+}
+
+//=======================================================================
+//function : Print
+//purpose  : 
+//=======================================================================
+void SMDS_PolyhedralVolumeOfNodes::Print (ostream & OS) const
+{
+  OS << "polyhedral volume <" << GetID() << "> : ";
+
+  int faces_len = myQuantities.size();
+  //int nodes_len = myNodesByFaces.size();
+  int cur_first_node = 0;
+
+  int i, j;
+  for (i = 0; i < faces_len; i++) {
+    OS << "face_" << i << " (";
+    for (j = 0; j < myQuantities[i] - 1; j++) {
+      OS << myNodesByFaces[cur_first_node + j] << ",";
+    }
+    OS << myNodesByFaces[cur_first_node + j] << ") ";
+    cur_first_node += myQuantities[i];
+  }
+}
+
+//=======================================================================
+//function : ChangeNodes
+//purpose  : usage disabled
+//=======================================================================
+bool SMDS_PolyhedralVolumeOfNodes::ChangeNodes (const SMDS_MeshNode* nodes[],
+                                                const int            nbNodes)
+{
+  return false;
+}
+
+/// ===================================================================
+/*!
+ * \brief Iterator on node of volume
+ */
+/// ===================================================================
+
+struct _MyIterator:public SMDS_NodeVectorElemIterator
+{
+  _MyIterator(const vector<const SMDS_MeshNode *>& nodes):
+    SMDS_NodeVectorElemIterator( nodes.begin(), nodes.end()) {}
+};
+
+/// ===================================================================
+/*!
+ * \brief Iterator on faces or edges of volume
+ */
+/// ===================================================================
+
+class _MySubIterator : public SMDS_ElemIterator
+{
+  vector< const SMDS_MeshElement* > myElems;
+  size_t                            myIndex;
+public:
+  _MySubIterator(const SMDS_MeshVolume* vol, SMDSAbs_ElementType type):myIndex(0) {
+    SMDS_VolumeTool vTool(vol);
+    if (type == SMDSAbs_Face)
+      vTool.GetAllExistingFaces( myElems );
+    else
+      vTool.GetAllExistingEdges( myElems );
+  }
+  /// Return true if and only if there are other object in this iterator
+  virtual bool more() { return myIndex < myElems.size(); }
+
+  /// Return the current object and step to the next one
+  virtual const SMDS_MeshElement* next() { return myElems[ myIndex++ ]; }
+};
+
+//================================================================================
+/*!
+ * \brief Return Iterator of sub elements
+ */
+//================================================================================
+
+SMDS_ElemIteratorPtr SMDS_PolyhedralVolumeOfNodes::elementsIterator(SMDSAbs_ElementType type) const
+{
+  switch(type)
+  {
+  case SMDSAbs_Volume:
+    return SMDS_MeshElement::elementsIterator(SMDSAbs_Volume);
+  case SMDSAbs_Node:
+    return SMDS_ElemIteratorPtr(new _MyIterator(myNodesByFaces));
+  case SMDSAbs_Face:
+    return SMDS_ElemIteratorPtr(new _MySubIterator(this,SMDSAbs_Face));
+  case SMDSAbs_Edge:
+    return SMDS_ElemIteratorPtr(new _MySubIterator(this,SMDSAbs_Edge));
+  default:
+    MESSAGE("ERROR : Iterator not implemented");
+    return SMDS_ElemIteratorPtr((SMDS_ElemIterator*)NULL);
+  }
+}
+
+//================================================================================
+/*!
+ * \brief Return iterator on unique nodes
+ */
+//================================================================================
+
+SMDS_ElemIteratorPtr SMDS_PolyhedralVolumeOfNodes::uniqueNodesIterator() const
+{
+  return SMDS_ElemIteratorPtr
+    (new SMDS_NodeArrayElemIterator( myNodes, & myNodes[ myNbNodes ]));
+}
+
+//================================================================================
+/*!
+ * \brief Return node by its index
+ */
+//================================================================================
+
+const SMDS_MeshNode* SMDS_PolyhedralVolumeOfNodes::GetNode(const int ind) const
+{
+  return myNodesByFaces[ ind ];
+}
diff --git a/src/SMDS/SMDS_PolyhedralVolumeOfNodes.hxx b/src/SMDS/SMDS_PolyhedralVolumeOfNodes.hxx
new file mode 100644 (file)
index 0000000..cba8a91
--- /dev/null
@@ -0,0 +1,91 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//  File   : SMDS_PolyhedralVolumeOfNodes.hxx
+//  Module : SMESH
+//
+#ifndef _SMDS_PolyhedralVolumeOfNodes_HeaderFile
+#define _SMDS_PolyhedralVolumeOfNodes_HeaderFile
+
+#include "SMESH_SMDS.hxx"
+
+#include "SMDS_VolumeOfNodes.hxx"
+
+class SMDS_EXPORT SMDS_PolyhedralVolumeOfNodes:public SMDS_VolumeOfNodes
+{
+ public:
+  SMDS_PolyhedralVolumeOfNodes (std::vector<const SMDS_MeshNode *> nodes,
+                                std::vector<int>                   quantities);
+
+  //virtual ~SMDS_PolyhedralVolumeOfNodes();
+
+  virtual SMDSAbs_ElementType GetType() const;  
+  virtual SMDSAbs_EntityType   GetEntityType() const { return SMDSEntity_Polyhedra; }
+  virtual bool IsPoly() const { return true; };
+
+  bool ChangeNodes (const std::vector<const SMDS_MeshNode *> & nodes,
+                    const std::vector<int> &                   quantities);
+
+  virtual int NbNodes() const;
+  virtual int NbEdges() const;
+  virtual int NbFaces() const;
+
+  int NbFaceNodes (const int face_ind) const;
+  // 1 <= face_ind <= NbFaces()
+
+  const SMDS_MeshNode* GetFaceNode (const int face_ind, const int node_ind) const;
+  // 1 <= face_ind <= NbFaces()
+  // 1 <= node_ind <= NbFaceNodes()
+
+  const std::vector<int> & GetQuanities() const { return myQuantities; }
+
+  virtual void Print (std::ostream & OS) const;
+
+  /*!
+   * \brief Return node by its index
+   */
+  virtual const SMDS_MeshNode* GetNode(const int ind) const;
+
+  /*!
+   * \brief Return iterator on unique nodes
+   */
+  SMDS_ElemIteratorPtr uniqueNodesIterator() const;
+  /*!
+   * \brief Return nb of unique nodes
+   */
+  int NbUniqueNodes() const { return myNbNodes; }
+
+protected:
+  SMDS_ElemIteratorPtr elementsIterator(SMDSAbs_ElementType type) const;
+
+ private:
+  // usage disabled
+  bool ChangeNodes (const SMDS_MeshNode* nodes[],
+                    const int            nbNodes);
+
+ private:
+  std::vector<const SMDS_MeshNode *> myNodesByFaces;
+  std::vector<int> myQuantities;
+};
+
+#endif
diff --git a/src/SMDS/SMDS_Position.cxx b/src/SMDS/SMDS_Position.cxx
new file mode 100644 (file)
index 0000000..e7c408f
--- /dev/null
@@ -0,0 +1,58 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//  File   : SMDS_Position.cxx
+//  Author : Jean-Michel BOULCOURT
+//  Module : SMESH
+//
+#include "SMDS_Position.hxx"
+#include "utilities.h"
+
+//=======================================================================
+//function : SMDS_Position
+//purpose  : 
+//=======================================================================
+
+SMDS_Position::SMDS_Position()
+{
+  //MESSAGE("########################## SMDS_Position ");
+}
+
+//=======================================================================
+//function : GetDim
+//purpose  : 
+//=======================================================================
+
+int SMDS_Position::GetDim() const
+{
+//   switch ( GetTypeOfPosition() ) {
+//   case SMDS_TOP_UNSPEC:  return -1;
+//   case SMDS_TOP_VERTEX:  return 0;
+//   case SMDS_TOP_EDGE:    return 1;
+//   case SMDS_TOP_FACE:    return 2;
+//   case SMDS_TOP_3DSPACE: return 3;
+//   }
+  return GetTypeOfPosition();
+}
+
+     
index 62c4042d3322fd09c299aa3afd83d3112b4408c7..b6976677d291a5ae3f9d6f5f3e5c875cd23158d0 100644 (file)
 #include "SMESH_SMDS.hxx"
 
 #include "SMDS_TypeOfPosition.hxx"
-#include <memory>
+#include <boost/shared_ptr.hpp>
 
-//class SMDS_Position;
+class SMDS_Position;
 //typedef boost::shared_ptr<SMDS_Position> SMDS_PositionPtr;
-//typedef SMDS_Position* SMDS_PositionPtr;
+typedef SMDS_Position* SMDS_PositionPtr;
 
 class SMDS_EXPORT SMDS_Position
 {
 
- public:
-  virtual SMDS_TypeOfPosition GetTypeOfPosition() const = 0;
-  int GetDim() const { return GetTypeOfPosition(); }
-  virtual const double* GetParameters() const = 0;
-  virtual ~SMDS_Position() {}
-};
-
-/*!
- * \brief Replace "typedef SMDS_Position* SMDS_PositionPtr" by a smart
- *        pointer allowing implicit casting to derived types; e.g.
- *        if ( SMDS_FacePositionPtr fPos = node->GetPosition() )
- *          fPos->SetUParameter(0);
- */
-
-template<class T>
-class SMDS_EXPORT SMDS_Ptr : public std::unique_ptr< T >
-{
-  bool myIsOwner;
-
- public:
-  SMDS_Ptr( T * pos = (T *) 0, bool isOwner=true ):
-    std::unique_ptr< T >( pos ), myIsOwner( isOwner ) {}
-
-  SMDS_Ptr( const SMDS_Ptr& from ) : myIsOwner( from.myIsOwner )
-  { this->swap( const_cast<SMDS_Ptr&>( from )); }
-
-  SMDS_Ptr& operator=( const SMDS_Ptr& from  )
-  {
-    myIsOwner = from.myIsOwner;
-    this->swap( const_cast<SMDS_Ptr&>( from ));
-    return *this;
-  }
-
-  template<class Y>
-    SMDS_Ptr( const SMDS_Ptr< Y >& base ): myIsOwner( true )
-  {
-    if ( const T* p = dynamic_cast<const T*>( base.get() ))
-    {
-      this->reset( const_cast<T*>( p ));
-      this->myIsOwner = base.IsOwner();
-      const_cast< SMDS_Ptr< Y >& >( base ).release();
-    }
-  }
-  ~SMDS_Ptr() { if ( !myIsOwner ) this->release(); }
+  public:
+        virtual SMDS_TypeOfPosition GetTypeOfPosition() const = 0;
+        virtual int GetDim() const;
+        virtual ~SMDS_Position() {}
 
-  operator bool () const { return bool( this->get() ); }
-  bool IsOwner() const { return myIsOwner; }
+  protected:
+          SMDS_Position();
 };
 
-class SMDS_EdgePosition;
-class SMDS_FacePosition;
-typedef SMDS_Ptr< SMDS_Position >     SMDS_PositionPtr;
-typedef SMDS_Ptr< SMDS_EdgePosition > SMDS_EdgePositionPtr;
-typedef SMDS_Ptr< SMDS_FacePosition > SMDS_FacePositionPtr;
 
 #endif
diff --git a/src/SMDS/SMDS_QuadraticEdge.cxx b/src/SMDS/SMDS_QuadraticEdge.cxx
new file mode 100644 (file)
index 0000000..9f6cf94
--- /dev/null
@@ -0,0 +1,160 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+// File:      SMDS_QuadraticEdge.cxx
+// Created:   16.01.06 16:25:42
+// Author:    Sergey KUUL
+//
+#include "SMDS_QuadraticEdge.hxx"
+
+#include "SMDS_SetIterator.hxx"
+#include "SMDS_IteratorOfElements.hxx"
+#include "SMDS_MeshNode.hxx"
+#include "utilities.h"
+
+using namespace std;
+
+//=======================================================================
+//function : SMDS_QuadraticEdge
+//purpose  : 
+//=======================================================================
+
+SMDS_QuadraticEdge::SMDS_QuadraticEdge(const SMDS_MeshNode * node1,
+                                       const SMDS_MeshNode * node2,
+                                       const SMDS_MeshNode * node12)
+     :SMDS_LinearEdge(node1,node2)
+{
+  //MESSAGE("******************************************************* SMDS_QuadraticEdge");
+  myNodes[2]=node12;
+}
+
+
+//=======================================================================
+//function : Print
+//purpose  : 
+//=======================================================================
+
+void SMDS_QuadraticEdge::Print(ostream & OS) const
+{
+  OS << "quadratic edge <" << GetID() << "> : ( first-" << myNodes[0]
+     << " , last-" << myNodes[1] << " , medium-" << myNodes[2] << ") " << endl;
+}
+
+
+//=======================================================================
+//function : NbNodes
+//purpose  : 
+//=======================================================================
+
+int SMDS_QuadraticEdge::NbNodes() const
+{
+  return 3;
+}
+
+//=======================================================================
+//function : ChangeNodes
+//purpose  : 
+//=======================================================================
+
+bool SMDS_QuadraticEdge::ChangeNodes(const SMDS_MeshNode * node1,
+                                     const SMDS_MeshNode * node2,
+                                     const SMDS_MeshNode * node12)
+{
+  myNodes[0]=node1;
+  myNodes[1]=node2;
+  myNodes[2]=node12;
+  return true;
+}
+
+//=======================================================================
+//function : IsMediumNode
+//purpose  : 
+//=======================================================================
+
+bool SMDS_QuadraticEdge::IsMediumNode(const SMDS_MeshNode * node) const
+{
+  return (myNodes[2]==node);
+}
+
+namespace
+{
+  //=======================================================================
+  //class : _MyInterlacedNodeIterator
+  //purpose  : 
+  //=======================================================================
+
+  class _MyInterlacedNodeIterator: public SMDS_NodeArrayIterator
+  {
+    const SMDS_MeshNode * myNodes[3];
+  public:
+    _MyInterlacedNodeIterator(const SMDS_MeshNode * const * nodes):
+      SMDS_NodeArrayIterator( myNodes, & myNodes[3] )
+    {
+      myNodes[0] = nodes[0];
+      myNodes[1] = nodes[2];
+      myNodes[2] = nodes[1];
+    }
+  };
+
+  //=======================================================================
+  //class : _MyNodeIterator
+  //purpose  : 
+  //=======================================================================
+
+  class _MyNodeIterator:public SMDS_NodeArrayElemIterator
+  {
+  public:
+    _MyNodeIterator(const SMDS_MeshNode * const * nodes):
+      SMDS_NodeArrayElemIterator( nodes, & nodes[3] ) {}
+  };
+}
+
+//=======================================================================
+//function : interlacedNodesIterator
+//purpose  : 
+//=======================================================================
+
+SMDS_NodeIteratorPtr SMDS_QuadraticEdge::interlacedNodesIterator() const
+{
+  return SMDS_NodeIteratorPtr (new _MyInterlacedNodeIterator (myNodes));
+}
+
+//=======================================================================
+//function : elementsIterator
+//purpose  : 
+//=======================================================================
+
+SMDS_ElemIteratorPtr SMDS_QuadraticEdge::elementsIterator(SMDSAbs_ElementType type) const
+{
+  switch(type)
+  {
+  case SMDSAbs_Edge:
+    return SMDS_MeshElement::elementsIterator(SMDSAbs_Edge); 
+  case SMDSAbs_Node:
+    return SMDS_ElemIteratorPtr(new _MyNodeIterator(myNodes));
+  default:
+    return SMDS_ElemIteratorPtr
+      (new SMDS_IteratorOfElements
+       (this,type, SMDS_ElemIteratorPtr(new _MyNodeIterator(myNodes))));
+  }
+}
diff --git a/src/SMDS/SMDS_QuadraticEdge.hxx b/src/SMDS/SMDS_QuadraticEdge.hxx
new file mode 100644 (file)
index 0000000..7eeabf6
--- /dev/null
@@ -0,0 +1,64 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//  File   : SMDS_QuadraticEdge.hxx
+//  Module : SMESH
+//
+#ifndef _SMDS_QuadraticEdge_HeaderFile
+#define _SMDS_QuadraticEdge_HeaderFile
+
+#include "SMESH_SMDS.hxx"
+
+#include "SMDS_LinearEdge.hxx"
+#include <iostream>
+
+class SMDS_EXPORT SMDS_QuadraticEdge: public SMDS_LinearEdge
+{
+
+public:
+  SMDS_QuadraticEdge(const SMDS_MeshNode * node1,
+                     const SMDS_MeshNode * node2,
+                     const SMDS_MeshNode * node12);
+
+  bool ChangeNodes(const SMDS_MeshNode * node1,
+                   const SMDS_MeshNode * node2,
+                   const SMDS_MeshNode * node12);
+
+  void Print(std::ostream & OS) const;
+
+  int NbNodes() const;
+
+  virtual SMDSAbs_EntityType GetEntityType() const { return SMDSEntity_Quad_Edge; }
+
+  virtual bool IsQuadratic() const { return true; }
+
+  virtual bool IsMediumNode(const SMDS_MeshNode* node) const;
+
+  SMDS_NodeIteratorPtr interlacedNodesIterator() const;
+
+protected:
+  SMDS_ElemIteratorPtr
+  elementsIterator(SMDSAbs_ElementType type) const;
+
+};
+#endif
diff --git a/src/SMDS/SMDS_QuadraticFaceOfNodes.cxx b/src/SMDS/SMDS_QuadraticFaceOfNodes.cxx
new file mode 100644 (file)
index 0000000..49066ac
--- /dev/null
@@ -0,0 +1,290 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+// File:      SMDS_QuadraticFaceOfNodes.cxx
+// Created:   16.01.06 17:12:58
+// Author:    Sergey KUUL
+//
+#include "SMDS_QuadraticFaceOfNodes.hxx"
+
+#include "SMDS_SetIterator.hxx"
+#include "SMDS_IteratorOfElements.hxx"
+#include "SMDS_MeshNode.hxx"
+#include "SMDS_Mesh.hxx"
+
+#include "utilities.h"
+
+using namespace std;
+
+
+//=======================================================================
+//function : SMDS_QuadraticFaceOfNodes()
+//purpose  : Constructor
+//=======================================================================
+
+SMDS_QuadraticFaceOfNodes::SMDS_QuadraticFaceOfNodes(const SMDS_MeshNode * n1,
+                                                     const SMDS_MeshNode * n2,
+                                                     const SMDS_MeshNode * n3,
+                                                     const SMDS_MeshNode * n12,
+                                                     const SMDS_MeshNode * n23,
+                                                     const SMDS_MeshNode * n31)
+{
+  //MESSAGE("********************************************** SMDS_QuadraticFaceOfNodes 1");
+  myNodes.resize( 6 );
+  myNodes[ 0 ] = n1;
+  myNodes[ 1 ] = n2;
+  myNodes[ 2 ] = n3;
+  myNodes[ 3 ] = n12;
+  myNodes[ 4 ] = n23;
+  myNodes[ 5 ] = n31;
+}
+
+
+//=======================================================================
+//function : SMDS_QuadraticFaceOfNodes()
+//purpose  : Constructor
+//=======================================================================
+
+SMDS_QuadraticFaceOfNodes::SMDS_QuadraticFaceOfNodes(const SMDS_MeshNode * n1,
+                                                     const SMDS_MeshNode * n2,
+                                                     const SMDS_MeshNode * n3,
+                                                     const SMDS_MeshNode * n4,
+                                                     const SMDS_MeshNode * n12,
+                                                     const SMDS_MeshNode * n23,
+                                                     const SMDS_MeshNode * n34,
+                                                     const SMDS_MeshNode * n41)
+{
+  //MESSAGE("********************************************* SMDS_QuadraticFaceOfNodes 2");
+  myNodes.resize( 8 );
+  myNodes[ 0 ] = n1;
+  myNodes[ 1 ] = n2;
+  myNodes[ 2 ] = n3;
+  myNodes[ 3 ] = n4;
+  myNodes[ 4 ] = n12;
+  myNodes[ 5 ] = n23;
+  myNodes[ 6 ] = n34;
+  myNodes[ 7 ] = n41;
+}
+
+
+//=======================================================================
+//function : IsMediumNode
+//purpose  : 
+//=======================================================================
+
+bool SMDS_QuadraticFaceOfNodes::IsMediumNode(const SMDS_MeshNode * node) const
+{
+  int i=NbNodes()/2;
+  for(; i<NbNodes(); i++) {
+    if(myNodes[i]==node) return true;
+  }
+  return false;
+}
+
+
+//=======================================================================
+//function : ChangeNodes
+//purpose  : 
+//=======================================================================
+
+bool SMDS_QuadraticFaceOfNodes::ChangeNodes(const SMDS_MeshNode* nodes[],
+                                            const int            nbNodes)
+{
+  if( nbNodes==6 || nbNodes==8 ) {
+    myNodes.resize(nbNodes);
+    int i=0;
+    for(; i<nbNodes; i++) {
+      myNodes[i] = nodes[i];
+    }
+    return true;
+  }
+  return false;
+}
+
+
+//=======================================================================
+//function : NbNodes
+//purpose  : 
+//=======================================================================
+int SMDS_QuadraticFaceOfNodes::NbNodes() const
+{
+  return myNodes.size();
+}
+
+
+//=======================================================================
+//function : NbEdges
+//purpose  : 
+//=======================================================================
+int SMDS_QuadraticFaceOfNodes::NbEdges() const
+{
+  return NbNodes()/2;
+}
+
+
+//=======================================================================
+//function : NbFaces
+//purpose  : 
+//=======================================================================
+int SMDS_QuadraticFaceOfNodes::NbFaces() const
+{
+  return 1;
+}
+
+//=======================================================================
+//function : Print
+//purpose  : 
+//=======================================================================
+void SMDS_QuadraticFaceOfNodes::Print(ostream & OS) const
+{
+  OS << "quadratic face <" << GetID() << " > : ";
+  int i, nbNodes = myNodes.size();
+  for (i = 0; i < nbNodes - 1; i++)
+    OS << myNodes[i] << ",";
+  OS << myNodes[i] << ") " << endl;
+}
+
+namespace {
+
+  //=======================================================================
+  //class : _MyInterlacedNodeIterator
+  //purpose  :
+  //=======================================================================
+
+  class _MyInterlacedNodeIterator:public SMDS_NodeIterator
+  {
+    const vector<const SMDS_MeshNode *>& mySet;
+    size_t                               myIndex;
+    const int *                          myInterlace;
+  public:
+    _MyInterlacedNodeIterator(const vector<const SMDS_MeshNode *>& s,
+                              const int * interlace):
+      mySet(s),myIndex(0),myInterlace(interlace) {}
+
+    bool more()
+    {
+      return myIndex < mySet.size();
+    }
+
+    const SMDS_MeshNode* next()
+    {
+      return mySet[ myInterlace[ myIndex++ ]];
+    }
+  };
+
+  //=======================================================================
+  //class : _MyNodeIterator
+  //purpose  : 
+  //=======================================================================
+
+  class _MyNodeIterator : public SMDS_NodeVectorElemIterator
+  {
+  public:
+    _MyNodeIterator(const vector<const SMDS_MeshNode *>& s):
+      SMDS_NodeVectorElemIterator( s.begin(), s.end() ) {}
+  };
+  
+}
+
+//=======================================================================
+//function : interlacedNodesIterator
+//purpose  : 
+//=======================================================================
+
+SMDS_NodeIteratorPtr SMDS_QuadraticFaceOfNodes::interlacedNodesIterator() const
+{
+  static int triaInterlace [] = { 0, 3, 1, 4, 2, 5 };
+  static int quadInterlace [] = { 0, 4, 1, 5, 2, 6, 3, 7 };
+  return SMDS_NodeIteratorPtr
+    (new _MyInterlacedNodeIterator (myNodes, myNodes.size()==6 ? triaInterlace : quadInterlace));
+}
+
+/// ===================================================================
+/*!
+ * \brief Iterator on edges of face
+ */
+/// ===================================================================
+
+class _MyEdgeIterator : public SMDS_ElemIterator
+{
+  vector< const SMDS_MeshElement* > myElems;
+  size_t                            myIndex;
+public:
+  _MyEdgeIterator(const SMDS_QuadraticFaceOfNodes* face):myIndex(0) {
+    myElems.reserve( face->NbNodes() );
+    SMDS_NodeIteratorPtr nIt = face->interlacedNodesIterator();
+    const SMDS_MeshNode* n0 = face->GetNodeWrap( -1 );
+    while ( nIt->more() ) {
+      const SMDS_MeshNode* n1 = nIt->next();
+      const SMDS_MeshElement* edge = SMDS_Mesh::FindEdge( n0, n1 );
+      if ( edge )
+        myElems.push_back( edge );
+      n0 = n1;
+    }
+  }
+  /// Return true if and only if there are other object in this iterator
+  virtual bool more() { return myIndex < myElems.size(); }
+
+  /// Return the current object and step to the next one
+  virtual const SMDS_MeshElement* next() { return myElems[ myIndex++ ]; }
+};
+
+//=======================================================================
+//function : elementsIterator
+//purpose  : 
+//=======================================================================
+
+SMDS_ElemIteratorPtr SMDS_QuadraticFaceOfNodes::elementsIterator
+                                         (SMDSAbs_ElementType type) const
+{
+  switch(type)
+  {
+  case SMDSAbs_Face:
+    return SMDS_MeshElement::elementsIterator(SMDSAbs_Face);
+  case SMDSAbs_Node:
+    return SMDS_ElemIteratorPtr(new _MyNodeIterator(myNodes));
+  case SMDSAbs_Edge:
+    return SMDS_ElemIteratorPtr(new _MyEdgeIterator( this ));
+    break;
+  default:
+    return SMDS_ElemIteratorPtr
+      (new SMDS_IteratorOfElements
+       (this,type,SMDS_ElemIteratorPtr (new _MyNodeIterator(myNodes))));
+  }
+  return SMDS_ElemIteratorPtr();
+}
+
+/*!
+ * \brief Return node by its index
+ * \param ind - node index
+ * \retval const SMDS_MeshNode* - the node
+ */
+const SMDS_MeshNode* SMDS_QuadraticFaceOfNodes::GetNode(const int ind) const
+{
+  return myNodes[ ind ];
+}
+
+SMDSAbs_EntityType SMDS_QuadraticFaceOfNodes::GetEntityType() const
+{
+  return NbNodes() == 6 ? SMDSEntity_Quad_Triangle : SMDSEntity_Quad_Quadrangle;
+}
diff --git a/src/SMDS/SMDS_QuadraticFaceOfNodes.hxx b/src/SMDS/SMDS_QuadraticFaceOfNodes.hxx
new file mode 100644 (file)
index 0000000..8ef0a9d
--- /dev/null
@@ -0,0 +1,83 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//  File   : SMDS_QuadraticVolumeOfNodes.hxx
+//  Module : SMESH
+//
+#ifndef _SMDS_QuadraticFaceOfNodes_HeaderFile
+#define _SMDS_QuadraticFaceOfNodes_HeaderFile
+
+#include "SMESH_SMDS.hxx"
+
+#include "SMDS_MeshFace.hxx"
+
+class SMDS_EXPORT SMDS_QuadraticFaceOfNodes:public SMDS_MeshFace
+{
+public:
+  SMDS_QuadraticFaceOfNodes (const SMDS_MeshNode * n1,
+                             const SMDS_MeshNode * n2,
+                             const SMDS_MeshNode * n3,
+                             const SMDS_MeshNode * n12,
+                             const SMDS_MeshNode * n23,
+                             const SMDS_MeshNode * n31);
+
+  SMDS_QuadraticFaceOfNodes(const SMDS_MeshNode * n1,
+                            const SMDS_MeshNode * n2,
+                            const SMDS_MeshNode * n3,
+                            const SMDS_MeshNode * n4,
+                            const SMDS_MeshNode * n12,
+                            const SMDS_MeshNode * n23,
+                            const SMDS_MeshNode * n34,
+                            const SMDS_MeshNode * n41);
+
+  virtual SMDSAbs_EntityType GetEntityType() const;
+  virtual bool IsQuadratic() const { return true; }
+
+  virtual bool IsMediumNode(const SMDS_MeshNode* node) const;
+
+  bool ChangeNodes(const SMDS_MeshNode* nodes[],
+                   const int            nbNodes);
+
+  virtual int NbNodes() const;
+  virtual int NbEdges() const;
+  virtual int NbFaces() const;
+
+  virtual void Print (std::ostream & OS) const;
+
+  SMDS_NodeIteratorPtr interlacedNodesIterator() const;
+
+  /*!
+   * \brief Return node by its index
+    * \param ind - node index
+    * \retval const SMDS_MeshNode* - the node
+   */
+  virtual const SMDS_MeshNode* GetNode(const int ind) const;
+
+protected:
+  virtual SMDS_ElemIteratorPtr elementsIterator (SMDSAbs_ElementType type) const;
+
+ private:
+  std::vector<const SMDS_MeshNode *> myNodes;
+};
+
+#endif
diff --git a/src/SMDS/SMDS_QuadraticVolumeOfNodes.cxx b/src/SMDS/SMDS_QuadraticVolumeOfNodes.cxx
new file mode 100644 (file)
index 0000000..0248ba8
--- /dev/null
@@ -0,0 +1,389 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+// File:      SMDS_QuadraticVolumeOfNodes.cxx
+// Created:   17.01.06 09:46:11
+// Author:    Sergey KUUL
+//
+#include "SMDS_QuadraticVolumeOfNodes.hxx"
+
+#include "SMDS_IteratorOfElements.hxx"
+#include "SMDS_MeshNode.hxx"
+#include "SMDS_SetIterator.hxx"
+#include "SMDS_VolumeTool.hxx"
+
+#include "utilities.h"
+
+using namespace std;
+
+
+//=======================================================================
+//function : SMDS_QuadraticVolumeOfNodes()
+//purpose  : Constructor tetrahedron of 10 nodes
+//=======================================================================
+
+SMDS_QuadraticVolumeOfNodes::SMDS_QuadraticVolumeOfNodes
+                                               (const SMDS_MeshNode * n1,
+                                                const SMDS_MeshNode * n2,
+                                                const SMDS_MeshNode * n3,
+                                                const SMDS_MeshNode * n4,
+                                                const SMDS_MeshNode * n12,
+                                                const SMDS_MeshNode * n23,
+                                                const SMDS_MeshNode * n31,
+                                                const SMDS_MeshNode * n14, 
+                                                const SMDS_MeshNode * n24,
+                                                const SMDS_MeshNode * n34)
+{
+  //MESSAGE("*********************************************** SMDS_QuadraticVolumeOfNodes");
+  myNodes.resize( 10 );
+  myNodes[ 0 ] = n1;
+  myNodes[ 1 ] = n2;
+  myNodes[ 2 ] = n3;
+  myNodes[ 3 ] = n4;
+  myNodes[ 4 ] = n12;
+  myNodes[ 5 ] = n23;
+  myNodes[ 6 ] = n31;
+  myNodes[ 7 ] = n14;
+  myNodes[ 8 ] = n24;
+  myNodes[ 9 ] = n34;
+}
+
+
+//=======================================================================
+//function : SMDS_QuadraticVolumeOfNodes()
+//purpose  : Constructor pyramid of 13 nodes
+//=======================================================================
+
+SMDS_QuadraticVolumeOfNodes::SMDS_QuadraticVolumeOfNodes
+                                               (const SMDS_MeshNode * n1,
+                                                const SMDS_MeshNode * n2,
+                                                const SMDS_MeshNode * n3,
+                                                const SMDS_MeshNode * n4,
+                                                const SMDS_MeshNode * n5,
+                                                const SMDS_MeshNode * n12,
+                                                const SMDS_MeshNode * n23,
+                                                const SMDS_MeshNode * n34,
+                                                const SMDS_MeshNode * n41, 
+                                                const SMDS_MeshNode * n15,
+                                                const SMDS_MeshNode * n25,
+                                                const SMDS_MeshNode * n35,
+                                                const SMDS_MeshNode * n45)
+{
+  //MESSAGE("*********************************************** SMDS_QuadraticVolumeOfNodes");
+  myNodes.resize( 13 );
+  myNodes[ 0 ] = n1;
+  myNodes[ 1 ] = n2;
+  myNodes[ 2 ] = n3;
+  myNodes[ 3 ] = n4;
+  myNodes[ 4 ] = n5;
+  myNodes[ 5 ] = n12;
+  myNodes[ 6 ] = n23;
+  myNodes[ 7 ] = n34;
+  myNodes[ 8 ] = n41;
+  myNodes[ 9 ] = n15;
+  myNodes[ 10 ] = n25;
+  myNodes[ 11 ] = n35;
+  myNodes[ 12 ] = n45;
+}
+
+
+//=======================================================================
+//function : SMDS_QuadraticVolumeOfNodes()
+//purpose  : Constructor Pentahedron with 15 nodes
+//=======================================================================
+
+SMDS_QuadraticVolumeOfNodes::SMDS_QuadraticVolumeOfNodes
+                                               (const SMDS_MeshNode * n1,
+                                                const SMDS_MeshNode * n2,
+                                                const SMDS_MeshNode * n3,
+                                                const SMDS_MeshNode * n4,
+                                                const SMDS_MeshNode * n5,
+                                                const SMDS_MeshNode * n6, 
+                                                const SMDS_MeshNode * n12,
+                                                const SMDS_MeshNode * n23,
+                                                const SMDS_MeshNode * n31, 
+                                                const SMDS_MeshNode * n45,
+                                                const SMDS_MeshNode * n56,
+                                                const SMDS_MeshNode * n64, 
+                                                const SMDS_MeshNode * n14,
+                                                const SMDS_MeshNode * n25,
+                                                const SMDS_MeshNode * n36)
+{
+  //MESSAGE("*********************************************** SMDS_QuadraticVolumeOfNodes");
+  myNodes.resize( 15 );
+  myNodes[ 0 ] = n1;
+  myNodes[ 1 ] = n2;
+  myNodes[ 2 ] = n3;
+  myNodes[ 3 ] = n4;
+  myNodes[ 4 ] = n5;
+  myNodes[ 5 ] = n6;
+  myNodes[ 6 ] = n12;
+  myNodes[ 7 ] = n23;
+  myNodes[ 8 ] = n31;
+  myNodes[ 9 ] = n45;
+  myNodes[ 10 ] = n56;
+  myNodes[ 11 ] = n64;
+  myNodes[ 12 ] = n14;
+  myNodes[ 13 ] = n25;
+  myNodes[ 14 ] = n36;
+}
+
+
+//=======================================================================
+//function : SMDS_QuadraticVolumeOfNodes()
+//purpose  : Constructor Hexahedrons with 20 nodes
+//=======================================================================
+
+SMDS_QuadraticVolumeOfNodes::SMDS_QuadraticVolumeOfNodes
+                                               (const SMDS_MeshNode * n1,
+                                                const SMDS_MeshNode * n2,
+                                                const SMDS_MeshNode * n3,
+                                                const SMDS_MeshNode * n4,
+                                                const SMDS_MeshNode * n5,
+                                                const SMDS_MeshNode * n6,
+                                                const SMDS_MeshNode * n7,
+                                                const SMDS_MeshNode * n8, 
+                                                const SMDS_MeshNode * n12,
+                                                const SMDS_MeshNode * n23,
+                                                const SMDS_MeshNode * n34,
+                                                const SMDS_MeshNode * n41, 
+                                                const SMDS_MeshNode * n56,
+                                                const SMDS_MeshNode * n67,
+                                                const SMDS_MeshNode * n78,
+                                                const SMDS_MeshNode * n85, 
+                                                const SMDS_MeshNode * n15,
+                                                const SMDS_MeshNode * n26,
+                                                const SMDS_MeshNode * n37,
+                                                const SMDS_MeshNode * n48)
+{
+  //MESSAGE("*********************************************** SMDS_QuadraticVolumeOfNodes");
+  myNodes.resize( 20 );
+  myNodes[ 0 ] = n1;
+  myNodes[ 1 ] = n2;
+  myNodes[ 2 ] = n3;
+  myNodes[ 3 ] = n4;
+  myNodes[ 4 ] = n5;
+  myNodes[ 5 ] = n6;
+  myNodes[ 6 ] = n7;
+  myNodes[ 7 ] = n8;
+  myNodes[ 8 ] = n12;
+  myNodes[ 9 ] = n23;
+  myNodes[ 10 ] = n34;
+  myNodes[ 11 ] = n41;
+  myNodes[ 12 ] = n56;
+  myNodes[ 13 ] = n67;
+  myNodes[ 14 ] = n78;
+  myNodes[ 15 ] = n85;
+  myNodes[ 16 ] = n15;
+  myNodes[ 17 ] = n26;
+  myNodes[ 18 ] = n37;
+  myNodes[ 19 ] = n48;
+}
+
+
+//=======================================================================
+//function : IsMediumNode
+//purpose  : 
+//=======================================================================
+
+bool SMDS_QuadraticVolumeOfNodes::IsMediumNode(const SMDS_MeshNode* node) const
+{
+  int nbCorners = 0;
+  switch (myNodes.size()) {
+  case 10: nbCorners = 4; break;
+  case 13: nbCorners = 5; break;
+  case 15: nbCorners = 6; break;
+  default: nbCorners = 8;
+  }
+  for ( size_t i = nbCorners; i<myNodes.size(); i++) {
+    if(myNodes[i]==node) return true;
+  }
+  return false;
+}
+
+
+//=======================================================================
+//function : ChangeNodes
+//purpose  : 
+//=======================================================================
+
+bool SMDS_QuadraticVolumeOfNodes::ChangeNodes(const SMDS_MeshNode* nodes[],
+                                              const int            nbNodes)
+{
+  if( nbNodes==10 || nbNodes==13 || nbNodes==15 || nbNodes==20 ) {
+    myNodes.resize(nbNodes);
+    int i=0;
+    for(; i<nbNodes; i++) {
+      myNodes[i] = nodes[i];
+    }
+    return true;
+  }
+  return false;
+}
+
+
+//=======================================================================
+//function : NbNodes
+//purpose  : 
+//=======================================================================
+int SMDS_QuadraticVolumeOfNodes::NbNodes() const
+{
+  return myNodes.size();
+}
+
+
+//=======================================================================
+//function : NbEdges
+//purpose  : 
+//=======================================================================
+int SMDS_QuadraticVolumeOfNodes::NbEdges() const
+{
+  if(myNodes.size()==10)
+    return 6;
+  else if(myNodes.size()==13)
+    return 8;
+  else if(myNodes.size()==15)
+    return 9;
+  else
+    return 12;
+}
+
+
+//=======================================================================
+//function : NbFaces
+//purpose  : 
+//=======================================================================
+int SMDS_QuadraticVolumeOfNodes::NbFaces() const
+{
+  if(myNodes.size()==10)
+    return 4;
+  else if(myNodes.size()==20)
+    return 6;
+  else
+    return 5;
+}
+
+//=======================================================================
+//function : Print
+//purpose  : 
+//=======================================================================
+void SMDS_QuadraticVolumeOfNodes::Print(ostream & OS) const
+{
+  OS << "quadratic volume <" << GetID() << " > : ";
+  int i, nbNodes = myNodes.size();
+  for (i = 0; i < nbNodes - 1; i++)
+    OS << myNodes[i] << ",";
+  OS << myNodes[i] << ") " << endl;
+}
+
+
+//=======================================================================
+//private class : SMDS_QuadraticVolumeOfNodes_MyIterator
+//purpose  : 
+//=======================================================================
+
+class SMDS_QuadraticVolumeOfNodes_MyIterator : public SMDS_NodeVectorElemIterator
+{
+public:
+  SMDS_QuadraticVolumeOfNodes_MyIterator(const vector<const SMDS_MeshNode *>& s):
+    SMDS_NodeVectorElemIterator( s.begin(), s.end() ) {}
+};
+
+/// ===================================================================
+/*!
+ * \brief Iterator on faces or edges of volume
+ */
+/// ===================================================================
+
+class _MySubIterator : public SMDS_ElemIterator
+{
+  vector< const SMDS_MeshElement* > myElems;
+  size_t                            myIndex;
+public:
+  _MySubIterator(const SMDS_MeshVolume* vol, SMDSAbs_ElementType type):myIndex(0) {
+    SMDS_VolumeTool vTool(vol);
+    if (type == SMDSAbs_Face)
+      vTool.GetAllExistingFaces( myElems );
+    else
+      vTool.GetAllExistingFaces( myElems );
+  }
+  /// Return true if and only if there are other object in this iterator
+  virtual bool more() { return myIndex < myElems.size(); }
+
+  /// Return the current object and step to the next one
+  virtual const SMDS_MeshElement* next() { return myElems[ myIndex++ ]; }
+};
+
+//=======================================================================
+//function : elementsIterator
+//purpose  : 
+//=======================================================================
+
+SMDS_ElemIteratorPtr SMDS_QuadraticVolumeOfNodes::elementsIterator
+                                         (SMDSAbs_ElementType type) const
+{
+  switch(type)
+  {
+  case SMDSAbs_Volume:
+    return SMDS_MeshElement::elementsIterator(SMDSAbs_Volume);
+  case SMDSAbs_Node:
+    return SMDS_ElemIteratorPtr(new SMDS_QuadraticVolumeOfNodes_MyIterator(myNodes));
+  case SMDSAbs_Edge:
+    return SMDS_ElemIteratorPtr(new _MySubIterator(this,SMDSAbs_Edge));
+    break;
+  case SMDSAbs_Face:
+    return SMDS_ElemIteratorPtr(new _MySubIterator(this,SMDSAbs_Face));
+    break;
+  default:
+    return SMDS_ElemIteratorPtr
+      (new SMDS_IteratorOfElements
+       (this,type,SMDS_ElemIteratorPtr
+        (new SMDS_QuadraticVolumeOfNodes_MyIterator(myNodes))));
+  }
+  return SMDS_ElemIteratorPtr();
+}
+
+/*!
+ * \brief Return node by its index
+ * \param ind - node index
+ * \retval const SMDS_MeshNode* - the node
+ */
+const SMDS_MeshNode* SMDS_QuadraticVolumeOfNodes::GetNode(const int ind) const
+{
+  return myNodes[ ind ];
+}
+
+SMDSAbs_EntityType SMDS_QuadraticVolumeOfNodes::GetEntityType() const
+{
+  SMDSAbs_EntityType aType = SMDSEntity_Quad_Tetra;
+  switch(NbNodes())
+  {
+  case 10: aType = SMDSEntity_Quad_Tetra;   break;
+  case 13: aType = SMDSEntity_Quad_Pyramid; break;
+  case 15: aType = SMDSEntity_Quad_Penta;   break;
+  case 18: aType = SMDSEntity_BiQuad_Penta; break;
+  case 20:
+  default: aType = SMDSEntity_Quad_Hexa;    break;
+  }
+  return aType;
+}
diff --git a/src/SMDS/SMDS_QuadraticVolumeOfNodes.hxx b/src/SMDS/SMDS_QuadraticVolumeOfNodes.hxx
new file mode 100644 (file)
index 0000000..0f3d6a8
--- /dev/null
@@ -0,0 +1,131 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//  File   : SMDS_QuadraticVolumeOfNodes.hxx
+//  Module : SMESH
+//
+#ifndef _SMDS_QuadraticVolumeOfNodes_HeaderFile
+#define _SMDS_QuadraticVolumeOfNodes_HeaderFile
+
+#include "SMESH_SMDS.hxx"
+
+#include "SMDS_MeshVolume.hxx"
+
+class SMDS_EXPORT SMDS_QuadraticVolumeOfNodes: public SMDS_MeshVolume
+{
+public:
+  // tetrahedron of 10 nodes
+  SMDS_QuadraticVolumeOfNodes (const SMDS_MeshNode * n1,
+                               const SMDS_MeshNode * n2,
+                               const SMDS_MeshNode * n3,
+                               const SMDS_MeshNode * n4,
+                               const SMDS_MeshNode * n12,
+                               const SMDS_MeshNode * n23,
+                               const SMDS_MeshNode * n31,
+                               const SMDS_MeshNode * n14, 
+                               const SMDS_MeshNode * n24,
+                               const SMDS_MeshNode * n34);
+
+  // pyramid of 13 nodes
+  SMDS_QuadraticVolumeOfNodes(const SMDS_MeshNode * n1,
+                              const SMDS_MeshNode * n2,
+                              const SMDS_MeshNode * n3,
+                              const SMDS_MeshNode * n4,
+                              const SMDS_MeshNode * n5,
+                              const SMDS_MeshNode * n12,
+                              const SMDS_MeshNode * n23,
+                              const SMDS_MeshNode * n34,
+                              const SMDS_MeshNode * n41, 
+                              const SMDS_MeshNode * n15,
+                              const SMDS_MeshNode * n25,
+                              const SMDS_MeshNode * n35,
+                              const SMDS_MeshNode * n45);
+
+  //  Pentahedron with 15 nodes
+  SMDS_QuadraticVolumeOfNodes(const SMDS_MeshNode * n1,
+                              const SMDS_MeshNode * n2,
+                              const SMDS_MeshNode * n3,
+                              const SMDS_MeshNode * n4,
+                              const SMDS_MeshNode * n5,
+                              const SMDS_MeshNode * n6, 
+                              const SMDS_MeshNode * n12,
+                              const SMDS_MeshNode * n23,
+                              const SMDS_MeshNode * n31, 
+                              const SMDS_MeshNode * n45,
+                              const SMDS_MeshNode * n56,
+                              const SMDS_MeshNode * n64, 
+                              const SMDS_MeshNode * n14,
+                              const SMDS_MeshNode * n25,
+                              const SMDS_MeshNode * n36);
+
+  // Hexahedrons with 20 nodes
+  SMDS_QuadraticVolumeOfNodes(const SMDS_MeshNode * n1,
+                              const SMDS_MeshNode * n2,
+                              const SMDS_MeshNode * n3,
+                              const SMDS_MeshNode * n4,
+                              const SMDS_MeshNode * n5,
+                              const SMDS_MeshNode * n6,
+                              const SMDS_MeshNode * n7,
+                              const SMDS_MeshNode * n8, 
+                              const SMDS_MeshNode * n12,
+                              const SMDS_MeshNode * n23,
+                              const SMDS_MeshNode * n34,
+                              const SMDS_MeshNode * n41, 
+                              const SMDS_MeshNode * n56,
+                              const SMDS_MeshNode * n67,
+                              const SMDS_MeshNode * n78,
+                              const SMDS_MeshNode * n85, 
+                              const SMDS_MeshNode * n15,
+                              const SMDS_MeshNode * n26,
+                              const SMDS_MeshNode * n37,
+                              const SMDS_MeshNode * n48);
+
+  virtual SMDSAbs_EntityType   GetEntityType() const;
+  virtual bool IsQuadratic() const { return true; }
+
+  virtual bool IsMediumNode(const SMDS_MeshNode* node) const;
+
+  bool ChangeNodes(const SMDS_MeshNode* nodes[],
+                   const int            nbNodes);
+
+  virtual int NbNodes() const;
+  virtual int NbEdges() const;
+  virtual int NbFaces() const;
+
+  virtual void Print (std::ostream & OS) const;
+
+  /*!
+   * \brief Return node by its index
+    * \param ind - node index
+    * \retval const SMDS_MeshNode* - the node
+   */
+  virtual const SMDS_MeshNode* GetNode(const int ind) const;
+
+ protected:
+  virtual SMDS_ElemIteratorPtr elementsIterator (SMDSAbs_ElementType type) const;
+
+ private:
+  std::vector<const SMDS_MeshNode *> myNodes;
+};
+
+#endif
index b7bcec930eae2a94cabc28e8eae7b46dd9cdcda6..b2b9a7f2ecb52ebe91886faf900b5bb54447f1d4 100644 (file)
 //
 
 #include "SMDS_SpacePosition.hxx"
-#include "SMDS_VertexPosition.hxx"
 
 SMDS_SpacePosition* SMDS_SpacePosition::_originPosition = new SMDS_SpacePosition();
 
-SMDS_PositionPtr SMDS_SpacePosition::originSpacePosition()
+SMDS_SpacePosition::SMDS_SpacePosition(double x, double y, double z)
 {
-  return SMDS_PositionPtr( _originPosition, /*isOwner=*/false );
 }
 
-SMDS_PositionPtr SMDS_VertexPosition::StaticPosition()
+SMDS_TypeOfPosition SMDS_SpacePosition::GetTypeOfPosition() const
 {
-  static SMDS_Position* _vertexPosition = new SMDS_VertexPosition;
-  return SMDS_PositionPtr( _vertexPosition, /*isOwner=*/false );
+  return SMDS_TOP_3DSPACE;
 }
 
+SMDS_PositionPtr SMDS_SpacePosition::originSpacePosition()
+{
+  return _originPosition;
+}
index 1bbac7b1f0818ebb597cbc45f43dbde22f01d8b3..fc2d22cc37f014204e60c178e8f29327ae9f8559 100644 (file)
 
 #include "SMDS_Position.hxx"
 
-class SMDS_EXPORT SMDS_SpacePosition : public SMDS_Position
+class SMDS_EXPORT SMDS_SpacePosition:public SMDS_Position
 {
- public:
 
-  virtual SMDS_TypeOfPosition GetTypeOfPosition() const { return SMDS_TOP_3DSPACE; }
-  static  SMDS_PositionPtr     originSpacePosition();
-  virtual const double* GetParameters() const { return 0; }
-
- private:
+public:
+  SMDS_SpacePosition(double x=0, double y=0, double z=0);
+  virtual inline SMDS_TypeOfPosition GetTypeOfPosition() const;
+  static SMDS_PositionPtr originSpacePosition();
+private:
   static SMDS_SpacePosition* _originPosition;
 };
 
index 03bff2d6662715edcf1582d0d7e457aa3ff7f7d3..bf9df36cffc1c1c80eb5fa3b3fde23e680f301a0 100644 (file)
@@ -36,6 +36,8 @@
 #include <list>
 #include <climits>
 
+using namespace std;
+
 SMDS_CellLinks* SMDS_CellLinks::New()
 {
   return new SMDS_CellLinks();
@@ -148,7 +150,7 @@ int SMDS_UnstructuredGrid::InsertNextLinkedCell(int type, int npts, vtkIdType *p
   // --- type = VTK_POLYHEDRON
   int cellid = this->InsertNextCell(type, npts, pts);
 
-  std::set<vtkIdType> setOfNodes;
+  set<vtkIdType> setOfNodes;
   setOfNodes.clear();
   int nbfaces = npts;
   int i = 0;
@@ -163,7 +165,7 @@ int SMDS_UnstructuredGrid::InsertNextLinkedCell(int type, int npts, vtkIdType *p
     }
   }
 
-  std::set<vtkIdType>::iterator it = setOfNodes.begin();
+  set<vtkIdType>::iterator it = setOfNodes.begin();
   for (; it != setOfNodes.end(); ++it)
   {
     this->Links->ResizeCellList(*it, 1);
@@ -179,24 +181,25 @@ void SMDS_UnstructuredGrid::setSMDS_mesh(SMDS_Mesh *mesh)
 }
 
 void SMDS_UnstructuredGrid::compactGrid(std::vector<int>& idNodesOldToNew, int newNodeSize,
-                                        std::vector<int>& idCellsNewToOld, int newCellSize)
+                                        std::vector<int>& idCellsOldToNew, int newCellSize)
 {
+  int alreadyCopied = 0;
+
   this->DeleteLinks();
 
-  // IDs of VTK nodes always correspond to SMDS IDs but there can be "holes" in SMDS numeration.
-  // We compact only if there were holes
+  // --- if newNodeSize, create a new compacted vtkPoints
 
-  int oldNodeSize = this->GetNumberOfPoints();
-  bool updateNodes = ( oldNodeSize > newNodeSize );
-  if ( true /*updateNodes*/ )
+  if ( newNodeSize )
   {
-    // 21125: EDF 1233 SMESH: Degradation of precision in a test case for quadratic conversion
-    // Use double type for storing coordinates of nodes instead float.
+    // rnv: to fix bug "21125: EDF 1233 SMESH: Degradation of precision in a test case for quadratic conversion"
+    // using double type for storing coordinates of nodes instead float.
     vtkPoints *newPoints = vtkPoints::New();
-    newPoints->SetDataType( VTK_DOUBLE );
-    newPoints->SetNumberOfPoints( newNodeSize );
+    newPoints->SetDataType(VTK_DOUBLE);
+    newPoints->SetNumberOfPoints(newNodeSize);
+
+    int oldNodeSize = idNodesOldToNew.size();
 
-    int i = 0, alreadyCopied = 0;
+    int i = 0;
     while ( i < oldNodeSize )
     {
       // skip a hole if any
@@ -212,20 +215,13 @@ void SMDS_UnstructuredGrid::compactGrid(std::vector<int>& idNodesOldToNew, int n
     this->SetPoints(newPoints);
     newPoints->Delete();
   }
-  else
-  {
-    this->Points->Squeeze();
-    this->Points->Modified();
-  }
+  this->Points->Squeeze();
 
-  // Compact cells if VTK IDs do not correspond to SMDS IDs or nodes compacted
+  // --- create new compacted Connectivity, Locations and Types
 
-  int  oldCellSize = this->Types->GetNumberOfTuples();
-  bool updateCells = ( updateNodes || newCellSize != oldCellSize );
-  for ( int newID = 0, nbIDs = idCellsNewToOld.size(); newID < nbIDs &&  !updateCells; ++newID )
-    updateCells = ( idCellsNewToOld[ newID ] != newID );
+  int oldCellSize = this->Types->GetNumberOfTuples();
 
-  if ( false /*!updateCells*/ ) // no holes in elements
+  if ( !newNodeSize && oldCellSize == newCellSize ) // no holes in elements
   {
     this->Connectivity->Squeeze();
     this->Locations->Squeeze();
@@ -235,28 +231,14 @@ void SMDS_UnstructuredGrid::compactGrid(std::vector<int>& idNodesOldToNew, int n
       this->FaceLocations->Squeeze();
       this->Faces->Squeeze();
     }
-    this->Connectivity->Modified();
+    for ( int i = 0; i < oldCellSize; ++i )
+      idCellsOldToNew[i] = i;
     return;
   }
-
-  if ((int) idNodesOldToNew.size() < oldNodeSize )
-  {
-    idNodesOldToNew.reserve( oldNodeSize );
-    for ( int i = idNodesOldToNew.size(); i < oldNodeSize; ++i )
-      idNodesOldToNew.push_back( i );
-  }
-
-  // --- create new compacted Connectivity, Locations and Types
-
-  int newConnectivitySize = this->Connectivity->GetNumberOfConnectivityEntries();
-  if ( newCellSize != oldCellSize )
-    for ( int i = 0; i < oldCellSize - 1; ++i )
-      if ( this->Types->GetValue( i ) == VTK_EMPTY_CELL )
-        newConnectivitySize -= this->Locations->GetValue( i+1 ) - this->Locations->GetValue( i );
-
   vtkCellArray *newConnectivity = vtkCellArray::New();
   newConnectivity->Initialize();
-  newConnectivity->Allocate( newConnectivitySize );
+  int oldCellDataSize = this->Connectivity->GetData()->GetSize();
+  newConnectivity->Allocate(oldCellDataSize);
 
   vtkUnsignedCharArray *newTypes = vtkUnsignedCharArray::New();
   newTypes->Initialize();
@@ -266,24 +248,41 @@ void SMDS_UnstructuredGrid::compactGrid(std::vector<int>& idNodesOldToNew, int n
   newLocations->Initialize();
   newLocations->SetNumberOfValues(newCellSize);
 
-  std::vector< vtkIdType > pointsCell(1024); // --- points id to fill a new cell
+  // TODO some polyhedron may be huge (only in some tests)
+  vtkIdType tmpid[NBMAXNODESINCELL];
+  vtkIdType *pointsCell = &tmpid[0]; // --- points id to fill a new cell
 
-  copyBloc(newTypes, idCellsNewToOld, idNodesOldToNew,
-           newConnectivity, newLocations, pointsCell );
+  alreadyCopied = 0;
+  int i = 0;
+  while ( i < oldCellSize )
+  {
+    // skip a hole if any
+    while ( i < oldCellSize && this->Types->GetValue(i) == VTK_EMPTY_CELL )
+      ++i;
+    int startBloc = i;
+    // look for a block end
+    while ( i < oldCellSize && this->Types->GetValue(i) != VTK_EMPTY_CELL )
+      ++i;
+    int endBloc = i;
+    if ( endBloc > startBloc )
+      copyBloc(newTypes,
+               idCellsOldToNew, idNodesOldToNew,
+               newConnectivity, newLocations,
+               pointsCell, alreadyCopied,
+               startBloc, endBloc);
+  }
+  newConnectivity->Squeeze();
 
   if (vtkDoubleArray* diameters =
       vtkDoubleArray::SafeDownCast( vtkDataSet::CellData->GetScalars() )) // Balls
   {
-    vtkDoubleArray* newDiameters = vtkDoubleArray::New();
-    newDiameters->SetNumberOfComponents(1);
-    for ( int newCellID = 0; newCellID < newCellSize; newCellID++ )
+    for (int oldCellID = 0; oldCellID < oldCellSize; oldCellID++)
     {
-      if ( newTypes->GetValue( newCellID ) == VTK_POLY_VERTEX )
-      {
-        int oldCellID = idCellsNewToOld[ newCellID ];
-        newDiameters->InsertValue( newCellID, diameters->GetValue( oldCellID ));
-      }
-      vtkDataSet::CellData->SetScalars( newDiameters );
+      if (this->Types->GetValue(oldCellID) == VTK_EMPTY_CELL)
+        continue;
+      int newCellId = idCellsOldToNew[ oldCellID ];
+      if (newTypes->GetValue(newCellId) == VTK_POLY_VERTEX)
+        diameters->SetValue( newCellId, diameters->GetValue( oldCellID ));
     }
   }
 
@@ -295,23 +294,25 @@ void SMDS_UnstructuredGrid::compactGrid(std::vector<int>& idNodesOldToNew, int n
     vtkIdTypeArray *newFaces = vtkIdTypeArray::New();
     newFaces->Initialize();
     newFaces->Allocate(this->Faces->GetSize());
-    for ( int newCellID = 0; newCellID < newCellSize; newCellID++ )
+    for (int i = 0; i < oldCellSize; i++)
     {
-      if ( newTypes->GetValue( newCellID ) == VTK_POLYHEDRON )
+      if (this->Types->GetValue(i) == VTK_EMPTY_CELL)
+        continue;
+      int newCellId = idCellsOldToNew[i];
+      if (newTypes->GetValue(newCellId) == VTK_POLYHEDRON)
       {
-        int oldCellId = idCellsNewToOld[ newCellID ];
-        newFaceLocations->InsertNextValue( newFaces->GetMaxId()+1 );
-        int oldFaceLoc = this->FaceLocations->GetValue( oldCellId );
-        int nCellFaces = this->Faces->GetValue( oldFaceLoc++ );
-        newFaces->InsertNextValue( nCellFaces );
-        for ( int n = 0; n < nCellFaces; n++ )
+        newFaceLocations->InsertNextValue(newFaces->GetMaxId()+1);
+        int oldFaceLoc = this->FaceLocations->GetValue(i);
+        int nCellFaces = this->Faces->GetValue(oldFaceLoc++);
+        newFaces->InsertNextValue(nCellFaces);
+        for (int n=0; n<nCellFaces; n++)
         {
-          int nptsInFace = this->Faces->GetValue( oldFaceLoc++ );
-          newFaces->InsertNextValue( nptsInFace );
-          for ( int k = 0; k < nptsInFace; k++ )
+          int nptsInFace = this->Faces->GetValue(oldFaceLoc++);
+          newFaces->InsertNextValue(nptsInFace);
+          for (int k=0; k<nptsInFace; k++)
           {
-            int oldpt = this->Faces->GetValue( oldFaceLoc++ );
-            newFaces->InsertNextValue( idNodesOldToNew[ oldpt ]);
+            int oldpt = this->Faces->GetValue(oldFaceLoc++);
+            newFaces->InsertNextValue(idNodesOldToNew[oldpt]);
           }
         }
       }
@@ -322,13 +323,13 @@ void SMDS_UnstructuredGrid::compactGrid(std::vector<int>& idNodesOldToNew, int n
     }
     newFaceLocations->Squeeze();
     newFaces->Squeeze();
-    this->SetCells( newTypes, newLocations, newConnectivity, newFaceLocations, newFaces );
+    this->SetCells(newTypes, newLocations, newConnectivity, newFaceLocations, newFaces);
     newFaceLocations->Delete();
     newFaces->Delete();
   }
   else
   {
-    this->SetCells( newTypes, newLocations, newConnectivity, FaceLocations, Faces );
+    this->SetCells(newTypes, newLocations, newConnectivity, FaceLocations, Faces);
   }
 
   newTypes->Delete();
@@ -348,35 +349,39 @@ void SMDS_UnstructuredGrid::copyNodes(vtkPoints *       newPoints,
   if (nbPoints > 0)
   {
     memcpy(target, source, 3 * sizeof(double) * nbPoints);
-    alreadyCopied += nbPoints;
+    for (int j = start; j < end; j++)
+      idNodesOldToNew[j] = alreadyCopied++; // old vtkId --> new vtkId
   }
 }
 
-void SMDS_UnstructuredGrid::copyBloc(vtkUnsignedCharArray *  newTypes,
-                                     const std::vector<int>& idCellsNewToOld,
-                                     const std::vector<int>& idNodesOldToNew,
-                                     vtkCellArray*           newConnectivity,
-                                     vtkIdTypeArray*         newLocations,
-                                     std::vector<vtkIdType>& pointsCell)
+void SMDS_UnstructuredGrid::copyBloc(vtkUnsignedCharArray *newTypes,
+                                     std::vector<int>&     idCellsOldToNew,
+                                     std::vector<int>&     idNodesOldToNew,
+                                     vtkCellArray*         newConnectivity,
+                                     vtkIdTypeArray*       newLocations,
+                                     vtkIdType*            pointsCell,
+                                     int&                  alreadyCopied,
+                                     int                   start,
+                                     int                   end)
 {
-  for ( size_t iNew = 0; iNew < idCellsNewToOld.size(); iNew++ )
+  for (int j = start; j < end; j++)
   {
-    int iOld = idCellsNewToOld[ iNew ];
-    newTypes->SetValue( iNew, this->Types->GetValue( iOld ));
-    vtkIdType oldLoc = this->Locations->GetValue( iOld );
+    newTypes->SetValue(alreadyCopied, this->Types->GetValue(j));
+    idCellsOldToNew[j] = alreadyCopied; // old vtkId --> new vtkId
+    vtkIdType oldLoc = this->Locations->GetValue(j);
     vtkIdType nbpts;
     vtkIdType *oldPtsCell = 0;
-    this->Connectivity->GetCell( oldLoc, nbpts, oldPtsCell );
-    if ((vtkIdType) pointsCell.size() < nbpts )
-      pointsCell.resize( nbpts );
-    for ( int l = 0; l < nbpts; l++ )
+    this->Connectivity->GetCell(oldLoc, nbpts, oldPtsCell);
+    assert(nbpts < NBMAXNODESINCELL);
+    for (int l = 0; l < nbpts; l++)
     {
       int oldval = oldPtsCell[l];
       pointsCell[l] = idNodesOldToNew[oldval];
     }
-    /*int newcnt = */newConnectivity->InsertNextCell( nbpts, pointsCell.data() );
-    int newLoc = newConnectivity->GetInsertLocation( nbpts );
-    newLocations->SetValue( iNew, newLoc );
+    /*int newcnt = */newConnectivity->InsertNextCell(nbpts, pointsCell);
+    int newLoc = newConnectivity->GetInsertLocation(nbpts);
+    newLocations->SetValue(alreadyCopied, newLoc);
+    alreadyCopied++;
   }
 }
 
@@ -651,7 +656,7 @@ void SMDS_UnstructuredGrid::BuildDownwardConnectivity(bool withEdges)
           int connEdgeId = _downArray[vtkEdgeType]->addCell(vtkEdgeId);
           SMDS_Down1D* downEdge = static_cast<SMDS_Down1D*> (_downArray[vtkEdgeType]);
           downEdge->setNodes(connEdgeId, vtkEdgeId);
-          std::vector<int> vtkIds;
+          vector<int> vtkIds;
           int nbVtkCells = downEdge->computeVtkCells(connEdgeId, vtkIds);
           int downFaces[1000];
           unsigned char downTypes[1000];
@@ -700,7 +705,7 @@ void SMDS_UnstructuredGrid::BuildDownwardConnectivity(bool withEdges)
               // --- check if the edge is already registered by exploration of the faces
 
               //CHRONO(41);
-              std::vector<int> vtkIds;
+              vector<int> vtkIds;
               unsigned char vtkEdgeType = edgesWithNodes.elems[iedge].vtkType;
               int *pts = &edgesWithNodes.elems[iedge].nodeIds[0];
               SMDS_Down1D* downEdge = static_cast<SMDS_Down1D*> (_downArray[vtkEdgeType]);
@@ -754,7 +759,7 @@ void SMDS_UnstructuredGrid::BuildDownwardConnectivity(bool withEdges)
 
   CHRONOSTOP(23);CHRONO(24);
 
-  // compact downward connectivity structure: adjust downward arrays size, replace std::vector<vector int>> by a single std::vector<int>
+  // compact downward connectivity structure: adjust downward arrays size, replace vector<vector int>> by a single vector<int>
   // 3D first then 2D and last 1D to release memory before edge upCells reorganization, (temporary memory use)
 
   for (int vtkType = VTK_QUADRATIC_PYRAMID; vtkType >= 0; vtkType--)
@@ -1068,11 +1073,15 @@ SMDS_UnstructuredGrid::extrudeVolumeFromFace(int vtkVolId,
                                              std::map<int, std::map<long, int> >& nodeQuadDomains)
 {
   //MESSAGE("extrudeVolumeFromFace " << vtkVolId);
-  std::vector<vtkIdType> orderedOriginals( originalNodes.begin(), originalNodes.end() );
+  vector<vtkIdType> orderedOriginals;
+  orderedOriginals.clear();
+  set<int>::const_iterator it = originalNodes.begin();
+  for (; it != originalNodes.end(); ++it)
+    orderedOriginals.push_back(*it);
 
   int dim = 0;
   int nbNodes = this->getOrderedNodesOfFace(vtkVolId, dim, orderedOriginals);
-  std::vector<vtkIdType> orderedNodes;
+  vector<vtkIdType> orderedNodes;
 
   bool isQuadratic = false;
   switch (orderedOriginals.size())
@@ -1121,7 +1130,7 @@ SMDS_UnstructuredGrid::extrudeVolumeFromFace(int vtkVolId,
             {
               double *coords = this->GetPoint(oldId);
               SMDS_MeshNode *newNode = _mesh->AddNode(coords[0], coords[1], coords[2]);
-              newId = newNode->GetVtkID();
+              newId = newNode->getVtkId();
               if (! nodeQuadDomains.count(oldId))
                 {
                   std::map<long, int> emptyMap;
index 448fed72d6e1e5aa69417c8aa43e68b46a11e668..5936e9759d70ad06f890330e8c93c2cf5be0a93f 100644 (file)
@@ -116,12 +116,9 @@ protected:
   SMDS_UnstructuredGrid();
   ~SMDS_UnstructuredGrid();
   void copyNodes(vtkPoints *newPoints, std::vector<int>& idNodesOldToNew, int& alreadyCopied, int start, int end);
-  void copyBloc(vtkUnsignedCharArray *newTypes,
-                const std::vector<int>& idCellsOldToNew,
-                const std::vector<int>& idNodesOldToNew,
-                vtkCellArray* newConnectivity,
-                vtkIdTypeArray* newLocations,
-                std::vector<vtkIdType>& pointsCell);
+  void copyBloc(vtkUnsignedCharArray *newTypes, std::vector<int>& idCellsOldToNew, std::vector<int>& idNodesOldToNew,
+                vtkCellArray* newConnectivity, vtkIdTypeArray* newLocations, vtkIdType* pointsCell, int& alreadyCopied,
+                int start, int end);
 
   std::vector<int> _cellIdToDownId; //!< convert vtk Id to downward[vtkType] id, initialized with -1
   std::vector<unsigned char> _downTypes;
diff --git a/src/SMDS/SMDS_VertexPosition.cxx b/src/SMDS/SMDS_VertexPosition.cxx
new file mode 100644 (file)
index 0000000..0e2d183
--- /dev/null
@@ -0,0 +1,48 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//  File   : SMDS_VertexPosition.cxx
+//  Author : Jean-Michel BOULCOURT
+//  Module : SMESH
+//
+#include "SMDS_VertexPosition.hxx"
+
+#include "utilities.h"
+
+using namespace std;
+
+//=======================================================================
+//function : SMDS_VertexPosition
+//purpose  : 
+//=======================================================================
+
+SMDS_VertexPosition:: SMDS_VertexPosition()
+{
+  //MESSAGE("*********************************************** SMDS_VertexPosition " << aVertexId);
+}
+
+SMDS_TypeOfPosition SMDS_VertexPosition::GetTypeOfPosition() const
+{
+  //MESSAGE("################################################# GetTypeOfPosition");
+        return SMDS_TOP_VERTEX;
+}
index 4db67d527abbfa8a1b91ca4a3cbb054da4749fc6..0943de91cfa832eab322b0144627fb378195c844 100644 (file)
 
 #include "SMDS_Position.hxx"
 
-class SMDS_EXPORT SMDS_VertexPosition : public SMDS_Position
+class SMDS_EXPORT SMDS_VertexPosition:public SMDS_Position
 {
- public:
-  SMDS_TypeOfPosition GetTypeOfPosition() const { return SMDS_TOP_VERTEX; }
-  virtual const double* GetParameters() const { return 0; }
-  static SMDS_PositionPtr StaticPosition(); 
+
+  public:       
+        SMDS_TypeOfPosition GetTypeOfPosition() const;
+        SMDS_VertexPosition();
 };
 
 #endif
diff --git a/src/SMDS/SMDS_VolumeOfFaces.cxx b/src/SMDS/SMDS_VolumeOfFaces.cxx
new file mode 100644 (file)
index 0000000..929c546
--- /dev/null
@@ -0,0 +1,169 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//  File   : SMDS_VolumeOfFaces.cxx
+//  Author : Jean-Michel BOULCOURT
+//  Module : SMESH
+//
+#ifdef _MSC_VER
+#pragma warning(disable:4786)
+#endif
+
+#include "SMDS_VolumeOfFaces.hxx"
+#include "SMDS_IteratorOfElements.hxx"
+#include "utilities.h"
+
+using namespace std;
+
+//=======================================================================
+//function : Print
+//purpose  : 
+//=======================================================================
+
+void SMDS_VolumeOfFaces::Print(ostream & OS) const
+{
+        OS << "volume <" << GetID() << "> : ";
+        int i;
+        for (i = 0; i < NbFaces()-1; ++i) OS << myFaces[i] << ",";
+        OS << myFaces[i]<< ") " << endl;
+}
+
+
+int SMDS_VolumeOfFaces::NbFaces() const
+{
+        return myNbFaces;
+}
+
+class SMDS_VolumeOfFaces_MyIterator:public SMDS_ElemIterator
+{
+  const SMDS_MeshFace* const *mySet;
+  int myLength;
+  int index;
+ public:
+  SMDS_VolumeOfFaces_MyIterator(const SMDS_MeshFace* const *s, int l):
+    mySet(s),myLength(l),index(0) {}
+
+  bool more()
+  {
+    return index<myLength;
+  }
+
+  const SMDS_MeshElement* next()
+  {
+    index++;
+    return mySet[index-1];
+  }
+};
+
+SMDS_ElemIteratorPtr SMDS_VolumeOfFaces::
+        elementsIterator(SMDSAbs_ElementType type) const
+{
+  switch(type)
+  {
+  case SMDSAbs_Volume:
+    return SMDS_MeshElement::elementsIterator(SMDSAbs_Volume);
+  case SMDSAbs_Face:
+    return SMDS_ElemIteratorPtr(new SMDS_VolumeOfFaces_MyIterator(myFaces,myNbFaces));
+  default:
+    return SMDS_ElemIteratorPtr
+      (new SMDS_IteratorOfElements
+       (this,type,SMDS_ElemIteratorPtr
+        (new SMDS_VolumeOfFaces_MyIterator(myFaces,myNbFaces))));
+  }
+}
+
+SMDS_VolumeOfFaces::SMDS_VolumeOfFaces(const SMDS_MeshFace * face1,
+                                       const SMDS_MeshFace * face2,
+                                       const SMDS_MeshFace * face3,
+                                       const SMDS_MeshFace * face4)
+{
+  //MESSAGE("****************************************************** SMDS_VolumeOfFaces");
+        myNbFaces = 4;
+        myFaces[0]=face1;
+        myFaces[1]=face2;
+        myFaces[2]=face3;
+        myFaces[3]=face4;
+        myFaces[4]=0;
+        myFaces[5]=0;
+}
+
+SMDS_VolumeOfFaces::SMDS_VolumeOfFaces(const SMDS_MeshFace * face1,
+                                       const SMDS_MeshFace * face2,
+                                       const SMDS_MeshFace * face3,
+                                       const SMDS_MeshFace * face4,
+                                       const SMDS_MeshFace * face5)
+{
+  //MESSAGE("****************************************************** SMDS_VolumeOfFaces");
+        myNbFaces = 5;
+        myFaces[0]=face1;
+        myFaces[1]=face2;
+        myFaces[2]=face3;
+        myFaces[3]=face4;
+        myFaces[4]=face5;
+        myFaces[5]=0;
+}
+
+SMDS_VolumeOfFaces::SMDS_VolumeOfFaces(const SMDS_MeshFace * face1,
+                                       const SMDS_MeshFace * face2,
+                                       const SMDS_MeshFace * face3,
+                                       const SMDS_MeshFace * face4,
+                                       const SMDS_MeshFace * face5,
+                                       const SMDS_MeshFace * face6)
+{
+  //MESSAGE("****************************************************** SMDS_VolumeOfFaces");
+        myNbFaces = 6;
+        myFaces[0]=face1;
+        myFaces[1]=face2;
+        myFaces[2]=face3;
+        myFaces[3]=face4;
+        myFaces[4]=face5;
+        myFaces[5]=face6;
+}
+
+SMDSAbs_EntityType SMDS_VolumeOfFaces::GetEntityType() const
+{
+  SMDSAbs_EntityType aType = SMDSEntity_Tetra;
+  switch(myNbFaces)
+  {
+  case 4: aType = SMDSEntity_Tetra;   break;
+  case 5: aType = SMDSEntity_Pyramid; break;
+  case 6: aType = SMDSEntity_Penta;   break;
+  case 8:
+  default: aType = SMDSEntity_Hexa;    break;
+  }
+  return aType;
+}
+
+SMDSAbs_GeometryType SMDS_VolumeOfFaces::GetGeomType() const
+{
+  SMDSAbs_GeometryType aType = SMDSGeom_NONE;
+  switch(myNbFaces)
+  {
+  case 4: aType = SMDSGeom_TETRA;   break;
+  case 5: aType = SMDSGeom_PYRAMID; break;
+  case 6: aType = SMDSGeom_PENTA;   break;
+  case 8:
+  default: aType = SMDSGeom_HEXA;   break;
+  }
+  return aType;
+}
diff --git a/src/SMDS/SMDS_VolumeOfFaces.hxx b/src/SMDS/SMDS_VolumeOfFaces.hxx
new file mode 100644 (file)
index 0000000..103b919
--- /dev/null
@@ -0,0 +1,71 @@
+// Copyright (C) 2007-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//  File   : SMDS_VolumeOfFaces.hxx
+//  Module : SMESH
+//
+#ifndef _SMDS_VolumeOfFaces_HeaderFile
+#define _SMDS_VolumeOfFaces_HeaderFile
+
+#include "SMESH_SMDS.hxx"
+
+#include "SMDS_MeshVolume.hxx"
+#include "SMDS_MeshFace.hxx"
+#include "SMDS_Iterator.hxx"
+#include <iostream>
+
+
+class SMDS_EXPORT SMDS_VolumeOfFaces:public SMDS_MeshVolume
+{
+        
+  public:
+        SMDS_VolumeOfFaces(const SMDS_MeshFace * face1,
+                           const SMDS_MeshFace * face2,
+                           const SMDS_MeshFace * face3,
+                           const SMDS_MeshFace * face4);
+        SMDS_VolumeOfFaces(const SMDS_MeshFace * face1,
+                           const SMDS_MeshFace * face2,
+                           const SMDS_MeshFace * face3,
+                           const SMDS_MeshFace * face4,
+                           const SMDS_MeshFace * face5);
+        SMDS_VolumeOfFaces(const SMDS_MeshFace * face1,
+                           const SMDS_MeshFace * face2,
+                           const SMDS_MeshFace * face3,
+                           const SMDS_MeshFace * face4,
+                           const SMDS_MeshFace * face5,
+                           const SMDS_MeshFace * face6);
+
+        virtual SMDSAbs_EntityType GetEntityType() const;
+        virtual SMDSAbs_GeometryType GetGeomType() const;
+        virtual bool ChangeNodes(const SMDS_MeshNode* nodes[],
+                                 const int            nbNodes) {return false;}
+        virtual void Print(std::ostream & OS) const;
+
+        virtual int NbFaces() const;
+
+  protected:
+        virtual SMDS_ElemIteratorPtr elementsIterator(SMDSAbs_ElementType type) const;
+        const SMDS_MeshFace * myFaces[6];
+        int                   myNbFaces;
+};
+#endif
index f652eeaf26ec57ab13a80b1bb1650a9ef11928da..3f76d5322040d2583d5635969472977b8176ef0e 100644 (file)
 #endif
 
 #include "SMDS_VolumeOfNodes.hxx"
-
 #include "SMDS_MeshNode.hxx"
 #include "SMDS_SetIterator.hxx"
+#include "SMDS_VolumeTool.hxx"
+#include "SMDS_Mesh.hxx"
+#include "utilities.h"
 
-#include <boost/make_shared.hpp>
-
-#include <utilities.h>
+using namespace std;
 
 ///////////////////////////////////////////////////////////////////////////////
 /// Create an hexahedron. node 1,2,3,4 and 5,6,7,8 are quadrangle and
 /// 5,1 and 7,3 are an edges.
 ///////////////////////////////////////////////////////////////////////////////
-SMDS_VolumeOfNodes::SMDS_VolumeOfNodes(const SMDS_MeshNode * node1,
-                                       const SMDS_MeshNode * node2,
-                                       const SMDS_MeshNode * node3,
-                                       const SMDS_MeshNode * node4,
-                                       const SMDS_MeshNode * node5,
-                                       const SMDS_MeshNode * node6,
-                                       const SMDS_MeshNode * node7,
-                                       const SMDS_MeshNode * node8)
-{
-  myNbNodes = 8;
-  myNodes = new const SMDS_MeshNode* [myNbNodes];
-  myNodes[0]=node1;
-  myNodes[1]=node2;
-  myNodes[2]=node3;
-  myNodes[3]=node4;
-  myNodes[4]=node5;
-  myNodes[5]=node6;
-  myNodes[6]=node7;
-  myNodes[7]=node8;
+SMDS_VolumeOfNodes::SMDS_VolumeOfNodes(
+                const SMDS_MeshNode * node1,
+                const SMDS_MeshNode * node2,
+                const SMDS_MeshNode * node3,
+                const SMDS_MeshNode * node4,
+                const SMDS_MeshNode * node5,
+                const SMDS_MeshNode * node6,
+                const SMDS_MeshNode * node7,
+                const SMDS_MeshNode * node8)
+{
+  //MESSAGE("***************************************************** SMDS_VolumeOfNodes");
+        myNbNodes = 8;
+        myNodes = new const SMDS_MeshNode* [myNbNodes];
+        myNodes[0]=node1;
+        myNodes[1]=node2;
+        myNodes[2]=node3;
+        myNodes[3]=node4;
+        myNodes[4]=node5;
+        myNodes[5]=node6;
+        myNodes[6]=node7;
+        myNodes[7]=node8;
 }
 
-SMDS_VolumeOfNodes::SMDS_VolumeOfNodes(const SMDS_MeshNode * node1,
-                                       const SMDS_MeshNode * node2,
-                                       const SMDS_MeshNode * node3,
-                                       const SMDS_MeshNode * node4)
+SMDS_VolumeOfNodes::SMDS_VolumeOfNodes(
+                const SMDS_MeshNode * node1,
+                const SMDS_MeshNode * node2,
+                const SMDS_MeshNode * node3,
+                const SMDS_MeshNode * node4)
 {
-  myNbNodes = 4;
-  myNodes = new const SMDS_MeshNode* [myNbNodes];
-  myNodes[0]=node1;
-  myNodes[1]=node2;
-  myNodes[2]=node3;
-  myNodes[3]=node4;
+  //MESSAGE("***************************************************** SMDS_VolumeOfNodes");
+        myNbNodes = 4;
+        myNodes = new const SMDS_MeshNode* [myNbNodes];
+        myNodes[0]=node1;
+        myNodes[1]=node2;
+        myNodes[2]=node3;
+        myNodes[3]=node4;
 }
 
-SMDS_VolumeOfNodes::SMDS_VolumeOfNodes(const SMDS_MeshNode * node1,
-                                       const SMDS_MeshNode * node2,
-                                       const SMDS_MeshNode * node3,
-                                       const SMDS_MeshNode * node4,
-                                       const SMDS_MeshNode * node5)
+SMDS_VolumeOfNodes::SMDS_VolumeOfNodes(
+                const SMDS_MeshNode * node1,
+                const SMDS_MeshNode * node2,
+                const SMDS_MeshNode * node3,
+                const SMDS_MeshNode * node4,
+                const SMDS_MeshNode * node5)
 {
-  myNbNodes = 5;
-  myNodes = new const SMDS_MeshNode* [myNbNodes];
-  myNodes[0]=node1;
-  myNodes[1]=node2;
-  myNodes[2]=node3;
-  myNodes[3]=node4;
-  myNodes[4]=node5;
+  //MESSAGE("***************************************************** SMDS_VolumeOfNodes");
+        myNbNodes = 5;
+        myNodes = new const SMDS_MeshNode* [myNbNodes];
+        myNodes[0]=node1;
+        myNodes[1]=node2;
+        myNodes[2]=node3;
+        myNodes[3]=node4;
+        myNodes[4]=node5;
 }
 
-SMDS_VolumeOfNodes::SMDS_VolumeOfNodes(const SMDS_MeshNode * node1,
-                                       const SMDS_MeshNode * node2,
-                                       const SMDS_MeshNode * node3,
-                                       const SMDS_MeshNode * node4,
-                                       const SMDS_MeshNode * node5,
-                                       const SMDS_MeshNode * node6)
+SMDS_VolumeOfNodes::SMDS_VolumeOfNodes(
+                const SMDS_MeshNode * node1,
+                const SMDS_MeshNode * node2,
+                const SMDS_MeshNode * node3,
+                const SMDS_MeshNode * node4,
+                const SMDS_MeshNode * node5,
+                const SMDS_MeshNode * node6)
 {
-  myNbNodes = 6;
-  myNodes = new const SMDS_MeshNode* [myNbNodes];
-  myNodes[0]=node1;
-  myNodes[1]=node2;
-  myNodes[2]=node3;
-  myNodes[3]=node4;
-  myNodes[4]=node5;
-  myNodes[5]=node6;
+  //MESSAGE("***************************************************** SMDS_VolumeOfNodes");
+        myNbNodes = 6;
+        myNodes = new const SMDS_MeshNode* [myNbNodes];
+        myNodes[0]=node1;
+        myNodes[1]=node2;
+        myNodes[2]=node3;
+        myNodes[3]=node4;
+        myNodes[4]=node5;
+        myNodes[5]=node6;
 }
 
 bool SMDS_VolumeOfNodes::ChangeNodes(const SMDS_MeshNode* nodes[],
@@ -128,49 +136,98 @@ SMDS_VolumeOfNodes::~SMDS_VolumeOfNodes()
   }
 }
 
-void SMDS_VolumeOfNodes::Print(std::ostream & OS) const
+void SMDS_VolumeOfNodes::Print(ostream & OS) const
 {
-  OS << "volume <" << GetID() << "> : ";
-  int i;
-  for (i = 0; i < NbNodes()-1; ++i) OS << myNodes[i] << ",";
-  OS << myNodes[NbNodes()-1]<< ") " << std::endl;
+        OS << "volume <" << GetID() << "> : ";
+        int i;
+        for (i = 0; i < NbNodes()-1; ++i) OS << myNodes[i] << ",";
+        OS << myNodes[NbNodes()-1]<< ") " << endl;
 }
 
 int SMDS_VolumeOfNodes::NbFaces() const
 {
-  switch(NbNodes())
-  {
-  case 4: return 4;
-  case 5: return 5;
-  case 6: return 5;
-  case 8: return 6;
-  default: MESSAGE("invalid number of nodes");
-  }
-  return 0;
+        switch(NbNodes())
+        {
+        case 4: return 4;
+        case 5: return 5;
+        case 6: return 5;
+        case 8: return 6;
+        default: MESSAGE("invalid number of nodes");
+        }
+        return 0;
 }
 
 int SMDS_VolumeOfNodes::NbNodes() const
 {
-  return myNbNodes;
+        return myNbNodes;
 }
 
 int SMDS_VolumeOfNodes::NbEdges() const
 {
-  switch(NbNodes())
+        switch(NbNodes())
+        {
+        case 4: return 6;
+        case 5: return 8;
+        case 6: return 9;
+        case 8: return 12;
+        default: MESSAGE("invalid number of nodes");
+        }
+        return 0;
+}
+
+/*!
+ * \brief Iterator on node of volume
+ */
+class SMDS_VolumeOfNodes_MyIterator:public SMDS_NodeArrayElemIterator
+{
+ public:
+  SMDS_VolumeOfNodes_MyIterator(const SMDS_MeshNode* const* s, int l):
+    SMDS_NodeArrayElemIterator( s, & s[ l ]) {}
+};
+
+/*!
+ * \brief Iterator on faces or edges of volume
+ */
+class _MySubIterator : public SMDS_ElemIterator
+{
+  vector< const SMDS_MeshElement* > myElems;
+  size_t myIndex;
+public:
+  _MySubIterator(const SMDS_VolumeOfNodes* vol, SMDSAbs_ElementType type):myIndex(0) {
+    SMDS_VolumeTool vTool(vol);
+    if (type == SMDSAbs_Face)
+      vTool.GetAllExistingFaces( myElems );
+    else
+      vTool.GetAllExistingFaces( myElems );
+  }
+  /// Return true if and only if there are other object in this iterator
+  virtual bool more() { return myIndex < myElems.size(); }
+
+  /// Return the current object and step to the next one
+  virtual const SMDS_MeshElement* next() { return myElems[ myIndex++ ]; }
+};
+
+SMDS_ElemIteratorPtr SMDS_VolumeOfNodes::elementsIterator(SMDSAbs_ElementType type) const
+{
+  switch(type)
   {
-  case 4: return 6;
-  case 5: return 8;
-  case 6: return 9;
-  case 8: return 12;
-  default: MESSAGE("invalid number of nodes");
+  case SMDSAbs_Volume:
+    return SMDS_MeshElement::elementsIterator(SMDSAbs_Volume);
+  case SMDSAbs_Node:
+    return SMDS_ElemIteratorPtr(new SMDS_VolumeOfNodes_MyIterator(myNodes,myNbNodes));
+  case SMDSAbs_Face:
+    return SMDS_ElemIteratorPtr(new _MySubIterator(this,SMDSAbs_Face));
+  case SMDSAbs_Edge:
+    return SMDS_ElemIteratorPtr(new _MySubIterator(this,SMDSAbs_Edge));
+  default:
+    MESSAGE("ERROR : Iterator not implemented");
+    return SMDS_ElemIteratorPtr((SMDS_ElemIterator*)NULL);
   }
-  return 0;
 }
 
-
 SMDSAbs_ElementType SMDS_VolumeOfNodes::GetType() const
 {
-  return SMDSAbs_Volume;
+        return SMDSAbs_Volume;
 }
 
 /*!
@@ -212,20 +269,3 @@ SMDSAbs_GeometryType SMDS_VolumeOfNodes::GetGeomType() const
   return aType;
 }
 
-int  SMDS_VolumeOfNodes::GetNodeIndex( const SMDS_MeshNode* node ) const
-{
-  for ( int i = 0; i < myNbNodes; ++i )
-    if ( myNodes[i] == node )
-      return i;
-  return -1;
-}
-
-SMDS_ElemIteratorPtr SMDS_VolumeOfNodes::nodesIterator() const
-{
-  return boost::make_shared< SMDS_NodeArrayElemIterator >( &myNodes[0], &myNodes[0] + NbNodes() );
-}
-
-SMDS_NodeIteratorPtr SMDS_VolumeOfNodes::nodeIterator() const
-{
-  return boost::make_shared< SMDS_NodeArrayIterator >( &myNodes[0], &myNodes[0] + NbNodes() );
-}
index 15f0058c69752fa07d4a22c36b9cdb0967ae4c3f..485ea7eda7de15732fa802d7a7a9fe0122c21d0b 100644 (file)
 
 #include "SMESH_SMDS.hxx"
 
-#include "SMDS_CellOfNodes.hxx"
+#include "SMDS_MeshVolume.hxx"
 
-class SMDS_EXPORT SMDS_VolumeOfNodes: public SMDS_CellOfNodes
+class SMDS_EXPORT SMDS_VolumeOfNodes:public SMDS_MeshVolume
 {
         
- public:
-  SMDS_VolumeOfNodes(const SMDS_MeshNode * node1,
-                     const SMDS_MeshNode * node2,
-                     const SMDS_MeshNode * node3,
-                     const SMDS_MeshNode * node4);
-  SMDS_VolumeOfNodes(const SMDS_MeshNode * node1,
-                     const SMDS_MeshNode * node2,
-                     const SMDS_MeshNode * node3,
-                     const SMDS_MeshNode * node4,
-                     const SMDS_MeshNode * node5);
-  SMDS_VolumeOfNodes(const SMDS_MeshNode * node1,
-                     const SMDS_MeshNode * node2,
-                     const SMDS_MeshNode * node3,
-                     const SMDS_MeshNode * node4,
-                     const SMDS_MeshNode * node5,
-                     const SMDS_MeshNode * node6);
-  SMDS_VolumeOfNodes(const SMDS_MeshNode * node1,
-                     const SMDS_MeshNode * node2,
-                     const SMDS_MeshNode * node3,
-                     const SMDS_MeshNode * node4,
-                     const SMDS_MeshNode * node5,
-                     const SMDS_MeshNode * node6,
-                     const SMDS_MeshNode * node7,
-                     const SMDS_MeshNode * node8);
-  bool ChangeNodes(const SMDS_MeshNode* nodes[],
-                   const int            nbNodes);
-  ~SMDS_VolumeOfNodes();
+  public:
+        SMDS_VolumeOfNodes(
+                const SMDS_MeshNode * node1,
+                const SMDS_MeshNode * node2,
+                const SMDS_MeshNode * node3,
+                const SMDS_MeshNode * node4);
+        SMDS_VolumeOfNodes(
+                const SMDS_MeshNode * node1,
+                const SMDS_MeshNode * node2,
+                const SMDS_MeshNode * node3,
+                const SMDS_MeshNode * node4,
+                const SMDS_MeshNode * node5);
+        SMDS_VolumeOfNodes(
+                const SMDS_MeshNode * node1,
+                const SMDS_MeshNode * node2,
+                const SMDS_MeshNode * node3,
+                const SMDS_MeshNode * node4,
+                const SMDS_MeshNode * node5,
+                const SMDS_MeshNode * node6);
+        SMDS_VolumeOfNodes(
+                const SMDS_MeshNode * node1,
+                const SMDS_MeshNode * node2,
+                const SMDS_MeshNode * node3,
+                const SMDS_MeshNode * node4,
+                const SMDS_MeshNode * node5,
+                const SMDS_MeshNode * node6,
+                const SMDS_MeshNode * node7,
+                const SMDS_MeshNode * node8);
+        bool ChangeNodes(const SMDS_MeshNode* nodes[],
+                         const int            nbNodes);
+        ~SMDS_VolumeOfNodes();
 
-  void Print(std::ostream & OS) const;
-  int NbFaces() const;
-  int NbNodes() const;
-  int NbEdges() const;
-  virtual SMDSAbs_ElementType  GetType() const;    
-  virtual SMDSAbs_EntityType   GetEntityType() const;
-  virtual SMDSAbs_GeometryType GetGeomType() const;
+        void Print(std::ostream & OS) const;
+        int NbFaces() const;
+        int NbNodes() const;
+        int NbEdges() const;
+        virtual SMDSAbs_ElementType  GetType() const;    
+        virtual SMDSAbs_EntityType   GetEntityType() const;
+        virtual SMDSAbs_GeometryType GetGeomType() const;
 
-  virtual bool IsPoly() const { return false; }
-  virtual bool IsQuadratic() const { return false; }
   /*!
    * \brief Return node by its index
-   * \param ind - node index
-   * \retval const SMDS_MeshNode* - the node
+    * \param ind - node index
+    * \retval const SMDS_MeshNode* - the node
    */
   virtual const SMDS_MeshNode* GetNode(const int ind) const;
 
-  virtual int  NbCornerNodes() const { return NbNodes(); }
-  virtual int  GetNodeIndex( const SMDS_MeshNode* node ) const;
-
-  virtual SMDS_ElemIteratorPtr nodesIterator() const;
-  virtual SMDS_NodeIteratorPtr nodeIterator() const;
-
- protected:
-
-  const SMDS_MeshNode** myNodes;
-  int                   myNbNodes;
+  protected:
+        SMDS_ElemIteratorPtr
+                elementsIterator(SMDSAbs_ElementType type) const;
+        const SMDS_MeshNode** myNodes;
+        int                   myNbNodes;
 
 };
 
index 6de1ac68e4efc8fed87c1b479ba58b5e261ec452..9e144a620aaae174eef73eaa48e66d836edb02bd 100644 (file)
 
 #include "SMDS_MeshElement.hxx"
 #include "SMDS_MeshNode.hxx"
+#include "SMDS_VtkVolume.hxx"
 #include "SMDS_Mesh.hxx"
 
-#include <utilities.h>
+#include "utilities.h"
 
 #include <map>
 #include <limits>
@@ -42,6 +43,8 @@
 #include <numeric>
 #include <algorithm>
 
+using namespace std;
+
 namespace
 {
 // ======================================================
@@ -503,7 +506,7 @@ bool SMDS_VolumeTool::Set (const SMDS_MeshElement*                  theVolume,
   myNbFaces = theVolume->NbFaces();
   if ( myVolume->IsPoly() )
   {
-    myPolyedre = SMDS_Mesh::DownCast<SMDS_MeshVolume>( myVolume );
+    myPolyedre = dynamic_cast<const SMDS_VtkVolume*>( myVolume );
     myPolyFacetOri.resize( myNbFaces, 0 );
   }
 
@@ -519,7 +522,10 @@ bool SMDS_VolumeTool::Set (const SMDS_MeshElement*                  theVolume,
   }
   else
   {
-    myVolumeNodes.assign( myVolume->begin_nodes(), myVolume->end_nodes() );
+    int iNode = 0;
+    SMDS_ElemIteratorPtr nodeIt = myVolume->nodesIterator();
+    while ( nodeIt->more() )
+      myVolumeNodes[ iNode++ ] = static_cast<const SMDS_MeshNode*>( nodeIt->next() );
   }
 
   // check validity
@@ -948,8 +954,8 @@ const int* SMDS_VolumeTool::GetFaceNodesIndices( int faceIndex ) const
 //purpose  : Return a set of face nodes.
 //=======================================================================
 
-bool SMDS_VolumeTool::GetFaceNodes (int                             faceIndex,
-                                    std::set<const SMDS_MeshNode*>& theFaceNodes ) const
+bool SMDS_VolumeTool::GetFaceNodes (int                        faceIndex,
+                                    set<const SMDS_MeshNode*>& theFaceNodes ) const
 {
   if ( !setFace( faceIndex ))
     return false;
@@ -1054,7 +1060,7 @@ bool SMDS_VolumeTool::IsFaceExternal( int faceIndex ) const
         {
           ori = ( -minProj < maxProj ? -1 : +1 );
           double convexity = std::min( -minProj, maxProj ) / std::max( -minProj, maxProj );
-          convexity2face.insert( std::make_pair( convexity, iF * ori ));
+          convexity2face.insert( make_pair( convexity, iF * ori ));
         }
       }
       if ( faceMostConvex < 0 ) // none facet has nodes on the same side
@@ -1083,7 +1089,7 @@ bool SMDS_VolumeTool::IsFaceExternal( int faceIndex ) const
   // compare orientation of links of the facet with myFwdLinks
   ori = 0;
   setFace( faceIndex );
-  std::vector< NLink > links( myCurFace.myNbNodes ), links2;
+  vector< NLink > links( myCurFace.myNbNodes ), links2;
   for ( int i = 0; i < myCurFace.myNbNodes && !ori; ++i )
   {
     NLink link( myCurFace.myNodes[i], myCurFace.myNodes[i+1] );
@@ -1204,7 +1210,7 @@ bool SMDS_VolumeTool::GetFaceNormal (int faceIndex, double & X, double & Y, doub
   }
 
   double size = cross.Magnitude();
-  if ( size <= std::numeric_limits<double>::min() )
+  if ( size <= numeric_limits<double>::min() )
     return false;
 
   X = cross.x / size;
@@ -1376,7 +1382,7 @@ bool SMDS_VolumeTool::IsLinked (const SMDS_MeshNode* theNode1,
     } else {
       d2 = 0;
     }
-    std::vector<const SMDS_MeshNode*>::const_iterator i;
+    vector<const SMDS_MeshNode*>::const_iterator i;
     for (int iface = 0; iface < myNbFaces; iface++)
     {
       from = to;
@@ -1423,8 +1429,8 @@ bool SMDS_VolumeTool::IsLinked (const int theNode1Index,
     return IsLinked(myVolumeNodes[theNode1Index], myVolumeNodes[theNode2Index]);
   }
 
-  int minInd = std::min( theNode1Index, theNode2Index );
-  int maxInd = std::max( theNode1Index, theNode2Index );
+  int minInd = min( theNode1Index, theNode2Index );
+  int maxInd = max( theNode1Index, theNode2Index );
 
   if ( minInd < 0 || maxInd > (int)myVolumeNodes.size() - 1 || maxInd == minInd )
     return false;
@@ -1559,7 +1565,7 @@ int SMDS_VolumeTool::GetNodeIndex(const SMDS_MeshNode* theNode) const
  */
 //================================================================================
 
-int SMDS_VolumeTool::GetAllExistingFaces(std::vector<const SMDS_MeshElement*> & faces) const
+int SMDS_VolumeTool::GetAllExistingFaces(vector<const SMDS_MeshElement*> & faces) const
 {
   faces.clear();
   SaveFacet savedFacet( myCurFace );
@@ -1600,7 +1606,7 @@ int SMDS_VolumeTool::GetAllExistingFaces(std::vector<const SMDS_MeshElement*> &
  */
 //================================================================================
 
-int SMDS_VolumeTool::GetAllExistingEdges(std::vector<const SMDS_MeshElement*> & edges) const
+int SMDS_VolumeTool::GetAllExistingEdges(vector<const SMDS_MeshElement*> & edges) const
 {
   edges.clear();
   edges.reserve( myVolumeNodes.size() * 2 );
@@ -1711,7 +1717,7 @@ bool SMDS_VolumeTool::IsFreeFace( int faceIndex, const SMDS_MeshElement** otherV
       //   int nb = myCurFace.myNbNodes;
       //   if ( myVolume->GetEntityType() != vol->GetEntityType() )
       //     nb -= ( GetCenterNodeIndex(0) > 0 );
-      //   std::set<const SMDS_MeshNode*> faceNodes( nodes, nodes + nb );
+      //   set<const SMDS_MeshNode*> faceNodes( nodes, nodes + nb );
       //   if ( SMDS_VolumeTool( vol ).GetFaceIndex( faceNodes ) < 0 )
       //     continue;
       // }
@@ -1741,7 +1747,7 @@ bool SMDS_VolumeTool::IsFreeFaceAdv( int faceIndex, const SMDS_MeshElement** oth
 
   // evaluate nb of face nodes shared by other volumes
   int maxNbShared = -1;
-  typedef std::map< const SMDS_MeshElement*, int > TElemIntMap;
+  typedef map< const SMDS_MeshElement*, int > TElemIntMap;
   TElemIntMap volNbShared;
   TElemIntMap::iterator vNbIt;
   for ( int iNode = 0; iNode < nbFaceNodes; iNode++ ) {
@@ -1750,7 +1756,7 @@ bool SMDS_VolumeTool::IsFreeFaceAdv( int faceIndex, const SMDS_MeshElement** oth
     while ( eIt->more() ) {
       const SMDS_MeshElement* elem = eIt->next();
       if ( elem != myVolume ) {
-        vNbIt = volNbShared.insert( std::make_pair( elem, 0 )).first;
+        vNbIt = volNbShared.insert( make_pair( elem, 0 )).first;
         (*vNbIt).second++;
         if ( vNbIt->second > maxNbShared )
           maxNbShared = vNbIt->second;
@@ -1849,7 +1855,7 @@ bool SMDS_VolumeTool::IsFreeFaceAdv( int faceIndex, const SMDS_MeshElement** oth
 //purpose  : Return index of a face formed by theFaceNodes
 //=======================================================================
 
-int SMDS_VolumeTool::GetFaceIndex( const std::set<const SMDS_MeshNode*>& theFaceNodes,
+int SMDS_VolumeTool::GetFaceIndex( const set<const SMDS_MeshNode*>& theFaceNodes,
                                    const int                        theFaceIndexHint ) const
 {
   if ( theFaceIndexHint >= 0 )
@@ -1892,12 +1898,12 @@ int SMDS_VolumeTool::GetFaceIndex( const std::set<const SMDS_MeshNode*>& theFace
 //purpose  : Return index of a face formed by theFaceNodes
 //=======================================================================
 
-/*int SMDS_VolumeTool::GetFaceIndex( const std::set<int>& theFaceNodesIndices )
+/*int SMDS_VolumeTool::GetFaceIndex( const set<int>& theFaceNodesIndices )
 {
   for ( int iFace = 0; iFace < myNbFaces; iFace++ ) {
     const int* nodes = GetFaceNodesIndices( iFace );
     int nbFaceNodes = NbFaceNodes( iFace );
-    std::set<int> nodeSet;
+    set<int> nodeSet;
     for ( int iNode = 0; iNode < nbFaceNodes; iNode++ )
       nodeSet.insert( nodes[ iNode ] );
     if ( theFaceNodesIndices == nodeSet )
@@ -1926,7 +1932,7 @@ bool SMDS_VolumeTool::setFace( int faceIndex ) const
 
   if (myVolume->IsPoly())
   {
-    if ( !myPolyedre ) {
+    if (!myPolyedre) {
       MESSAGE("Warning: bad volumic element");
       return false;
     }
index d0a1f31211f1c8fbe261d8bb8bc4cac0add52efa..271ab4af5dcb0113d6470129fd0110ffb5d71f41 100644 (file)
@@ -33,6 +33,7 @@
 
 class SMDS_MeshElement;
 class SMDS_MeshNode;
+class SMDS_VtkVolume;
 class SMDS_MeshVolume;
 
 #include <vector>
@@ -251,7 +252,7 @@ class SMDS_EXPORT SMDS_VolumeTool
   bool projectNodesToNormal( int faceIndex, double& minProj, double& maxProj ) const;
 
   const SMDS_MeshElement* myVolume;
-  const SMDS_MeshVolume*  myPolyedre;
+  const SMDS_VtkVolume*   myPolyedre;
   bool                    myIgnoreCentralNodes;
 
   bool                    myVolForward;
index 0f474492576f364de0d49ef933eba26ec49e4e2f..a0f0d378425d14c48c1fda1433c6f832f1bcdb5a 100644 (file)
 #include "SMDS_VtkCellIterator.hxx"
 #include "utilities.h"
 
-#include <vtkCell.h>
-#include <vtkIdList.h>
-
-_GetVtkNodes::_GetVtkNodes( vtkIdList*         _vtkIdList,
-                            SMDS_Mesh*         mesh,
-                            int                vtkCellId,
-                            SMDSAbs_EntityType aType )
+SMDS_VtkCellIterator::SMDS_VtkCellIterator(SMDS_Mesh* mesh, int vtkCellId, SMDSAbs_EntityType aType) :
+  _mesh(mesh), _cellId(vtkCellId), _index(0), _type(aType)
 {
-  vtkUnstructuredGrid* grid = mesh->GetGrid();
+  vtkUnstructuredGrid* grid = _mesh->getGrid();
+  _vtkIdList = vtkIdList::New();
   const std::vector<int>& interlace = SMDS_MeshCell::fromVtkOrder( aType );
   if ( interlace.empty() )
   {
-    grid->GetCellPoints( vtkCellId, _vtkIdList );
+    grid->GetCellPoints(_cellId, _vtkIdList);
+    _nbNodes = _vtkIdList->GetNumberOfIds();
   }
   else
   {
     vtkIdType npts, *pts;
-    grid->GetCellPoints( vtkCellId, npts, pts );
-    _vtkIdList->SetNumberOfIds( npts );
-    for (int i = 0; i < npts; i++)
+    grid->GetCellPoints( _cellId, npts, pts );
+    _vtkIdList->SetNumberOfIds( _nbNodes = npts );
+    for (int i = 0; i < _nbNodes; i++)
       _vtkIdList->SetId(i, pts[interlace[i]]);
   }
 }
 
-_GetVtkNodesToUNV::_GetVtkNodesToUNV( vtkIdList*         _vtkIdList,
-                                      SMDS_Mesh*         mesh,
-                                      int                vtkCellId,
-                                      SMDSAbs_EntityType aType )
+SMDS_VtkCellIterator::~SMDS_VtkCellIterator()
+{
+  _vtkIdList->Delete();
+}
+
+bool SMDS_VtkCellIterator::more()
+{
+  return (_index < _nbNodes);
+}
+
+const SMDS_MeshElement* SMDS_VtkCellIterator::next()
 {
-  vtkIdType * pts, npts;
-  vtkUnstructuredGrid* grid = mesh->GetGrid();
-  grid->GetCellPoints( (vtkIdType)vtkCellId, npts, pts );
+  vtkIdType id = _vtkIdList->GetId(_index++);
+  return _mesh->FindNodeVtk(id);
+}
+
+SMDS_VtkCellIteratorToUNV::SMDS_VtkCellIteratorToUNV(SMDS_Mesh* mesh, int vtkCellId, SMDSAbs_EntityType aType) :
+  SMDS_VtkCellIterator()
+{
+  _mesh = mesh;
+  _cellId = vtkCellId;
+  _index = 0;
+  _type = aType;
+  //MESSAGE("SMDS_VtkCellInterlacedIterator (UNV)" << _type);
+
+  _vtkIdList = vtkIdList::New();
+  vtkIdType* pts;
+  vtkUnstructuredGrid* grid = _mesh->getGrid();
+  grid->GetCellPoints((vtkIdType)_cellId, (vtkIdType&)_nbNodes, pts);
+  _vtkIdList->SetNumberOfIds(_nbNodes);
   const int *ids = 0;
-  switch (aType)
+  switch (_type)
   {
   case SMDSEntity_Quad_Edge:
   {
@@ -66,7 +85,7 @@ _GetVtkNodesToUNV::_GetVtkNodesToUNV( vtkIdList*         _vtkIdList,
   {
     static int id[] = { 0, 3, 1, 4, 2, 5 };
     ids = id;
-    npts = 6;
+    _nbNodes = 6;
     break;
   }
   case SMDSEntity_Quad_Quadrangle:
@@ -74,7 +93,7 @@ _GetVtkNodesToUNV::_GetVtkNodesToUNV( vtkIdList*         _vtkIdList,
   {
     static int id[] = { 0, 4, 1, 5, 2, 6, 3, 7 };
     ids = id;
-    npts = 8;
+    _nbNodes = 8;
     break;
   }
   case SMDSEntity_Quad_Tetra:
@@ -107,7 +126,7 @@ _GetVtkNodesToUNV::_GetVtkNodesToUNV( vtkIdList*         _vtkIdList,
   {
     static int id[] = { 0, 8, 1, 9, 2, 10, 3, 11, 16, 17, 18, 19, 4, 12, 5, 13, 6, 14, 7, 15 };
     ids = id;
-    npts = 20;
+    _nbNodes = 20;
     break;
   }
   case SMDSEntity_Polygon:
@@ -115,42 +134,62 @@ _GetVtkNodesToUNV::_GetVtkNodesToUNV( vtkIdList*         _vtkIdList,
   case SMDSEntity_Polyhedra:
   case SMDSEntity_Quad_Polyhedra:
   default:
-    const std::vector<int>& i = SMDS_MeshCell::interlacedSmdsOrder( aType, npts );
+    const std::vector<int>& i = SMDS_MeshCell::interlacedSmdsOrder(aType, _nbNodes);
     if ( !i.empty() )
       ids = & i[0];
   }
 
-  _vtkIdList->SetNumberOfIds( npts );
-
   if ( ids )
-    for (int i = 0; i < npts; i++)
+    for (int i = 0; i < _nbNodes; i++)
       _vtkIdList->SetId(i, pts[ids[i]]);
   else
-    for (int i = 0; i < npts; i++)
+    for (int i = 0; i < _nbNodes; i++)
       _vtkIdList->SetId(i, pts[i]);
 }
 
-_GetVtkNodesPolyh::_GetVtkNodesPolyh( vtkIdList*         _vtkIdList,
-                                      SMDS_Mesh*         mesh,
-                                      int                vtkCellId,
-                                      SMDSAbs_EntityType aType )
+bool SMDS_VtkCellIteratorToUNV::more()
 {
-  vtkUnstructuredGrid* grid = mesh->GetGrid();
-  switch (aType)
+  return SMDS_VtkCellIterator::more();
+}
+
+const SMDS_MeshNode* SMDS_VtkCellIteratorToUNV::next()
+{
+  return static_cast< const SMDS_MeshNode* >( SMDS_VtkCellIterator::next() );
+}
+
+SMDS_VtkCellIteratorToUNV::~SMDS_VtkCellIteratorToUNV()
+{
+}
+
+SMDS_VtkCellIteratorPolyH::SMDS_VtkCellIteratorPolyH(SMDS_Mesh* mesh, int vtkCellId, SMDSAbs_EntityType aType) :
+  SMDS_VtkCellIterator()
+{
+  _mesh = mesh;
+  _cellId = vtkCellId;
+  _index = 0;
+  _type = aType;
+  //MESSAGE("SMDS_VtkCellIteratorPolyH " << _type);
+  _vtkIdList = vtkIdList::New();
+  vtkUnstructuredGrid* grid = _mesh->getGrid();
+  grid->GetCellPoints(_cellId, _vtkIdList);
+  _nbNodes = _vtkIdList->GetNumberOfIds();
+  switch (_type)
   {
   case SMDSEntity_Polyhedra:
   {
+    //MESSAGE("SMDS_VtkCellIterator Polyhedra");
     vtkIdType nFaces = 0;
     vtkIdType* ptIds = 0;
-    grid->GetFaceStream( vtkCellId, nFaces, ptIds );
-    int id = 0, nbNodesInFaces = 0;
+    grid->GetFaceStream(_cellId, nFaces, ptIds);
+    int id = 0;
+    _nbNodesInFaces = 0;
     for (int i = 0; i < nFaces; i++)
     {
       int nodesInFace = ptIds[id]; // nodeIds in ptIds[id+1 .. id+nodesInFace]
-      nbNodesInFaces += nodesInFace;
+      _nbNodesInFaces += nodesInFace;
       id += (nodesInFace + 1);
     }
-    _vtkIdList->SetNumberOfIds( nbNodesInFaces );
+    _vtkIdList->SetNumberOfIds(_nbNodesInFaces);
     id = 0;
     int n = 0;
     for (int i = 0; i < nFaces; i++)
@@ -166,3 +205,12 @@ _GetVtkNodesPolyh::_GetVtkNodesPolyh( vtkIdList*         _vtkIdList,
     assert(0);
   }
 }
+
+SMDS_VtkCellIteratorPolyH::~SMDS_VtkCellIteratorPolyH()
+{
+}
+
+bool SMDS_VtkCellIteratorPolyH::more()
+{
+  return (_index < _nbNodesInFaces);
+}
index 92fdc17a240187f3c466e85421c76222a1d573a3..30ddadee52cc4cdebf53ad4314e57a961f24605f 100644 (file)
 #include <vtkCell.h>
 #include <vtkIdList.h>
 
-//--------------------------------------------------------------------------------
-/*!
- * \brief Retrieve nodes of a cell
- */
-struct _GetVtkNodes
-{
-  _GetVtkNodes( vtkIdList* nodeIds, SMDS_Mesh* mesh, int vtkCellId, SMDSAbs_EntityType type);
-};
-struct _GetVtkNodesToUNV
-{
-  _GetVtkNodesToUNV( vtkIdList* nodeIds, SMDS_Mesh* mesh, int vtkCellId, SMDSAbs_EntityType type);
-};
-struct _GetVtkNodesPolyh
-{
-  _GetVtkNodesPolyh( vtkIdList* nodeIds, SMDS_Mesh* mesh, int vtkCellId, SMDSAbs_EntityType type);
-};
-
-//--------------------------------------------------------------------------------
-/*!
- * \brief Iterator on nodes of a cell
- */
-template< class SMDS_ITERATOR = SMDS_ElemIterator, class GET_VTK_NODES = _GetVtkNodes >
-class SMDS_VtkCellIterator: public SMDS_ITERATOR
+class SMDS_VtkCellIterator: public SMDS_ElemIterator
 {
 public:
-  typedef typename SMDS_ITERATOR::value_type result_type;
-
-  SMDS_VtkCellIterator(SMDS_Mesh* mesh, int vtkCellId, SMDSAbs_EntityType aType)
-    : _mesh(mesh), _index(0), _vtkIdList( vtkIdList::New() )
+  SMDS_VtkCellIterator(SMDS_Mesh* mesh, int vtkCellId, SMDSAbs_EntityType aType);
+  virtual ~SMDS_VtkCellIterator();
+  virtual bool more();
+  virtual const SMDS_MeshElement* next();
+  inline void exchange(vtkIdType a, vtkIdType b)
   {
-    GET_VTK_NODES getNodes( _vtkIdList, mesh, vtkCellId, aType );
-  }
-  virtual ~SMDS_VtkCellIterator() { _vtkIdList->Delete(); }
-  virtual bool        more()      {  return ( _index < _vtkIdList->GetNumberOfIds() ); }
-  virtual result_type next()      {
-    vtkIdType id = _vtkIdList->GetId( _index++ );
-    return static_cast<result_type>( _mesh->FindNodeVtk( id ));
+    vtkIdType t = _vtkIdList->GetId(a);
+    _vtkIdList->SetId(a, _vtkIdList->GetId(b));
+    _vtkIdList->SetId(b, t);
   }
+
 protected:
+  SMDS_VtkCellIterator() {};
+
   SMDS_Mesh* _mesh;
-  int        _index;
+  int _cellId;
+  int _index;
+  int _nbNodes;
+  SMDSAbs_EntityType _type;
   vtkIdList* _vtkIdList;
 };
 
-//--------------------------------------------------------------------------------
-template< class SMDS_ITERATOR = SMDS_ElemIterator >
-class SMDS_VtkCellIteratorToUNV: public SMDS_VtkCellIterator< SMDS_ITERATOR, _GetVtkNodesToUNV >
+class SMDS_VtkCellIteratorToUNV: public SMDS_NodeIterator, protected SMDS_VtkCellIterator
 {
-  typedef SMDS_VtkCellIterator< SMDS_ITERATOR, _GetVtkNodesToUNV > parent_t;
 public:
-  SMDS_VtkCellIteratorToUNV(SMDS_Mesh* mesh, int vtkCellId, SMDSAbs_EntityType type):
-    parent_t( mesh, vtkCellId, type ) {}
+  SMDS_VtkCellIteratorToUNV(SMDS_Mesh* mesh, int vtkCellId, SMDSAbs_EntityType aType);
+  virtual const SMDS_MeshNode* next();
+  virtual bool more();
+  virtual ~SMDS_VtkCellIteratorToUNV();
 };
 
-//--------------------------------------------------------------------------------
-template< class SMDS_ITERATOR = SMDS_ElemIterator >
-class SMDS_VtkCellIteratorPolyH: public SMDS_VtkCellIterator< SMDS_ITERATOR, _GetVtkNodesPolyh >
+class SMDS_VtkCellIteratorPolyH: public SMDS_VtkCellIterator
 {
-  typedef SMDS_VtkCellIterator< SMDS_ITERATOR, _GetVtkNodesPolyh > parent_t;
 public:
-  SMDS_VtkCellIteratorPolyH(SMDS_Mesh* mesh, int vtkCellId, SMDSAbs_EntityType type):
-    parent_t( mesh, vtkCellId, type ) {}
+  SMDS_VtkCellIteratorPolyH(SMDS_Mesh* mesh, int vtkCellId, SMDSAbs_EntityType aType);
+  virtual ~SMDS_VtkCellIteratorPolyH();
+  virtual bool more();
+protected:
+  int _nbNodesInFaces;
 };
 
 #endif
diff --git a/src/SMDS/SMDS_VtkEdge.cxx b/src/SMDS/SMDS_VtkEdge.cxx
new file mode 100644 (file)
index 0000000..edf40f7
--- /dev/null
@@ -0,0 +1,167 @@
+// Copyright (C) 2010-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+#include "SMDS_VtkEdge.hxx"
+#include "SMDS_MeshNode.hxx"
+#include "SMDS_Mesh.hxx"
+#include "SMDS_VtkCellIterator.hxx"
+
+#include "utilities.h"
+
+#include <vector>
+#include <cassert>
+
+using namespace std;
+
+SMDS_VtkEdge::SMDS_VtkEdge()
+{
+}
+
+SMDS_VtkEdge::SMDS_VtkEdge(std::vector<vtkIdType>& nodeIds, SMDS_Mesh* mesh)
+{
+  init(nodeIds, mesh);
+}
+
+SMDS_VtkEdge::~SMDS_VtkEdge()
+{
+}
+
+void SMDS_VtkEdge::init(std::vector<vtkIdType>& nodeIds, SMDS_Mesh* mesh)
+{
+  SMDS_MeshEdge::init();
+  myMeshId = mesh->getMeshId();
+  vtkIdType aType = ( nodeIds.size() == 3 ) ? VTK_QUADRATIC_EDGE : VTK_LINE;
+  myVtkID = mesh->getGrid()->InsertNextLinkedCell(aType, nodeIds.size(), &nodeIds[0]);
+  mesh->setMyModified();
+}
+
+bool SMDS_VtkEdge::ChangeNodes(const SMDS_MeshNode * node1, const SMDS_MeshNode * node2)
+{
+  const SMDS_MeshNode* nodes[] = { node1, node2 };
+  SMDS_Mesh::_meshList[myMeshId]->setMyModified();
+  return ChangeNodes(nodes, 2);
+}
+
+bool SMDS_VtkEdge::ChangeNodes(const SMDS_MeshNode* nodes[], const int nbNodes)
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType npts = 0;
+  vtkIdType* pts = 0;
+  grid->GetCellPoints(myVtkID, npts, pts);
+  if (nbNodes != npts)
+  {
+    MESSAGE("ChangeNodes problem: not the same number of nodes " << npts << " -> " << nbNodes);
+    return false;
+  }
+  for (int i = 0; i < nbNodes; i++)
+  {
+    pts[i] = nodes[i]->getVtkId();
+  }
+  SMDS_Mesh::_meshList[myMeshId]->setMyModified();
+  return true;
+}
+
+bool SMDS_VtkEdge::IsMediumNode(const SMDS_MeshNode* node) const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType npts = 0;
+  vtkIdType* pts = 0;
+  grid->GetCellPoints(myVtkID, npts, pts);
+  return ((npts == 3) && (node->getVtkId() == pts[2]));
+}
+
+void SMDS_VtkEdge::Print(std::ostream & OS) const
+{
+  OS << "edge <" << GetID() << "> : ";
+}
+
+int SMDS_VtkEdge::NbNodes() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType *pts, npts;
+  grid->GetCellPoints( myVtkID, npts, pts );
+  assert(npts >= 2);
+  return npts;
+}
+
+int SMDS_VtkEdge::NbEdges() const
+{
+  return 1;
+}
+
+SMDSAbs_EntityType SMDS_VtkEdge::GetEntityType() const
+{
+  if (NbNodes() == 2)
+    return SMDSEntity_Edge;
+  else
+    return SMDSEntity_Quad_Edge;
+}
+
+vtkIdType SMDS_VtkEdge::GetVtkType() const
+{
+  if (NbNodes() == 2)
+    return VTK_LINE;
+  else
+    return VTK_QUADRATIC_EDGE;
+
+}
+
+/*!
+ * \brief Return node by its index
+ * \param ind - node index
+ * \retval const SMDS_MeshNode* - the node
+ */
+const SMDS_MeshNode*
+SMDS_VtkEdge::GetNode(const int ind) const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType npts, *pts;
+  grid->GetCellPoints( this->myVtkID, npts, pts );
+  return SMDS_Mesh::_meshList[myMeshId]->FindNodeVtk( pts[ ind ]);
+}
+
+bool SMDS_VtkEdge::IsQuadratic() const
+{
+  if (this->NbNodes() > 2)
+    return true;
+  else
+    return false;
+}
+
+SMDS_ElemIteratorPtr SMDS_VtkEdge::elementsIterator(SMDSAbs_ElementType type) const
+{
+  switch (type)
+  {
+    case SMDSAbs_Node:
+      return SMDS_ElemIteratorPtr(new SMDS_VtkCellIterator(SMDS_Mesh::_meshList[myMeshId], myVtkID, GetEntityType()));
+    default:
+      MESSAGE("ERROR : Iterator not implemented");
+      return SMDS_ElemIteratorPtr((SMDS_ElemIterator*) NULL);
+  }
+}
+
+SMDS_NodeIteratorPtr SMDS_VtkEdge::nodesIteratorToUNV() const
+{
+  return SMDS_NodeIteratorPtr(new SMDS_VtkCellIteratorToUNV(SMDS_Mesh::_meshList[myMeshId], myVtkID, GetEntityType()));
+}
+
+SMDS_NodeIteratorPtr SMDS_VtkEdge::interlacedNodesIterator() const
+{
+  return nodesIteratorToUNV();
+}
diff --git a/src/SMDS/SMDS_VtkEdge.hxx b/src/SMDS/SMDS_VtkEdge.hxx
new file mode 100644 (file)
index 0000000..aebfb6e
--- /dev/null
@@ -0,0 +1,59 @@
+// Copyright (C) 2010-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  SMESH SMDS : implementation of Salome mesh data structure
+//  File   : SMDS_VtkEdge.hxx
+//  Module : SMESH
+
+#ifndef _SMDS_VTKEDGE_HXX_
+#define _SMDS_VTKEDGE_HXX_
+
+#include "SMESH_SMDS.hxx"
+
+#include "SMDS_MeshEdge.hxx"
+#include <vtkUnstructuredGrid.h>
+#include <vector>
+
+class SMDS_EXPORT SMDS_VtkEdge: public SMDS_MeshEdge
+{
+
+public:
+  SMDS_VtkEdge();
+  SMDS_VtkEdge(std::vector<vtkIdType>& nodeIds, SMDS_Mesh* mesh);
+  ~SMDS_VtkEdge();
+  void init(std::vector<vtkIdType>& nodeIds, SMDS_Mesh* mesh);
+  bool ChangeNodes(const SMDS_MeshNode * node1, const SMDS_MeshNode * node2);
+  virtual bool ChangeNodes(const SMDS_MeshNode* nodes[], const int nbNodes);
+  virtual bool IsMediumNode(const SMDS_MeshNode* node) const;
+
+  virtual void Print(std::ostream & OS) const;
+  virtual int NbNodes() const;
+  virtual int NbEdges() const;
+
+  virtual vtkIdType GetVtkType() const;
+  virtual SMDSAbs_EntityType GetEntityType() const;
+  virtual const SMDS_MeshNode* GetNode(const int ind) const;
+  virtual bool IsQuadratic() const;
+
+  virtual SMDS_ElemIteratorPtr elementsIterator(SMDSAbs_ElementType type) const;
+  virtual SMDS_NodeIteratorPtr nodesIteratorToUNV() const;
+  virtual SMDS_NodeIteratorPtr interlacedNodesIterator() const;
+protected:
+};
+#endif
diff --git a/src/SMDS/SMDS_VtkFace.cxx b/src/SMDS/SMDS_VtkFace.cxx
new file mode 100644 (file)
index 0000000..724a7ec
--- /dev/null
@@ -0,0 +1,334 @@
+// Copyright (C) 2010-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+#include "SMDS_VtkFace.hxx"
+#include "SMDS_MeshNode.hxx"
+#include "SMDS_Mesh.hxx"
+#include "SMDS_VtkCellIterator.hxx"
+
+#include "utilities.h"
+
+#include <vector>
+
+using namespace std;
+
+SMDS_VtkFace::SMDS_VtkFace()
+{
+}
+
+SMDS_VtkFace::SMDS_VtkFace(const std::vector<vtkIdType>& nodeIds, SMDS_Mesh* mesh)
+{
+  init(nodeIds, mesh);
+}
+
+SMDS_VtkFace::~SMDS_VtkFace()
+{
+}
+
+void SMDS_VtkFace::init(const std::vector<vtkIdType>& nodeIds, SMDS_Mesh* mesh)
+{
+  SMDS_MeshFace::init();
+  myMeshId = mesh->getMeshId();
+  vtkIdType aType = VTK_TRIANGLE;
+  switch (nodeIds.size())
+  {
+    case 3:  aType = VTK_TRIANGLE;            break;
+    case 4:  aType = VTK_QUAD;                break;
+    case 6:  aType = VTK_QUADRATIC_TRIANGLE;  break;
+    case 8:  aType = VTK_QUADRATIC_QUAD;      break;
+    case 9:  aType = VTK_BIQUADRATIC_QUAD;    break;
+    case 7:  aType = VTK_BIQUADRATIC_TRIANGLE;break;
+    default: aType = VTK_POLYGON;
+  }
+  myVtkID = mesh->getGrid()->InsertNextLinkedCell(aType, nodeIds.size(), (vtkIdType*) &nodeIds[0]);
+  mesh->setMyModified();
+}
+
+void SMDS_VtkFace::initPoly(const std::vector<vtkIdType>& nodeIds, SMDS_Mesh* mesh)
+{
+  SMDS_MeshFace::init();
+  myMeshId = mesh->getMeshId();
+  vtkIdType aType = VTK_POLYGON;
+  myVtkID = mesh->getGrid()->InsertNextLinkedCell(aType, nodeIds.size(), (vtkIdType*) &nodeIds[0]);
+  mesh->setMyModified();
+}
+
+void SMDS_VtkFace::initQuadPoly(const std::vector<vtkIdType>& nodeIds, SMDS_Mesh* mesh)
+{
+  SMDS_MeshFace::init();
+  myMeshId = mesh->getMeshId();
+  vtkIdType aType = VTK_QUADRATIC_POLYGON;
+  myVtkID = mesh->getGrid()->InsertNextLinkedCell(aType, nodeIds.size(), (vtkIdType*) &nodeIds[0]);
+  mesh->setMyModified();
+}
+
+bool SMDS_VtkFace::ChangeNodes(const SMDS_MeshNode* nodes[], const int nbNodes)
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType npts = 0;
+  vtkIdType* pts = 0;
+  grid->GetCellPoints(myVtkID, npts, pts);
+  if (nbNodes != npts)
+  {
+    MESSAGE("ChangeNodes problem: not the same number of nodes " << npts << " -> " << nbNodes);
+    return false;
+  }
+  for (int i = 0; i < nbNodes; i++)
+  {
+    pts[i] = nodes[i]->getVtkId();
+  }
+  SMDS_Mesh::_meshList[myMeshId]->setMyModified();
+  return true;
+}
+
+void SMDS_VtkFace::Print(std::ostream & OS) const
+{
+  OS << "face <" << GetID() << "> : ";
+}
+
+int SMDS_VtkFace::NbEdges() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  int nbEdges = 3;
+  switch (aVtkType)
+  {
+  case VTK_TRIANGLE:
+  case VTK_QUADRATIC_TRIANGLE:
+  case VTK_BIQUADRATIC_TRIANGLE:
+    nbEdges = 3;
+    break;
+  case VTK_QUAD:
+  case VTK_QUADRATIC_QUAD:
+  case VTK_BIQUADRATIC_QUAD:
+    nbEdges = 4;
+    break;
+  case VTK_QUADRATIC_POLYGON:
+    nbEdges = NbNodes() / 2;
+    break;
+  case VTK_POLYGON:
+  default:
+    nbEdges = NbNodes();
+    break;
+  }
+  return nbEdges;
+}
+
+int SMDS_VtkFace::NbFaces() const
+{
+  return 1;
+}
+
+int SMDS_VtkFace::NbNodes() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType *pts, npts;
+  grid->GetCellPoints( myVtkID, npts, pts );
+  return npts;
+}
+
+/*!
+ * \brief Return node by its index
+ * \param ind - node index
+ * \retval const SMDS_MeshNode* - the node
+ */
+const SMDS_MeshNode*
+SMDS_VtkFace::GetNode(const int ind) const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType npts, *pts;
+  grid->GetCellPoints( this->myVtkID, npts, pts );
+  return SMDS_Mesh::_meshList[myMeshId]->FindNodeVtk( pts[ ind ]);
+}
+
+/*!
+ * \brief Check if a node belongs to the element
+ * \param node - the node to check
+ * \retval int - node index within the element, -1 if not found
+ */
+int SMDS_VtkFace::GetNodeIndex( const SMDS_MeshNode* node ) const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType npts, *pts;
+  grid->GetCellPoints( this->myVtkID, npts, pts );
+  for ( vtkIdType i = 0; i < npts; ++i )
+    if ( pts[i] == node->getVtkId() )
+      return i;
+  return -1;
+}
+
+bool SMDS_VtkFace::IsQuadratic() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  // TODO quadratic polygons ?
+  switch (aVtkType)
+  {
+    case VTK_QUADRATIC_TRIANGLE:
+    case VTK_QUADRATIC_QUAD:
+    case VTK_QUADRATIC_POLYGON:
+    case VTK_BIQUADRATIC_QUAD:
+    case VTK_BIQUADRATIC_TRIANGLE:
+      return true;
+      break;
+    default:
+      return false;
+  }
+}
+
+bool SMDS_VtkFace::IsPoly() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  return ( aVtkType == VTK_POLYGON || aVtkType == VTK_QUADRATIC_POLYGON );
+}
+
+bool SMDS_VtkFace::IsMediumNode(const SMDS_MeshNode* node) const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType npts = 0;
+  vtkIdType* pts = 0;
+  grid->GetCellPoints(myVtkID, npts, pts);
+
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  int rankFirstMedium = 0;
+  switch (aVtkType)
+  {
+  case VTK_QUADRATIC_TRIANGLE:
+  case VTK_BIQUADRATIC_TRIANGLE:
+    rankFirstMedium = 3; // medium nodes are of rank 3,4,5
+    break;
+  case VTK_QUADRATIC_QUAD:
+  case VTK_BIQUADRATIC_QUAD:
+    rankFirstMedium = 4; // medium nodes are of rank 4,5,6,7
+    break;
+  case VTK_QUADRATIC_POLYGON:
+    rankFirstMedium = npts / 2;
+    break;
+  default:
+    //MESSAGE("wrong element type " << aVtkType);
+    return false;
+  }
+  vtkIdType nodeId = node->getVtkId();
+  for (int rank = 0; rank < npts; rank++)
+  {
+    if (pts[rank] == nodeId)
+    {
+      //MESSAGE("rank " << rank << " is medium node " << (rank < rankFirstMedium));
+      if (rank < rankFirstMedium)
+        return false;
+      else
+        return true;
+    }
+  }
+  //throw SALOME_Exception(LOCALIZED("node does not belong to this element"));
+  MESSAGE("======================================================");
+  MESSAGE("= IsMediumNode: node does not belong to this element =");
+  MESSAGE("======================================================");
+  return false;
+}
+
+int SMDS_VtkFace::NbCornerNodes() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  int       nbPoints = NbNodes();
+  vtkIdType aVtkType = grid->GetCellType(myVtkID);
+  switch ( aVtkType )
+  {
+  case VTK_POLYGON:
+    break;
+  case VTK_QUADRATIC_POLYGON:
+    nbPoints /= 2;
+    break;
+  default:
+    if ( nbPoints > 4 )
+      nbPoints /= 2;
+  }
+  return nbPoints;
+}
+
+SMDSAbs_EntityType SMDS_VtkFace::GetEntityType() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  return SMDS_MeshCell::toSmdsType( VTKCellType( aVtkType ));
+}
+
+SMDSAbs_GeometryType SMDS_VtkFace::GetGeomType() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  switch ( aVtkType ) {
+  case VTK_TRIANGLE:
+  case VTK_QUADRATIC_TRIANGLE:
+  case VTK_BIQUADRATIC_TRIANGLE: return SMDSGeom_TRIANGLE;
+
+  case VTK_QUAD:
+  case VTK_QUADRATIC_QUAD:
+  case VTK_BIQUADRATIC_QUAD: return SMDSGeom_QUADRANGLE;
+
+  case VTK_POLYGON:
+  case VTK_QUADRATIC_POLYGON: return SMDSGeom_POLYGON;
+  default:;
+  }
+  return SMDSGeom_NONE;
+}
+
+vtkIdType SMDS_VtkFace::GetVtkType() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  return aVtkType;
+}
+
+SMDS_ElemIteratorPtr SMDS_VtkFace::elementsIterator(SMDSAbs_ElementType type) const
+{
+  switch (type)
+  {
+    case SMDSAbs_Node:
+      return SMDS_ElemIteratorPtr(new SMDS_VtkCellIterator(SMDS_Mesh::_meshList[myMeshId], myVtkID, GetEntityType()));
+    default:
+      MESSAGE("ERROR : Iterator not implemented")
+      ;
+      return SMDS_ElemIteratorPtr((SMDS_ElemIterator*) NULL);
+  }
+}
+
+SMDS_NodeIteratorPtr SMDS_VtkFace::nodesIteratorToUNV() const
+{
+  return SMDS_NodeIteratorPtr(new SMDS_VtkCellIteratorToUNV(SMDS_Mesh::_meshList[myMeshId], myVtkID, GetEntityType()));
+}
+
+SMDS_NodeIteratorPtr SMDS_VtkFace::interlacedNodesIterator() const
+{
+  return nodesIteratorToUNV();
+}
+
+//! change only the first node, used for temporary triangles in quadrangle to triangle adaptor
+void SMDS_VtkFace::ChangeApex(SMDS_MeshNode* node)
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType npts = 0;
+  vtkIdType* pts = 0;
+  grid->GetCellPoints(myVtkID, npts, pts);
+  grid->RemoveReferenceToCell(pts[0], myVtkID);
+  pts[0] = node->getVtkId();
+  node->AddInverseElement(this),
+  SMDS_Mesh::_meshList[myMeshId]->setMyModified();
+}
diff --git a/src/SMDS/SMDS_VtkFace.hxx b/src/SMDS/SMDS_VtkFace.hxx
new file mode 100644 (file)
index 0000000..50c49a0
--- /dev/null
@@ -0,0 +1,64 @@
+// Copyright (C) 2010-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+#ifndef _SMDS_VTKFACE_HXX_
+#define _SMDS_VTKFACE_HXX_
+
+#include "SMESH_SMDS.hxx"
+
+#include "SMDS_MeshFace.hxx"
+#include <vtkUnstructuredGrid.h>
+#include <vector>
+
+class SMDS_EXPORT SMDS_VtkFace: public SMDS_MeshFace
+{
+public:
+  SMDS_VtkFace();
+  SMDS_VtkFace(const std::vector<vtkIdType>& nodeIds, SMDS_Mesh* mesh);
+  ~SMDS_VtkFace();
+  void init(const std::vector<vtkIdType>& nodeIds, SMDS_Mesh* mesh);
+  void initPoly(const std::vector<vtkIdType>& nodeIds, SMDS_Mesh* mesh);
+  void initQuadPoly(const std::vector<vtkIdType>& nodeIds, SMDS_Mesh* mesh);
+
+  bool ChangeNodes(const SMDS_MeshNode* nodes[], const int nbNodes);
+  void ChangeApex(SMDS_MeshNode* node); // to use only for tmp triangles
+
+  virtual void Print(std::ostream & OS) const;
+  virtual int NbEdges() const;
+  virtual int NbFaces() const;
+  virtual int NbNodes() const;
+
+  virtual vtkIdType            GetVtkType() const;
+  virtual SMDSAbs_EntityType   GetEntityType() const;
+  virtual SMDSAbs_GeometryType GetGeomType() const;
+  virtual const SMDS_MeshNode* GetNode(const int ind) const;
+  virtual int GetNodeIndex( const SMDS_MeshNode* node ) const;
+
+  virtual bool IsQuadratic() const;
+  virtual bool IsPoly() const;
+  virtual bool IsMediumNode(const SMDS_MeshNode* node) const;
+  virtual int  NbCornerNodes() const;
+
+  virtual SMDS_ElemIteratorPtr elementsIterator(SMDSAbs_ElementType type) const;
+  virtual SMDS_NodeIteratorPtr nodesIteratorToUNV() const;
+  virtual SMDS_NodeIteratorPtr interlacedNodesIterator() const;
+protected:
+};
+
+#endif
diff --git a/src/SMDS/SMDS_VtkVolume.cxx b/src/SMDS/SMDS_VtkVolume.cxx
new file mode 100644 (file)
index 0000000..ecbcd92
--- /dev/null
@@ -0,0 +1,698 @@
+// Copyright (C) 2010-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+#include "SMDS_VtkVolume.hxx"
+#include "SMDS_MeshNode.hxx"
+#include "SMDS_Mesh.hxx"
+#include "SMDS_VtkCellIterator.hxx"
+
+#include "utilities.h"
+
+#include <vector>
+
+SMDS_VtkVolume::SMDS_VtkVolume()
+{
+}
+
+SMDS_VtkVolume::SMDS_VtkVolume(const std::vector<vtkIdType>& nodeIds, SMDS_Mesh* mesh)
+{
+  init(nodeIds, mesh);
+}
+/*!
+ * typed used are vtk types (@see vtkCellType.h)
+ * see GetEntityType() for conversion in SMDS type (@see SMDSAbs_ElementType.hxx)
+ */
+void SMDS_VtkVolume::init(const std::vector<vtkIdType>& nodeIds, SMDS_Mesh* mesh)
+{
+  SMDS_MeshVolume::init();
+  myMeshId = mesh->getMeshId();
+  vtkIdType aType = VTK_TETRA;
+  switch (nodeIds.size()) // cases are in order of usage frequency
+  {
+    case 4:  aType = VTK_TETRA;                        break;
+    case 8:  aType = VTK_HEXAHEDRON;                   break;
+    case 5:  aType = VTK_PYRAMID;                      break;
+    case 6:  aType = VTK_WEDGE;                        break;
+    case 10: aType = VTK_QUADRATIC_TETRA;              break;
+    case 20: aType = VTK_QUADRATIC_HEXAHEDRON;         break;
+    case 13: aType = VTK_QUADRATIC_PYRAMID;            break;
+    case 15: aType = VTK_QUADRATIC_WEDGE;              break;
+    case 18: aType = VTK_BIQUADRATIC_QUADRATIC_WEDGE;  break;
+    case 12: aType = VTK_HEXAGONAL_PRISM;              break;
+    case 27: aType = VTK_TRIQUADRATIC_HEXAHEDRON;      break;
+    default: aType = VTK_HEXAHEDRON;
+  }
+  myVtkID = mesh->getGrid()->InsertNextLinkedCell(aType, nodeIds.size(), (vtkIdType *) &nodeIds[0]);
+  mesh->setMyModified();
+}
+
+void SMDS_VtkVolume::initPoly(const std::vector<vtkIdType>& nodeIds,
+                              const std::vector<int>&       nbNodesPerFace,
+                              SMDS_Mesh*                    mesh)
+{
+  SMDS_MeshVolume::init();
+  SMDS_UnstructuredGrid* grid = mesh->getGrid();
+  //double center[3];
+  //this->gravityCenter(grid, &nodeIds[0], nodeIds.size(), &center[0]);
+  std::vector<vtkIdType> ptIds;
+  vtkIdType nbFaces = nbNodesPerFace.size();
+  int k = 0;
+  for (int i = 0; i < nbFaces; i++)
+  {
+    int nf = nbNodesPerFace[i];
+    ptIds.push_back(nf);
+    // EAP: a right approach is:
+    // - either the user should care of order of nodes or
+    // - the user should use a service method arranging nodes if he
+    //   don't want or can't to do it by him-self
+    // The method below works OK only with planar faces and convex polyhedrones
+    //
+    // double a[3];
+    // double b[3];
+    // double c[3];
+    // grid->GetPoints()->GetPoint(nodeIds[k], a);
+    // grid->GetPoints()->GetPoint(nodeIds[k + 1], b);
+    // grid->GetPoints()->GetPoint(nodeIds[k + 2], c);
+    // bool isFaceForward = this->isForward(a, b, c, center);
+    const vtkIdType *facePts = &nodeIds[k];
+    //if (isFaceForward)
+    for (int n = 0; n < nf; n++)
+      ptIds.push_back(facePts[n]);
+    // else
+    //   for (int n = nf - 1; n >= 0; n--)
+    //     ptIds.push_back(facePts[n]);
+    k += nf;
+  }
+  myVtkID = grid->InsertNextLinkedCell(VTK_POLYHEDRON, nbFaces, &ptIds[0]);
+  mesh->setMyModified();
+}
+
+bool SMDS_VtkVolume::ChangeNodes(const SMDS_MeshNode* nodes[], const int nbNodes)
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType npts = 0;
+  vtkIdType* pts = 0;
+  grid->GetCellPoints(myVtkID, npts, pts);
+  if (nbNodes != npts)
+  {
+    MESSAGE("ChangeNodes problem: not the same number of nodes " << npts << " -> " << nbNodes);
+    return false;
+  }
+  for (int i = 0; i < nbNodes; i++)
+  {
+    pts[i] = nodes[i]->getVtkId();
+  }
+  SMDS_Mesh::_meshList[myMeshId]->setMyModified();
+  return true;
+}
+
+/*!
+ * Reorder in VTK order a list of nodes given in SMDS order.
+ * To be used before ChangeNodes: lists are given or computed in SMDS order.
+ */
+bool SMDS_VtkVolume::vtkOrder(const SMDS_MeshNode* nodes[], const int nbNodes)
+{
+  if (nbNodes != this->NbNodes())
+  {
+    MESSAGE("vtkOrder, wrong number of nodes " << nbNodes << " instead of "<< this->NbNodes());
+    return false;
+  }
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  const std::vector<int>& interlace = SMDS_MeshCell::toVtkOrder( VTKCellType( aVtkType ));
+  if ( !interlace.empty() )
+  {
+    ASSERT( (int)interlace.size() == nbNodes );
+    std::vector<const SMDS_MeshNode*> initNodes( nodes, nodes+nbNodes );
+    for ( size_t i = 0; i < interlace.size(); ++i )
+      nodes[i] = initNodes[ interlace[i] ];
+  }
+  return true;
+}
+
+SMDS_VtkVolume::~SMDS_VtkVolume()
+{
+}
+
+void SMDS_VtkVolume::Print(ostream & OS) const
+{
+  OS << "volume <" << GetID() << "> : ";
+}
+
+int SMDS_VtkVolume::NbFaces() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  int nbFaces = 4;
+  switch (aVtkType)
+  {
+    case VTK_TETRA:
+    case VTK_QUADRATIC_TETRA:
+      nbFaces = 4;
+      break;
+    case VTK_PYRAMID:
+    case VTK_WEDGE:
+    case VTK_QUADRATIC_PYRAMID:
+    case VTK_QUADRATIC_WEDGE:
+    case VTK_BIQUADRATIC_QUADRATIC_WEDGE:
+      nbFaces = 5;
+      break;
+    case VTK_HEXAHEDRON:
+    case VTK_QUADRATIC_HEXAHEDRON:
+    case VTK_TRIQUADRATIC_HEXAHEDRON:
+      nbFaces = 6;
+      break;
+    case VTK_POLYHEDRON:
+      {
+        vtkIdType nFaces = 0;
+        vtkIdType* ptIds = 0;
+        grid->GetFaceStream(this->myVtkID, nFaces, ptIds);
+        nbFaces = nFaces;
+        break;
+      }
+    case VTK_HEXAGONAL_PRISM:
+      nbFaces = 8;
+      break;
+    default:
+      MESSAGE("invalid volume type")
+      ;
+      nbFaces = 0;
+      break;
+  }
+  return nbFaces;
+}
+
+int SMDS_VtkVolume::NbNodes() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  vtkIdType nbPoints = 0;
+  if (aVtkType != VTK_POLYHEDRON)
+  {
+    vtkIdType *pts;
+    grid->GetCellPoints( myVtkID, nbPoints, pts );
+  }
+  else
+  {
+    vtkIdType nFaces = 0;
+    vtkIdType* ptIds = 0;
+    grid->GetFaceStream(this->myVtkID, nFaces, ptIds);
+    int id = 0;
+    for (int i = 0; i < nFaces; i++)
+    {
+      int nodesInFace = ptIds[id];
+      nbPoints += nodesInFace;
+      id += (nodesInFace + 1);
+    }
+  }
+  return nbPoints;
+}
+
+int SMDS_VtkVolume::NbEdges() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  int nbEdges = 6;
+  switch (aVtkType)
+  {
+    case VTK_TETRA:
+    case VTK_QUADRATIC_TETRA:
+      nbEdges = 6;
+      break;
+    case VTK_PYRAMID:
+    case VTK_QUADRATIC_PYRAMID:
+      nbEdges = 8;
+      break;
+    case VTK_WEDGE:
+    case VTK_QUADRATIC_WEDGE:
+    case VTK_BIQUADRATIC_QUADRATIC_WEDGE:
+      nbEdges = 9;
+      break;
+    case VTK_HEXAHEDRON:
+    case VTK_QUADRATIC_HEXAHEDRON:
+    case VTK_TRIQUADRATIC_HEXAHEDRON:
+      nbEdges = 12;
+      break;
+    case VTK_POLYHEDRON:
+      {
+        vtkIdType nFaces = 0;
+        vtkIdType* ptIds = 0;
+        grid->GetFaceStream(this->myVtkID, nFaces, ptIds);
+        nbEdges = 0;
+        int id = 0;
+        for (int i = 0; i < nFaces; i++)
+          {
+            int edgesInFace = ptIds[id];
+            id += (edgesInFace + 1);
+            nbEdges += edgesInFace;
+          }
+        nbEdges = nbEdges / 2;
+        break;
+      }
+    case VTK_HEXAGONAL_PRISM:
+      nbEdges = 18;
+      break;
+    default:
+      MESSAGE("invalid volume type")
+      ;
+      nbEdges = 0;
+      break;
+  }
+  return nbEdges;
+}
+
+/*! polyhedron only,
+ *  1 <= face_ind <= NbFaces()
+ */
+int SMDS_VtkVolume::NbFaceNodes(const int face_ind) const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  int nbNodes = 0;
+  if (aVtkType == VTK_POLYHEDRON)
+  {
+    vtkIdType nFaces = 0;
+    vtkIdType* ptIds = 0;
+    grid->GetFaceStream(this->myVtkID, nFaces, ptIds);
+    int id = 0;
+    for (int i = 0; i < nFaces; i++)
+    {
+      int nodesInFace = ptIds[id];
+      id += (nodesInFace + 1);
+      if (i == face_ind - 1)
+      {
+        nbNodes = nodesInFace;
+        break;
+      }
+    }
+  }
+  return nbNodes;
+}
+
+/*! polyhedron only,
+ *  1 <= face_ind <= NbFaces()
+ *  1 <= node_ind <= NbFaceNodes()
+ */
+const SMDS_MeshNode* SMDS_VtkVolume::GetFaceNode(const int face_ind, const int node_ind) const
+{
+  SMDS_Mesh *mesh = SMDS_Mesh::_meshList[myMeshId];
+  vtkUnstructuredGrid* grid = mesh->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  const SMDS_MeshNode* node = 0;
+  if (aVtkType == VTK_POLYHEDRON)
+  {
+    vtkIdType nFaces = 0;
+    vtkIdType* ptIds = 0;
+    grid->GetFaceStream(this->myVtkID, nFaces, ptIds);
+    int id = 0;
+    for (int i = 0; i < nFaces; i++)
+    {
+      int nodesInFace = ptIds[id]; // nodeIds in ptIds[id+1 .. id+nodesInFace]
+      if (i == face_ind - 1) // first face is number 1
+      {
+        if ((node_ind > 0) && (node_ind <= nodesInFace))
+          node = mesh->FindNodeVtk(ptIds[id + node_ind]); // ptIds[id+1] : first node
+        break;
+      }
+      id += (nodesInFace + 1);
+    }
+  }
+  return node;
+}
+
+/*! polyhedron only,
+ *  return number of nodes for each face
+ */
+std::vector<int> SMDS_VtkVolume::GetQuantities() const
+{
+  std::vector<int> quantities;
+  SMDS_Mesh *mesh = SMDS_Mesh::_meshList[myMeshId];
+  vtkUnstructuredGrid* grid = mesh->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  if (aVtkType == VTK_POLYHEDRON)
+  {
+    vtkIdType nFaces = 0;
+    vtkIdType* ptIds = 0;
+    grid->GetFaceStream(this->myVtkID, nFaces, ptIds);
+    int id = 0;
+    for (int i = 0; i < nFaces; i++)
+    {
+      int nodesInFace = ptIds[id]; // nodeIds in ptIds[id+1 .. id+nodesInFace]
+      quantities.push_back(nodesInFace);
+      id += (nodesInFace + 1);
+    }
+  }
+  return quantities;
+}
+
+SMDS_ElemIteratorPtr SMDS_VtkVolume::elementsIterator(SMDSAbs_ElementType type) const
+{
+  switch (type)
+  {
+    case SMDSAbs_Node:
+      {
+        SMDSAbs_EntityType aType = this->GetEntityType();
+        if (aType == SMDSEntity_Polyhedra)
+          return SMDS_ElemIteratorPtr(new SMDS_VtkCellIteratorPolyH(SMDS_Mesh::_meshList[myMeshId], myVtkID, aType));
+        else
+          return SMDS_ElemIteratorPtr(new SMDS_VtkCellIterator(SMDS_Mesh::_meshList[myMeshId], myVtkID, aType));
+      }
+    default:
+      MESSAGE("ERROR : Iterator not implemented");
+      return SMDS_ElemIteratorPtr((SMDS_ElemIterator*) NULL);
+  }
+}
+
+SMDS_NodeIteratorPtr SMDS_VtkVolume::nodesIteratorToUNV() const
+{
+  return SMDS_NodeIteratorPtr(new SMDS_VtkCellIteratorToUNV(SMDS_Mesh::_meshList[myMeshId], myVtkID, GetEntityType()));
+}
+
+SMDS_NodeIteratorPtr SMDS_VtkVolume::interlacedNodesIterator() const
+{
+  return SMDS_NodeIteratorPtr(new SMDS_VtkCellIteratorToUNV(SMDS_Mesh::_meshList[myMeshId], myVtkID, GetEntityType()));
+}
+
+SMDSAbs_ElementType SMDS_VtkVolume::GetType() const
+{
+  return SMDSAbs_Volume;
+}
+
+/*!
+ * \brief Return node by its index
+ * \param ind - node index
+ * \retval const SMDS_MeshNode* - the node
+ */
+const SMDS_MeshNode* SMDS_VtkVolume::GetNode(const int ind) const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  if ( aVtkType == VTK_POLYHEDRON)
+  {
+    vtkIdType nFaces = 0;
+    vtkIdType* ptIds = 0;
+    grid->GetFaceStream(this->myVtkID, nFaces, ptIds);
+    int id = 0, nbPoints = 0;
+    for (int i = 0; i < nFaces; i++)
+    {
+      int nodesInFace = ptIds[id];
+      if ( ind < nbPoints + nodesInFace )
+        return SMDS_Mesh::_meshList[myMeshId]->FindNodeVtk( ptIds[ ind + i ]);
+      nbPoints += nodesInFace;
+      id += (nodesInFace + 1);
+    }
+    return 0;
+  }
+  vtkIdType npts, *pts;
+  grid->GetCellPoints( this->myVtkID, npts, pts );
+  const std::vector<int>& interlace = SMDS_MeshCell::fromVtkOrder( VTKCellType( aVtkType ));
+  return SMDS_Mesh::_meshList[myMeshId]->FindNodeVtk( pts[ interlace.empty() ? ind : interlace[ind]] );
+}
+/*!
+ * \brief Check if a node belongs to the element
+ * \param node - the node to check
+ * \retval int - node index within the element, -1 if not found
+ */
+int SMDS_VtkVolume::GetNodeIndex( const SMDS_MeshNode* node ) const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  const  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  if ( aVtkType == VTK_POLYHEDRON)
+  {
+    vtkIdType nFaces = 0;
+    vtkIdType* ptIds = 0;
+    grid->GetFaceStream(this->myVtkID, nFaces, ptIds);
+    int id = 0;
+    for (int iF = 0; iF < nFaces; iF++)
+    {
+      int nodesInFace = ptIds[id];
+      for ( vtkIdType i = 0; i < nodesInFace; ++i )
+        if ( ptIds[id+i+1] == node->getVtkId() )
+          return id+i-iF;
+      id += (nodesInFace + 1);
+    }
+    return -1;
+  }
+  vtkIdType npts, *pts;
+  grid->GetCellPoints( this->myVtkID, npts, pts );
+  for ( vtkIdType i = 0; i < npts; ++i )
+    if ( pts[i] == node->getVtkId() )
+    {
+      const std::vector<int>& interlace = SMDS_MeshCell::toVtkOrder( VTKCellType( aVtkType ));
+      return interlace.empty() ? i : interlace[i];
+    }
+  return -1;
+}
+
+bool SMDS_VtkVolume::IsQuadratic() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  // TODO quadratic polyhedrons ?
+  switch (aVtkType)
+  {
+    case VTK_QUADRATIC_TETRA:
+    case VTK_QUADRATIC_PYRAMID:
+    case VTK_QUADRATIC_WEDGE:
+    case VTK_BIQUADRATIC_QUADRATIC_WEDGE:
+    case VTK_QUADRATIC_HEXAHEDRON:
+    case VTK_TRIQUADRATIC_HEXAHEDRON:
+      return true;
+      break;
+    default:
+      return false;
+  }
+}
+
+bool SMDS_VtkVolume::IsPoly() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  return (aVtkType == VTK_POLYHEDRON);
+}
+
+bool SMDS_VtkVolume::IsMediumNode(const SMDS_MeshNode* node) const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+  int rankFirstMedium = 0;
+  switch (aVtkType)
+  {
+    case VTK_QUADRATIC_TETRA:
+      rankFirstMedium = 4; // medium nodes are of rank 4 to 9
+      break;
+    case VTK_QUADRATIC_PYRAMID:
+      rankFirstMedium = 5; // medium nodes are of rank 5 to 12
+      break;
+    case VTK_QUADRATIC_WEDGE:
+    case VTK_BIQUADRATIC_QUADRATIC_WEDGE:
+      rankFirstMedium = 6; // medium nodes are of rank 6 to 14
+      break;
+    case VTK_QUADRATIC_HEXAHEDRON:
+    case VTK_TRIQUADRATIC_HEXAHEDRON:
+      rankFirstMedium = 8; // medium nodes are of rank 8 to 19
+      break;
+    default:
+      return false;
+  }
+  vtkIdType npts = 0;
+  vtkIdType* pts = 0;
+  grid->GetCellPoints(myVtkID, npts, pts);
+  vtkIdType nodeId = node->getVtkId();
+  for (int rank = 0; rank < npts; rank++)
+  {
+    if (pts[rank] == nodeId)
+    {
+      if (rank < rankFirstMedium)
+        return false;
+      else
+        return true;
+    }
+  }
+  MESSAGE("======================================================");
+  MESSAGE("= IsMediumNode: node does not belong to this element =");
+  MESSAGE("======================================================");
+  return false;
+}
+
+int SMDS_VtkVolume::NbCornerNodes() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(myVtkID);
+  switch (aVtkType)
+  {
+  case VTK_QUADRATIC_TETRA:             return 4;
+  case VTK_QUADRATIC_PYRAMID:           return 5;
+  case VTK_QUADRATIC_WEDGE:
+  case VTK_BIQUADRATIC_QUADRATIC_WEDGE: return 6;
+  case VTK_QUADRATIC_HEXAHEDRON:
+  case VTK_TRIQUADRATIC_HEXAHEDRON:     return 8;
+  default:;
+  }
+  return NbNodes();
+}
+
+SMDSAbs_EntityType SMDS_VtkVolume::GetEntityType() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+
+  SMDSAbs_EntityType aType = SMDSEntity_Tetra;
+  switch (aVtkType)
+  {
+    case VTK_TETRA:
+      aType = SMDSEntity_Tetra;
+      break;
+    case VTK_PYRAMID:
+      aType = SMDSEntity_Pyramid;
+      break;
+    case VTK_WEDGE:
+      aType = SMDSEntity_Penta;
+      break;
+    case VTK_HEXAHEDRON:
+      aType = SMDSEntity_Hexa;
+      break;
+    case VTK_QUADRATIC_TETRA:
+      aType = SMDSEntity_Quad_Tetra;
+      break;
+    case VTK_QUADRATIC_PYRAMID:
+      aType = SMDSEntity_Quad_Pyramid;
+      break;
+    case VTK_QUADRATIC_WEDGE:
+      aType = SMDSEntity_Quad_Penta;
+      break;
+    case VTK_BIQUADRATIC_QUADRATIC_WEDGE:
+      aType = SMDSEntity_BiQuad_Penta;
+      break;
+    case VTK_QUADRATIC_HEXAHEDRON:
+      aType = SMDSEntity_Quad_Hexa;
+      break;
+    case VTK_TRIQUADRATIC_HEXAHEDRON:
+      aType = SMDSEntity_TriQuad_Hexa;
+      break;
+    case VTK_HEXAGONAL_PRISM:
+      aType = SMDSEntity_Hexagonal_Prism;
+      break;
+    case VTK_POLYHEDRON:
+      aType = SMDSEntity_Polyhedra;
+      break;
+    default:
+      aType = SMDSEntity_Polyhedra;
+      break;
+  }
+  return aType;
+}
+
+SMDSAbs_GeometryType SMDS_VtkVolume::GetGeomType() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aVtkType = grid->GetCellType(this->myVtkID);
+
+  SMDSAbs_GeometryType aType = SMDSGeom_NONE;
+  switch (aVtkType)
+  {
+    case VTK_TETRA:
+    case VTK_QUADRATIC_TETRA:
+      aType = SMDSGeom_TETRA;
+      break;
+    case VTK_PYRAMID:
+    case VTK_QUADRATIC_PYRAMID:
+      aType = SMDSGeom_PYRAMID;
+      break;
+    case VTK_WEDGE:
+    case VTK_QUADRATIC_WEDGE:
+    case VTK_BIQUADRATIC_QUADRATIC_WEDGE:
+      aType = SMDSGeom_PENTA;
+      break;
+    case VTK_HEXAHEDRON:
+    case VTK_QUADRATIC_HEXAHEDRON:
+    case VTK_TRIQUADRATIC_HEXAHEDRON:
+      aType = SMDSGeom_HEXA;
+      break;
+    case VTK_HEXAGONAL_PRISM:
+      aType = SMDSGeom_HEXAGONAL_PRISM;
+      break;
+    case VTK_POLYHEDRON:
+      aType = SMDSGeom_POLYHEDRA;
+      break;
+    default:
+      aType = SMDSGeom_POLYHEDRA;
+      break;
+  }
+  return aType;
+}
+
+vtkIdType SMDS_VtkVolume::GetVtkType() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  vtkIdType aType = grid->GetCellType(myVtkID);
+  return aType;
+}
+
+void SMDS_VtkVolume::gravityCenter(SMDS_UnstructuredGrid* grid,
+                                   const vtkIdType *      nodeIds,
+                                   int                    nbNodes,
+                                   double*                result)
+{
+  for (int j = 0; j < 3; j++)
+    result[j] = 0;
+  if (nbNodes <= 0)
+    return;
+  for (int i = 0; i < nbNodes; i++)
+    {
+      double *coords = grid->GetPoint(nodeIds[i]);
+      for (int j = 0; j < 3; j++)
+        result[j] += coords[j];
+    }
+  for (int j = 0; j < 3; j++)
+    result[j] = result[j] / nbNodes;
+  return;
+}
+
+bool SMDS_VtkVolume::isForward(double* a, double* b, double* c, double* d)
+{
+  double u[3], v[3], w[3];
+  for (int j = 0; j < 3; j++)
+  {
+    u[j] = b[j] - a[j];
+    v[j] = c[j] - a[j];
+    w[j] = d[j] - a[j];
+  }
+  double prodmixte = ((u[1]*v[2] - u[2]*v[1]) * w[0]
+                      + (u[2]*v[0] - u[0]*v[2]) * w[1]
+                      + (u[0]*v[1] - u[1]*v[0]) * w[2] );
+  return (prodmixte < 0);
+}
+
+/*! For polyhedron only
+ *  @return actual number of nodes (not the sum of nodes of all faces)
+ */
+int SMDS_VtkVolume::NbUniqueNodes() const
+{
+  vtkUnstructuredGrid* grid = SMDS_Mesh::_meshList[myMeshId]->getGrid();
+  return grid->GetCell(myVtkID)->GetNumberOfPoints();
+}
+
+/*! For polyhedron use only
+ *  @return iterator on actual nodes (not through the faces)
+ */
+SMDS_ElemIteratorPtr SMDS_VtkVolume::uniqueNodesIterator() const
+{
+  return SMDS_ElemIteratorPtr(new SMDS_VtkCellIterator(SMDS_Mesh::_meshList[myMeshId], myVtkID, GetEntityType()));
+}
diff --git a/src/SMDS/SMDS_VtkVolume.hxx b/src/SMDS/SMDS_VtkVolume.hxx
new file mode 100644 (file)
index 0000000..02f86ce
--- /dev/null
@@ -0,0 +1,80 @@
+// Copyright (C) 2010-2016  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+#ifndef _SMDS_VTKVOLUME_HXX_
+#define _SMDS_VTKVOLUME_HXX_
+
+#include "SMESH_SMDS.hxx"
+
+#include "SMDS_MeshVolume.hxx"
+#include "SMDS_UnstructuredGrid.hxx"
+#include <vector>
+
+class SMDS_EXPORT SMDS_VtkVolume: public SMDS_MeshVolume
+{
+public:
+  SMDS_VtkVolume();
+  SMDS_VtkVolume(const std::vector<vtkIdType>& nodeIds, SMDS_Mesh* mesh);
+  ~SMDS_VtkVolume();
+  void init(const std::vector<vtkIdType>& nodeIds, SMDS_Mesh* mesh);
+//#ifdef VTK_HAVE_POLYHEDRON
+  void initPoly(const std::vector<vtkIdType>& nodeIds,
+                const std::vector<int>& nbNodesPerFace, SMDS_Mesh* mesh);
+//#endif
+  virtual bool ChangeNodes(const SMDS_MeshNode* nodes[], const int nbNodes);
+  virtual bool vtkOrder(const SMDS_MeshNode* nodes[], const int nbNodes);
+
+  virtual void Print(std::ostream & OS) const;
+  virtual int NbFaces() const;
+  virtual int NbNodes() const;
+  virtual int NbEdges() const;
+
+  // 1 <= face_ind <= NbFaces()
+  int NbFaceNodes (const int face_ind) const;
+  // 1 <= face_ind <= NbFaces()
+  // 1 <= node_ind <= NbFaceNodes()
+  const SMDS_MeshNode* GetFaceNode (const int face_ind, const int node_ind) const;
+
+  virtual SMDSAbs_ElementType  GetType() const;
+  virtual vtkIdType            GetVtkType() const;
+  virtual SMDSAbs_EntityType   GetEntityType() const;
+  virtual SMDSAbs_GeometryType GetGeomType() const;
+  virtual const SMDS_MeshNode* GetNode(const int ind) const;
+  virtual int GetNodeIndex( const SMDS_MeshNode* node ) const;
+  virtual bool IsQuadratic() const;
+  virtual bool IsPoly() const;
+  virtual bool IsMediumNode(const SMDS_MeshNode* node) const;
+  virtual int  NbCornerNodes() const;
+  static void gravityCenter(SMDS_UnstructuredGrid* grid,
+                            const vtkIdType *nodeIds,
+                            int nbNodes,
+                            double* result);
+  static bool isForward(double* a,double* b,double* c,double* d);
+  int NbUniqueNodes() const;
+  SMDS_ElemIteratorPtr uniqueNodesIterator() const;
+  std::vector<int> GetQuantities() const;
+
+  virtual SMDS_ElemIteratorPtr elementsIterator(SMDSAbs_ElementType type) const;
+  virtual SMDS_NodeIteratorPtr nodesIteratorToUNV() const;
+  virtual SMDS_NodeIteratorPtr interlacedNodesIterator() const;
+
+protected:
+};
+
+#endif
index d0ee85cb8fe61a136f752405ef01baf5f721d9ee..561f64471f04bd14af51428a18bacd5de113570e 100644 (file)
@@ -358,9 +358,12 @@ bool SMESH_Algo::GetNodeParamOnEdge(const SMESHDS_Mesh* theMesh,
     SMDS_NodeIteratorPtr nIt = eSubMesh->GetNodes();
     while ( nIt->more() )
     {
-      SMDS_EdgePositionPtr epos = nIt->next()->GetPosition();
-      if ( !epos )
+      const SMDS_MeshNode* node = nIt->next();
+      const SMDS_PositionPtr& pos = node->GetPosition();
+      if ( pos->GetTypeOfPosition() != SMDS_TOP_EDGE )
         return false;
+      const SMDS_EdgePosition* epos =
+        static_cast<const SMDS_EdgePosition*>(node->GetPosition());
       if ( !paramSet.insert( epos->GetUParameter() ).second )
         return false; // equal parameters
     }
@@ -421,9 +424,11 @@ bool SMESH_Algo::GetSortedNodesOnEdge(const SMESHDS_Mesh*                   theM
       const SMDS_MeshNode* node = nIt->next();
       if ( ignoreMediumNodes && SMESH_MesherHelper::IsMedium( node, typeToCheck ))
         continue;
-      SMDS_EdgePositionPtr epos = node->GetPosition();
-      if ( ! epos )
+      const SMDS_PositionPtr& pos = node->GetPosition();
+      if ( pos->GetTypeOfPosition() != SMDS_TOP_EDGE )
         return false;
+      const SMDS_EdgePosition* epos =
+        static_cast<const SMDS_EdgePosition*>(node->GetPosition());
       theNodes.insert( theNodes.end(), make_pair( epos->GetUParameter(), node ));
       ++nbNodes;
     }
@@ -909,12 +914,7 @@ bool SMESH_Algo::error(SMESH_ComputeErrorPtr error)
   if ( error ) {
     _error   = error->myName;
     _comment = error->myComment;
-    if ( error->HasBadElems() )
-    {
-      SMESH_BadInputElements* badElems = static_cast<SMESH_BadInputElements*>( error.get() );
-      _badInputElements = badElems->GetElements();
-      _mesh             = badElems->GetMesh();
-    }
+    _badInputElements = error->myBadElements;
     return error->IsOK();
   }
   return true;
@@ -928,15 +928,11 @@ bool SMESH_Algo::error(SMESH_ComputeErrorPtr error)
 
 SMESH_ComputeErrorPtr SMESH_Algo::GetComputeError() const
 {
-  if ( !_badInputElements.empty() && _mesh )
-  {
-    SMESH_BadInputElements* err = new SMESH_BadInputElements( _mesh, _error, _comment, this );
-    // hope this method is called by only SMESH_subMesh after this->Compute()
-    err->myBadElements.splice( err->myBadElements.end(),
-                               (list<const SMDS_MeshElement*>&) _badInputElements );
-    return SMESH_ComputeErrorPtr( err );
-  }
-  return SMESH_ComputeError::New( _error, _comment, this );
+  SMESH_ComputeErrorPtr err = SMESH_ComputeError::New( _error, _comment, this );
+  // hope this method is called by only SMESH_subMesh after this->Compute()
+  err->myBadElements.splice( err->myBadElements.end(),
+                             (list<const SMDS_MeshElement*>&) _badInputElements );
+  return err;
 }
 
 //================================================================================
@@ -954,7 +950,6 @@ void SMESH_Algo::InitComputeError()
     if ( (*elem)->GetID() < 1 )
       delete *elem;
   _badInputElements.clear();
-  _mesh = 0;
 
   _computeCanceled = false;
   _progressTic     = 0;
@@ -1248,7 +1243,7 @@ bool SMESH_2D_Algo::FixInternalNodes(const SMESH_ProxyMesh& mesh,
       gp_Pnt p = S->Value( uv.Coord(1), uv.Coord(2));
       const SMDS_MeshNode* n = nodeRows[iRow][iCol];
       meshDS->MoveNode( n, p.X(), p.Y(), p.Z() );
-      if ( SMDS_FacePositionPtr pos = n->GetPosition() )
+      if ( SMDS_FacePosition* pos = dynamic_cast< SMDS_FacePosition*>( n->GetPosition() ))
         pos->SetParameters( uv.Coord(1), uv.Coord(2) );
     }
   }
index cceb370ef09e4d21a407ca9b1b00da7fc0a4d92c..81ff8eb3aabda71a1c9cd8e603110b2395afb9bb 100644 (file)
@@ -462,7 +462,6 @@ protected:
   int         _error;    //!< SMESH_ComputeErrorName or anything algo specific
   std::string _comment;  //!< any text explaining what is wrong in Compute()
   std::list<const SMDS_MeshElement*> _badInputElements; //!< to explain COMPERR_BAD_INPUT_MESH
-  const SMDS_Mesh* _mesh; //!< mesh being computed, needed to create SMESH_BadInputElements
 
   volatile bool _computeCanceled; //!< is set to True while computing to stop it
 
index f87162e45de947a63c8c93497a4f68bead3d03e5..c62e70e32ba4006cb04e535064b53a6e567a90c3 100644 (file)
@@ -54,6 +54,9 @@
 
 using namespace std;
 
+//#include <vtkDebugLeaks.h>
+
+
 //=============================================================================
 /*!
  *  Constructor
@@ -65,7 +68,9 @@ SMESH_Gen::SMESH_Gen()
   _localId = 0;
   _hypId   = 0;
   _segmentation = _nbSegments = 10;
+  SMDS_Mesh::_meshList.clear();
   _compute_canceled = false;
+  //vtkDebugLeaks::SetExitError(0);
 }
 
 namespace
@@ -402,10 +407,8 @@ bool SMESH_Gen::Compute(SMESH_Mesh &          aMesh,
   }
 
   if ( aCompactMesh )
-  {
-    aMesh.GetMeshDS()->Modified();
-    aMesh.GetMeshDS()->CompactMesh();
-  }
+    aMesh.GetMeshDS()->compactMesh();
+
   return ret;
 }
 
index 1dcdd53595ecb66ff5fa662adf984135cb596b6b..3e21e9a1179530cf07bbdfc6d7f9a349c5fefd94 100644 (file)
@@ -450,7 +450,7 @@ void SMESH_Mesh::Clear()
 
 void SMESH_Mesh::ClearSubMesh(const int theShapeId)
 {
-  // clear sub-meshes; get ready to re-compute as a side-effect
+  // clear sub-meshes; get ready to re-compute as a side-effect 
   if ( SMESH_subMesh *sm = GetSubMeshContaining( theShapeId ) )
   {
     SMESH_subMeshIteratorPtr smIt = sm->getDependsOnIterator(/*includeSelf=*/true,
@@ -458,7 +458,7 @@ void SMESH_Mesh::ClearSubMesh(const int theShapeId)
     while ( smIt->more() )
     {
       sm = smIt->next();
-      TopAbs_ShapeEnum shapeType = sm->GetSubShape().ShapeType();
+      TopAbs_ShapeEnum shapeType = sm->GetSubShape().ShapeType();      
       if ( shapeType == TopAbs_VERTEX || shapeType < TopAbs_SOLID )
         // all other shapes depends on vertices so they are already cleaned
         sm->ComputeStateEngine( SMESH_subMesh::CLEAN );
@@ -470,7 +470,7 @@ void SMESH_Mesh::ClearSubMesh(const int theShapeId)
 
 //=======================================================================
 //function : UNVToMesh
-//purpose  :
+//purpose  : 
 //=======================================================================
 
 int SMESH_Mesh::UNVToMesh(const char* theFileName)
@@ -485,19 +485,32 @@ int SMESH_Mesh::UNVToMesh(const char* theFileName)
   myReader.SetMeshId(-1);
   myReader.Perform();
 
-  TGroupNamesMap& aGroupNames = myReader.GetGroupNamesMap();
-  TGroupNamesMap::iterator gr2names;
-  int anId = 1 + ( _mapGroup.empty() ? 0 : _mapGroup.rbegin()->first );
-  for ( gr2names = aGroupNames.begin(); gr2names != aGroupNames.end(); ++gr2names )
+  if ( SMDS_MeshGroup* aGroup = (SMDS_MeshGroup*) myReader.GetGroup() )
   {
-    SMDS_MeshGroup*   aGroup = gr2names->first;
-    const std::string& aName = gr2names->second;
-    SMESHDS_Group* aGroupDS = new SMESHDS_Group( anId++, _myMeshDS, aGroup->GetType() );
-    aGroupDS->SMDSGroup() = std::move( *aGroup );
-    aGroupDS->SetStoreName( aName.c_str() );
-    AddGroup( aGroupDS );
+    TGroupNamesMap aGroupNames = myReader.GetGroupNamesMap();
+    aGroup->InitSubGroupsIterator();
+    while (aGroup->MoreSubGroups())
+    {
+      SMDS_MeshGroup* aSubGroup = (SMDS_MeshGroup*) aGroup->NextSubGroup();
+      string aName = aGroupNames[aSubGroup];
+      int aId;
+      if ( SMESH_Group* aSMESHGroup = AddGroup( aSubGroup->GetType(), aName.c_str(), aId ))
+      {
+        SMESHDS_Group* aGroupDS = dynamic_cast<SMESHDS_Group*>( aSMESHGroup->GetGroupDS() );
+        if ( aGroupDS ) {
+          aGroupDS->SetStoreName(aName.c_str());
+          aSubGroup->InitIterator();
+          const SMDS_MeshElement* aElement = 0;
+          while ( aSubGroup->More() )
+            if (( aElement = aSubGroup->Next() ))
+              aGroupDS->SMDSGroup().Add( aElement );
+
+          if (aElement)
+            aGroupDS->SetType( aElement->GetType() );
+        }
+      }
+    }
   }
-
   return 1;
 }
 
@@ -538,16 +551,12 @@ int SMESH_Mesh::MEDToMesh(const char* theFileName, const char* theMeshName)
       }
     }
   }
-
-  _myMeshDS->Modified();
-  _myMeshDS->CompactMesh();
-
   return (int) status;
 }
 
 //=======================================================================
 //function : STLToMesh
-//purpose  :
+//purpose  : 
 //=======================================================================
 
 std::string SMESH_Mesh::STLToMesh(const char* theFileName)
index e9dbc5a32ed3b43bb4fa4cadc23a58de98833919..9b581c9cefcda6558de97d2738d59b8f5e53f06d 100644 (file)
@@ -162,7 +162,7 @@ SMESH_MeshEditor::ElemFeatures::Init( const SMDS_MeshElement* elem, bool basicOn
         myIsQuad = elem->IsQuadratic();
         if ( myType == SMDSAbs_Volume && !basicOnly )
         {
-          vector<int> quant = static_cast<const SMDS_MeshVolume* >( elem )->GetQuantities();
+          vector<int > quant = static_cast<const SMDS_VtkVolume* >( elem )->GetQuantities();
           myPolyhedQuantities.swap( quant );
         }
       }
@@ -682,16 +682,16 @@ bool SMESH_MeshEditor::InverseDiag (const SMDS_MeshElement * theTria1,
 {
   ClearLastCreated();
 
-  if ( !theTria1 || !theTria2 ||
-       !dynamic_cast<const SMDS_MeshCell*>( theTria1 ) ||
-       !dynamic_cast<const SMDS_MeshCell*>( theTria2 ) ||
-       theTria1->GetType() != SMDSAbs_Face ||
-       theTria2->GetType() != SMDSAbs_Face )
+  if (!theTria1 || !theTria2)
     return false;
 
+  const SMDS_VtkFace* F1 = dynamic_cast<const SMDS_VtkFace*>( theTria1 );
+  if (!F1) return false;
+  const SMDS_VtkFace* F2 = dynamic_cast<const SMDS_VtkFace*>( theTria2 );
+  if (!F2) return false;
   if ((theTria1->GetEntityType() == SMDSEntity_Triangle) &&
-      (theTria2->GetEntityType() == SMDSEntity_Triangle))
-  {
+      (theTria2->GetEntityType() == SMDSEntity_Triangle)) {
+
     //  1 +--+ A  theTria1: ( 1 A B ) A->2 ( 1 2 B ) 1 +--+ A
     //    | /|    theTria2: ( B A 2 ) B->1 ( 1 A 2 )   |\ |
     //    |/ |                                         | \|
@@ -805,9 +805,9 @@ bool SMESH_MeshEditor::InverseDiag (const SMDS_MeshElement * theTria1,
     gp_Pnt xyz;
     if ( F.IsNull() )
     {
-      xyz = ( SMESH_NodeXYZ( nodes[3] ) +
-              SMESH_NodeXYZ( nodes[4] ) +
-              SMESH_NodeXYZ( nodes[5] )) / 3.;
+      xyz = ( SMESH_TNodeXYZ( nodes[3] ) +
+              SMESH_TNodeXYZ( nodes[4] ) +
+              SMESH_TNodeXYZ( nodes[5] )) / 3.;
     }
     else
     {
@@ -886,10 +886,10 @@ bool SMESH_MeshEditor::InverseDiag (const SMDS_MeshNode * theNode1,
   if ( !findTriangles( theNode1, theNode2, tr1, tr2 ))
     return false;
 
-  if ( !dynamic_cast<const SMDS_MeshCell*>( tr1 ) ||
-       !dynamic_cast<const SMDS_MeshCell*>( tr2 ))
-    return false;
-
+  const SMDS_VtkFace* F1 = dynamic_cast<const SMDS_VtkFace*>( tr1 );
+  if (!F1) return false;
+  const SMDS_VtkFace* F2 = dynamic_cast<const SMDS_VtkFace*>( tr2 );
+  if (!F2) return false;
   if ((tr1->GetEntityType() == SMDSEntity_Triangle) &&
       (tr2->GetEntityType() == SMDSEntity_Triangle)) {
 
@@ -1006,15 +1006,15 @@ bool SMESH_MeshEditor::DeleteDiag (const SMDS_MeshNode * theNode1,
   if ( !findTriangles( theNode1, theNode2, tr1, tr2 ))
     return false;
 
-  if ( !dynamic_cast<const SMDS_MeshCell*>( tr1 ) ||
-       !dynamic_cast<const SMDS_MeshCell*>( tr2 ))
-    return false;
-
+  const SMDS_VtkFace* F1 = dynamic_cast<const SMDS_VtkFace*>( tr1 );
+  if (!F1) return false;
+  const SMDS_VtkFace* F2 = dynamic_cast<const SMDS_VtkFace*>( tr2 );
+  if (!F2) return false;
   SMESHDS_Mesh * aMesh = GetMeshDS();
 
   if ((tr1->GetEntityType() == SMDSEntity_Triangle) &&
-      (tr2->GetEntityType() == SMDSEntity_Triangle))
-  {
+      (tr2->GetEntityType() == SMDSEntity_Triangle)) {
+
     const SMDS_MeshNode* aNodes [ 4 ];
     if ( ! getQuadrangleNodes( aNodes, theNode1, theNode2, tr1, tr2 ))
       return false;
@@ -1025,8 +1025,9 @@ bool SMESH_MeshEditor::DeleteDiag (const SMDS_MeshNode * theNode1,
     AddToSameGroups( newElem, tr1, aMesh );
     int aShapeId = tr1->getshapeId();
     if ( aShapeId )
+    {
       aMesh->SetMeshElementOnShape( newElem, aShapeId );
-
+    }
     aMesh->RemoveElement( tr1 );
     aMesh->RemoveElement( tr2 );
 
@@ -1108,7 +1109,8 @@ bool SMESH_MeshEditor::Reorient (const SMDS_MeshElement * theElem)
   const SMDSAbs_EntityType geomType = theElem->GetEntityType();
   if ( geomType == SMDSEntity_Polyhedra ) // polyhedron
   {
-    const SMDS_MeshVolume* aPolyedre = SMDS_Mesh::DownCast< SMDS_MeshVolume >( theElem );
+    const SMDS_VtkVolume* aPolyedre =
+      dynamic_cast<const SMDS_VtkVolume*>( theElem );
     if (!aPolyedre) {
       MESSAGE("Warning: bad volumic element");
       return false;
@@ -1166,7 +1168,7 @@ int SMESH_MeshEditor::Reorient2D (TIDSortedElemSet &       theFaces,
 
   if ( theFaces.empty() )
   {
-    SMDS_FaceIteratorPtr fIt = GetMeshDS()->facesIterator(/*idInceasingOrder=true*/);
+    SMDS_FaceIteratorPtr fIt = GetMeshDS()->facesIterator(/*idInceasingOrder=*/true);
     while ( fIt->more() )
       theFaces.insert( theFaces.end(), fIt->next() );
   }
@@ -1554,7 +1556,7 @@ void SMESH_MeshEditor::QuadTo4Tri (TIDSortedElemSet & theElems)
       if ( F.IsNull() )
       {
         for ( ; iN < nodes.size(); ++iN )
-          xyz[ iN ] = SMESH_NodeXYZ( nodes[ iN ] );
+          xyz[ iN ] = SMESH_TNodeXYZ( nodes[ iN ] );
 
         for ( ; iN < 8; ++iN ) // mid-side points of a linear qudrangle
           xyz[ iN ] = 0.5 * ( xyz[ iN - 4 ] + xyz[( iN - 3 )%4 ] );
@@ -2359,7 +2361,7 @@ void SMESH_MeshEditor::SplitVolumes (const TFacetOfElem & theElems,
           if ( fSubMesh ) // update position of the bary node on geometry
           {
             if ( subMesh )
-              subMesh->RemoveNode( baryNode );
+              subMesh->RemoveNode( baryNode, false );
             GetMeshDS()->SetNodeOnFace( baryNode, fSubMesh->GetID() );
             const TopoDS_Shape& s = GetMeshDS()->IndexToShape( fSubMesh->GetID() );
             if ( !s.IsNull() && s.ShapeType() == TopAbs_FACE )
@@ -3828,7 +3830,7 @@ void SMESH_MeshEditor::Smooth (TIDSortedElemSet &          theElems,
         // }
         if ( project ) { // compute new UV
           gp_XY newUV;
-          gp_Pnt pNode = SMESH_NodeXYZ( node );
+          gp_Pnt pNode = SMESH_TNodeXYZ( node );
           if ( !getClosestUV( projector, pNode, newUV )) {
             MESSAGE("Node Projection Failed " << node);
           }
@@ -4083,7 +4085,7 @@ void SMESH_MeshEditor::Smooth (TIDSortedElemSet &          theElems,
         const SMDS_MeshElement* QF = *elemIt;
         if ( QF->IsQuadratic() )
         {
-          nodes.assign( SMDS_MeshElement::iterator( QF->interlacedNodesIterator() ),
+          nodes.assign( SMDS_MeshElement::iterator( QF->interlacedNodesElemIterator() ),
                         SMDS_MeshElement::iterator() );
           nodes.push_back( nodes[0] );
           gp_Pnt xyz;
@@ -4097,9 +4099,9 @@ void SMESH_MeshEditor::Smooth (TIDSortedElemSet &          theElems,
               xyz = surface->Value( uv.X(), uv.Y() );
             }
             else {
-              xyz = 0.5 * ( SMESH_NodeXYZ( nodes[i-1] ) + SMESH_NodeXYZ( nodes[i+1] ));
+              xyz = 0.5 * ( SMESH_TNodeXYZ( nodes[i-1] ) + SMESH_TNodeXYZ( nodes[i+1] ));
             }
-            if (( SMESH_NodeXYZ( nodes[i] ) - xyz.XYZ() ).Modulus() > disttol )
+            if (( SMESH_TNodeXYZ( nodes[i] ) - xyz.XYZ() ).Modulus() > disttol )
               // we have to move a medium node
               aMesh->MoveNode( nodes[i], xyz.X(), xyz.Y(), xyz.Z() );
           }
@@ -4127,8 +4129,8 @@ namespace
                  const int                           iNotSame)
   {
 
-    SMESH_NodeXYZ pP = prevNodes[ iNotSame ];
-    SMESH_NodeXYZ pN = nextNodes[ iNotSame ];
+    SMESH_TNodeXYZ pP = prevNodes[ iNotSame ];
+    SMESH_TNodeXYZ pN = nextNodes[ iNotSame ];
     gp_XYZ extrDir( pN - pP ), faceNorm;
     SMESH_MeshAlgos::FaceNormal( face, faceNorm, /*normalized=*/false );
 
@@ -4832,9 +4834,9 @@ void SMESH_MeshEditor::makeWalls (TNodeOfNodeListMap &     mapNewNodes,
         SMDS_VolumeTool vTool( *v, /*ignoreCentralNodes=*/false );
         int iF, nbF = vTool.NbFaces();
         for ( iF = 0; iF < nbF; iF ++ ) {
-          if ( vTool.IsFreeFace( iF ) &&
-               vTool.GetFaceNodes( iF, faceNodeSet ) &&
-               initNodeSet != faceNodeSet) // except an initial face
+          if (vTool.IsFreeFace( iF ) &&
+              vTool.GetFaceNodes( iF, faceNodeSet ) &&
+              initNodeSet != faceNodeSet) // except an initial face
           {
             if ( nbSteps == 1 && faceNodeSet == topNodeSet )
               continue;
@@ -5323,7 +5325,7 @@ void SMESH_MeshEditor::ExtrusParam::SetElementsToUse( const TIDSortedElemSet& el
         while ( itN->more() ) {
           const SMDS_MeshElement* node = itN->next();
           if ( newNodes.insert( node ).second )
-            myBaseP += SMESH_NodeXYZ( node );
+            myBaseP += SMESH_TNodeXYZ( node );
         }
       }
     }
@@ -5389,7 +5391,7 @@ makeNodesByDir( SMESHDS_Mesh*                     mesh,
                 std::list<const SMDS_MeshNode*> & newNodes,
                 const bool                        makeMediumNodes)
 {
-  gp_XYZ p = SMESH_NodeXYZ( srcNode );
+  gp_XYZ p = SMESH_TNodeXYZ( srcNode );
 
   int nbNodes = 0;
   for ( beginStepIter( makeMediumNodes ); moreSteps(); ++nbNodes ) // loop on steps
@@ -5426,7 +5428,7 @@ makeNodesByDir( SMESHDS_Mesh*                     mesh,
       iSc += int( makeMediumNodes );
       ScaleIt& scale = scales[ iSc % 2 ];
       
-      gp_XYZ xyz = SMESH_NodeXYZ( *nIt );
+      gp_XYZ xyz = SMESH_TNodeXYZ( *nIt );
       xyz = ( *scale * ( xyz - center )) + center;
       mesh->MoveNode( *nIt, xyz.X(), xyz.Y(), xyz.Z() );
 
@@ -5447,7 +5449,7 @@ makeNodesByDirAndSew( SMESHDS_Mesh*                     mesh,
                       std::list<const SMDS_MeshNode*> & newNodes,
                       const bool                        makeMediumNodes)
 {
-  gp_XYZ P1 = SMESH_NodeXYZ( srcNode );
+  gp_XYZ P1 = SMESH_TNodeXYZ( srcNode );
 
   int nbNodes = 0;
   for ( beginStepIter( makeMediumNodes ); moreSteps(); ++nbNodes ) // loop on steps
@@ -5458,11 +5460,10 @@ makeNodesByDirAndSew( SMESHDS_Mesh*                     mesh,
     // if myNodes.size()>0 we 'nave to use given sequence
     // else - use all nodes of mesh
     const SMDS_MeshNode * node = 0;
-    if ( myNodes.Length() > 0 )
-    {
-      for ( int i = 1; i <= myNodes.Length(); i++ )
-      {
-        SMESH_NodeXYZ P2 = myNodes.Value(i);
+    if ( myNodes.Length() > 0 ) {
+      int i;
+      for ( i = 1; i <= myNodes.Length(); i++ ) {
+        gp_XYZ P2 = SMESH_TNodeXYZ( myNodes.Value(i) );
         if (( P1 - P2 ).SquareModulus() < myTolerance * myTolerance )
         {
           node = myNodes.Value(i);
@@ -5470,12 +5471,10 @@ makeNodesByDirAndSew( SMESHDS_Mesh*                     mesh,
         }
       }
     }
-    else
-    {
+    else {
       SMDS_NodeIteratorPtr itn = mesh->nodesIterator();
-      while(itn->more())
-      {
-        SMESH_NodeXYZ P2 = itn->next();
+      while(itn->more()) {
+        SMESH_TNodeXYZ P2( itn->next() );
         if (( P1 - P2 ).SquareModulus() < myTolerance * myTolerance )
         {
           node = P2._node;
@@ -5507,7 +5506,7 @@ makeNodesByNormal2D( SMESHDS_Mesh*                     mesh,
 {
   const bool alongAvgNorm = ( myFlags & EXTRUSION_FLAG_BY_AVG_NORMAL );
 
-  gp_XYZ p = SMESH_NodeXYZ( srcNode );
+  gp_XYZ p = SMESH_TNodeXYZ( srcNode );
 
   // get normals to faces sharing srcNode
   vector< gp_XYZ > norms, baryCenters;
@@ -5527,7 +5526,7 @@ makeNodesByNormal2D( SMESHDS_Mesh*                     mesh,
         gp_XYZ bc(0,0,0);
         int nbN = 0;
         for ( SMDS_ElemIteratorPtr nIt = face->nodesIterator(); nIt->more(); ++nbN )
-          bc += SMESH_NodeXYZ( nIt->next() );
+          bc += SMESH_TNodeXYZ( nIt->next() );
         baryCenters.push_back( bc / nbN );
       }
     }
@@ -5795,8 +5794,9 @@ SMESH_MeshEditor::ExtrusionAlongTrack (TIDSortedElemSet     theElements[2],
       return EXTR_BAD_STARTING_NODE;
     aItN = pSubMeshDS->GetNodes();
     while ( aItN->more() ) {
-      const SMDS_MeshNode*  pNode = aItN->next();
-      SMDS_EdgePositionPtr pEPos = pNode->GetPosition();
+      const SMDS_MeshNode* pNode = aItN->next();
+      const SMDS_EdgePosition* pEPos =
+        static_cast<const SMDS_EdgePosition*>( pNode->GetPosition() );
       double aT = pEPos->GetUParameter();
       aPrms.push_back( aT );
     }
@@ -5839,7 +5839,8 @@ SMESH_MeshEditor::ExtrusionAlongTrack (TIDSortedElemSet     theElements[2],
         aItN = locMeshDS->GetNodes();
         while ( aItN->more() ) {
           const SMDS_MeshNode* pNode = aItN->next();
-          SMDS_EdgePositionPtr pEPos = pNode->GetPosition();
+          const SMDS_EdgePosition* pEPos =
+            static_cast<const SMDS_EdgePosition*>( pNode->GetPosition() );
           double aT = pEPos->GetUParameter();
           aPrms.push_back( aT );
         }
@@ -5961,7 +5962,7 @@ SMESH_MeshEditor::ExtrusionAlongTrack (TIDSortedElemSet     theElements[2],
     SMDS_ElemIteratorPtr nIt;
 
     //check start node
-    if( !theTrack->GetMeshDS()->Contains( theN1 )) {
+    if( !theTrack->GetMeshDS()->Contains(theN1) ) {
       return EXTR_BAD_STARTING_NODE;
     }
 
@@ -6021,8 +6022,8 @@ SMESH_MeshEditor::ExtrusionAlongTrack (TIDSortedElemSet     theElements[2],
     int startNid = theN1->GetID();
     for ( size_t i = 1; i < aNodesList.size(); i++ )
     {
-      gp_Pnt     p1 = SMESH_NodeXYZ( aNodesList[i-1] );
-      gp_Pnt     p2 = SMESH_NodeXYZ( aNodesList[i] );
+      gp_Pnt     p1 = SMESH_TNodeXYZ( aNodesList[i-1] );
+      gp_Pnt     p2 = SMESH_TNodeXYZ( aNodesList[i] );
       TopoDS_Edge e = BRepBuilderAPI_MakeEdge( p1, p2 );
       list<SMESH_MeshEditor_PathPoint> LPP;
       aPrms.clear();
@@ -6078,7 +6079,8 @@ SMESH_MeshEditor::ExtrusionAlongTrack (TIDSortedElemSet     theElements[2],
     while ( aItN->more() ) {
       const SMDS_MeshNode* pNode = aItN->next();
       if( pNode==aN1 || pNode==aN2 ) continue;
-      SMDS_EdgePositionPtr pEPos = pNode->GetPosition();
+      const SMDS_EdgePosition* pEPos =
+        static_cast<const SMDS_EdgePosition*>( pNode->GetPosition() );
       double aT = pEPos->GetUParameter();
       aPrms.push_back( aT );
     }
@@ -6134,8 +6136,9 @@ SMESH_MeshEditor::ExtrusionAlongTrack (TIDSortedElemSet     theElements[2],
         aPrms.clear();
         aItN = locMeshDS->GetNodes();
         while ( aItN->more() ) {
-          const SMDS_MeshNode*  pNode = aItN->next();
-          SMDS_EdgePositionPtr pEPos = pNode->GetPosition();
+          const SMDS_MeshNode*     pNode = aItN->next();
+          const SMDS_EdgePosition* pEPos =
+            static_cast<const SMDS_EdgePosition*>( pNode->GetPosition() );
           double aT = pEPos->GetUParameter();
           aPrms.push_back( aT );
         }
@@ -6293,7 +6296,7 @@ SMESH_MeshEditor::makeExtrElements(TIDSortedElemSet                  theElemSets
         while ( itN->more() ) {
           const SMDS_MeshElement* node = itN->next();
           if ( newNodes.insert( node ).second )
-            aGC += SMESH_NodeXYZ( node );
+            aGC += SMESH_TNodeXYZ( node );
         }
       }
     }
@@ -6337,7 +6340,7 @@ SMESH_MeshEditor::makeExtrElements(TIDSortedElemSet                  theElemSets
           aTolAng=1.e-4;
 
           aV0x = aV0;
-          aPN0 = SMESH_NodeXYZ( node );
+          aPN0 = SMESH_TNodeXYZ( node );
 
           const SMESH_MeshEditor_PathPoint& aPP0 = aPPs[0];
           aP0x = aPP0.Pnt();
@@ -6657,8 +6660,8 @@ SMESH_MeshEditor::Transform (TIDSortedElemSet & theElems,
 
     if ( geomType == SMDSGeom_POLYHEDRA )  // ------------------ polyhedral volume
     {
-      const SMDS_MeshVolume* aPolyedre = SMDS_Mesh::DownCast< SMDS_MeshVolume >( elem );
-      if ( !aPolyedre )
+      const SMDS_VtkVolume* aPolyedre = dynamic_cast<const SMDS_VtkVolume*>( elem );
+      if (!aPolyedre)
         continue;
       nodes.clear();
       bool allTransformed = true;
@@ -7032,7 +7035,7 @@ void SMESH_MeshEditor::FindCoincidentNodes (TIDSortedNodeSet &   theNodes,
   if ( theNodes.empty() ) // get all nodes in the mesh
   {
     TIDSortedNodeSet* nodes[2] = { &corners, &medium };
-    SMDS_NodeIteratorPtr nIt = GetMeshDS()->nodesIterator();
+    SMDS_NodeIteratorPtr nIt = GetMeshDS()->nodesIterator(/*idInceasingOrder=*/true);
     if ( theSeparateCornersAndMedium )
       while ( nIt->more() )
       {
@@ -7220,7 +7223,7 @@ void SMESH_MeshEditor::MergeNodes (TListOfListOfNodes & theGroupsOfNodes,
       AddToSameGroups( nToKeep, nToRemove, mesh );
       // set _alwaysComputed to a sub-mesh of VERTEX to enable further mesh computing
       // w/o creating node in place of merged ones.
-      SMDS_PositionPtr pos = nToRemove->GetPosition();
+      const SMDS_PositionPtr& pos = nToRemove->GetPosition();
       if ( pos && pos->GetTypeOfPosition() == SMDS_TOP_VERTEX )
         if ( SMESH_subMesh* sm = myMesh->GetSubMeshContaining( nToRemove->getshapeId() ))
           sm->SetIsAlwaysComputed( true );
@@ -7408,7 +7411,7 @@ bool SMESH_MeshEditor::applyMerge( const SMDS_MeshElement* elem,
       if ( nbUniqueNodes >= 4 )
       {
         // each face has to be analyzed in order to check volume validity
-        if ( const SMDS_MeshVolume* aPolyedre = SMDS_Mesh::DownCast< SMDS_MeshVolume >( elem ))
+        if ( const SMDS_VtkVolume* aPolyedre = dynamic_cast<const SMDS_VtkVolume*>( elem ))
         {
           int nbFaces = aPolyedre->NbFaces();
 
@@ -7953,11 +7956,24 @@ bool SMESH_MeshEditor::FindFreeBorder (const SMDS_MeshNode*             theFirst
       if ( e == curElem || foundElems.insert( e ).second ) {
         // get nodes
         int iNode = 0, nbNodes = e->NbNodes();
-        vector<const SMDS_MeshNode*> nodes( nbNodes+1 );
-        nodes.assign( SMDS_MeshElement::iterator( e->interlacedNodesIterator() ),
-                      SMDS_MeshElement::iterator() );
-        nodes.push_back( nodes[ 0 ]);
-
+        vector<const SMDS_MeshNode*> nodes(nbNodes+1);
+
+        if ( e->IsQuadratic() ) {
+          const SMDS_VtkFace* F =
+            dynamic_cast<const SMDS_VtkFace*>(e);
+          if (!F) throw SALOME_Exception(LOCALIZED("not an SMDS_VtkFace"));
+          // use special nodes iterator
+          SMDS_ElemIteratorPtr anIter = F->interlacedNodesElemIterator();
+          while( anIter->more() ) {
+            nodes[ iNode++ ] = cast2Node(anIter->next());
+          }
+        }
+        else {
+          SMDS_ElemIteratorPtr nIt = e->nodesIterator();
+          while ( nIt->more() )
+            nodes[ iNode++ ] = static_cast<const SMDS_MeshNode*>( nIt->next() );
+        }
+        nodes[ iNode ] = nodes[ 0 ];
         // check 2 links
         for ( iNode = 0; iNode < nbNodes; iNode++ )
           if (((nodes[ iNode ] == nStart && nodes[ iNode + 1] != nIgnore ) ||
@@ -8214,13 +8230,27 @@ SMESH_MeshEditor::SewFreeBorder (const SMDS_MeshNode* theBordFirstNode,
         const SMDS_MeshNode** nodes = isVolume ? volume.GetNodes() : & faceNodes[0];
         if ( isVolume ) // --volume
           hasVolumes = true;
-        else if ( elem->GetType() == SMDSAbs_Face ) { // --face
+        else if ( elem->GetType()==SMDSAbs_Face ) { // --face
           // retrieve all face nodes and find iPrevNode - an index of the prevSideNode
-          SMDS_NodeIteratorPtr nIt = elem->interlacedNodesIterator();
-          while ( nIt->more() ) {
-            nodes[ iNode ] = cast2Node( nIt->next() );
-            if ( nodes[ iNode++ ] == prevSideNode )
-              iPrevNode = iNode - 1;
+          if(elem->IsQuadratic()) {
+            const SMDS_VtkFace* F =
+              dynamic_cast<const SMDS_VtkFace*>(elem);
+            if (!F) throw SALOME_Exception(LOCALIZED("not an SMDS_VtkFace"));
+            // use special nodes iterator
+            SMDS_ElemIteratorPtr anIter = F->interlacedNodesElemIterator();
+            while( anIter->more() ) {
+              nodes[ iNode ] = cast2Node(anIter->next());
+              if ( nodes[ iNode++ ] == prevSideNode )
+                iPrevNode = iNode - 1;
+            }
+          }
+          else {
+            SMDS_ElemIteratorPtr nIt = elem->nodesIterator();
+            while ( nIt->more() ) {
+              nodes[ iNode ] = cast2Node( nIt->next() );
+              if ( nodes[ iNode++ ] == prevSideNode )
+                iPrevNode = iNode - 1;
+            }
           }
           // there are 2 links to check
           nbNodes = 2;
@@ -8680,21 +8710,48 @@ void SMESH_MeshEditor::InsertNodesIntoLink(const SMDS_MeshElement*     theElemen
 
     // add nodes of face up to first node of link
     bool isFLN = false;
-    SMDS_NodeIteratorPtr nodeIt = theFace->interlacedNodesIterator();
-    while ( nodeIt->more() && !isFLN ) {
-      const SMDS_MeshNode* n = nodeIt->next();
-      poly_nodes[iNode++] = n;
-      isFLN = ( n == nodes[il1] );
-    }
-    // add nodes to insert
-    list<const SMDS_MeshNode*>::iterator nIt = aNodesToInsert.begin();
-    for (; nIt != aNodesToInsert.end(); nIt++) {
-      poly_nodes[iNode++] = *nIt;
+
+    if ( theFace->IsQuadratic() ) {
+      const SMDS_VtkFace* F = dynamic_cast<const SMDS_VtkFace*>(theFace);
+      if (!F) throw SALOME_Exception(LOCALIZED("not an SMDS_VtkFace"));
+      // use special nodes iterator
+      SMDS_ElemIteratorPtr anIter = F->interlacedNodesElemIterator();
+      while( anIter->more()  && !isFLN ) {
+        const SMDS_MeshNode* n = cast2Node(anIter->next());
+        poly_nodes[iNode++] = n;
+        if (n == nodes[il1]) {
+          isFLN = true;
+        }
+      }
+      // add nodes to insert
+      list<const SMDS_MeshNode*>::iterator nIt = aNodesToInsert.begin();
+      for (; nIt != aNodesToInsert.end(); nIt++) {
+        poly_nodes[iNode++] = *nIt;
+      }
+      // add nodes of face starting from last node of link
+      while ( anIter->more() ) {
+        poly_nodes[iNode++] = cast2Node(anIter->next());
+      }
     }
-    // add nodes of face starting from last node of link
-    while ( nodeIt->more() ) {
-      const SMDS_MeshNode* n = static_cast<const SMDS_MeshNode*>( nodeIt->next() );
-      poly_nodes[iNode++] = n;
+    else {
+      SMDS_ElemIteratorPtr nodeIt = theFace->nodesIterator();
+      while ( nodeIt->more() && !isFLN ) {
+        const SMDS_MeshNode* n = static_cast<const SMDS_MeshNode*>( nodeIt->next() );
+        poly_nodes[iNode++] = n;
+        if (n == nodes[il1]) {
+          isFLN = true;
+        }
+      }
+      // add nodes to insert
+      list<const SMDS_MeshNode*>::iterator nIt = aNodesToInsert.begin();
+      for (; nIt != aNodesToInsert.end(); nIt++) {
+        poly_nodes[iNode++] = *nIt;
+      }
+      // add nodes of face starting from last node of link
+      while ( nodeIt->more() ) {
+        const SMDS_MeshNode* n = static_cast<const SMDS_MeshNode*>( nodeIt->next() );
+        poly_nodes[iNode++] = n;
+      }
     }
 
     // make a new face
@@ -9036,7 +9093,7 @@ int SMESH_MeshEditor::convertElemToQuadratic(SMESHDS_SubMesh *   theSm,
     const int nbNodes = elem->NbCornerNodes();
     nodes.assign(elem->begin_nodes(), elem->end_nodes());
     if ( aGeomType == SMDSEntity_Polyhedra )
-      nbNodeInFaces = static_cast<const SMDS_MeshVolume* >( elem )->GetQuantities();
+      nbNodeInFaces = static_cast<const SMDS_VtkVolume* >( elem )->GetQuantities();
     else if ( aGeomType == SMDSEntity_Hexagonal_Prism )
       volumeToPolyhedron( elem, nodes, nbNodeInFaces );
 
@@ -9257,7 +9314,7 @@ void SMESH_MeshEditor::ConvertToQuadratic(const bool theForce3d, const bool theT
       const int id = volume->GetID();
       vector<const SMDS_MeshNode *> nodes (volume->begin_nodes(), volume->end_nodes());
       if ( type == SMDSEntity_Polyhedra )
-        nbNodeInFaces = static_cast<const SMDS_MeshVolume* >(volume)->GetQuantities();
+        nbNodeInFaces = static_cast<const SMDS_VtkVolume* >(volume)->GetQuantities();
       else if ( type == SMDSEntity_Hexagonal_Prism )
         volumeToPolyhedron( volume, nodes, nbNodeInFaces );
 
@@ -10019,8 +10076,20 @@ SMESH_MeshEditor::SewSideElements (TIDSortedElemSet&    theSide1,
         //cout << " F " << face[ iSide]->GetID() <<endl;
         faceSetPtr[ iSide ]->erase( face[ iSide ]);
         // put face nodes to fnodes
-        SMDS_MeshElement::iterator nIt( face[ iSide ]->interlacedNodesIterator() ), nEnd;
-        fnodes[ iSide ].assign( nIt, nEnd );
+        if ( face[ iSide ]->IsQuadratic() )
+        {
+          // use interlaced nodes iterator
+          const SMDS_VtkFace* F = dynamic_cast<const SMDS_VtkFace*>( face[ iSide ]);
+          if (!F) throw SALOME_Exception(LOCALIZED("not an SMDS_VtkFace"));
+          SMDS_ElemIteratorPtr nIter = F->interlacedNodesElemIterator();
+          while ( nIter->more() )
+            fnodes[ iSide ].push_back( cast2Node( nIter->next() ));
+        }
+        else
+        {
+          fnodes[ iSide ].assign( face[ iSide ]->begin_nodes(),
+                                  face[ iSide ]->end_nodes() );
+        }
         fnodes[ iSide ].push_back( fnodes[ iSide ].front());
       }
     }
@@ -10916,9 +10985,9 @@ void SMESH_MeshEditor::DoubleElements( const TIDSortedElemSet& theElements )
       if ( mesh->GetMeshInfo().NbElements( types[i] ))
       {
         type = types[i];
-        elemIt = mesh->elementsIterator( type );
         break;
       }
+    elemIt = mesh->elementsIterator( type );
   }
   else
   {
@@ -11137,7 +11206,8 @@ namespace {
                 const double            theTol)
   {
     gp_XYZ centerXYZ (0, 0, 0);
-    for ( SMDS_ElemIteratorPtr aNodeItr = theElem->nodesIterator(); aNodeItr->more(); )
+    SMDS_ElemIteratorPtr aNodeItr = theElem->nodesIterator();
+    while ( aNodeItr->more() )
       centerXYZ += SMESH_NodeXYZ( aNodeItr->next() );
 
     gp_Pnt aPnt = centerXYZ / theElem->NbNodes();
@@ -11362,7 +11432,7 @@ bool SMESH_MeshEditor::DoubleNodesOnGroupBoundaries( const std::vector<TIDSorted
   SMESHDS_Mesh *meshDS = this->myMesh->GetMeshDS();
   meshDS->BuildDownWardConnectivity(true);
   CHRONO(50);
-  SMDS_UnstructuredGrid *grid = meshDS->GetGrid();
+  SMDS_UnstructuredGrid *grid = meshDS->getGrid();
 
   // --- build the list of faces shared by 2 domains (group of elements), with their domain and volume indexes
   //     build the list of cells with only a node or an edge on the border, with their domain and volume indexes
@@ -11428,7 +11498,7 @@ bool SMESH_MeshEditor::DoubleNodesOnGroupBoundaries( const std::vector<TIDSorted
       const SMDS_MeshElement* anElem = *elemItr;
       if (!anElem)
         continue;
-      int vtkId = anElem->GetVtkID();
+      int vtkId = anElem->getVtkId();
       //MESSAGE("  vtkId " << vtkId << " smdsId " << anElem->GetID());
       int neighborsVtkIds[NBMAXNEIGHBORS];
       int downIds[NBMAXNEIGHBORS];
@@ -11436,7 +11506,7 @@ bool SMESH_MeshEditor::DoubleNodesOnGroupBoundaries( const std::vector<TIDSorted
       int nbNeighbors = grid->GetNeighbors(neighborsVtkIds, downIds, downTypes, vtkId);
       for (int n = 0; n < nbNeighbors; n++)
       {
-        int smdsId = meshDS->FromVtkToSmds(neighborsVtkIds[n]);
+        int smdsId = meshDS->fromVtkToSmds(neighborsVtkIds[n]);
         const SMDS_MeshElement* elem = meshDS->FindElement(smdsId);
         if (elem && ! domain.count(elem)) // neighbor is in another domain : face is shared
         {
@@ -11499,7 +11569,7 @@ bool SMESH_MeshEditor::DoubleNodesOnGroupBoundaries( const std::vector<TIDSorted
         for (int i=0; i<l.ncells; i++)
         {
           int vtkId = l.cells[i];
-          const SMDS_MeshElement* anElem = GetMeshDS()->FindElement(GetMeshDS()->FromVtkToSmds(vtkId));
+          const SMDS_MeshElement* anElem = GetMeshDS()->FindElement(GetMeshDS()->fromVtkToSmds(vtkId));
           if (!domain.count(anElem))
             continue;
           int vtkType = grid->GetCellType(vtkId);
@@ -11583,7 +11653,7 @@ bool SMESH_MeshEditor::DoubleNodesOnGroupBoundaries( const std::vector<TIDSorted
             double *coords = grid->GetPoint(oldId);
             SMDS_MeshNode *newNode = meshDS->AddNode(coords[0], coords[1], coords[2]);
             copyPosition( meshDS->FindNodeVtk( oldId ), newNode );
-            int newId = newNode->GetVtkID();
+            int newId = newNode->getVtkId();
             nodeDomains[oldId][idom] = newId; // cloned node for other domains
             //MESSAGE("-+-+-c     oldNode " << oldId << " domain " << idomain << " newNode " << newId << " domain " << idom << " size=" <<nodeDomains[oldId].size());
           }
@@ -11656,7 +11726,7 @@ bool SMESH_MeshEditor::DoubleNodesOnGroupBoundaries( const std::vector<TIDSorted
                 gp_Pnt p1(coords[0], coords[1], coords[2]);
                 gp_Pnt gref;
                 int vtkVolIds[1000];  // an edge can belong to a lot of volumes
-                map<int, SMDS_MeshVolume*> domvol; // domain --> a volume with the edge
+                map<int, SMDS_VtkVolume*> domvol; // domain --> a volume with the edge
                 map<int, double> angleDom; // oriented angles between planes defined by edge and volume centers
                 int nbvol = grid->GetParentVolumes(vtkVolIds, downEdgeIds[ie], edgeType[ie]);
                 for ( size_t id = 0; id < doms.size(); id++ )
@@ -11665,31 +11735,26 @@ bool SMESH_MeshEditor::DoubleNodesOnGroupBoundaries( const std::vector<TIDSorted
                   const TIDSortedElemSet& domain = (idom == iRestDom) ? theRestDomElems : theElems[idom];
                   for ( int ivol = 0; ivol < nbvol; ivol++ )
                   {
-                    int smdsId = meshDS->FromVtkToSmds(vtkVolIds[ivol]);
-                    const SMDS_MeshElement* elem = meshDS->FindElement(smdsId);
+                    int smdsId = meshDS->fromVtkToSmds(vtkVolIds[ivol]);
+                    SMDS_MeshElement* elem = (SMDS_MeshElement*)meshDS->FindElement(smdsId);
                     if (domain.count(elem))
                     {
-                      const SMDS_MeshVolume* svol = SMDS_Mesh::DownCast<SMDS_MeshVolume>(elem);
-                      domvol[idom] = (SMDS_MeshVolume*) svol;
+                      SMDS_VtkVolume* svol = dynamic_cast<SMDS_VtkVolume*>(elem);
+                      domvol[idom] = svol;
                       //MESSAGE("  domain " << idom << " volume " << elem->GetID());
-                      double values[3] = { 0,0,0 };
+                      double values[3];
                       vtkIdType npts = 0;
                       vtkIdType* pts = 0;
                       grid->GetCellPoints(vtkVolIds[ivol], npts, pts);
-                      for ( vtkIdType i = 0; i < npts; ++i )
-                      {
-                        double *coords = grid->GetPoint( pts[i] );
-                        for ( int j = 0; j < 3; ++j )
-                          values[j] += coords[j] / npts;
-                      }
-                      if ( id == 0 )
+                      SMDS_VtkVolume::gravityCenter(grid, pts, npts, values);
+                      if (id ==0)
                       {
-                        gref.SetCoord( values[0], values[1], values[2] );
+                        gref.SetXYZ(gp_XYZ(values[0], values[1], values[2]));
                         angleDom[idom] = 0;
                       }
                       else
                       {
-                        gp_Pnt g( values[0], values[1], values[2] );
+                        gp_Pnt g(values[0], values[1], values[2]);
                         angleDom[idom] = OrientedAngle(p0, p1, gref, g); // -pi<angle<+pi
                         //MESSAGE("  angle=" << angleDom[idom]);
                       }
@@ -11878,7 +11943,7 @@ bool SMESH_MeshEditor::DoubleNodesOnGroupBoundaries( const std::vector<TIDSorted
               feDom[vtkId] = idomain;
               faceOrEdgeDom[aCell] = emptyMap;
               faceOrEdgeDom[aCell][idomain] = vtkId; // affect face or edge to the first domain only
-              //MESSAGE("affect cell " << this->GetMeshDS()->FromVtkToSmds(vtkId) << " domain " << idomain
+              //MESSAGE("affect cell " << this->GetMeshDS()->fromVtkToSmds(vtkId) << " domain " << idomain
               //        << " type " << vtkType << " downId " << downId);
             }
       }
@@ -11910,7 +11975,7 @@ bool SMESH_MeshEditor::DoubleNodesOnGroupBoundaries( const std::vector<TIDSorted
       {
         int idom = itdom->first;
         int vtkVolId = itdom->second;
-        //MESSAGE("modify nodes of cell " << this->GetMeshDS()->FromVtkToSmds(vtkVolId) << " domain " << idom);
+        //MESSAGE("modify nodes of cell " << this->GetMeshDS()->fromVtkToSmds(vtkVolId) << " domain " << idom);
         localClonedNodeIds.clear();
         for (itn = oldNodes.begin(); itn != oldNodes.end(); ++itn)
         {
@@ -11977,7 +12042,8 @@ bool SMESH_MeshEditor::CreateFlatElementsOnFacesGroups(const std::vector<TIDSort
     TIDSortedElemSet::const_iterator elemItr = domain.begin();
     for ( ; elemItr != domain.end(); ++elemItr )
     {
-      const SMDS_MeshFace* aFace = meshDS->DownCast<SMDS_MeshFace> ( *elemItr );
+      SMDS_MeshElement* anElem = (SMDS_MeshElement*) *elemItr;
+      SMDS_MeshFace* aFace = dynamic_cast<SMDS_MeshFace*> (anElem);
       if (!aFace)
         continue;
       // MESSAGE("aFace=" << aFace->GetID());
@@ -11986,11 +12052,11 @@ bool SMESH_MeshEditor::CreateFlatElementsOnFacesGroups(const std::vector<TIDSort
 
       // --- clone the nodes, create intermediate nodes for non medium nodes of a quad face
 
-      SMDS_NodeIteratorPtr nodeIt = aFace->nodeIterator();
+      SMDS_ElemIteratorPtr nodeIt = aFace->nodesIterator();
       while (nodeIt->more())
       {
-        const SMDS_MeshNode* node = nodeIt->next();
-        bool isMedium = ( isQuad && aFace->IsMediumNode( node ));
+        const SMDS_MeshNode* node = static_cast<const SMDS_MeshNode*> (nodeIt->next());
+        bool isMedium = isQuad && (aFace->IsMediumNode(node));
         if (isMedium)
           ln2.push_back(node);
         else
@@ -12098,7 +12164,7 @@ bool SMESH_MeshEditor::CreateFlatElementsOnFacesGroups(const std::vector<TIDSort
 
       // --- modify the face
 
-      const_cast<SMDS_MeshFace*>( aFace )->ChangeNodes( &ln[0], ln.size() );
+      aFace->ChangeNodes(&ln[0], ln.size());
     }
   }
   return true;
@@ -12209,7 +12275,7 @@ void SMESH_MeshEditor::CreateHoleSkin(double                          radius,
 
   SMESHDS_Mesh *meshDS = this->myMesh->GetMeshDS();
   meshDS->BuildDownWardConnectivity(true);
-  SMDS_UnstructuredGrid* grid = meshDS->GetGrid();
+  SMDS_UnstructuredGrid* grid = meshDS->getGrid();
 
   // --- set of volumes detected inside
 
@@ -12236,7 +12302,7 @@ void SMESH_MeshEditor::CreateHoleSkin(double                          radius,
       while (volItr->more())
       {
         vol = (SMDS_MeshElement*)volItr->next();
-        setOfInsideVol.insert(vol->GetVtkID());
+        setOfInsideVol.insert(vol->getVtkId());
         sgrp->Add(vol->GetID());
       }
     }
@@ -12291,7 +12357,7 @@ void SMESH_MeshEditor::CreateHoleSkin(double                          radius,
     while (volItr->more())
     {
       startVol = (SMDS_MeshElement*)volItr->next();
-      setOfVolToCheck.insert(startVol->GetVtkID());
+      setOfVolToCheck.insert(startVol->getVtkId());
     }
     if (setOfVolToCheck.empty())
     {
@@ -12310,7 +12376,7 @@ void SMESH_MeshEditor::CreateHoleSkin(double                          radius,
     {
       std::set<int>::iterator it = setOfVolToCheck.begin();
       int vtkId = *it;
-      //MESSAGE("volume to check,  vtkId " << vtkId << " smdsId " << meshDS->FromVtkToSmds(vtkId));
+      //MESSAGE("volume to check,  vtkId " << vtkId << " smdsId " << meshDS->fromVtkToSmds(vtkId));
       bool volInside = false;
       vtkIdType npts = 0;
       vtkIdType* pts = 0;
@@ -12344,14 +12410,14 @@ void SMESH_MeshEditor::CreateHoleSkin(double                          radius,
         if (distance2 < radius2)
         {
           volInside = true; // one or more nodes inside the domain
-          sgrp->Add(meshDS->FromVtkToSmds(vtkId));
+          sgrp->Add(meshDS->fromVtkToSmds(vtkId));
           break;
         }
       }
       if (volInside)
       {
         setOfInsideVol.insert(vtkId);
-        //MESSAGE("  volume inside,  vtkId " << vtkId << " smdsId " << meshDS->FromVtkToSmds(vtkId));
+        //MESSAGE("  volume inside,  vtkId " << vtkId << " smdsId " << meshDS->fromVtkToSmds(vtkId));
         int neighborsVtkIds[NBMAXNEIGHBORS];
         int downIds[NBMAXNEIGHBORS];
         unsigned char downTypes[NBMAXNEIGHBORS];
@@ -12363,7 +12429,7 @@ void SMESH_MeshEditor::CreateHoleSkin(double                          radius,
       else
       {
         setOfOutsideVol.insert(vtkId);
-        //MESSAGE("  volume outside, vtkId " << vtkId << " smdsId " << meshDS->FromVtkToSmds(vtkId));
+        //MESSAGE("  volume outside, vtkId " << vtkId << " smdsId " << meshDS->fromVtkToSmds(vtkId));
       }
       setOfVolToCheck.erase(vtkId);
     }
@@ -12398,7 +12464,7 @@ void SMESH_MeshEditor::CreateHoleSkin(double                          radius,
       int vtkId = *it;
       if (grid->GetCellType(vtkId) == VTK_HEXAHEDRON)
       {
-        //MESSAGE("volume to recheck,  vtkId " << vtkId << " smdsId " << meshDS->FromVtkToSmds(vtkId));
+        //MESSAGE("volume to recheck,  vtkId " << vtkId << " smdsId " << meshDS->fromVtkToSmds(vtkId));
         int countInside = 0;
         int neighborsVtkIds[NBMAXNEIGHBORS];
         int downIds[NBMAXNEIGHBORS];
@@ -12410,9 +12476,9 @@ void SMESH_MeshEditor::CreateHoleSkin(double                          radius,
         //MESSAGE("countInside " << countInside);
         if (countInside > 1)
         {
-          //MESSAGE("  volume inside,  vtkId " << vtkId << " smdsId " << meshDS->FromVtkToSmds(vtkId));
+          //MESSAGE("  volume inside,  vtkId " << vtkId << " smdsId " << meshDS->fromVtkToSmds(vtkId));
           setOfInsideVol.insert(vtkId);
-          sgrp->Add(meshDS->FromVtkToSmds(vtkId));
+          sgrp->Add(meshDS->fromVtkToSmds(vtkId));
           addedInside = true;
         }
         else
@@ -12433,7 +12499,7 @@ void SMESH_MeshEditor::CreateHoleSkin(double                          radius,
   for (; it != setOfInsideVol.end(); ++it)
   {
     int vtkId = *it;
-    //MESSAGE("  vtkId " << vtkId  << " smdsId " << meshDS->FromVtkToSmds(vtkId));
+    //MESSAGE("  vtkId " << vtkId  << " smdsId " << meshDS->fromVtkToSmds(vtkId));
     int neighborsVtkIds[NBMAXNEIGHBORS];
     int downIds[NBMAXNEIGHBORS];
     unsigned char downTypes[NBMAXNEIGHBORS];
@@ -12452,7 +12518,7 @@ void SMESH_MeshEditor::CreateHoleSkin(double                          radius,
         int vtkFaceId = grid->getDownArray(downTypes[n])->getVtkCellId(downIds[n]);
         if (vtkFaceId >= 0)
         {
-          sgrpi->Add(meshDS->FromVtkToSmds(vtkFaceId));
+          sgrpi->Add(meshDS->fromVtkToSmds(vtkFaceId));
           // find also the smds edges on this face
           int nbEdges = grid->getDownArray(downTypes[n])->getNumberOfDownCells(downIds[n]);
           const int* dEdges = grid->getDownArray(downTypes[n])->getDownCells(downIds[n]);
@@ -12461,7 +12527,7 @@ void SMESH_MeshEditor::CreateHoleSkin(double                          radius,
           {
             int vtkEdgeId = grid->getDownArray(dTypes[i])->getVtkCellId(dEdges[i]);
             if (vtkEdgeId >= 0)
-              sgrpei->Add(meshDS->FromVtkToSmds(vtkEdgeId));
+              sgrpei->Add(meshDS->fromVtkToSmds(vtkEdgeId));
           }
         }
       }
@@ -12471,7 +12537,7 @@ void SMESH_MeshEditor::CreateHoleSkin(double                          radius,
         skinFaces[face] = vtkId;
         int vtkFaceId = grid->getDownArray(downTypes[n])->getVtkCellId(downIds[n]);
         if (vtkFaceId >= 0)
-          sgrps->Add(meshDS->FromVtkToSmds(vtkFaceId));
+          sgrps->Add(meshDS->fromVtkToSmds(vtkFaceId));
       }
     }
   }
@@ -12490,7 +12556,7 @@ void SMESH_MeshEditor::CreateHoleSkin(double                          radius,
   {
     const SMDS_MeshElement *elem = itelem->next();
     int shapeId = elem->getshapeId();
-    int   vtkId = elem->GetVtkID();
+    int vtkId = elem->getVtkId();
     if (!shapeIdToVtkIdSet.count(shapeId))
     {
       shapeIdToVtkIdSet[shapeId] = emptySet;
@@ -12525,7 +12591,7 @@ void SMESH_MeshEditor::CreateHoleSkin(double                          radius,
       {
         if (neighborsVtkIds[n]<0) // only smds faces are considered as neighbors here
           continue;
-        int smdsId = meshDS->FromVtkToSmds(neighborsVtkIds[n]);
+        int smdsId = meshDS->fromVtkToSmds(neighborsVtkIds[n]);
         const SMDS_MeshElement* elem = meshDS->FindElement(smdsId);
         if ( shapeIds.count(elem->getshapeId()) && !sgrps->Contains(elem)) // edge : neighbor in the set of shape, not in the group
         {
@@ -12765,7 +12831,7 @@ int SMESH_MeshEditor::MakeBoundaryMesh(const TIDSortedElemSet& elements,
   if (elements.empty()) eIt = aMesh->elementsIterator(elemType);
   else                  eIt = SMESHUtils::elemSetIterator( elements );
 
-  while ( eIt->more() )
+  while (eIt->more())
   {
     const SMDS_MeshElement* elem = eIt->next();
     const int              iQuad = elem->IsQuadratic();
@@ -12846,7 +12912,7 @@ int SMESH_MeshEditor::MakeBoundaryMesh(const TIDSortedElemSet& elements,
     else if ( elem->GetType() == SMDSAbs_Face ) // elem is a face ------------------------
     {
       avoidSet.clear(), avoidSet.insert( elem );
-      elemNodes.assign( SMDS_MeshElement::iterator( elem->interlacedNodesIterator() ),
+      elemNodes.assign( SMDS_MeshElement::iterator( elem->interlacedNodesElemIterator() ),
                         SMDS_MeshElement::iterator() );
       elemNodes.push_back( elemNodes[0] );
       nodes.resize( 2 + iQuad );
@@ -13000,7 +13066,7 @@ void SMESH_MeshEditor::copyPosition( const SMDS_MeshNode* from,
 
   case SMDS_TOP_FACE:
   {
-    SMDS_FacePositionPtr fPos = pos;
+    const SMDS_FacePosition* fPos = static_cast< const SMDS_FacePosition* >( pos );
     GetMeshDS()->SetNodeOnFace( to, from->getshapeId(),
                                 fPos->GetUParameter(), fPos->GetVParameter() );
     break;
@@ -13008,7 +13074,7 @@ void SMESH_MeshEditor::copyPosition( const SMDS_MeshNode* from,
   case SMDS_TOP_EDGE:
   {
     // WARNING: it is dangerous to set equal nodes on one EDGE!!!!!!!!
-    SMDS_EdgePositionPtr ePos = pos;
+    const SMDS_EdgePosition* ePos = static_cast< const SMDS_EdgePosition* >( pos );
     GetMeshDS()->SetNodeOnEdge( to, from->getshapeId(), ePos->GetUParameter() );
     break;
   }
index ad48bd49d1bdb8a90e740ac56b004ef0086318ec..242900a749d0877a3c4f9e25ace56a0c2fdf43eb 100644 (file)
@@ -643,22 +643,22 @@ gp_XY SMESH_MesherHelper::GetNodeUV(const TopoDS_Face&   F,
 {
   gp_Pnt2d uv( Precision::Infinite(), Precision::Infinite() );
 
-  SMDS_PositionPtr pos = n->GetPosition();
+  const SMDS_PositionPtr Pos = n->GetPosition();
   bool uvOK = false;
-  if ( pos->GetTypeOfPosition() == SMDS_TOP_FACE )
+  if ( Pos->GetTypeOfPosition() == SMDS_TOP_FACE )
   {
     // node has position on face
-    SMDS_FacePositionPtr fpos = pos;
+    const SMDS_FacePosition* fpos = static_cast<const SMDS_FacePosition*>( Pos );
     uv.SetCoord( fpos->GetUParameter(), fpos->GetVParameter() );
     if ( check )
       uvOK = CheckNodeUV( F, n, uv.ChangeCoord(), 2.*getFaceMaxTol( F )); // 2. from 22830
   }
-  else if ( pos->GetTypeOfPosition() == SMDS_TOP_EDGE )
+  else if ( Pos->GetTypeOfPosition() == SMDS_TOP_EDGE )
   {
     // node has position on EDGE => it is needed to find
     // corresponding EDGE from FACE, get pcurve for this
     // EDGE and retrieve value from this pcurve
-    SMDS_EdgePositionPtr epos = pos;
+    const SMDS_EdgePosition* epos = static_cast<const SMDS_EdgePosition*>( Pos );
     const int              edgeID = n->getshapeId();
     const TopoDS_Edge& E = TopoDS::Edge( GetMeshDS()->IndexToShape( edgeID ));
     double f, l, u = epos->GetUParameter();
@@ -699,7 +699,7 @@ gp_XY SMESH_MesherHelper::GetNodeUV(const TopoDS_Face&   F,
       uv = newUV;
     }
   }
-  else if ( pos->GetTypeOfPosition() == SMDS_TOP_VERTEX )
+  else if ( Pos->GetTypeOfPosition() == SMDS_TOP_VERTEX )
   {
     if ( int vertexID = n->getshapeId() ) {
       const TopoDS_Vertex& V = TopoDS::Vertex(GetMeshDS()->IndexToShape(vertexID));
@@ -1031,7 +1031,8 @@ double SMESH_MesherHelper::GetNodeU(const TopoDS_Edge&   E,
   const SMDS_PositionPtr pos = n->GetPosition();
   if ( pos->GetTypeOfPosition()==SMDS_TOP_EDGE )
   {
-    param = pos->GetParameters()[0];
+    const SMDS_EdgePosition* epos = static_cast<const SMDS_EdgePosition*>( pos );
+    param =  epos->GetUParameter();
   }
   else if( pos->GetTypeOfPosition() == SMDS_TOP_VERTEX )
   {
@@ -4561,16 +4562,8 @@ namespace { // Structures used by FixQuadraticElements()
     TopoDS_Shape  shape = theHelper.GetSubShape().Oriented( TopAbs_FORWARD );
     if ( shape.IsNull() ) return;
 
-    if ( !dynamic_cast<SMESH_BadInputElements*>( theError.get() ))
-    {
-      if ( !theError )
-        theError.reset( new SMESH_BadInputElements( meshDS ));
-      else
-        theError.reset( new SMESH_BadInputElements( meshDS,
-                                                    theError->myName,
-                                                    theError->myComment,
-                                                    theError->myAlgo));
-    }
+    if ( !theError ) theError = SMESH_ComputeError::New();
+
     gp_XYZ faceNorm;
 
     if ( shape.ShapeType() == TopAbs_FACE ) // 2D
@@ -4688,13 +4681,13 @@ namespace { // Structures used by FixQuadraticElements()
                 gp_XYZ pMid3D = 0.5 * ( pN0 + SMESH_TNodeXYZ( nOnEdge[1] ));
                 meshDS->MoveNode( n, pMid3D.X(), pMid3D.Y(), pMid3D.Z() );
                 MSG( "move OUT of face " << n );
-                static_cast<SMESH_BadInputElements*>( theError.get() )->add( f );
+                theError->myBadElements.push_back( f );
               }
             }
           }
         }
       }
-      if ( theError->HasBadElems() )
+      if ( !theError->myBadElements.empty() )
         theError->myName = EDITERR_NO_MEDIUM_ON_GEOM;
       return;
 
@@ -4882,13 +4875,13 @@ namespace { // Structures used by FixQuadraticElements()
                   MSG( "move OUT of solid " << nMedium );
                 }
               }
-              static_cast<SMESH_BadInputElements*>( theError.get() )->add( vol );
+              theError->myBadElements.push_back( vol );
             }
           } // loop on volumes sharing a node on FACE
         } // loop on nodes on FACE
       }  // loop on FACEs of a SOLID
 
-      if ( theError->HasBadElems() )
+      if ( !theError->myBadElements.empty() )
         theError->myName = EDITERR_NO_MEDIUM_ON_GEOM;
     } // 3D case
   }
@@ -4900,7 +4893,7 @@ namespace { // Structures used by FixQuadraticElements()
  * \brief Move medium nodes of faces and volumes to fix distorted elements
  * \param error - container of fixed distorted elements
  * \param volumeOnly - to fix nodes on faces or not, if the shape is solid
- *
+ * 
  * Issue 0020307: EDF 992 SMESH : Linea/Quadratic with Medium Node on Geometry
  */
 //=======================================================================
@@ -5275,7 +5268,8 @@ void SMESH_MesherHelper::FixQuadraticElements(SMESH_ComputeErrorPtr& compError,
               gp_XY newUV   = ApplyIn2D( s, oldUV, gp_XY( move.X(),move.Y()), gp_XY_Added );
               gp_Pnt newPnt = s->Value( newUV.X(), newUV.Y());
               move = gp_Vec( XYZ((*link1)->_mediumNode), newPnt.Transformed(loc) );
-              if ( SMDS_FacePositionPtr nPos = (*link1)->_mediumNode->GetPosition())
+              if ( SMDS_FacePosition* nPos =
+                   dynamic_cast< SMDS_FacePosition* >((*link1)->_mediumNode->GetPosition()))
                 nPos->SetParameters( newUV.X(), newUV.Y() );
 #ifdef _DEBUG_
               if ( (XYZ((*link1)->node1()) - XYZ((*link1)->node2())).SquareModulus() <
index f032ae475df0b522a7bfba9215e39cd17377f41b..b307ba31c334759c7869b2b73ec0beb83d7c857a 100644 (file)
@@ -801,7 +801,8 @@ bool SMESH_Pattern::Load (SMESH_Mesh*        theMesh,
             ++nbMeduimNodes;
             continue;
           }
-          SMDS_EdgePositionPtr epos = node->GetPosition();
+          const SMDS_EdgePosition* epos =
+            static_cast<const SMDS_EdgePosition*>(node->GetPosition());
           double u = epos->GetUParameter();
           paramNodeMap.insert( make_pair( u, node ));
         }
@@ -928,7 +929,8 @@ bool SMESH_Pattern::Load (SMESH_Mesh*        theMesh,
         if ( theProject || edgesUVBox.IsOut( p->myInitUV ) )
           p->myInitUV = project( node, projector );
         else {
-          SMDS_FacePositionPtr pos = node->GetPosition();
+          const SMDS_FacePosition* pos =
+            static_cast<const SMDS_FacePosition*>(node->GetPosition());
           p->myInitUV.SetCoord( pos->GetUParameter(), pos->GetVParameter() );
         }
         p->myInitXYZ.SetCoord( p->myInitUV.X(), p->myInitUV.Y(), 0 );
@@ -3286,7 +3288,8 @@ bool SMESH_Pattern::Load (SMESH_Mesh*         theMesh,
         const SMDS_MeshNode* node = nIt->next();
         if ( isQuadMesh && SMESH_MeshEditor::IsMedium( node, SMDSAbs_Edge ))
           continue;
-        SMDS_EdgePositionPtr epos = node->GetPosition();
+        const SMDS_EdgePosition* epos =
+          static_cast<const SMDS_EdgePosition*>(node->GetPosition());
         double u = ( epos->GetUParameter() - f ) / ( l - f );
         (*pIt)->myInitXYZ.SetCoord( iCoord, isForward ? u : 1 - u );
       }
@@ -4169,8 +4172,7 @@ bool SMESH_Pattern::MakeMesh(SMESH_Mesh* theMesh,
     createElements( theMesh, nodesVector, myElemPointIDs, myElements );
   }
 
-  aMeshDS->Modified();
-  aMeshDS->CompactMesh();
+  aMeshDS->compactMesh();
 
   if ( myToKeepNodes )
     myOutNodes.swap( nodesVector );
index 9e2e34792d130057528f85c1d3107b734bddcdc4..a28033fda4fe6c43d0bf337a5b1ec1ea1f66f75c 100644 (file)
  */
 //================================================================================
 
-SMESH_ProxyMesh::SMESH_ProxyMesh():_mesh(0), _subContainer(0)
+SMESH_ProxyMesh::SMESH_ProxyMesh():_mesh(0)
 {
 }
-//================================================================================
-/*!
- * \brief Constructor
- */
-//================================================================================
-
-SMESH_ProxyMesh::SMESH_ProxyMesh(const SMESH_Mesh& mesh)
-  : _mesh( &mesh ),
-    _subContainer( new SubMesh( GetMeshDS() ) )
-{
-}
-
 //================================================================================
 /*!
  * \brief Make a proxy mesh from components. Components become empty
@@ -71,7 +59,7 @@ SMESH_ProxyMesh::SMESH_ProxyMesh(std::vector<SMESH_ProxyMesh::Ptr>& components):
 
     takeTmpElemsInMesh( m );
 
-    if ( !_mesh && m->_mesh ) setMesh( *( m->_mesh ));
+    if ( !_mesh ) _mesh = m->_mesh;
     if ( _allowedTypes.empty() ) _allowedTypes = m->_allowedTypes;
 
     if ( _subMeshes.size() < m->_subMeshes.size() )
@@ -113,8 +101,6 @@ SMESH_ProxyMesh::SMESH_ProxyMesh(std::vector<SMESH_ProxyMesh::Ptr>& components):
 
 SMESH_ProxyMesh::~SMESH_ProxyMesh()
 {
-  delete _subContainer;
-
   for ( size_t i = 0; i < _subMeshes.size(); ++i )
     delete _subMeshes[i];
   _subMeshes.clear();
@@ -125,19 +111,6 @@ SMESH_ProxyMesh::~SMESH_ProxyMesh()
   _elemsInMesh.clear();
 }
 
-//================================================================================
-/*!
- * \brief Set mesh
- */
-//================================================================================
-
-void SMESH_ProxyMesh::setMesh(const SMESH_Mesh& mesh)
-{
-  _mesh = &mesh;
-  if ( _mesh )
-    _subContainer = new SubMesh( GetMeshDS() );
-}
-
 //================================================================================
 /*!
  * \brief Returns index of a shape
@@ -149,19 +122,6 @@ int SMESH_ProxyMesh::shapeIndex(const TopoDS_Shape& shape) const
   return ( shape.IsNull() || !_mesh->HasShapeToMesh() ? 0 : GetMeshDS()->ShapeToIndex(shape));
 }
 
-//================================================================================
-/*!
- * \brief Create a SubMesh
- *  \param [ino] index - shape index
- *  \return SubMesh* - new SubMesh
- */
-//================================================================================
-
-SMESH_ProxyMesh::SubMesh* SMESH_ProxyMesh::newSubmesh(int index) const
-{
-  return new SubMesh( GetMeshDS(),index );
-}
-
 //================================================================================
 /*!
  * \brief Returns the submesh of a shape; it can be a proxy sub-mesh
@@ -285,15 +245,15 @@ SMDS_ElemIteratorPtr SMESH_ProxyMesh::GetFaces(const TopoDS_Shape& shape) const
   if ( !_mesh->HasShapeToMesh() )
     return SMDS_ElemIteratorPtr();
 
-  _subContainer->RemoveAllSubmeshes();
+  _subContainer.RemoveAllSubmeshes();
 
   TopTools_IndexedMapOfShape FF;
   TopExp::MapShapes( shape, TopAbs_FACE, FF );
   for ( int i = 1; i <= FF.Extent(); ++i )
     if ( const SMESHDS_SubMesh* sm = GetSubMesh( FF(i)))
-      _subContainer->AddSubMesh( sm );
+      _subContainer.AddSubMesh( sm );
 
-  return _subContainer->SMESHDS_SubMesh::GetElements();
+  return _subContainer.SMESHDS_SubMesh::GetElements();
 }
 
 //================================================================================
@@ -308,16 +268,16 @@ SMDS_ElemIteratorPtr SMESH_ProxyMesh::GetFaces() const
   if ( _mesh->HasShapeToMesh() )
     return SMDS_ElemIteratorPtr();
 
-  _subContainer->RemoveAllSubmeshes();
+  _subContainer.RemoveAllSubmeshes();
   for ( unsigned i = 0; i < _subMeshes.size(); ++i )
     if ( _subMeshes[i] )
-      _subContainer->AddSubMesh( _subMeshes[i] );
+      _subContainer.AddSubMesh( _subMeshes[i] );
 
-  if ( _subContainer->NbSubMeshes() == 0 ) // no elements substituted
+  if ( _subContainer.NbSubMeshes() == 0 ) // no elements substituted
     return GetMeshDS()->elementsIterator(SMDSAbs_Face);
 
   // if _allowedTypes is empty, only elements from _subMeshes are returned,...
-  SMDS_ElemIteratorPtr proxyIter = _subContainer->SMESHDS_SubMesh::GetElements();
+  SMDS_ElemIteratorPtr proxyIter = _subContainer.SMESHDS_SubMesh::GetElements();
   if ( _allowedTypes.empty() || NbFaces() == _mesh->NbFaces() )
     return proxyIter;
 
@@ -573,7 +533,7 @@ int SMESH_ProxyMesh::SubMesh::NbElements() const
  */
 //================================================================================
 
-SMDS_ElemIteratorPtr SMESH_ProxyMesh::SubMesh::GetElements() const
+SMDS_ElemIteratorPtr SMESH_ProxyMesh::SubMesh::GetElements(bool reverse) const
 {
   return SMDS_ElemIteratorPtr
     ( new SMDS_ElementVectorIterator( _elements.begin(), _elements.end() ));
@@ -598,7 +558,7 @@ int SMESH_ProxyMesh::SubMesh::NbNodes() const
  */
 //================================================================================
 
-SMDS_NodeIteratorPtr SMESH_ProxyMesh::SubMesh::GetNodes() const
+SMDS_NodeIteratorPtr SMESH_ProxyMesh::SubMesh::GetNodes(bool reverse) const
 {
   if ( !_uvPtStructVec.empty() )
     return SMDS_NodeIteratorPtr ( new SMDS_SetIterator
index 35a4c3a97b8ff6d2804084a0a6d7d1cd89ed7a47..a64002e02527730fc238d6ca4568f4efeed9927b 100644 (file)
@@ -26,7 +26,6 @@
 
 #include "SMESH_SMESH.hxx"
 
-#include "SMDS_ElementHolder.hxx"
 #include "SMESHDS_SubMesh.hxx"
 #include "SMESH_TypeDefs.hxx"
 
@@ -57,7 +56,7 @@ public:
   /*!
    * \brief Proxy sub-mesh
    */
-  class SMESH_EXPORT SubMesh : public SMESHDS_SubMesh, SMDS_ElementHolder
+  class SMESH_EXPORT SubMesh : public SMESHDS_SubMesh
   {
   public:
 
@@ -67,20 +66,19 @@ public:
     virtual void         AddElement(const SMDS_MeshElement * e);
     virtual int          NbElements() const;
     virtual int          NbNodes() const;
-    virtual SMDS_ElemIteratorPtr GetElements() const;
-    virtual SMDS_NodeIteratorPtr GetNodes() const;
+    virtual SMDS_ElemIteratorPtr GetElements(bool reverse=false) const;
+    virtual SMDS_NodeIteratorPtr GetNodes(bool reverse=false) const;
     virtual void         Clear();
     virtual bool         Contains(const SMDS_MeshElement * ME) const;
 
     template< class ITERATOR >
-      void ChangeElements( ITERATOR it, ITERATOR end )
+    void ChangeElements( ITERATOR it, ITERATOR end )
     {
       // change SubMesh contents without deleting tmp elements
       // for which the caller is responsible
       _elements.assign( it, end );
     }
-    SubMesh(const SMDS_Mesh* mesh, int index=0)
-      :SMESHDS_SubMesh(0,index), SMDS_ElementHolder(mesh), _n2n(0) {}
+    SubMesh(int index=0):SMESHDS_SubMesh(0,index),_n2n(0) {}
     virtual ~SubMesh() { Clear(); }
 
   protected:
@@ -88,20 +86,13 @@ public:
     TN2NMap*                              _n2n;
     UVPtStructVec                         _uvPtStructVec; // for SubMesh of EDGE
     friend class SMESH_ProxyMesh;
-
-  protected: // methods of SMDS_ElementHolder; remove elements before mesh compacting or clearing
-    virtual SMDS_ElemIteratorPtr getElements() { Clear(); return GetElements(); }
-    virtual void tmpClear() {}
-    virtual void add( const SMDS_MeshElement* element ) {}
-    virtual void compact() {}
-    virtual void clear() { Clear(); }
   };
   //--------------------------------------------------------------------------------
   // Public interface
 
   SMESH_ProxyMesh();
   SMESH_ProxyMesh(std::vector<SMESH_ProxyMesh::Ptr>& components);
-  SMESH_ProxyMesh(const SMESH_Mesh& mesh);
+  SMESH_ProxyMesh(const SMESH_Mesh& mesh) { _mesh = &mesh; }
   virtual ~SMESH_ProxyMesh();
 
   // Returns the submesh of a shape; it can be a proxy sub-mesh
@@ -138,11 +129,11 @@ public:
   // Interface for descendants
  protected:
 
-  void     setMesh(const SMESH_Mesh& mesh);
+  void     setMesh(const SMESH_Mesh& mesh) { _mesh = &mesh; }
 
   int      shapeIndex(const TopoDS_Shape& shape) const;
 
-  virtual SubMesh* newSubmesh(int index=0) const;
+  virtual SubMesh* newSubmesh(int index=0) const { return new SubMesh(index); }
 
   // returns a proxy sub-mesh; zero index is for the case of mesh w/o shape
   SubMesh* findProxySubMesh(int shapeIndex=0) const;
@@ -186,7 +177,7 @@ public:
   std::set< const SMDS_MeshElement* > _elemsInMesh;
 
   // Complex submesh used to iterate over elements in other sub-meshes
-  mutable SubMesh* _subContainer;
+  mutable SubMesh _subContainer;
 };
 
 #endif
index e8a61f295e8675f80d042240b222e5d77b3c80f9..05800491ba7ffb27dbff708c1a3f9ba00cea635d 100644 (file)
@@ -1293,19 +1293,40 @@ static void cleanSubMesh( SMESH_subMesh * subMesh )
       SMESHDS_Mesh * meshDS = subMesh->GetFather()->GetMeshDS();
       int nbElems = subMeshDS->NbElements();
       if ( nbElems > 0 )
-        for ( SMDS_ElemIteratorPtr ite = subMeshDS->GetElements(); ite->more(); )
-          meshDS->RemoveFreeElement( ite->next(), subMeshDS );
-
+      {
+        // start from elem with max ID to avoid filling the pool of IDs
+        bool rev = true;
+        SMDS_ElemIteratorPtr ite = subMeshDS->GetElements( rev );
+        const SMDS_MeshElement * lastElem = ite->next();
+        rev = ( lastElem->GetID() == meshDS->MaxElementID() );
+        if ( !rev )
+          ite = subMeshDS->GetElements( rev );
+        else
+          meshDS->RemoveFreeElement( lastElem, subMeshDS );
+        while (ite->more()) {
+          const SMDS_MeshElement * elt = ite->next();
+          meshDS->RemoveFreeElement( elt, subMeshDS );
+        }
+      }
       int nbNodes = subMeshDS->NbNodes();
       if ( nbNodes > 0 )
-        for ( SMDS_NodeIteratorPtr itn = subMeshDS->GetNodes(); itn->more() ; )
-        {
+      {
+        bool rev = true;
+        SMDS_NodeIteratorPtr itn = subMeshDS->GetNodes( rev );
+        const SMDS_MeshNode * lastNode = itn->next();
+        rev = ( lastNode->GetID() == meshDS->MaxNodeID() );
+        if ( !rev )
+          itn = subMeshDS->GetNodes( rev );
+        else
+          meshDS->RemoveNode( lastNode );
+        while (itn->more()) {
           const SMDS_MeshNode * node = itn->next();
           if ( node->NbInverseElements() == 0 )
             meshDS->RemoveFreeNode( node, subMeshDS );
           else // for StdMeshers_CompositeSegment_1D: node in one submesh, edge in another
-            meshDS->RemoveNode( node );
+            meshDS->RemoveNode(node);
         }
+      }
       subMeshDS->Clear();
     }
   }
index 73ad16111c6d62fc1f33011195dc58f3ffa54dc4..f556f1a9245d175477f2d6f2900fc7597f3d4f8b 100644 (file)
@@ -749,30 +749,30 @@ namespace
                                      SMESH::log_array_var& theSeq,
                                      CORBA::Long theId)
   {
-    // const SMESH::long_array& anIndexes = theSeq[theId].indexes;
-    // CORBA::Long iind = 0, aNbElems = theSeq[theId].number;
-
-    // for (CORBA::Long anElemId = 0; anElemId < aNbElems; anElemId++)
-    // {
-    //   // find element
-    //   const SMDS_MeshElement* elem = FindElement(theMesh, anIndexes[iind++]);
-    //   // nb nodes
-    //   int nbNodes = anIndexes[iind++];
-    //   // nodes
-    //   std::vector<const SMDS_MeshNode*> aNodes (nbNodes);
-    //   for (int iNode = 0; iNode < nbNodes; iNode++) {
-    //     aNodes[iNode] = FindNode(theMesh, anIndexes[iind++]);
-    //   }
-    //   // nb faces
-    //   int nbFaces = anIndexes[iind++];
-    //   // quantities
-    //   std::vector<int> quantities (nbFaces);
-    //   for (int iFace = 0; iFace < nbFaces; iFace++) {
-    //     quantities[iFace] = anIndexes[iind++];
-    //   }
-    //   // change
-    //   theMesh->ChangePolyhedronNodes(elem, aNodes, quantities);
-    // }
+    const SMESH::long_array& anIndexes = theSeq[theId].indexes;
+    CORBA::Long iind = 0, aNbElems = theSeq[theId].number;
+
+    for (CORBA::Long anElemId = 0; anElemId < aNbElems; anElemId++)
+    {
+      // find element
+      const SMDS_MeshElement* elem = FindElement(theMesh, anIndexes[iind++]);
+      // nb nodes
+      int nbNodes = anIndexes[iind++];
+      // nodes
+      std::vector<const SMDS_MeshNode*> aNodes (nbNodes);
+      for (int iNode = 0; iNode < nbNodes; iNode++) {
+        aNodes[iNode] = FindNode(theMesh, anIndexes[iind++]);
+      }
+      // nb faces
+      int nbFaces = anIndexes[iind++];
+      // quantities
+      std::vector<int> quantities (nbFaces);
+      for (int iFace = 0; iFace < nbFaces; iFace++) {
+        quantities[iFace] = anIndexes[iind++];
+      }
+      // change
+      theMesh->ChangePolyhedronNodes(elem, aNodes, quantities);
+    }
   }
 }
 
@@ -986,10 +986,10 @@ SMESH_Client::Update(bool theIsClear)
           ChangePolyhedronNodes(mySMDSMesh, aSeq, anId);
           break;
         case SMESH::RENUMBER:
-          // for(CORBA::Long i=0; anElemId < aNbElems; anElemId++, i+=3)
-          // {
-          //   mySMDSMesh->Renumber( anIndexes[i], anIndexes[i+1], anIndexes[i+2] );
-          // }
+          for(CORBA::Long i=0; anElemId < aNbElems; anElemId++, i+=3)
+          {
+            mySMDSMesh->Renumber( anIndexes[i], anIndexes[i+1], anIndexes[i+2] );
+          }
           break;
 
         default:;
index e6df602ff343532c4a4bda2185c1ee3ed681d323..6ffa1b19cba4e962fd5ea0db5ade44880a6afd7c 100644 (file)
 //
 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
 //
+
+//  SMESH SMESHDS : idl implementation based on 'SMESH' unit's classes
 //  File   : SMESHDS_Group.cxx
 //  Module : SMESH
+//  $Header$
 //
-
 #include "SMESHDS_Group.hxx"
 #include "SMESHDS_Mesh.hxx"
 
+using namespace std;
+
 //=============================================================================
 /*!
  *  
@@ -35,8 +39,8 @@
 SMESHDS_Group::SMESHDS_Group (const int                 theID,
                               const SMESHDS_Mesh*       theMesh,
                               const SMDSAbs_ElementType theType)
-  : SMESHDS_GroupBase(theID,theMesh,theType),
-    myGroup(theMesh,theType)
+     : SMESHDS_GroupBase(theID,theMesh,theType),
+       myGroup(theMesh,theType)
 {
 }
 
@@ -143,7 +147,20 @@ void SMESHDS_Group::Clear()
   myGroup.Clear();
   resetIterator();
 }
-  
+
+// =====================
+// class MyGroupIterator
+// =====================
+
+class MyGroupIterator: public SMDS_ElemIterator
+{
+  const SMDS_MeshGroup& myGroup;
+ public:
+  MyGroupIterator(const SMDS_MeshGroup& group): myGroup(group) { myGroup.InitIterator(); }
+  bool more() { return myGroup.More(); }
+  const SMDS_MeshElement* next() { return myGroup.Next(); }
+};
+   
 //=======================================================================
 //function : GetElements
 //purpose  : 
@@ -151,7 +168,7 @@ void SMESHDS_Group::Clear()
 
 SMDS_ElemIteratorPtr SMESHDS_Group::GetElements() const
 {
-  return myGroup.GetElements();
+  return SMDS_ElemIteratorPtr( new MyGroupIterator ( myGroup ));
 }
 
 //================================================================================
@@ -172,14 +189,11 @@ int SMESHDS_Group::GetTic() const
 
 void SMESHDS_Group::SetType(SMDSAbs_ElementType theType)
 {
-  if ( myGroup.IsEmpty() || GetType() == SMDSAbs_All )
-  {
+  if ( myGroup.IsEmpty() || GetType() == SMDSAbs_All ) {
     SMESHDS_GroupBase::SetType( theType );
     myGroup.SetType ( theType );
   }
   else
-  {
     SMESHDS_GroupBase::SetType( myGroup.GetType() );
-  }
 }
 
index e5b2fb736bd3d75362f0f6aae9a85343fc3cf8bf..7653e176ce6811b594cd62b99d60e335bf8d7079 100644 (file)
 #include "SMESHDS_GroupOnFilter.hxx"
 
 #include "SMDS_SetIterator.hxx"
-#include "ObjectPool.hxx"
 #include "SMESHDS_Mesh.hxx"
 
 #include <numeric>
 #include <limits>
 
-#include <boost/make_shared.hpp>
-
 using namespace std;
 
 //#undef WITH_TBB
@@ -48,12 +45,11 @@ SMESHDS_GroupOnFilter::SMESHDS_GroupOnFilter (const int                 theID,
                                               const SMESHDS_Mesh*       theMesh,
                                               const SMDSAbs_ElementType theType,
                                               const SMESH_PredicatePtr& thePredicate)
-  : SMESHDS_GroupBase( theID, theMesh, theType ),
-    SMDS_ElementHolder( theMesh ),
+  : SMESHDS_GroupBase(theID,theMesh,theType),
     myMeshInfo( SMDSEntity_Last, 0 ),
-    myMeshModifTime( 0 ),
-    myPredicateTic( 0 ),
-    myNbElemToSkip( 0 )
+    myMeshModifTime(0),
+    myPredicateTic(0),
+    myNbElemToSkip(0)
 {
   SetPredicate( thePredicate );
 }
@@ -536,38 +532,3 @@ SMESHDS_GroupOnFilter::setNbElemToSkip( SMDS_ElemIteratorPtr& okElemIt )
   }
   return firstOkElem;
 }
-
-//================================================================================
-/*!
- * \brief Return elements before mesh compacting
- */
-//================================================================================
-
-SMDS_ElemIteratorPtr SMESHDS_GroupOnFilter::getElements()
-{
-  return boost::make_shared< SMDS_ElementVectorIterator >( myElements.begin(), myElements.end() );
-}
-
-//================================================================================
-/*!
- * \brief clear myElements before re-filling after mesh compacting
- */
-//================================================================================
-
-void SMESHDS_GroupOnFilter::tmpClear()
-{
-  std::vector< const SMDS_MeshElement*> newElems( myElements.size() );
-  myElements.swap( newElems );
-  myElements.clear();
-}
-
-//================================================================================
-/*!
- * \brief Re-fill myElements after mesh compacting
- */
-//================================================================================
-
-void SMESHDS_GroupOnFilter::add( const SMDS_MeshElement* element )
-{
-  myElements.push_back( element );
-}
index 9b235c1a318dc31a1da240da1d7adae7284350b7..94bc25af44f4dde93e41f5ef24a565f1084c2e46 100644 (file)
 
 #include "SMESH_SMESHDS.hxx"
 
-#include "SMDS_ElementHolder.hxx"
 #include "SMESHDS_GroupBase.hxx"
 #include "SMESH_Controls.hxx"
-
+  
 /*!
  * \brief Groups whose contents is dynamically updated using the filter
  */
-class SMESHDS_EXPORT SMESHDS_GroupOnFilter: public SMESHDS_GroupBase, SMDS_ElementHolder
+class SMESHDS_EXPORT SMESHDS_GroupOnFilter: public SMESHDS_GroupBase
 {
  public:
 
@@ -70,13 +69,6 @@ class SMESHDS_EXPORT SMESHDS_GroupOnFilter: public SMESHDS_GroupBase, SMDS_Eleme
 
   bool         IsUpToDate() const;
 
- protected: // methods of SMDS_ElementHolder
-
-  virtual SMDS_ElemIteratorPtr getElements();
-  virtual void tmpClear();
-  virtual void add( const SMDS_MeshElement* element );
-  virtual void compact() {};
-
  private:
 
   void update() const;
index e973495bf8a20c10c3b2c3bdeabb78754883ea92..865e700c13332585d7087bbc0cf6195ac25c0bcd 100644 (file)
@@ -50,6 +50,8 @@
 
 #include "utilities.h"
 
+using namespace std;
+
 class SMESHDS_Mesh::SubMeshHolder : public SMESHDS_TSubMeshHolder< const SMESHDS_SubMesh >
 {
 };
@@ -103,7 +105,7 @@ int SMESHDS_Mesh::GetPersistentId() const
 //=======================================================================
 void SMESHDS_Mesh::ShapeToMesh(const TopoDS_Shape & S)
 {
-  if ( !myShape.IsNull() && S.IsNull() ) // case: "save study" after geometry removal
+  if ( !myShape.IsNull() && S.IsNull() )
   {
     // removal of a shape to mesh, delete ...
     // - hypotheses
@@ -114,7 +116,7 @@ void SMESHDS_Mesh::ShapeToMesh(const TopoDS_Shape & S)
       if ( !sm->IsComplexSubmesh() ) {
         SMDS_NodeIteratorPtr nIt = sm->GetNodes();
         while ( nIt->more() )
-          sm->RemoveNode(nIt->next());
+          sm->RemoveNode(nIt->next(), false);
       }
     }
     // - sub-meshes
@@ -122,7 +124,7 @@ void SMESHDS_Mesh::ShapeToMesh(const TopoDS_Shape & S)
 
     myIndexToShape.Clear();
     // - groups on geometry
-    std::set<SMESHDS_GroupBase*>::iterator gr = myGroups.begin();
+    set<SMESHDS_GroupBase*>::iterator gr = myGroups.begin();
     while ( gr != myGroups.end() ) {
       if ( dynamic_cast<SMESHDS_GroupOnGeom*>( *gr ))
         myGroups.erase( gr++ );
@@ -135,8 +137,6 @@ void SMESHDS_Mesh::ShapeToMesh(const TopoDS_Shape & S)
     if ( !S.IsNull() )
       TopExp::MapShapes(myShape, myIndexToShape);
   }
-
-  SMDS_Mesh::setNbShapes( MaxShapeIndex() );
 }
 
 //=======================================================================
@@ -148,14 +148,14 @@ bool SMESHDS_Mesh::AddHypothesis(const TopoDS_Shape & SS,
                                  const SMESHDS_Hypothesis * H)
 {
   if (!myShapeToHypothesis.IsBound(SS/*.Oriented(TopAbs_FORWARD)*/)) {
-    std::list<const SMESHDS_Hypothesis *> aList;
+    list<const SMESHDS_Hypothesis *> aList;
     myShapeToHypothesis.Bind(SS/*.Oriented(TopAbs_FORWARD)*/, aList);
   }
-  std::list<const SMESHDS_Hypothesis *>& alist =
+  list<const SMESHDS_Hypothesis *>& alist =
     myShapeToHypothesis(SS/*.Oriented(TopAbs_FORWARD)*/); // ignore orientation of SS
 
   //Check if the Hypothesis is still present
-  std::list<const SMESHDS_Hypothesis*>::iterator ith = find(alist.begin(),alist.end(), H );
+  list<const SMESHDS_Hypothesis*>::iterator ith = find(alist.begin(),alist.end(), H );
 
   if (alist.end() != ith) return false;
 
@@ -173,8 +173,8 @@ bool SMESHDS_Mesh::RemoveHypothesis(const TopoDS_Shape &       S,
 {
   if( myShapeToHypothesis.IsBound( S/*.Oriented(TopAbs_FORWARD)*/ ) )
   {
-    std::list<const SMESHDS_Hypothesis *>& alist=myShapeToHypothesis.ChangeFind( S/*.Oriented(TopAbs_FORWARD)*/ );
-    std::list<const SMESHDS_Hypothesis*>::iterator ith=find(alist.begin(),alist.end(), H );
+    list<const SMESHDS_Hypothesis *>& alist=myShapeToHypothesis.ChangeFind( S/*.Oriented(TopAbs_FORWARD)*/ );
+    list<const SMESHDS_Hypothesis*>::iterator ith=find(alist.begin(),alist.end(), H );
     if (ith != alist.end())
     {
       alist.erase(ith);
@@ -223,7 +223,7 @@ bool SMESHDS_Mesh::ChangeElementNodes(const SMDS_MeshElement * elem,
   if ( ! SMDS_Mesh::ChangeElementNodes( elem, nodes, nbnodes ))
     return false;
 
-  std::vector<int> IDs( nbnodes );
+  vector<int> IDs( nbnodes );
   for ( int i = 0; i < nbnodes; i++ )
     IDs [ i ] = nodes[ i ]->GetID();
   myScript->ChangeElementNodes( elem->GetID(), &IDs[0], nbnodes);
@@ -236,8 +236,8 @@ bool SMESHDS_Mesh::ChangeElementNodes(const SMDS_MeshElement * elem,
 //purpose  : 
 //=======================================================================
 bool SMESHDS_Mesh::ChangePolygonNodes
-(const SMDS_MeshElement *     elem,
std::vector<const SMDS_MeshNode*> nodes)
+                   (const SMDS_MeshElement *     elem,
                   vector<const SMDS_MeshNode*> nodes)
 {
   ASSERT(nodes.size() > 3);
 
@@ -249,14 +249,14 @@ bool SMESHDS_Mesh::ChangePolygonNodes
 //purpose  : 
 //=======================================================================
 bool SMESHDS_Mesh::ChangePolyhedronNodes
-(const SMDS_MeshElement * elem,
- std::vector<const SMDS_MeshNode*> nodes,
- std::vector<int>                  quantities)
+                   (const SMDS_MeshElement * elem,
                   std::vector<const SMDS_MeshNode*> nodes,
                   std::vector<int>                  quantities)
 {
   ASSERT(nodes.size() > 3);
 
-  //if (!SMDS_Mesh::ChangePolyhedronNodes(elem, nodes, quantities))
-  return false;
+  if (!SMDS_Mesh::ChangePolyhedronNodes(elem, nodes, quantities))
+    return false;
 
   int i, len = nodes.size();
   std::vector<int> nodes_ids (len);
@@ -276,10 +276,10 @@ bool SMESHDS_Mesh::ChangePolyhedronNodes
 void SMESHDS_Mesh::Renumber (const bool isNodes, const int startID, const int deltaID)
 {
   // TODO not possible yet to have node numbers not starting to O and continuous.
-  if ( !this->IsCompacted() )
-    this->CompactMesh();
-  //  SMDS_Mesh::Renumber( isNodes, startID, deltaID );
-  //  myScript->Renumber( isNodes, startID, deltaID );
+  if (!this->isCompacted())
+    this->compactMesh();
+//  SMDS_Mesh::Renumber( isNodes, startID, deltaID );
+//  myScript->Renumber( isNodes, startID, deltaID );
 }
 
 //=======================================================================
@@ -294,7 +294,7 @@ SMDS_Mesh0DElement* SMESHDS_Mesh::Add0DElementWithID(int nodeID, int ID)
 }
 
 SMDS_Mesh0DElement* SMESHDS_Mesh::Add0DElementWithID
-(const SMDS_MeshNode * node, int ID)
+                                  (const SMDS_MeshNode * node, int ID)
 {
   return Add0DElementWithID(node->GetID(), ID);
 }
@@ -801,9 +801,9 @@ SMDS_MeshVolume* SMESHDS_Mesh::AddPolyhedralVolumeWithID (const std::vector<int>
 }
 
 SMDS_MeshVolume* SMESHDS_Mesh::AddPolyhedralVolumeWithID
-(const std::vector<const SMDS_MeshNode*>& nodes,
- const std::vector<int>&                  quantities,
- const int                                ID)
+                               (const std::vector<const SMDS_MeshNode*>& nodes,
                               const std::vector<int>&                  quantities,
                               const int                                ID)
 {
   SMDS_MeshVolume *anElem = SMDS_Mesh::AddPolyhedralVolumeWithID(nodes, quantities, ID);
   if (anElem) {
@@ -818,8 +818,8 @@ SMDS_MeshVolume* SMESHDS_Mesh::AddPolyhedralVolumeWithID
 }
 
 SMDS_MeshVolume* SMESHDS_Mesh::AddPolyhedralVolume
-(const std::vector<const SMDS_MeshNode*>& nodes,
- const std::vector<int>&                  quantities)
+                               (const std::vector<const SMDS_MeshNode*>& nodes,
                               const std::vector<int>&                  quantities)
 {
   SMDS_MeshVolume *anElem = SMDS_Mesh::AddPolyhedralVolume(nodes, quantities);
   if (anElem) {
@@ -838,9 +838,10 @@ SMDS_MeshVolume* SMESHDS_Mesh::AddPolyhedralVolume
 //purpose  : 
 //=======================================================================
 
-static void removeFromContainers (SMESHDS_Mesh*                         theMesh,
-                                  std::set<SMESHDS_GroupBase*>&         theGroups,
-                                  std::vector<const SMDS_MeshElement*>& theElems)
+static void removeFromContainers (SMESHDS_Mesh*                  theMesh,
+                                  set<SMESHDS_GroupBase*>&       theGroups,
+                                  list<const SMDS_MeshElement*>& theElems,
+                                  const bool                     isNode)
 {
   if ( theElems.empty() )
     return;
@@ -849,13 +850,13 @@ static void removeFromContainers (SMESHDS_Mesh*                         theMesh,
   // Element can belong to several groups
   if ( !theGroups.empty() )
   {
-    std::set<SMESHDS_GroupBase*>::iterator GrIt = theGroups.begin();
+    set<SMESHDS_GroupBase*>::iterator GrIt = theGroups.begin();
     for ( ; GrIt != theGroups.end(); GrIt++ )
     {
       SMESHDS_Group* group = dynamic_cast<SMESHDS_Group*>( *GrIt );
       if ( !group || group->IsEmpty() ) continue;
 
-      std::vector<const SMDS_MeshElement *>::iterator elIt = theElems.begin();
+      list<const SMDS_MeshElement *>::iterator elIt = theElems.begin();
       for ( ; elIt != theElems.end(); elIt++ )
       {
         group->SMDSGroup().Remove( *elIt );
@@ -864,24 +865,24 @@ static void removeFromContainers (SMESHDS_Mesh*                         theMesh,
     }
   }
 
-  //const bool deleted=true;
+  const bool deleted=true;
 
   // Rm from sub-meshes
   // Element should belong to only one sub-mesh
-  // if ( theMesh->SubMeshes()->more() )
-  // {
-  //   std::list<const SMDS_MeshElement *>::iterator elIt = theElems.begin();
-  //   if ( isNode ) {
-  //     for ( ; elIt != theElems.end(); ++elIt )
-  //       if ( SMESHDS_SubMesh* sm = theMesh->MeshElements( (*elIt)->getshapeId() ))
-  //         sm->RemoveNode( static_cast<const SMDS_MeshNode*> (*elIt), deleted );
-  //   }
-  //   else {
-  //     for ( ; elIt != theElems.end(); ++elIt )
-  //       if ( SMESHDS_SubMesh* sm = theMesh->MeshElements( (*elIt)->getshapeId() ))
-  //         sm->RemoveElement( *elIt, deleted );
-  //   }
-  // }
+  if ( theMesh->SubMeshes()->more() )
+  {
+    list<const SMDS_MeshElement *>::iterator elIt = theElems.begin();
+    if ( isNode ) {
+      for ( ; elIt != theElems.end(); ++elIt )
+        if ( SMESHDS_SubMesh* sm = theMesh->MeshElements( (*elIt)->getshapeId() ))
+          sm->RemoveNode( static_cast<const SMDS_MeshNode*> (*elIt), deleted );
+    }
+    else {
+      for ( ; elIt != theElems.end(); ++elIt )
+        if ( SMESHDS_SubMesh* sm = theMesh->MeshElements( (*elIt)->getshapeId() ))
+          sm->RemoveElement( *elIt, deleted );
+    }
+  }
 }
 
 //=======================================================================
@@ -890,69 +891,56 @@ static void removeFromContainers (SMESHDS_Mesh*                         theMesh,
 //=======================================================================
 void SMESHDS_Mesh::RemoveNode(const SMDS_MeshNode * n)
 {
-  if ( RemoveFreeNode( n, 0, true ))
+  if ( n->NbInverseElements() == 0 && !(hasConstructionEdges() || hasConstructionFaces()))
+  {
+    RemoveFreeNode( n, 0, true );
     return;
+  }
 
   myScript->RemoveNode(n->GetID());
 
-  // remove inverse elements from the sub-meshes
-  for ( SMDS_ElemIteratorPtr eIt = n->GetInverseElementIterator(); eIt->more() ; )
-  {
-    const SMDS_MeshElement* e = eIt->next();
-    if ( SMESHDS_SubMesh * sm = MeshElements( e->getshapeId() ))
-      sm->RemoveElement( e );
-  }
-  if ( SMESHDS_SubMesh * sm = MeshElements( n->getshapeId() ))
-    sm->RemoveNode( n );
-    
-  
-  std::vector<const SMDS_MeshElement *> removedElems;
-  std::vector<const SMDS_MeshElement *> removedNodes;
+  list<const SMDS_MeshElement *> removedElems;
+  list<const SMDS_MeshElement *> removedNodes;
 
   SMDS_Mesh::RemoveElement( n, removedElems, removedNodes, true );
 
-  removeFromContainers( this, myGroups, removedElems );
-  removeFromContainers( this, myGroups, removedNodes );
+  removeFromContainers( this, myGroups, removedElems, false );
+  removeFromContainers( this, myGroups, removedNodes, true );
 }
 
 //=======================================================================
 //function : RemoveFreeNode
 //purpose  : 
 //=======================================================================
-bool SMESHDS_Mesh::RemoveFreeNode(const SMDS_MeshNode * n,
+void SMESHDS_Mesh::RemoveFreeNode(const SMDS_MeshNode * n,
                                   SMESHDS_SubMesh *     subMesh,
                                   bool                  fromGroups)
 {
-  if ( n->NbInverseElements() > 0 )
-    return false;
-
   myScript->RemoveNode(n->GetID());
 
   // Rm from group
   // Node can belong to several groups
-  if ( fromGroups && !myGroups.empty() ) {
-    std::set<SMESHDS_GroupBase*>::iterator GrIt = myGroups.begin();
+  if (fromGroups && !myGroups.empty()) {
+    set<SMESHDS_GroupBase*>::iterator GrIt = myGroups.begin();
     for (; GrIt != myGroups.end(); GrIt++) {
       SMESHDS_Group* group = dynamic_cast<SMESHDS_Group*>(*GrIt);
-      if (group && group->GetType() == SMDSAbs_Node )
+      if (group && !group->IsEmpty())
         group->SMDSGroup().Remove(n);
     }
   }
 
   // Rm from sub-mesh
   // Node should belong to only one sub-mesh
-  if ( !subMesh || !subMesh->RemoveNode( n ))
+  if ( !subMesh || !subMesh->RemoveNode(n,/*deleted=*/false))
     if (( subMesh = MeshElements( n->getshapeId() )))
-      subMesh->RemoveNode(n);
+      subMesh->RemoveNode(n,/*deleted=*/false );
 
   SMDS_Mesh::RemoveFreeElement(n);
-
-  return true;
 }
 
 //=======================================================================
 //function : RemoveElement
-//purpose  :
+//purpose  : 
 //========================================================================
 void SMESHDS_Mesh::RemoveElement(const SMDS_MeshElement * elt)
 {
@@ -961,7 +949,7 @@ void SMESHDS_Mesh::RemoveElement(const SMDS_MeshElement * elt)
     RemoveNode( static_cast<const SMDS_MeshNode*>( elt ));
     return;
   }
-  //if (!hasConstructionEdges() && !hasConstructionFaces())
+  if (!hasConstructionEdges() && !hasConstructionFaces())
   {
     SMESHDS_SubMesh* subMesh=0;
     if ( elt->getshapeId() > 0 )
@@ -973,12 +961,12 @@ void SMESHDS_Mesh::RemoveElement(const SMDS_MeshElement * elt)
  
   myScript->RemoveElement(elt->GetID());
 
-  std::vector<const SMDS_MeshElement *> removedElems;
-  std::vector<const SMDS_MeshElement *> removedNodes;
+  list<const SMDS_MeshElement *> removedElems;
+  list<const SMDS_MeshElement *> removedNodes;
 
-  SMDS_Mesh::RemoveElement(elt, removedElems, removedNodes );
+  SMDS_Mesh::RemoveElement(elt, removedElems, removedNodes, false );
   
-  removeFromContainers( this, myGroups, removedElems );
+  removeFromContainers( this, myGroups, removedElems, false );
 }
 
 //=======================================================================
@@ -994,16 +982,16 @@ void SMESHDS_Mesh::RemoveFreeElement(const SMDS_MeshElement * elt,
     return;
   }
 
-  // if (hasConstructionEdges() || hasConstructionFaces())
-  //   // this methods is only for meshes without descendants
-  //   return;
+  if (hasConstructionEdges() || hasConstructionFaces())
+    // this methods is only for meshes without descendants
+    return;
 
   myScript->RemoveElement(elt->GetID());
 
   // Rm from group
   // Element can belong to several groups
   if ( fromGroups && !myGroups.empty() ) {
-    std::set<SMESHDS_GroupBase*>::iterator GrIt = myGroups.begin();
+    set<SMESHDS_GroupBase*>::iterator GrIt = myGroups.begin();
     for (; GrIt != myGroups.end(); GrIt++) {
       SMESHDS_Group* group = dynamic_cast<SMESHDS_Group*>(*GrIt);
       if (group && !group->IsEmpty())
@@ -1016,7 +1004,7 @@ void SMESHDS_Mesh::RemoveFreeElement(const SMDS_MeshElement * elt,
   if ( !subMesh && elt->getshapeId() > 0 )
     subMesh = MeshElements( elt->getshapeId() );
   if ( subMesh )
-    subMesh->RemoveElement( elt );
+    subMesh->RemoveElement( elt, /*deleted=*/false );
 
   SMDS_Mesh::RemoveFreeElement( elt );
 }
@@ -1055,8 +1043,8 @@ void SMESHDS_Mesh::ClearMesh()
 //================================================================================
 /*!
  * \brief return submesh by shape
- * \param shape - the sub-shape
- * \retval SMESHDS_SubMesh* - the found submesh
 * \param shape - the sub-shape
 * \retval SMESHDS_SubMesh* - the found submesh
  */
 //================================================================================
 
@@ -1071,81 +1059,84 @@ SMESHDS_SubMesh* SMESHDS_Mesh::getSubmesh( const TopoDS_Shape & shape )
 //================================================================================
 /*!
  * \brief Add element or node to submesh
- * \param elem - element to add
- * \param subMesh - submesh to be filled in
 * \param elem - element to add
 * \param subMesh - submesh to be filled in
  */
 //================================================================================
 
-int SMESHDS_Mesh::add(const SMDS_MeshElement* elem, SMESHDS_SubMesh* subMesh )
+bool SMESHDS_Mesh::add(const SMDS_MeshElement* elem, SMESHDS_SubMesh* subMesh )
 {
   if ( elem && subMesh ) {
-    subMesh->AddElement( elem );
-    return subMesh->GetID();
+    if ( elem->GetType() == SMDSAbs_Node )
+      subMesh->AddNode( static_cast<const SMDS_MeshNode* >( elem ));
+    else
+      subMesh->AddElement( elem );
+    return true;
   }
-  return 0;
+  return false;
 }
 
 //=======================================================================
 //function : SetNodeOnVolume
-//purpose  :
+//purpose  : 
 //=======================================================================
 void SMESHDS_Mesh::SetNodeInVolume(const SMDS_MeshNode* aNode,
                                    const TopoDS_Shell & S)
 {
-  if ( int shapeID = add( aNode, getSubmesh( S )))
+  if ( add( aNode, getSubmesh(S) ))
     const_cast< SMDS_MeshNode* >
-      ( aNode )->SetPosition( SMDS_SpacePosition::originSpacePosition(), shapeID );
+      ( aNode )->SetPosition( SMDS_SpacePosition::originSpacePosition() );
 }
 
 //=======================================================================
 //function : SetNodeOnVolume
-//purpose  :
+//purpose  : 
 //=======================================================================
 void SMESHDS_Mesh::SetNodeInVolume(const SMDS_MeshNode *      aNode,
                                    const TopoDS_Solid & S)
 {
-  if ( int shapeID = add( aNode, getSubmesh( S )))
+  if ( add( aNode, getSubmesh(S) ))
     const_cast< SMDS_MeshNode* >
-      ( aNode )->SetPosition( SMDS_SpacePosition::originSpacePosition(), shapeID );
+      ( aNode )->SetPosition( SMDS_SpacePosition::originSpacePosition() );
 }
 
 //=======================================================================
 //function : SetNodeOnFace
-//purpose  :
+//purpose  : 
 //=======================================================================
-void SMESHDS_Mesh::SetNodeOnFace(const SMDS_MeshNode * aNode,
-                                 const TopoDS_Face &   S,
-                                 double                u,
-                                 double                v)
+void SMESHDS_Mesh::SetNodeOnFace(const SMDS_MeshNode *     aNode,
+                                 const TopoDS_Face & S,
+                                 double              u,
+                                 double              v)
 {
-  if ( int shapeID = add( aNode, getSubmesh( S )))
+  if ( add( aNode, getSubmesh(S) ))
     const_cast< SMDS_MeshNode* >
-      ( aNode )->SetPosition(SMDS_PositionPtr( new SMDS_FacePosition( u, v )), shapeID );
+      ( aNode )->SetPosition(SMDS_PositionPtr(new SMDS_FacePosition( u, v)));
 }
 
 //=======================================================================
 //function : SetNodeOnEdge
-//purpose  :
+//purpose  : 
 //=======================================================================
-void SMESHDS_Mesh::SetNodeOnEdge(const SMDS_MeshNode * aNode,
-                                 const TopoDS_Edge &   S,
-                                 double                u)
+void SMESHDS_Mesh::SetNodeOnEdge(const SMDS_MeshNode *     aNode,
+                                 const TopoDS_Edge & S,
+                                 double              u)
 {
-  if ( int shapeID = add( aNode, getSubmesh( S )))
+  if ( add( aNode, getSubmesh(S) ))
     const_cast< SMDS_MeshNode* >
-      ( aNode )->SetPosition(SMDS_PositionPtr( new SMDS_EdgePosition( u )), shapeID );
+      ( aNode )->SetPosition(SMDS_PositionPtr(new SMDS_EdgePosition(u)));
 }
 
 //=======================================================================
 //function : SetNodeOnVertex
-//purpose  :
+//purpose  : 
 //=======================================================================
-void SMESHDS_Mesh::SetNodeOnVertex(const SMDS_MeshNode * aNode,
+void SMESHDS_Mesh::SetNodeOnVertex(const SMDS_MeshNode *       aNode,
                                    const TopoDS_Vertex & S)
 {
-  if ( int shapeID = add( aNode, getSubmesh( S )))
+  if ( add( aNode, getSubmesh(S) ))
     const_cast< SMDS_MeshNode* >
-      ( aNode )->SetPosition(SMDS_PositionPtr( new SMDS_VertexPosition()), shapeID );
+      ( aNode )->SetPosition(SMDS_PositionPtr(new SMDS_VertexPosition()));
 }
 
 //=======================================================================
@@ -1157,12 +1148,12 @@ void SMESHDS_Mesh::UnSetNodeOnShape(const SMDS_MeshNode* aNode)
   int shapeId = aNode->getshapeId();
   if (shapeId > 0)
     if ( SMESHDS_SubMesh* sm = MeshElements( shapeId ))
-      sm->RemoveNode(aNode);
+      sm->RemoveNode(aNode, /*deleted=*/false);
 }
 
 //=======================================================================
 //function : SetMeshElementOnShape
-//purpose  :
+//purpose  : 
 //=======================================================================
 void SMESHDS_Mesh::SetMeshElementOnShape(const SMDS_MeshElement * anElement,
                                          const TopoDS_Shape &     S)
@@ -1178,7 +1169,12 @@ void SMESHDS_Mesh::UnSetMeshElementOnShape(const SMDS_MeshElement * elem,
                                            const TopoDS_Shape &     S)
 {
   if ( SMESHDS_SubMesh* sm = MeshElements( S ))
-    sm->RemoveElement(elem);
+  {
+    if (elem->GetType() == SMDSAbs_Node)
+      sm->RemoveNode(static_cast<const SMDS_MeshNode*> (elem), /*deleted=*/false);
+    else
+      sm->RemoveElement(elem, /*deleted=*/false);
+  }
 }
 
 //=======================================================================
@@ -1230,9 +1226,9 @@ SMESHDS_SubMesh * SMESHDS_Mesh::MeshElements(const int Index) const
 //function : SubMeshIndices
 //purpose  : 
 //=======================================================================
-std::list<int> SMESHDS_Mesh::SubMeshIndices() const
+list<int> SMESHDS_Mesh::SubMeshIndices() const
 {
-  std::list<int> anIndices;
+  list<int> anIndices;
   SMESHDS_SubMeshIteratorPtr smIt = SubMeshes();
   while ( const SMESHDS_SubMesh* sm = smIt->next() )
     anIndices.push_back( sm->GetID() );
@@ -1255,13 +1251,13 @@ SMESHDS_SubMeshIteratorPtr SMESHDS_Mesh::SubMeshes() const
 //purpose  : 
 //=======================================================================
 
-const std::list<const SMESHDS_Hypothesis*>&
+const list<const SMESHDS_Hypothesis*>&
 SMESHDS_Mesh::GetHypothesis(const TopoDS_Shape & S) const
 {
   if ( myShapeToHypothesis.IsBound( S/*.Oriented(TopAbs_FORWARD)*/ ) ) // ignore orientation of S
-    return myShapeToHypothesis.Find( S/*.Oriented(TopAbs_FORWARD)*/ );
+     return myShapeToHypothesis.Find( S/*.Oriented(TopAbs_FORWARD)*/ );
 
-  static std::list<const SMESHDS_Hypothesis*> empty;
+  static list<const SMESHDS_Hypothesis*> empty;
   return empty;
 }
 
@@ -1286,7 +1282,7 @@ bool SMESHDS_Mesh::IsUsedHypothesis(const SMESHDS_Hypothesis * H) const
 //=======================================================================
 SMESHDS_Script* SMESHDS_Mesh::GetScript()
 {
-  return myScript;
+        return myScript;
 }
 
 //=======================================================================
@@ -1295,7 +1291,7 @@ SMESHDS_Script* SMESHDS_Mesh::GetScript()
 //=======================================================================
 void SMESHDS_Mesh::ClearScript()
 {
-  myScript->Clear();
+        myScript->Clear();
 }
 
 //=======================================================================
@@ -1412,46 +1408,46 @@ int SMESHDS_Mesh::ShapeToIndex(const TopoDS_Shape & S) const
 //=======================================================================
 void SMESHDS_Mesh::SetNodeInVolume(const SMDS_MeshNode* aNode, int Index)
 {
-  if ( int shapeID = add( aNode, NewSubMesh( Index )))
-    ((SMDS_MeshNode*) aNode)->SetPosition( SMDS_SpacePosition::originSpacePosition(), shapeID );
+  if ( add( aNode, NewSubMesh( Index )))
+    ((SMDS_MeshNode*) aNode)->SetPosition( SMDS_SpacePosition::originSpacePosition());
 }
 
 //=======================================================================
 //function : SetNodeOnFace
-//purpose  :
+//purpose  : 
 //=======================================================================
 void SMESHDS_Mesh::SetNodeOnFace(const SMDS_MeshNode* aNode, int Index, double u, double v)
 {
   //Set Position on Node
-  if ( int shapeID = add( aNode, NewSubMesh( Index )))
+  if ( add( aNode, NewSubMesh( Index )))
     const_cast< SMDS_MeshNode* >
-      ( aNode )->SetPosition(SMDS_PositionPtr(new SMDS_FacePosition( u, v )), shapeID );
+      ( aNode )->SetPosition(SMDS_PositionPtr(new SMDS_FacePosition( u, v)));
 }
 
 //=======================================================================
 //function : SetNodeOnEdge
-//purpose  :
+//purpose  : 
 //=======================================================================
 void SMESHDS_Mesh::SetNodeOnEdge(const SMDS_MeshNode* aNode,
                                  int                  Index,
                                  double               u)
 {
   //Set Position on Node
-  if (  int shapeID = add( aNode, NewSubMesh( Index )))
+  if ( add( aNode, NewSubMesh( Index )))
     const_cast< SMDS_MeshNode* >
-      ( aNode )->SetPosition(SMDS_PositionPtr(new SMDS_EdgePosition( u )), shapeID );
+      ( aNode )->SetPosition(SMDS_PositionPtr(new SMDS_EdgePosition(u)));
 }
 
 //=======================================================================
 //function : SetNodeOnVertex
-//purpose  :
+//purpose  : 
 //=======================================================================
 void SMESHDS_Mesh::SetNodeOnVertex(const SMDS_MeshNode* aNode, int Index)
 {
   //Set Position on Node
-  if (  int shapeID = add( aNode, NewSubMesh( Index )))
+  if ( add( aNode, NewSubMesh( Index )))
     const_cast< SMDS_MeshNode* >
-      ( aNode )->SetPosition(SMDS_PositionPtr(new SMDS_VertexPosition()), shapeID );
+      ( aNode )->SetPosition(SMDS_PositionPtr(new SMDS_VertexPosition()));
 }
 
 //=======================================================================
@@ -2217,7 +2213,7 @@ SMDS_MeshVolume* SMESHDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
                                                const SMDS_MeshNode * n15,
                                                const SMDS_MeshNode * n26,
                                                const SMDS_MeshNode * n37,
-                                               const SMDS_MeshNode * n48,
+                                               const SMDS_MeshNode * n48, 
                                                const SMDS_MeshNode * n1234,
                                                const SMDS_MeshNode * n1256,
                                                const SMDS_MeshNode * n2367,
@@ -2236,14 +2232,126 @@ SMDS_MeshVolume* SMESHDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
                          n1458->GetID(),n5678->GetID(),nCenter->GetID(), ID);
 }
 
-void SMESHDS_Mesh::CompactMesh()
+void SMESHDS_Mesh::compactMesh()
 {
-  if ( IsCompacted() )
+  if ( isCompacted() )
     return;
+  SMDS_Mesh::compactMesh();
+
+  int newNodeSize = 0;
+  int nbNodes     = myNodes.size();
+  int nbVtkNodes  = myGrid->GetNumberOfPoints();
+  int nbNodeTemp  = Max( nbVtkNodes, nbNodes );
+  vector<int> idNodesOldToNew(nbNodeTemp, -1); // all unused id will be -1
+
+  for (int i = 0; i < nbNodes; i++)
+  {
+    if (myNodes[i])
+    {
+      int vtkid = myNodes[i]->getVtkId();
+      idNodesOldToNew[vtkid] = i; // old vtkId --> old smdsId (valid smdsId are >= 0)
+      newNodeSize++;
+    }
+  }
+  bool areNodesModified = (newNodeSize != nbVtkNodes);
+  areNodesModified = true;
+
+  int newCellSize = 0;
+  int nbCells     = myCells.size();
+  int nbVtkCells  = myGrid->GetNumberOfCells();
+  int nbCellTemp  = Max( nbVtkCells, nbCells );
+  vector<int> idCellsOldToNew(nbCellTemp, -1); // all unused id will be -1
+
+  for (int i = 0; i < nbCells; i++)
+  {
+    if (myCells[i])
+    {
+      newCellSize++;
+    }
+  }
+  if (areNodesModified)
+    myGrid->compactGrid(idNodesOldToNew, newNodeSize, idCellsOldToNew, newCellSize);
+  else
+    myGrid->compactGrid(idNodesOldToNew, 0, idCellsOldToNew, newCellSize);
+
+  int nbVtkPts = myGrid->GetNumberOfPoints();
+  nbVtkCells = myGrid->GetNumberOfCells();
+  if (nbVtkPts != newNodeSize)
+  {
+    MESSAGE("===> nbVtkPts != newNodeSize " << nbVtkPts << " " << newNodeSize);
+    if (nbVtkPts > newNodeSize) newNodeSize = nbVtkPts; // several points with same SMDS Id
+  }
+  if (nbVtkCells != newCellSize)
+  {
+    MESSAGE("===> nbVtkCells != newCellSize " << nbVtkCells << " " << newCellSize);
+    if (nbVtkCells > newCellSize) newCellSize = nbVtkCells; // several cells with same SMDS Id
+  }
 
-  SMDS_Mesh::CompactMesh();
+  // --- SMDS_MeshNode and myNodes, myNodeIdFactory
+
+  if ( true )
+  {
+    SetOfNodes newNodes(newNodeSize+1,NULL); // 0 not used, SMDS numbers 1..n
+    int newSmdsId = 0;
+    for (int i = 0; i < nbNodes; i++)
+    {
+      if (myNodes[i])
+      {
+        newSmdsId++; // SMDS id starts from 1
+        int oldVtkId = myNodes[i]->getVtkId();
+        int newVtkId = idNodesOldToNew[oldVtkId];
+        myNodes[i]->setVtkId(newVtkId);
+        myNodes[i]->setId(newSmdsId);
+        newNodes[newSmdsId] = myNodes[i];
+      }
+    }
+    myNodes.swap(newNodes);
+    this->myNodeIDFactory->emptyPool(newSmdsId); // newSmdsId = number of nodes
+  }
+
+  // --- SMDS_MeshCell, myCellIdVtkToSmds, myCellIdSmdsToVtk, myCells
+
+  int vtkIndexSize = myCellIdVtkToSmds.size();
+  for (int oldVtkId = 0; oldVtkId < vtkIndexSize; oldVtkId++)
+  {
+    int oldSmdsId = this->myCellIdVtkToSmds[oldVtkId];
+    if (oldSmdsId > 0)
+    {
+      int newVtkId = idCellsOldToNew[oldVtkId];
+      myCells[oldSmdsId]->setVtkId(newVtkId);
+    }
+  }
+
+  SetOfCells      newCells(newCellSize+1, NULL); // 0 not used, SMDS numbers 1..n
+  vector<int> newVtkToSmds(newCellSize+1, -1);
+
+  int myCellsSize = myCells.size();
+  int newSmdsId = 0;
+  for (int i = 0; i < myCellsSize; i++)
+  {
+    if ( myCells[i] )
+    {
+      newSmdsId++; // SMDS id starts from 1
+      assert(newSmdsId <= newCellSize);
+      newCells[newSmdsId] = myCells[i];
+      newCells[newSmdsId]->setId(newSmdsId);
+      int idvtk = myCells[i]->getVtkId();
+      assert(idvtk < newCellSize);
+      newVtkToSmds[idvtk] = newSmdsId;
+    }
+  }
+
+  myCells.swap(newCells);
+  myCellIdVtkToSmds.swap(newVtkToSmds);
+  this->myElementIDFactory->emptyPool(newSmdsId);
 
   this->myScript->SetModified(true); // notify GUI client for buildPrs when update
+
+  // --- compact list myNodes and myElements in submeshes
+
+  SMESHDS_SubMeshIteratorPtr smIt = SubMeshes();
+  while ( SMESHDS_SubMesh* sm = const_cast< SMESHDS_SubMesh* >( smIt->next() ))
+    sm->compactList();
 }
 
 void SMESHDS_Mesh::CleanDownWardConnectivity()
index 51baee630af1e6b3b9adbd17a5785de8e66b1128..92f631890ed558fb02a0d17d91a74548c109ae84 100644 (file)
@@ -66,7 +66,7 @@ class DownIdType;
 
 class SMESHDS_EXPORT SMESHDS_Mesh : public SMDS_Mesh
 {
- public:
+public:
   SMESHDS_Mesh(int theMeshID, bool theIsEmbeddedMode);
   bool IsEmbeddedMode();
   void SetPersistentId(int id);
@@ -566,18 +566,18 @@ class SMESHDS_EXPORT SMESHDS_Mesh : public SMDS_Mesh
   virtual SMDS_MeshFace* AddQuadPolygonalFace(const std::vector<const SMDS_MeshNode*> & nodes);
 
   virtual SMDS_MeshVolume* AddPolyhedralVolumeWithID
-    (const std::vector<int>& nodes_ids,
-     const std::vector<int>& quantities,
-     const int               ID);
+                           (const std::vector<int>& nodes_ids,
+                            const std::vector<int>& quantities,
+                            const int               ID);
 
   virtual SMDS_MeshVolume* AddPolyhedralVolumeWithID
-    (const std::vector<const SMDS_MeshNode*>& nodes,
-     const std::vector<int>&                  quantities,
-     const int                                ID);
+                           (const std::vector<const SMDS_MeshNode*>& nodes,
+                            const std::vector<int>&                  quantities,
+                            const int                                ID);
 
   virtual SMDS_MeshVolume* AddPolyhedralVolume
-    (const std::vector<const SMDS_MeshNode*>& nodes,
-     const std::vector<int>&                  quantities);
+                           (const std::vector<const SMDS_MeshNode*>& nodes,
+                            const std::vector<int>&                  quantities);
 
   virtual void MoveNode(const SMDS_MeshNode *, double x, double y, double z);
   virtual void RemoveNode(const SMDS_MeshNode *);
@@ -587,7 +587,7 @@ class SMESHDS_EXPORT SMESHDS_Mesh : public SMDS_Mesh
    *  Methods do not work for meshes with descendants.
    *  Implemented for fast cleaning of meshes.
    */
-  bool RemoveFreeNode   (const SMDS_MeshNode *,    SMESHDS_SubMesh *, bool fromGroups=true);
+  void RemoveFreeNode   (const SMDS_MeshNode *,    SMESHDS_SubMesh *, bool fromGroups=true);
   void RemoveFreeElement(const SMDS_MeshElement *, SMESHDS_SubMesh *, bool fromGroups=true);
 
   void ClearMesh();
@@ -646,13 +646,13 @@ class SMESHDS_EXPORT SMESHDS_Mesh : public SMDS_Mesh
 
   bool IsGroupOfSubShapes (const TopoDS_Shape& aSubShape) const;
 
-  virtual void CompactMesh();
+  virtual void compactMesh();
   void CleanDownWardConnectivity();
   void BuildDownWardConnectivity(bool withEdges);
 
   ~SMESHDS_Mesh();
   
- private:
+private:
 
   ShapeToHypothesis          myShapeToHypothesis;
 
@@ -665,12 +665,12 @@ class SMESHDS_EXPORT SMESHDS_Mesh : public SMDS_Mesh
   TopTools_IndexedMapOfShape myIndexToShape;
 
   typedef std::set<SMESHDS_GroupBase*> TGroups;
-  TGroups                    myGroups;
+  TGroups myGroups;
 
   SMESHDS_Script*            myScript;
   bool                       myIsEmbeddedMode;
 
-  int add( const SMDS_MeshElement* elem, SMESHDS_SubMesh* subMesh );
+  bool add( const SMDS_MeshElement* elem, SMESHDS_SubMesh* subMesh );
   SMESHDS_SubMesh* getSubmesh( const TopoDS_Shape & shape);
 };
 
index 4a086e3b7073fc8d84be84192fe8c158b8302076..89287301641073332320037784571d4cf499aa12 100644 (file)
 //  $Header: 
 //
 #include "SMESHDS_SubMesh.hxx"
-
 #include "SMESHDS_Mesh.hxx"
+
+#include "utilities.h"
 #include "SMDS_SetIterator.hxx"
-#include "SMDS_ElementFactory.hxx"
+#include <iostream>
+#include <cassert>
+
+using namespace std;
 
-#include <utilities.h>
 
 //================================================================================
 /*!
@@ -44,8 +47,8 @@ SMESHDS_SubMesh::SMESHDS_SubMesh(SMESHDS_Mesh *parent, int index)
 {
   myParent = parent;
   myIndex = index;
-  myNbElements = 0;
-  myNbNodes = 0;
+  myUnusedIdNodes = 0;
+  myUnusedIdElements = 0;
 }
 
 //================================================================================
@@ -63,16 +66,16 @@ SMESHDS_SubMesh::~SMESHDS_SubMesh()
 //purpose  :
 //=======================================================================
 
-void SMESHDS_SubMesh::AddElement(const SMDS_MeshElement * elem)
+void SMESHDS_SubMesh::AddElement(const SMDS_MeshElement * ME)
 {
   if (!IsComplexSubmesh())
   {
-    if ( elem->GetType() == SMDSAbs_Node )
+    if ( ME->GetType() == SMDSAbs_Node )
     {
-      AddNode( static_cast< const SMDS_MeshNode* >( elem ));
+      AddNode( static_cast< const SMDS_MeshNode* >( ME ));
       return;
     }
-    int oldShapeId = elem->GetShapeID();
+    int oldShapeId = ME->getshapeId();
     if ( oldShapeId > 0 )
     {
       if (oldShapeId != myIndex)
@@ -80,10 +83,28 @@ void SMESHDS_SubMesh::AddElement(const SMDS_MeshElement * elem)
         throw SALOME_Exception
           (LOCALIZED("add element in subshape already belonging to a subshape"));
       }
+      int idInSubShape = ME->getIdInShape();
+      if (idInSubShape >= 0)
+      {
+        MESSAGE("add element in subshape already belonging to that subshape "
+                << ME->GetID() << " " << oldShapeId << " " << idInSubShape);
+        // check if ok: do nothing if ok
+        if (idInSubShape >= (int)myElements.size())
+        {
+          throw SALOME_Exception(LOCALIZED("out of bounds"));
+        }
+        if (ME != myElements[idInSubShape])
+        {
+          throw SALOME_Exception(LOCALIZED("not the same element"));
+        }
+        return;
+      }
     }
 
-    elem->setShapeID( myIndex );
-    myNbElements++;
+    SMDS_MeshElement* elem = (SMDS_MeshElement*) (ME);
+    elem->setShapeId(myIndex);
+    elem->setIdInShape(myElements.size());
+    myElements.push_back(ME);
   }
 }
 
@@ -92,17 +113,41 @@ void SMESHDS_SubMesh::AddElement(const SMDS_MeshElement * elem)
 //purpose  :
 //=======================================================================
 
-bool SMESHDS_SubMesh::RemoveElement(const SMDS_MeshElement * elem )
+bool SMESHDS_SubMesh::RemoveElement(const SMDS_MeshElement * ME, bool isElemDeleted)
 {
-  if ( !elem || elem->IsNull() || elem->getshapeId() != myIndex )
+  if (!ME)
   {
     return false;
   }
-  if ( !IsComplexSubmesh() )
+  if (!IsComplexSubmesh())
   {
-    elem->setShapeID( 0 );
-    myNbElements--;
-    return true;
+    if ( ME->getshapeId() != myIndex ) // elem not in a pool can loose it's data already
+    {
+      if ( isElemDeleted )
+        for ( size_t i = 0; i < myElements.size(); ++i )
+          if ( myElements[i] == ME )
+          {
+            myElements[i] = 0;
+            ++myUnusedIdElements;
+            return true;
+          }
+      return false;
+    }
+    int idInSubShape = ME->getIdInShape();
+    SMDS_MeshElement* elem = (SMDS_MeshElement*) (ME);
+    elem->setShapeId(0);
+    elem->setIdInShape(-1);
+    if ((idInSubShape >= 0) && (idInSubShape < (int) myElements.size()))
+    {
+      myElements[idInSubShape] = 0; // this vector entry is no more used
+      if ( ++myUnusedIdElements == (int) myElements.size() )
+      {
+        clearVector( myElements );
+        myUnusedIdElements = 0;
+      }
+      return true;
+    }
+    return false;
   }
   return false;
 }
@@ -116,16 +161,22 @@ void SMESHDS_SubMesh::AddNode(const SMDS_MeshNode * N)
 {
   if ( !IsComplexSubmesh() )
   {
-    const int shapeId = N->getshapeId();
-    if ( shapeId > 0 )
+    const int idInSubShape = N->getIdInShape();
+    const int shapeId      = N->getshapeId();
+    if ((shapeId > 0) && (idInSubShape >= 0))
     {
       if ( shapeId != myIndex )
         throw SALOME_Exception
           (LOCALIZED("a node being in sub-mesh is added to another sub-mesh"));
+      if ( idInSubShape >= (int)myNodes.size() || myNodes[ idInSubShape ] != N )
+        throw SALOME_Exception
+          (LOCALIZED("a node with wrong idInSubShape is re-added to the same sub-mesh"));
       return; // already in
     }
-    N->setShapeID( myIndex );
-    myNbNodes++;
+    SMDS_MeshNode* node = (SMDS_MeshNode*)(N);
+    node->setShapeId(myIndex);
+    node->setIdInShape(myNodes.size());
+    myNodes.push_back(N);
   }
 }
 
@@ -134,18 +185,38 @@ void SMESHDS_SubMesh::AddNode(const SMDS_MeshNode * N)
 //purpose  :
 //=======================================================================
 
-bool SMESHDS_SubMesh::RemoveNode(const SMDS_MeshNode * N)
+bool SMESHDS_SubMesh::RemoveNode(const SMDS_MeshNode * N, bool isNodeDeleted)
 {
-  if ( !N || N->getshapeId() != myIndex )
+  if (!IsComplexSubmesh())
   {
+    if ( N->getshapeId() != myIndex )
+    {
+      if ( isNodeDeleted )
+        for ( size_t i = 0; i < myNodes.size(); ++i )
+          if ( myNodes[i] == N )
+          {
+            myNodes[i] = 0;
+            ++myUnusedIdNodes;
+            return true;
+          }
+      return false;
+    }
+    int idInSubShape = N->getIdInShape();
+    SMDS_MeshNode* node = (SMDS_MeshNode*) (N);
+    node->setShapeId(0);
+    node->setIdInShape(-1);
+    if ((idInSubShape >= 0) && (idInSubShape < (int) myNodes.size()))
+    {
+      myNodes[idInSubShape] = 0; // this vector entry is no more used
+      if ( ++myUnusedIdNodes == (int) myNodes.size() )
+      {
+        clearVector( myNodes );
+        myUnusedIdNodes = 0;
+      }
+      return true;
+    }
     return false;
   }
-  if ( !IsComplexSubmesh() )
-  {
-    N->setShapeID( 0 );
-    myNbNodes--;
-    return true;
-  }
   return false;
 }
 
@@ -157,10 +228,10 @@ bool SMESHDS_SubMesh::RemoveNode(const SMDS_MeshNode * N)
 int SMESHDS_SubMesh::NbElements() const
 {
   if ( !IsComplexSubmesh() )
-    return myNbElements;
+    return myElements.size() - myUnusedIdElements;
 
   int nbElems = 0;
-  TSubMeshSet::const_iterator it = mySubMeshes.begin();
+  set<const SMESHDS_SubMesh*>::const_iterator it = mySubMeshes.begin();
   for ( ; it != mySubMeshes.end(); it++ )
     nbElems += (*it)->NbElements();
 
@@ -175,10 +246,10 @@ int SMESHDS_SubMesh::NbElements() const
 int SMESHDS_SubMesh::NbNodes() const
 {
   if ( !IsComplexSubmesh() )
-    return myNbNodes;
+    return myNodes.size() - myUnusedIdNodes;
 
   int nbElems = 0;
-  TSubMeshSet::const_iterator it = mySubMeshes.begin();
+  set<const SMESHDS_SubMesh*>::const_iterator it = mySubMeshes.begin();
   for ( ; it != mySubMeshes.end(); it++ )
     nbElems += (*it)->NbNodes();
 
@@ -235,7 +306,7 @@ public:
 template<typename VALUE> class MyIterator : public SMDS_Iterator<VALUE>
 {
 public:
-  MyIterator (const TSubMeshSet& theSubMeshes)
+  MyIterator (const set<const SMESHDS_SubMesh*>& theSubMeshes)
     : myMore(false), mySubIt( theSubMeshes.begin() ), mySubEnd( theSubMeshes.end() )
   {}
   bool more()
@@ -260,9 +331,9 @@ protected:
   getElements(const SMESHDS_SubMesh*) const = 0;
 
 private:
-  bool                                      myMore;
-  TSubMeshSet::const_iterator               mySubIt, mySubEnd;
-  boost::shared_ptr< SMDS_Iterator<VALUE> > myElemIt;
+  bool                                        myMore;
+  set<const SMESHDS_SubMesh*>::const_iterator mySubIt, mySubEnd;
+  boost::shared_ptr< SMDS_Iterator<VALUE> >   myElemIt;
 };
 
 // =====================
@@ -272,7 +343,7 @@ private:
 class MyElemIterator: public MyIterator<const SMDS_MeshElement*>
 {
 public:
-  MyElemIterator (const TSubMeshSet& theSubMeshes)
+  MyElemIterator (const set<const SMESHDS_SubMesh*>& theSubMeshes)
     :MyIterator<const SMDS_MeshElement*>( theSubMeshes ) {}
   SMDS_ElemIteratorPtr getElements(const SMESHDS_SubMesh* theSubMesh) const
   { return theSubMesh->GetElements(); }
@@ -285,7 +356,7 @@ public:
 class MyNodeIterator: public MyIterator<const SMDS_MeshNode*>
 {
 public:
-  MyNodeIterator (const TSubMeshSet& theSubMeshes)
+  MyNodeIterator (const set<const SMESHDS_SubMesh*>& theSubMeshes)
     :MyIterator<const SMDS_MeshNode*>( theSubMeshes ) {}
   SMDS_NodeIteratorPtr getElements(const SMESHDS_SubMesh* theSubMesh) const
   { return theSubMesh->GetNodes(); }
@@ -296,12 +367,13 @@ public:
 //purpose  :
 //=======================================================================
 
-SMDS_ElemIteratorPtr SMESHDS_SubMesh::GetElements() const
+SMDS_ElemIteratorPtr SMESHDS_SubMesh::GetElements( bool reverse ) const
 {
   if ( IsComplexSubmesh() )
     return SMDS_ElemIteratorPtr( new MyElemIterator( mySubMeshes ));
 
-  return myParent->shapeElementsIterator( myIndex, myNbElements );
+  typedef MySetIterator< const SMDS_MeshElement*, std::vector<const SMDS_MeshElement*> > TIter;
+  return SMDS_ElemIteratorPtr( new TIter( myElements, reverse ));
 }
 
 //=======================================================================
@@ -309,12 +381,13 @@ SMDS_ElemIteratorPtr SMESHDS_SubMesh::GetElements() const
 //purpose  :
 //=======================================================================
 
-SMDS_NodeIteratorPtr SMESHDS_SubMesh::GetNodes() const
+SMDS_NodeIteratorPtr SMESHDS_SubMesh::GetNodes( bool reverse ) const
 {
   if ( IsComplexSubmesh() )
     return SMDS_NodeIteratorPtr( new MyNodeIterator( mySubMeshes ));
 
-  return myParent->shapeNodesIterator( myIndex, myNbNodes );
+  typedef MySetIterator< const SMDS_MeshNode*, std::vector<const SMDS_MeshNode*> > TIter;
+  return SMDS_NodeIteratorPtr( new TIter( myNodes, reverse ));
 }
 
 //=======================================================================
@@ -324,18 +397,35 @@ SMDS_NodeIteratorPtr SMESHDS_SubMesh::GetNodes() const
 
 bool SMESHDS_SubMesh::Contains(const SMDS_MeshElement * ME) const
 {
-  if ( !ME || ME->IsNull() )
+  // DO NOT TRY TO FIND A REMOVED ELEMENT !!
+  //if ( IsComplexSubmesh() || !ME )
+  if (!ME)
     return false;
 
   if ( IsComplexSubmesh() )
   {
-    TSubMeshSet::const_iterator aSubIt = mySubMeshes.begin();
+    set<const SMESHDS_SubMesh*>::const_iterator aSubIt = mySubMeshes.begin();
     for (; aSubIt != mySubMeshes.end(); aSubIt++)
       if ((*aSubIt)->Contains(ME))
         return true;
     return false;
   }
-  return ME->getshapeId() == myIndex;
+
+  if (ME->GetType() == SMDSAbs_Node)
+  {
+    int idInShape = ME->getIdInShape();
+    if ((idInShape >= 0) && (idInShape < (int) myNodes.size()))
+      if (myNodes[idInShape] == ME)
+        return true;
+  }
+  else
+  {
+    int idInShape = ME->getIdInShape();
+    if ((idInShape >= 0) && (idInShape < (int) myElements.size()))
+      if (myElements[idInShape] == ME)
+        return true;
+  }
+  return false;
 }
 
 //=======================================================================
@@ -347,18 +437,18 @@ bool SMESHDS_SubMesh::IsQuadratic() const
 {
   if ( IsComplexSubmesh() )
   {
-    TSubMeshSet::const_iterator aSubIt = mySubMeshes.begin();
+    set<const SMESHDS_SubMesh*>::const_iterator aSubIt = mySubMeshes.begin();
     for (; aSubIt != mySubMeshes.end(); aSubIt++)
       if ((*aSubIt)->IsQuadratic())
         return true;
     return false;
   }
 
-  if ( myNbElements == 0 )
-    return false;
+  for ( size_t i = 0; i < myElements.size(); ++i )
+    if ( myElements[i] )
+      return myElements[i]->IsQuadratic();
 
-  SMDS_ElemIteratorPtr it = GetElements();
-  return it->more() && it->next()->IsQuadratic();
+  return false;
 }
 
 //=======================================================================
@@ -409,8 +499,10 @@ bool SMESHDS_SubMesh::ContainsSubMesh( const SMESHDS_SubMesh* theSubMesh ) const
 
 SMESHDS_SubMeshIteratorPtr SMESHDS_SubMesh::GetSubMeshIterator() const
 {
-  typedef SMDS_SetIterator< const SMESHDS_SubMesh*, TSubMeshSet::const_iterator > TIterator;
-  return boost::make_shared< TIterator >( mySubMeshes.begin(), mySubMeshes.end());
+  typedef set<const SMESHDS_SubMesh*>::const_iterator TIterator;
+  return SMESHDS_SubMeshIteratorPtr
+    ( new SMDS_SetIterator< const SMESHDS_SubMesh*, TIterator >( mySubMeshes.begin(),
+                                                                 mySubMeshes.end()));
 }
 
 //=======================================================================
@@ -422,22 +514,26 @@ void SMESHDS_SubMesh::Clear()
 {
   if ( myParent && myParent->NbNodes() > 0 )
   {
-    if ( myNbElements > 0 )
-      for ( SMDS_ElemIteratorPtr it = GetElements(); it->more(); )
-      {
-        const SMDS_MeshElement * elem = it->next();
-        elem->setShapeID( 0 );
-      }
-    if ( myNbNodes > 0 )
-      for ( SMDS_NodeIteratorPtr it = GetNodes(); it->more(); )
-      {
-        const SMDS_MeshNode * elem = it->next();
-        elem->setShapeID( 0 );
-      }
+    for ( size_t i = 0; i < myElements.size(); ++i )
+    {
+      if ( myElements[i] &&
+           myElements[i]->GetID() > 0 &&
+           myElements[i] == myParent->FindElement( myElements[i]->GetID() )) // not deleted
+        const_cast< SMDS_MeshElement* >( myElements[i] )->setShapeId( 0 );
+    }
+    for ( size_t i = 0; i < myNodes.size(); ++i )
+    {
+      if ( myNodes[i] &&
+           myNodes[i]->GetID() > 0 &&
+           myNodes[i] == myParent->FindNode( myNodes[i]->GetID() )) // not deleted
+        const_cast< SMDS_MeshNode* >( myNodes[i] )->setShapeId( 0 );
+    }
   }
 
-  myNbElements = 0;
-  myNbNodes = 0;
+  clearVector( myElements );
+  clearVector( myNodes );
+  myUnusedIdNodes = 0;
+  myUnusedIdElements = 0;
   if ( NbSubMeshes() > 0 )
   {
     SMESHDS_SubMeshIteratorPtr sub = GetSubMeshIterator();
@@ -447,3 +543,71 @@ void SMESHDS_SubMesh::Clear()
     }
   }
 }
+
+int SMESHDS_SubMesh::getSize()
+{
+  int c = NbNodes();
+  int d = NbElements();
+  return c+d;
+}
+
+void SMESHDS_SubMesh::compactList()
+{
+  if ( myUnusedIdElements > 0 )
+  {
+    std::vector<const SMDS_MeshElement*> newElems;
+    newElems.reserve( myElements.size() - myUnusedIdElements );
+    for ( size_t i = 0; i < myElements.size(); i++)
+      if ( myElements[i] )
+      {
+        SMDS_MeshElement* elem = (SMDS_MeshElement*)myElements[i];
+        elem->setIdInShape( newElems.size() );
+        newElems.push_back( elem );
+      }
+    myElements.swap(newElems);
+    myUnusedIdElements = 0;
+  }
+  else
+  {
+    std::vector<const SMDS_MeshElement*>( myElements ).swap( myElements );
+  }
+
+  if ( myUnusedIdNodes > 0 )
+  {
+    std::vector<const SMDS_MeshNode*> newNodes;
+    newNodes.reserve( myNodes.size() - myUnusedIdNodes );
+    for ( size_t i = 0; i < myNodes.size(); i++ )
+      if ( myNodes[i] )
+      {
+        SMDS_MeshNode* node = (SMDS_MeshNode*)myNodes[i];
+        node->setIdInShape( newNodes.size() );
+        newNodes.push_back( node );
+      }
+    myNodes.swap(newNodes);
+    myUnusedIdNodes = 0;
+  }
+  else
+  {
+    std::vector<const SMDS_MeshNode*>( myNodes ).swap( myNodes );
+  }
+}
+
+//=======================================================================
+//function : GetElement
+//purpose  : Return an element by its IdInShape
+//=======================================================================
+
+const SMDS_MeshElement* SMESHDS_SubMesh::GetElement( size_t idInShape ) const
+{
+  return ( !IsComplexSubmesh() && idInShape < myElements.size() ) ? myElements[idInShape] : 0;
+}
+
+//=======================================================================
+//function : GetElement
+//purpose  : Return a node by its IdInShape
+//=======================================================================
+
+const SMDS_MeshNode* SMESHDS_SubMesh::GetNode( size_t idInShape ) const
+{
+  return ( !IsComplexSubmesh() && idInShape < myNodes.size() ) ? myNodes[idInShape] : 0;
+}
index 2caffb10b15b8e91a117f79f85abfaf3701feee2..9a9d61f63db944e90b705aa40d657d1423cd43c5 100644 (file)
 #include "SMESH_SMESHDS.hxx"
 
 #include "SMDS_Mesh.hxx"
+#include <set>
 #include <vector>
 
-#include <boost/container/flat_set.hpp>
-class SMESHDS_SubMesh;
-typedef boost::container::flat_set< const SMESHDS_SubMesh* > TSubMeshSet;
-
 class SMESHDS_SubMesh;
 typedef SMDS_Iterator<const SMESHDS_SubMesh*> SMESHDS_SubMeshIterator;
 typedef boost::shared_ptr< SMESHDS_SubMeshIterator > SMESHDS_SubMeshIteratorPtr;
@@ -52,11 +49,11 @@ class SMESHDS_EXPORT SMESHDS_SubMesh
 
   // if !IsComplexSubmesh()
   virtual void AddElement(const SMDS_MeshElement * ME);
-  virtual bool RemoveElement(const SMDS_MeshElement * ME); // ret true if ME was in
+  virtual bool RemoveElement(const SMDS_MeshElement * ME, bool isElemDeleted); // ret true if ME was in
   virtual void AddNode(const SMDS_MeshNode * ME);
-  virtual bool RemoveNode(const SMDS_MeshNode * ME);       // ret true if ME was in
-  //virtual const SMDS_MeshElement* GetElement( size_t idInShape ) const;
-  //virtual const SMDS_MeshNode*    GetNode   ( size_t idInShape ) const;
+  virtual bool RemoveNode(const SMDS_MeshNode * ME, bool isNodeDeleted);       // ret true if ME was in
+  virtual const SMDS_MeshElement* GetElement( size_t idInShape ) const;
+  virtual const SMDS_MeshNode*    GetNode   ( size_t idInShape ) const;
 
   // if IsComplexSubmesh()
   void AddSubMesh( const SMESHDS_SubMesh* theSubMesh );
@@ -68,25 +65,29 @@ class SMESHDS_EXPORT SMESHDS_SubMesh
 
   // for both types
   virtual int NbElements() const;
+  virtual SMDS_ElemIteratorPtr GetElements(bool reverse=false) const;
   virtual int NbNodes() const;
-  virtual SMDS_ElemIteratorPtr GetElements() const;
-  virtual SMDS_NodeIteratorPtr GetNodes() const;
+  virtual SMDS_NodeIteratorPtr GetNodes(bool reverse=false) const;
   virtual bool Contains(const SMDS_MeshElement * ME) const;      // check if elem or node is in
   virtual bool IsQuadratic() const;
 
   // clear the contents
   virtual void Clear();
+  int  getSize();
+  void compactList();
 
   SMESHDS_Mesh* GetParent() const { return const_cast< SMESHDS_Mesh*>( myParent ); }
   int           GetID()     const { return myIndex; }
 
  private:
+  SMESHDS_Mesh *                       myParent;
+  std::vector<const SMDS_MeshElement*> myElements;
+  std::vector<const SMDS_MeshNode*>    myNodes;
 
-  int             myIndex;
-  int             myNbElements;
-  int             myNbNodes;
-  SMESHDS_Mesh *  myParent;
-  TSubMeshSet     mySubMeshes;
+  int myUnusedIdNodes;
+  int myUnusedIdElements;
+  int myIndex;
 
+  std::set<const SMESHDS_SubMesh*> mySubMeshes;
 };
 #endif
index 0491cfef92d410b15b730e703e856bf80e7f283b..30ab3e6d067c820bcd4958777f7b8cb78bba4324 100644 (file)
@@ -1289,7 +1289,7 @@ void SMESHGUI_ExtrusionDlg::ClickOnHelp()
 #endif
     SUIT_MessageBox::warning(this, tr("WRN_WARNING"),
                              tr("EXTERNAL_BROWSER_CANNOT_SHOW_PAGE").
-                             arg(app->resourceMgr()->stringValue("ExternalBrowser",
+                             arg(app->resourceMgr()->stringValue("ExternalBrowser", 
                                                                  platform)).
                              arg(myHelpFileName));
   }
@@ -1323,7 +1323,7 @@ void SMESHGUI_ExtrusionDlg::SelectionIntoArgument()
       return;
 
     const SMDS_MeshFace* face =
-      aMesh->DownCast< SMDS_MeshFace >(aMesh->FindElement(aMapIndex(1)));
+      dynamic_cast<const SMDS_MeshFace*>(aMesh->FindElement(aMapIndex(1)));
     if (!face)
       return;
 
index 7b9f4974f9ad6f7d6a569f1c207dfe5423c7f8f9..4f9b3cce3252ff435f8eaa0eafedf2995b150049 100644 (file)
@@ -1426,8 +1426,8 @@ void SMESHGUI_GroupDlg::onObjectSelectionChanged()
           aGroupMainShape = aGeomGroup;
           aGroupMainShape->Register();
         }
-        CORBA::String_var entry = aGroupMainShape->GetStudyEntry();
-        _PTR(SObject) aGroupMainShapeSO = aStudy->FindObjectID( entry.in() );
+        _PTR(SObject) aGroupMainShapeSO =
+          aStudy->FindObjectID(aGroupMainShape->GetStudyEntry());
 
         _PTR(SObject) anObj, aRef;
         bool isRefOrSubShape = false;
@@ -1451,10 +1451,10 @@ void SMESHGUI_GroupDlg::onObjectSelectionChanged()
 
       myGeomObjects->length(i);
       if ( i == 0 )
-      {
-        myIsBusy = false;
-        return;
-      }
+        {
+          myIsBusy = false;
+          return;
+        }
 
       aNbSel = i;
     }
@@ -2453,9 +2453,9 @@ void SMESHGUI_GroupDlg::onPublishShapeByMeshDlg(SUIT_Operation* op)
     GEOM::GEOM_Object_var aGeomVar = myShapeByMeshOp->GetShape();
     if ( !aGeomVar->_is_nil() )
     {
-      CORBA::String_var ID = aGeomVar->GetStudyEntry();
-      _PTR(Study)   aStudy = SMESH::GetActiveStudyDocument();
-      if ( _PTR(SObject) aGeomSO = aStudy->FindObjectID( ID.in() )) {
+      QString ID = aGeomVar->GetStudyEntry();
+      _PTR(Study) aStudy = SMESH::GetActiveStudyDocument();
+      if ( _PTR(SObject) aGeomSO = aStudy->FindObjectID( ID.toLatin1().data() )) {
         SALOME_ListIO anIOList;
         Handle(SALOME_InteractiveObject) anIO = new SALOME_InteractiveObject
           ( aGeomSO->GetID().c_str(), "SMESH", aGeomSO->GetName().c_str() );
index 57bd8236d37d1f2a449bc0c9f72c7396260067b7..03e542d6ab6e08daa665651fcde58f9dd6b43efe 100644 (file)
@@ -1121,7 +1121,7 @@ SMESHGUI_ElemInfo::XYZ SMESHGUI_ElemInfo::gravityCenter( const SMDS_MeshElement*
 */
 SMESHGUI_ElemInfo::XYZ SMESHGUI_ElemInfo::normal( const SMDS_MeshElement* element )
 {
-  gp_XYZ n = SMESH::getNormale( SMDS_Mesh::DownCast<SMDS_MeshFace>( element ));
+  gp_XYZ n = SMESH::getNormale( dynamic_cast<const SMDS_MeshFace*>( element ));
   return XYZ(n.X(), n.Y(), n.Z());
 }
 
@@ -1397,7 +1397,7 @@ void SMESHGUI_SimpleElemInfo::information( const QList<long>& ids )
         if ( e->GetEntityType() > SMDSEntity_0D && e->GetEntityType() < SMDSEntity_Ball ) {
           myInfo->append( QString( "<b>%1?</b> %2" ).arg( SMESHGUI_ElemInfo::tr( "QUADRATIC" )).arg( e->IsQuadratic() ? SMESHGUI_ElemInfo::tr( "YES" ) : SMESHGUI_ElemInfo::tr( "NO" )) );
         }
-        if ( const SMDS_BallElement* ball = SMDS_Mesh::DownCast<SMDS_BallElement>( e )) {
+        if ( const SMDS_BallElement* ball = dynamic_cast<const SMDS_BallElement*>( e )) {
           // Ball diameter
           myInfo->append( QString( "<b>%1:</b> %2" ).arg( SMESHGUI_ElemInfo::tr( "BALL_DIAMETER" )).arg( ball->GetDiameter() ));
         }
@@ -1915,7 +1915,7 @@ void SMESHGUI_TreeElemInfo::information( const QList<long>& ids )
         case SMDSEntity_Polyhedra:
         case SMDSEntity_Quad_Polyhedra:
           gtype = SMESHGUI_ElemInfo::tr( "POLYHEDRON" ); break;
-        default:
+        default: 
           break;
         }
         if ( !gtype.isEmpty() ) {
@@ -1930,7 +1930,7 @@ void SMESHGUI_TreeElemInfo::information( const QList<long>& ids )
           quadItem->setText( 0, SMESHGUI_ElemInfo::tr( "QUADRATIC" ));
           quadItem->setText( 1, e->IsQuadratic() ? SMESHGUI_ElemInfo::tr( "YES" ) : SMESHGUI_ElemInfo::tr( "NO" ));
         }
-        if ( const SMDS_BallElement* ball = SMDS_Mesh::DownCast< SMDS_BallElement >( e )) {
+        if ( const SMDS_BallElement* ball = dynamic_cast<const SMDS_BallElement*>( e )) {
           // ball diameter
           QTreeWidgetItem* diamItem = createItem( elemItem, Bold );
           diamItem->setText( 0, SMESHGUI_ElemInfo::tr( "BALL_DIAMETER" ));
@@ -1949,14 +1949,12 @@ void SMESHGUI_TreeElemInfo::information( const QList<long>& ids )
           }
         }
         else {
-          SMDS_NodeIteratorPtr nodeIt = e->nodeIterator();
-          std::set< const SMDS_MeshNode* > addedNodes;
+          const SMDS_VtkVolume* aVtkVolume = dynamic_cast<const SMDS_VtkVolume*>(e);
+          SMDS_ElemIteratorPtr nodeIt = aVtkVolume->uniqueNodesIterator();
           QList<const SMDS_MeshElement*> uniqueNodes;
-          while ( nodeIt->more() ) {
-            const SMDS_MeshNode* node = nodeIt->next();
-            if ( addedNodes.insert( node ).second )
-              uniqueNodes.append( nodeIt->next() );
-          }
+          while ( nodeIt->more() )
+            uniqueNodes.append( nodeIt->next() );
+
           SMDS_VolumeTool vtool( e );
           const int nbFaces = vtool.NbFaces();
           for( int face_id = 0; face_id < nbFaces; face_id++ ) {
@@ -1965,10 +1963,10 @@ void SMESHGUI_TreeElemInfo::information( const QList<long>& ids )
             faceItem->setExpanded( true );
 
             const SMDS_MeshNode** aNodeIds = vtool.GetFaceNodes( face_id );
-            const int              nbNodes = vtool.NbFaceNodes ( face_id );
+            const int nbNodes = vtool.NbFaceNodes( face_id );
             for( int node_id = 0; node_id < nbNodes; node_id++ ) {
               const SMDS_MeshNode* node = aNodeIds[node_id];
-              nodeInfo( node, uniqueNodes.indexOf(node) + 1, uniqueNodes.size(), faceItem );
+              nodeInfo( node, uniqueNodes.indexOf(node) + 1, aVtkVolume->NbUniqueNodes(), faceItem );
             }
           }
         }
index 1aa8e927e941ea3ee8ac3b7e776f141bd9cbcc60..5b350d06e62ac0436bf3934e84ca7f4441776778 100644 (file)
@@ -98,7 +98,7 @@ bool SMESHGUI_PreVisualObj::IsValid() const
 
 vtkUnstructuredGrid* SMESHGUI_PreVisualObj::GetUnstructuredGrid()
 {
-  return myMesh->GetGrid();
+  return myMesh->getGrid();
 }
 
 
@@ -116,13 +116,13 @@ vtkIdType SMESHGUI_PreVisualObj::GetNodeVTKId( int theObjID )
 
 vtkIdType SMESHGUI_PreVisualObj::GetElemObjId( int theVTKID )
 {
-  return this->GetMesh()->FromVtkToSmds(theVTKID);
+  return this->GetMesh()->fromVtkToSmds(theVTKID);
 }
 
 vtkIdType SMESHGUI_PreVisualObj::GetElemVTKId( int theObjID )
 {
   const SMDS_MeshElement* e = myMesh->FindElement(theObjID);
-  return e ? e->GetVtkID() : -1;
+  return e ? e->getVtkId() : -1;
 }
 
 void SMESHGUI_PreVisualObj::ClearEntitiesFlags()
index 9e7554e1e3ffb9e2e6b4010f742b4d0c9523c17f..33787322d67f5ea6d5c48a5afb78ccc25ed14bb4 100644 (file)
@@ -641,7 +641,7 @@ void SMESHGUI_RevolutionDlg::SelectionIntoArgument()
     else if ( isFaceSelected )
     {
       const SMDS_MeshFace* face =
-        SMDS_Mesh::DownCast<SMDS_MeshFace>( aMesh->FindElement( aMapIndex( 1 )));
+        dynamic_cast<const SMDS_MeshFace*>(aMesh->FindElement(aMapIndex(1)));
       if (!face)
         return;
       gp_XYZ aNormale = SMESH::getNormale(face);
index cf78362b27f22c3b828934c4024a43559bfd6991..4055741ff4a7c4b11facdaac06b50cf79f2e2824 100644 (file)
@@ -25,7 +25,6 @@
 #define SMESH_ComputeError_HeaderFile
 
 #include "SMESH_Utils.hxx"
-#include "SMDS_ElementHolder.hxx"
 
 #include <string>
 #include <list>
@@ -76,20 +75,22 @@ struct SMESHUtils_EXPORT SMESH_ComputeError
   std::string       myComment;
   const SMESH_Algo* myAlgo;
 
+  std::list<const SMDS_MeshElement*> myBadElements; //!< to explain COMPERR_BAD_INPUT_MESH
+
   static SMESH_ComputeErrorPtr New( int               error   = COMPERR_OK,
                                     std::string       comment = "",
                                     const SMESH_Algo* algo    = 0)
   { return SMESH_ComputeErrorPtr( new SMESH_ComputeError( error, comment, algo )); }
 
-  SMESH_ComputeError( int               error   = COMPERR_OK,
-                      std::string       comment = "",
-                      const SMESH_Algo* algo    = 0)
-    : myName(error), myComment(comment), myAlgo(algo) {}
+  SMESH_ComputeError(int               error   = COMPERR_OK,
+                     std::string       comment = "",
+                     const SMESH_Algo* algo    = 0)
+    :myName(error),myComment(comment),myAlgo(algo) {}
 
   bool IsOK()        const { return myName == COMPERR_OK; }
   bool IsKO()        const { return myName != COMPERR_OK && myName != COMPERR_WARNING; }
   bool IsCommon()    const { return myName < 0 && myName > COMPERR_LAST_ALGO_ERROR; }
-  virtual bool HasBadElems() const { return false; }
+  bool HasBadElems() const { return !myBadElements.empty(); }
 
   // not inline methods are implemented in   src/SMESHUtils/SMESH_TryCatch.cxx
 
@@ -99,31 +100,6 @@ struct SMESHUtils_EXPORT SMESH_ComputeError
   // Return the most severe error
   static SMESH_ComputeErrorPtr Worst( SMESH_ComputeErrorPtr er1,
                                       SMESH_ComputeErrorPtr er2 );
-
-  virtual ~SMESH_ComputeError() {}
-};
-
-struct SMESHUtils_EXPORT SMESH_BadInputElements : public SMESH_ComputeError, SMDS_ElementHolder
-{
-  typedef std::list<const SMDS_MeshElement*> TElemList;
-  TElemList myBadElements; //!< to explain COMPERR_BAD_INPUT_MESH
-
-  SMESH_BadInputElements(const SMDS_Mesh*  mesh,
-                         int               error   = COMPERR_OK,
-                         std::string       comment = "",
-                         const SMESH_Algo* algo    = 0)
-    :SMESH_ComputeError(error, comment ,algo), SMDS_ElementHolder(mesh) {}
-
-  const SMDS_Mesh* GetMesh() const { return myMesh; }
-  const TElemList& GetElements()   { return myBadElements; }
-
-  virtual bool HasBadElems() const { return !myBadElements.empty(); }
-
-  // methods of SMDS_ElementHolder
-  virtual SMDS_ElemIteratorPtr getElements();
-  virtual void tmpClear();
-  virtual void add( const SMDS_MeshElement* element );
-  virtual void compact() { }
 };
 
 #endif
index cc724d3ce8174be926d542469b41bfd19a6f3663..ee22ef944fd4d79ea7b1ab427c19d4ceeb043b8c 100644 (file)
@@ -28,9 +28,8 @@
 
 #include "SMESH_Comment.hxx"
 
-#include "ObjectPool.hxx"
-#include "SMDS_Mesh.hxx"
 #include "SMESH_TypeDefs.hxx"
+#include "SMDS_Mesh.hxx"
 
 #include <Utils_SALOME_Exception.hxx>
 
index 2793d4cda206a58009129e77bb523ac79f59fee9..d098604656bde77db45f5dd3de814c60cdbfd816 100644 (file)
@@ -92,7 +92,7 @@ namespace
       myNodes[0] = node1->Node();
       myNodes[1] = node2->Node();
       myFace     = face;
-      setID( ID ); // mesh element ID
+      setId( ID ); // mesh element ID
     }
     bool IsInGroup() const
     {
index c953da5155596fde6f73177c80acad78a284b118..646fb7bffcab3f0c6c2a995a2350e08deff7b4d0 100644 (file)
@@ -28,7 +28,6 @@
 
 #include "SMESH_MeshAlgos.hxx"
 
-#include "ObjectPool.hxx"
 #include "SMDS_FaceOfNodes.hxx"
 #include "SMDS_LinearEdge.hxx"
 #include "SMDS_Mesh.hxx"
@@ -70,7 +69,7 @@ struct SMESH_NodeSearcherImpl: public SMESH_NodeSearcher
 
     TIDSortedNodeSet nodes;
     if ( theMesh ) {
-      SMDS_NodeIteratorPtr nIt = theMesh->nodesIterator();
+      SMDS_NodeIteratorPtr nIt = theMesh->nodesIterator(/*idInceasingOrder=*/true);
       while ( nIt->more() )
         nodes.insert( nodes.end(), nIt->next() );
     }
@@ -1293,7 +1292,7 @@ bool SMESH_MeshAlgos::IsOut( const SMDS_MeshElement* element, const gp_Pnt& poin
 
   std::vector< SMESH_TNodeXYZ > xyz; xyz.reserve( element->NbNodes()+1 );
 
-  SMDS_NodeIteratorPtr nodeIt = element->interlacedNodesIterator();
+  SMDS_ElemIteratorPtr nodeIt = element->interlacedNodesElemIterator();
   for ( int i = 0; nodeIt->more(); ++i )
     xyz.push_back( SMESH_TNodeXYZ( nodeIt->next() ));
 
@@ -1529,11 +1528,11 @@ double SMESH_MeshAlgos::GetDistance( const SMDS_MeshElement* elem,
   switch ( elem->GetType() )
   {
   case SMDSAbs_Volume:
-    return GetDistance( static_cast<const SMDS_MeshVolume*>( elem ), point, closestPnt );
+    return GetDistance( dynamic_cast<const SMDS_MeshVolume*>( elem ), point, closestPnt );
   case SMDSAbs_Face:
-    return GetDistance( static_cast<const SMDS_MeshFace*>( elem ), point, closestPnt );
+    return GetDistance( dynamic_cast<const SMDS_MeshFace*>( elem ), point, closestPnt );
   case SMDSAbs_Edge:
-    return GetDistance( static_cast<const SMDS_MeshEdge*>( elem ), point, closestPnt );
+    return GetDistance( dynamic_cast<const SMDS_MeshEdge*>( elem ), point, closestPnt );
   case SMDSAbs_Node:
     if ( closestPnt ) *closestPnt = SMESH_TNodeXYZ( elem );
     return point.Distance( SMESH_TNodeXYZ( elem ));
@@ -1665,8 +1664,9 @@ double SMESH_MeshAlgos::GetDistance( const SMDS_MeshEdge* seg,
   int i = 0, nbNodes = seg->NbNodes();
 
   std::vector< SMESH_TNodeXYZ > xyz( nbNodes );
-  for ( SMDS_NodeIteratorPtr nodeIt = seg->interlacedNodesIterator(); nodeIt->more(); i++ )
-    xyz[ i ].Set( nodeIt->next() );
+  SMDS_ElemIteratorPtr nodeIt = seg->interlacedNodesElemIterator();
+  while ( nodeIt->more() )
+    xyz[ i++ ].Set( nodeIt->next() );
 
   for ( i = 1; i < nbNodes; ++i )
   {
@@ -1836,7 +1836,7 @@ SMESH_MeshAlgos::FindFaceInSet(const SMDS_MeshNode*    n1,
     if ( !face && elem->IsQuadratic())
     {
       // analysis for quadratic elements using all nodes
-      SMDS_NodeIteratorPtr anIter = elem->interlacedNodesIterator();
+      SMDS_ElemIteratorPtr anIter = elem->interlacedNodesElemIterator();
       const SMDS_MeshNode* prevN = static_cast<const SMDS_MeshNode*>( anIter->next() );
       for ( i1 = -1, i2 = 0; anIter->more() && !face; i1++, i2++ )
       {
index b026cdd6bf8427c9a309ec25c97830915b6f1d53..71e587caa6f566ecb4432640588176d0a7475bfc 100644 (file)
@@ -39,10 +39,7 @@ const char* SMESH::returnError(const char* txt)
 }
 
 // ------------------------------------------------------------------
-
 #include "SMESH_ComputeError.hxx"
-#include "SMDS_SetIterator.hxx"
-#include <boost/make_shared.hpp>
 
 #define _case2char(err) case err: return #err;
 
@@ -81,31 +78,11 @@ SMESH_ComputeErrorPtr SMESH_ComputeError::Worst( SMESH_ComputeErrorPtr er1,
   if ( !er1->IsKO() ) return er2;
   if ( !er2->IsKO() ) return er1;
   // both KO
-  bool hasInfo1 = er1->myComment.size() || er1->HasBadElems();
-  bool hasInfo2 = er2->myComment.size() || er2->HasBadElems();
+  bool hasInfo1 = er1->myComment.size() || !er1->myBadElements.empty();
+  bool hasInfo2 = er2->myComment.size() || !er2->myBadElements.empty();
   if ( er1->myName == er2->myName ||
        hasInfo1    != hasInfo2 )
     return hasInfo1 < hasInfo2 ? er2 : er1;
 
   return er1->myName == COMPERR_CANCELED ? er2 : er1;
 }
-
-// Return bad elements
-SMDS_ElemIteratorPtr SMESH_BadInputElements::getElements()
-{
-  typedef SMDS_SetIterator< const SMDS_MeshElement*,
-                            std::list< const SMDS_MeshElement* >::const_iterator> TIterator;
-  return boost::make_shared< TIterator >( myBadElements.begin(), myBadElements.end() );
-}
-
-// Temporary remove its elements before the mesh compacting
-void SMESH_BadInputElements::tmpClear()
-{
-  myBadElements.clear();
-}
-
-// Re-add elements after the mesh compacting
-void SMESH_BadInputElements::add( const SMDS_MeshElement* element )
-{
-  myBadElements.push_back( element );
-}
index ea45c41ce356f2b2070925e3f1c829db0c7f5353..2e11e27e580236fa7145fa8da347eea2a65ae923 100644 (file)
@@ -85,6 +85,7 @@
 #include "MED_Factory.hxx"
 #include "SMDS_EdgePosition.hxx"
 #include "SMDS_FacePosition.hxx"
+#include "SMDS_PolyhedralVolumeOfNodes.hxx"
 #include "SMDS_SetIterator.hxx"
 #include "SMDS_SpacePosition.hxx"
 #include "SMDS_VertexPosition.hxx"
@@ -1638,7 +1639,7 @@ SMESH::compute_error_array* SMESH_Gen_i::GetComputeErrors( SMESH::SMESH_Mesh_ptr
           else {
             errStruct.algoName = error->myAlgo->GetName();
           }
-          errStruct.hasBadMesh = error->HasBadElems();
+          errStruct.hasBadMesh = !error->myBadElements.empty();
         }
       }
       error_array->length( nbErr );
@@ -1680,7 +1681,7 @@ SMESH_Gen_i::GetBadInputElements( SMESH::SMESH_Mesh_ptr theMesh,
       {
         // compute error
         SMESH_ComputeErrorPtr error = sm->GetComputeError();
-        if ( error && error->HasBadElems() )
+        if ( error && !error->myBadElements.empty())
         {
           typedef map<const SMDS_MeshElement*, int > TNode2LocalIDMap;
           typedef TNode2LocalIDMap::iterator         TNodeLocalID;
@@ -1690,10 +1691,8 @@ SMESH_Gen_i::GetBadInputElements( SMESH::SMESH_Mesh_ptr theMesh,
           list< TNodeLocalID > connectivity;
           int i, nbElements = 0, nbConnNodes = 0;
 
-          const list<const SMDS_MeshElement*>& badElems =
-            static_cast<SMESH_BadInputElements*>( error.get() )->myBadElements;
-          list<const SMDS_MeshElement*>::const_iterator elemIt  = badElems.begin();
-          list<const SMDS_MeshElement*>::const_iterator elemEnd = badElems.end();
+          list<const SMDS_MeshElement*>::iterator elemIt  = error->myBadElements.begin();
+          list<const SMDS_MeshElement*>::iterator elemEnd = error->myBadElements.end();
           for ( ; elemIt != elemEnd; ++elemIt, ++nbElements )
           {
             SMDS_ElemIteratorPtr nIt = (*elemIt)->nodesIterator();
@@ -1720,7 +1719,7 @@ SMESH_Gen_i::GetBadInputElements( SMESH::SMESH_Mesh_ptr theMesh,
           }
           // fill element types
           result->elementTypes.length( nbElements );
-          for ( i = 0, elemIt = badElems.begin(); i <nbElements; ++i, ++elemIt )
+          for ( i = 0, elemIt = error->myBadElements.begin(); i <nbElements; ++i, ++elemIt )
           {
             const SMDS_MeshElement* elem = *elemIt;
             result->elementTypes[i].SMDS_ElementType = (SMESH::ElementType) elem->GetType();
@@ -3127,9 +3126,8 @@ SALOMEDS::TMPFile* SMESH_Gen_i::Save( SALOMEDS::SComponent_ptr theComponent,
           if ( !myHyp->_is_nil() ) {
             SMESH_Hypothesis_i* myImpl = dynamic_cast<SMESH_Hypothesis_i*>( GetServant( myHyp ).in() );
             if ( myImpl ) {
-              CORBA::String_var hn = myHyp->GetName(), ln = myHyp->GetLibName();
-              std::string hypname = hn.in();
-              std::string libname = ln.in();
+              string hypname = string( myHyp->GetName() );
+              string libname = string( myHyp->GetLibName() );
               // BUG SWP13062
               // Needs for save crossplatform libname, i.e. parth of name ( ".dll" for
               // WIN32 and ".so" for X-system) must be deleted
@@ -3141,13 +3139,13 @@ SALOMEDS::TMPFile* SMESH_Gen_i::Save( SALOMEDS::SComponent_ptr theComponent,
               // PAL17753 (Regression: missing hypothesis in restored study)
               // "lib" also should be removed from the beginning
               //if( libname_len > 3 )
-              //libname.resize( libname_len - 3 );
+                //libname.resize( libname_len - 3 );
               if( libname_len > 6 )
                 libname = libname.substr( 3, libname_len - 3 - 3 );
 #endif
-              CORBA::String_var  objStr = GetORB()->object_to_string( anObject );
-              CORBA::String_var hypdata = myImpl->SaveTo();
-              int                    id = myStudyContext->findId( string( objStr.in() ));
+              CORBA::String_var objStr = GetORB()->object_to_string( anObject );
+              int    id      = myStudyContext->findId( string( objStr.in() ) );
+              string hypdata = string( myImpl->SaveTo() );
 
               // for each hypothesis create HDF group basing on its id
               char hypGrpName[30];
@@ -3167,10 +3165,10 @@ SALOMEDS::TMPFile* SMESH_Gen_i::Save( SALOMEDS::SComponent_ptr theComponent,
               aDataset->WriteOnDisk( ( char* )( libname.c_str() ) );
               aDataset->CloseOnDisk();
               // --> persistent data of hypothesis
-              aSize[ 0 ] = strlen( hypdata.in() ) + 1;
+              aSize[ 0 ] = hypdata.length() + 1;
               aDataset = new HDFdataset( "Data", aGroup, HDF_STRING, aSize, 1 );
               aDataset->CreateOnDisk();
-              aDataset->WriteOnDisk( ( char* )( hypdata.in() ) );
+              aDataset->WriteOnDisk( ( char* )( hypdata.c_str() ) );
               aDataset->CloseOnDisk();
               // close hypothesis HDF group
               aGroup->CloseOnDisk();
@@ -3197,9 +3195,8 @@ SALOMEDS::TMPFile* SMESH_Gen_i::Save( SALOMEDS::SComponent_ptr theComponent,
           if ( !myHyp->_is_nil() ) {
             SMESH_Hypothesis_i* myImpl = dynamic_cast<SMESH_Hypothesis_i*>( GetServant( myHyp ).in() );
             if ( myImpl ) {
-              CORBA::String_var hn = myHyp->GetName(), ln = myHyp->GetLibName();
-              std::string hypname = hn.in();
-              std::string libname = ln.in();
+              string hypname = string( myHyp->GetName() );
+              string libname = string( myHyp->GetLibName() );
               // BUG SWP13062
               // Needs for save crossplatform libname, i.e. parth of name ( ".dll" for
               // WIN32 and ".so" for X-system) must be deleted
@@ -3211,13 +3208,13 @@ SALOMEDS::TMPFile* SMESH_Gen_i::Save( SALOMEDS::SComponent_ptr theComponent,
               // PAL17753 (Regression: missing hypothesis in restored study)
               // "lib" also should be removed from the beginning
               //if( libname_len > 3 )
-              //libname.resize( libname_len - 3 );
+                //libname.resize( libname_len - 3 );
               if( libname_len > 6 )
                 libname = libname.substr( 3, libname_len - 3 - 3 );
 #endif
-              CORBA::String_var  objStr = GetORB()->object_to_string( anObject );
-              CORBA::String_var hypdata = myImpl->SaveTo();
-              int                    id = myStudyContext->findId( string( objStr.in() ) );
+              CORBA::String_var objStr = GetORB()->object_to_string( anObject );
+              int    id      = myStudyContext->findId( string( objStr.in() ) );
+              string hypdata = string( myImpl->SaveTo() );
 
               // for each algorithm create HDF group basing on its id
               char hypGrpName[30];
@@ -3237,10 +3234,10 @@ SALOMEDS::TMPFile* SMESH_Gen_i::Save( SALOMEDS::SComponent_ptr theComponent,
               aDataset->WriteOnDisk( ( char* )( libname.c_str() ) );
               aDataset->CloseOnDisk();
               // --> persistent data of algorithm
-              aSize[0] = strlen( hypdata.in() ) + 1;
+              aSize[0] = hypdata.length() + 1;
               aDataset = new HDFdataset( "Data", aGroup, HDF_STRING, aSize, 1 );
               aDataset->CreateOnDisk();
-              aDataset->WriteOnDisk( ( char* )( hypdata.in() ));
+              aDataset->WriteOnDisk( ( char* )( hypdata.c_str() ) );
               aDataset->CloseOnDisk();
               // close algorithm HDF group
               aGroup->CloseOnDisk();
@@ -3322,14 +3319,13 @@ SALOMEDS::TMPFile* SMESH_Gen_i::Save( SALOMEDS::SComponent_ptr theComponent,
               SALOMEDS::SObject_wrap myShape;
               bool ok = myRef->ReferencedObject( myShape.inout() );
               if ( ok ) {
-                CORBA::Object_var shapeObj = myShape->GetObject();
-                shapeRefFound = (! CORBA::is_nil( shapeObj ));
-                CORBA::String_var myRefOnObject = myShape->GetID();
-                if ( shapeRefFound && myRefOnObject.in()[0] ) {
-                  aSize[ 0 ] = strlen( myRefOnObject.in() ) + 1;
+                shapeRefFound = (! CORBA::is_nil( myShape->GetObject() ));
+                string myRefOnObject = myShape->GetID();
+                if ( shapeRefFound && myRefOnObject.length() > 0 ) {
+                  aSize[ 0 ] = myRefOnObject.length() + 1;
                   aDataset = new HDFdataset( "Ref on shape", aTopGroup, HDF_STRING, aSize, 1 );
                   aDataset->CreateOnDisk();
-                  aDataset->WriteOnDisk( ( char* )( myRefOnObject.in() ) );
+                  aDataset->WriteOnDisk( ( char* )( myRefOnObject.c_str() ) );
                   aDataset->CloseOnDisk();
                 }
               }
@@ -3338,7 +3334,7 @@ SALOMEDS::TMPFile* SMESH_Gen_i::Save( SALOMEDS::SComponent_ptr theComponent,
             // write applied hypotheses if exist
             SALOMEDS::SObject_wrap myHypBranch;
             found = gotBranch->FindSubObject( GetRefOnAppliedHypothesisTag(), myHypBranch.inout() );
-            if ( found && !shapeRefFound && hasShape ) { // remove applied hyps
+            if ( found && !shapeRefFound && hasShape) { // remove applied hyps
               myCurrentStudy->NewBuilder()->RemoveObjectWithChildren( myHypBranch );
             }
             if ( found && (shapeRefFound || !hasShape) ) {
@@ -3675,8 +3671,8 @@ SALOMEDS::TMPFile* SMESH_Gen_i::Save( SALOMEDS::SComponent_ptr theComponent,
 
                     // For each group, create a dataset named "Group <group_persistent_id>"
                     // and store the group's user name into it
-                    const char*         grpName = aGrpBaseDS->GetStoreName();
-                    CORBA::String_var aUserName = myGroupImpl->GetName();
+                    const char* grpName = aGrpBaseDS->GetStoreName();
+                    char* aUserName = myGroupImpl->GetName();
                     aSize[ 0 ] = strlen( aUserName ) + 1;
 
                     aDataset = new HDFdataset( grpName, aGroup, HDF_STRING, aSize, 1 );
@@ -3714,14 +3710,14 @@ SALOMEDS::TMPFile* SMESH_Gen_i::Save( SALOMEDS::SComponent_ptr theComponent,
                           mySubRef->ReferencedObject( myShape.inout() ) &&
                           !CORBA::is_nil( myShape->GetObject() ))
                       {
-                        CORBA::String_var myRefOnObject = myShape->GetID();
-                        if ( myRefOnObject.in()[0] ) {
+                        string myRefOnObject = myShape->GetID();
+                        if ( myRefOnObject.length() > 0 ) {
                           char aRefName[ 30 ];
                           sprintf( aRefName, "Ref on shape %d", anId);
-                          aSize[ 0 ] = strlen( myRefOnObject.in() ) + 1;
+                          aSize[ 0 ] = myRefOnObject.length() + 1;
                           aDataset = new HDFdataset(aRefName, aGroup, HDF_STRING, aSize, 1);
                           aDataset->CreateOnDisk();
-                          aDataset->WriteOnDisk( ( char* )( myRefOnObject.in() ));
+                          aDataset->WriteOnDisk( ( char* )( myRefOnObject.c_str() ) );
                           aDataset->CloseOnDisk();
                         }
                       }
@@ -3869,7 +3865,8 @@ SALOMEDS::TMPFile* SMESH_Gen_i::Save( SALOMEDS::SComponent_ptr theComponent,
                       // Position
                       const SMDS_PositionPtr pos = node->GetPosition();
                       if ( onFace ) { // on FACE
-                        SMDS_FacePositionPtr fPos = pos;
+                        const SMDS_FacePosition* fPos =
+                          dynamic_cast<const SMDS_FacePosition*>( pos );
                         if ( fPos ) {
                           aUPos[ iNode ] = fPos->GetUParameter();
                           aVPos[ iNode ] = fPos->GetVParameter();
@@ -3879,7 +3876,8 @@ SALOMEDS::TMPFile* SMESH_Gen_i::Save( SALOMEDS::SComponent_ptr theComponent,
                           nbNodes--;
                       }
                       else { // on EDGE
-                        SMDS_EdgePositionPtr ePos = pos;
+                        const SMDS_EdgePosition* ePos =
+                          dynamic_cast<const SMDS_EdgePosition*>( pos );
                         if ( ePos ) {
                           aUPos[ iNode ] = ePos->GetUParameter();
                           iNode++;
@@ -4560,7 +4558,6 @@ bool SMESH_Gen_i::Load( SALOMEDS::SComponent_ptr theComponent,
                     myStudyContext->mapOldToNew( subid, newSubId );
                   }
                 }
-                delete [] refFromFile;
               }
 
               if ( aSubMesh->_is_nil() )
@@ -4595,7 +4592,6 @@ bool SMESH_Gen_i::Load( SALOMEDS::SComponent_ptr theComponent,
                           myNewMeshImpl->addHypothesis( aSubShapeObject, anHyp );
                       }
                     }
-                    delete [] refFromFile;
                   }
                 }
                 // close "applied algorithms" HDF group
@@ -4631,7 +4627,6 @@ bool SMESH_Gen_i::Load( SALOMEDS::SComponent_ptr theComponent,
                           myNewMeshImpl->addHypothesis( aSubShapeObject, anHyp );
                       }
                     }
-                    delete [] refFromFile;
                   }
                 }
                 // close "APPLIED HYPOTHESES" hdf group
@@ -4713,7 +4708,6 @@ bool SMESH_Gen_i::Load( SALOMEDS::SComponent_ptr theComponent,
                       aShape = GeomObjectToShape( aShapeObject );
                   }
                 }
-                delete [] refFromFile;
               }
               // Try to read a filter of SMESH_GroupOnFilter
               SMESH::Filter_var filter;
@@ -4732,14 +4726,12 @@ bool SMESH_Gen_i::Load( SALOMEDS::SComponent_ptr theComponent,
                   predicate = SMESH_GroupOnFilter_i::GetPredicate( filter );
                   filters.push_back( filter );
                 }
-                delete [] persistStr;
               }
 
               // Create group servant
               SMESH::ElementType type = (SMESH::ElementType)(ii - GetNodeGroupsTag() + 1);
               SMESH::SMESH_GroupBase_var aNewGroup = SMESH::SMESH_GroupBase::_duplicate
                 ( myNewMeshImpl->createGroup( type, nameFromFile, aShape, predicate ) );
-              delete [] nameFromFile;
               // Obtain a SMESHDS_Group object
               if ( aNewGroup->_is_nil() )
                 continue;
@@ -4778,7 +4770,6 @@ bool SMESH_Gen_i::Load( SALOMEDS::SComponent_ptr theComponent,
                 aDataset->CloseOnDisk();
                 Quantity_Color aColor( anRGB[0], anRGB[1], anRGB[2], Quantity_TOC_RGB );
                 aGroupBaseDS->SetColor( aColor );
-                delete [] anRGB;
               }
             }
           }
@@ -4796,7 +4787,7 @@ bool SMESH_Gen_i::Load( SALOMEDS::SComponent_ptr theComponent,
       }
 
       // read Sub-Mesh ORDER if any
-      if ( aTopGroup->ExistInternalObject( "Mesh Order" )) {
+      if( aTopGroup->ExistInternalObject( "Mesh Order" ) ) {
         aDataset = new HDFdataset( "Mesh Order", aTopGroup );
         aDataset->OpenOnDisk();
         size = aDataset->GetSize();
@@ -4812,7 +4803,6 @@ bool SMESH_Gen_i::Load( SALOMEDS::SComponent_ptr theComponent,
             anOrderIds.back().push_back(smIDs[ i ]);
 
         myNewMeshImpl->GetImpl().SetMeshOrder( anOrderIds );
-        delete [] smIDs;
       }
     } // loop on meshes
 
index 2fcac5a7f9122551b4efb276f0f3c77fd0daf3a0..ca0103c016e6cb9994a8eb21f1d0ef7c35dcb8cf 100644 (file)
@@ -255,13 +255,16 @@ static void enlargeBoundingBox(const SMESH::SMESH_IDSource_ptr theObject,
       enlargeBoundingBox( aMesh->FindNode( aElementsId[i] ), theMeasure);
     else
     {
-      if ( const SMDS_MeshElement* elem = aMesh->FindElement( aElementsId[i] ))
-        for (SMDS_NodeIteratorPtr aNodeIter = elem->nodeIterator(); aNodeIter->more(); )
-          enlargeBoundingBox( aNodeIter->next(), theMeasure);
+      const SMDS_MeshElement* elem = aMesh->FindElement( aElementsId[i] );
+      if (!elem)
+        continue;
+      SMDS_ElemIteratorPtr aNodeIter = elem->nodesIterator();
+      while( aNodeIter->more() )
+        enlargeBoundingBox( dynamic_cast<const SMDS_MeshNode*>( aNodeIter->next() ), theMeasure);
     }
   }
 }
-
+                               
 //=======================================================================
 // name    : BoundingBox
 // Purpose : compute common bounding box of entities
index 2bd6040631cc82ee6d8b3811d0b2031cb73743fe..d7afbed39f5ec69c7c73eefbbf905161daf70672 100644 (file)
@@ -42,6 +42,7 @@
 #include "SMDS_Mesh0DElement.hxx"
 #include "SMDS_MeshFace.hxx"
 #include "SMDS_MeshVolume.hxx"
+#include "SMDS_PolyhedralVolumeOfNodes.hxx"
 #include "SMDS_SetIterator.hxx"
 #include "SMDS_VolumeTool.hxx"
 #include "SMESHDS_Group.hxx"
@@ -533,9 +534,7 @@ SMESH::MeshPreviewStruct* SMESH_MeshEditor_i::GetPreviewData()
     SMESHDS_Mesh* aMeshDS;
     std::unique_ptr< SMESH_MeshPartDS > aMeshPartDS;
     if ( hasBadElems ) {
-      const list<const SMDS_MeshElement*>& badElems =
-        static_cast<SMESH_BadInputElements*>( getEditor().GetError().get() )->myBadElements;
-      aMeshPartDS.reset( new SMESH_MeshPartDS( badElems ));
+      aMeshPartDS.reset( new SMESH_MeshPartDS( getEditor().GetError()->myBadElements ));
       aMeshDS = aMeshPartDS.get();
     }
     else {
@@ -681,7 +680,7 @@ SMESH::ComputeError* SMESH_MeshEditor_i::GetLastError()
     errOut->code       = -( errIn->myName < 0 ? errIn->myName + 1: errIn->myName ); // -1 -> 0
     errOut->comment    = errIn->myComment.c_str();
     errOut->subShapeID = -1;
-    errOut->hasBadMesh = errIn->HasBadElems();
+    errOut->hasBadMesh = !errIn->myBadElements.empty();
   }
   else
   {
@@ -6964,7 +6963,7 @@ CORBA::Long SMESH_MeshEditor_i::MakeBoundaryElements(SMESH::Bnd_Dimension dim,
   // group of boundary elements
   SMESH_Group* smesh_group = 0;
   SMDSAbs_ElementType elemType = (dim == SMESH::BND_2DFROM3D) ? SMDSAbs_Volume : SMDSAbs_Face;
-  if ( strlen( groupName ))
+  if ( strlen(groupName) )
   {
     SMESH::ElementType groupType = SMESH::ElementType( int(elemType)-1 );
     group_var = mesh_i->CreateGroup( groupType, groupName );
index 4c81674a2e069eefdf212f784b21676aa9028f33..986ee3c06ad4ffa93801c99a3f1b5fd76c453842 100644 (file)
@@ -47,10 +47,10 @@ public:
   SMESH_MeshPartDS(SMESH::SMESH_IDSource_ptr                    meshPart);
   SMESH_MeshPartDS(const std::list< const SMDS_MeshElement* > & badElems );
 
-  virtual SMDS_NodeIteratorPtr   nodesIterator  () const;
-  virtual SMDS_EdgeIteratorPtr   edgesIterator  () const;
-  virtual SMDS_FaceIteratorPtr   facesIterator  () const;
-  virtual SMDS_VolumeIteratorPtr volumesIterator() const;
+  virtual SMDS_NodeIteratorPtr   nodesIterator     (bool idInceasingOrder=false) const;
+  virtual SMDS_EdgeIteratorPtr   edgesIterator     (bool idInceasingOrder=false) const;
+  virtual SMDS_FaceIteratorPtr   facesIterator     (bool idInceasingOrder=false) const;
+  virtual SMDS_VolumeIteratorPtr volumesIterator   (bool idInceasingOrder=false) const;
 
   virtual SMDS_ElemIteratorPtr elementsIterator(SMDSAbs_ElementType type=SMDSAbs_All) const;
   virtual SMDS_ElemIteratorPtr elementGeomIterator(SMDSAbs_GeometryType type) const;
@@ -61,6 +61,24 @@ public:
 private:
   TIDSortedElemSet _elements[ SMDSAbs_NbElementTypes ];
   SMESHDS_Mesh*    _meshDS;
+  /*!
+   * \brief Class used to access to protected data of SMDS_MeshInfo
+   */
+  struct TMeshInfo : public SMDS_MeshInfo
+  {
+    void Add(const SMDS_MeshElement* e) { SMDS_MeshInfo::addWithPoly( e ); }
+  };
+  /*!
+   * \brief Element holing its ID only
+   */
+  struct TElemID : public SMDS_MeshElement
+  {
+    TElemID(int ID) : SMDS_MeshElement( ID ) {}
+    virtual SMDSAbs_ElementType  GetType() const { return SMDSAbs_All; }
+    virtual SMDSAbs_EntityType   GetEntityType() const { return SMDSEntity_Last; }
+    virtual SMDSAbs_GeometryType GetGeomType() const { return SMDSGeom_NONE; }
+    virtual vtkIdType            GetVtkType() const { return -1; }
+  };
 };
 
 #endif
index f97541aef6f34a2bf7f3edbfb7b47ad2a232a3b9..a170d36d5e2b1f060a01efac948d781fae12ef32 100644 (file)
 #include "DriverMED_W_Field.h"
 #include "DriverMED_W_SMESHDS_Mesh.h"
 #include "MED_Factory.hxx"
-#include "SMDS_LinearEdge.hxx"
 #include "SMDS_EdgePosition.hxx"
 #include "SMDS_ElemIterator.hxx"
 #include "SMDS_FacePosition.hxx"
 #include "SMDS_IteratorOnIterators.hxx"
 #include "SMDS_MeshGroup.hxx"
 #include "SMDS_SetIterator.hxx"
-#include "SMDS_StdIterator.hxx"
 #include "SMDS_VolumeTool.hxx"
 #include "SMESHDS_Command.hxx"
 #include "SMESHDS_CommandType.hxx"
@@ -1104,8 +1102,7 @@ void SMESH_Mesh_i::RemoveGroupWithContents( SMESH::SMESH_GroupBase_ptr theGroup
     return;
 
   vector<int> nodeIds; // to remove nodes becoming free
-  bool isNodal = ( theGroup->GetType() == SMESH::NODE );
-  if ( !isNodal && !theGroup->IsEmpty() )
+  if ( !theGroup->IsEmpty() )
   {
     CORBA::Long elemID = theGroup->GetID( 1 );
     int nbElemNodes = GetElemNbNodes( elemID );
@@ -1113,44 +1110,36 @@ void SMESH_Mesh_i::RemoveGroupWithContents( SMESH::SMESH_GroupBase_ptr theGroup
       nodeIds.reserve( theGroup->Size() * nbElemNodes );
   }
 
-  // Retrieve contents
+  // Remove contents
   SMESH::SMESH_IDSource_var idSrc = SMESH::SMESH_IDSource::_narrow( theGroup );
   SMDS_ElemIteratorPtr     elemIt = GetElements( idSrc, theGroup->GetType() );
-  SMDS_StdIterator< const SMDS_MeshElement*, SMDS_ElemIteratorPtr > elemBeg( elemIt ), elemEnd;
-  std::vector< const SMDS_MeshElement* > elems( theGroup->Size() );
-  elems.assign( elemBeg, elemEnd );
-
-  TPythonDump pyDump; // Suppress dump from RemoveGroup()
-
-  // Remove group
-  RemoveGroup( theGroup );
-
-  // Remove contents
-  for ( size_t i = 0; i < elems.size(); ++i )
+  while ( elemIt->more() )
   {
-    if ( !isNodal )
-    {
-      for ( SMDS_ElemIteratorPtr nIt = elems[i]->nodesIterator(); nIt->more(); )
-        nodeIds.push_back( nIt->next()->GetID() );
+    const SMDS_MeshElement* e = elemIt->next();
 
-      _impl->GetMeshDS()->RemoveFreeElement( elems[i], /*sm=*/0 );
-    }
-    else
-    {
-      _impl->GetMeshDS()->RemoveElement( elems[i] );
-    }
+    SMDS_ElemIteratorPtr nIt = e->nodesIterator();
+    while ( nIt->more() )
+      nodeIds.push_back( nIt->next()->GetID() );
+
+    _impl->GetMeshDS()->RemoveElement( e );
   }
 
   // Remove free nodes
-  for ( size_t i = 0 ; i < nodeIds.size(); ++i )
-    if ( const SMDS_MeshNode* n = _impl->GetMeshDS()->FindNode( nodeIds[i] ))
-      if ( n->NbInverseElements() == 0 )
-        _impl->GetMeshDS()->RemoveFreeNode( n, /*sm=*/0 );
+  if ( theGroup->GetType() != SMESH::NODE )
+    for ( size_t i = 0 ; i < nodeIds.size(); ++i )
+      if ( const SMDS_MeshNode* n = _impl->GetMeshDS()->FindNode( nodeIds[i] ))
+        if ( n->NbInverseElements() == 0 )
+          _impl->GetMeshDS()->RemoveFreeNode( n, /*sm=*/0 );
+
+  TPythonDump pyDump; // Suppress dump from RemoveGroup()
 
   // Update Python script (theGroup must be alive for this)
   pyDump << SMESH::SMESH_Mesh_var(_this())
          << ".RemoveGroupWithContents( " << theGroup << " )";
 
+  // Remove group
+  RemoveGroup( theGroup );
+
   SMESH_CATCH( SMESH::throwCorbaException );
 }
 
@@ -2563,7 +2552,7 @@ SMESH::SMESH_GroupBase_ptr SMESH_Mesh_i::createGroup (SMESH::ElementType
                                                       const SMESH_PredicatePtr& thePredicate )
 {
   std::string newName;
-  if ( !theName || !theName[0] )
+  if ( !theName || strlen( theName ) == 0 )
   {
     std::set< std::string > presentNames;
     std::map<int, SMESH::SMESH_GroupBase_ptr>::const_iterator i_gr = _mapGroups.begin();
@@ -4110,14 +4099,14 @@ SMESH::long_array* SMESH_Mesh_i::GetNodesId()
     _preMeshInfo->FullLoadFromFile();
 
   SMESH::long_array_var aResult = new SMESH::long_array();
-  SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS();
+  SMESHDS_Mesh* aSMESHDS_Mesh = _impl->GetMeshDS();
 
-  if ( aMeshDS == NULL )
+  if ( aSMESHDS_Mesh == NULL )
     return aResult._retn();
 
   long nbNodes = NbNodes();
   aResult->length( nbNodes );
-  SMDS_NodeIteratorPtr anIt = aMeshDS->nodesIterator();
+  SMDS_NodeIteratorPtr anIt = aSMESHDS_Mesh->nodesIterator(/*idInceasingOrder=*/true);
   for ( int i = 0, n = nbNodes; i < n && anIt->more(); i++ )
     aResult[i] = anIt->next()->GetID();
 
@@ -4337,12 +4326,12 @@ SMESH::double_array* SMESH_Mesh_i::GetNodeXYZ(const CORBA::Long id)
     _preMeshInfo->FullLoadFromFile();
 
   SMESH::double_array_var aResult = new SMESH::double_array();
-  SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS();
-  if ( aMeshDS == NULL )
+  SMESHDS_Mesh* aSMESHDS_Mesh = _impl->GetMeshDS();
+  if ( aSMESHDS_Mesh == NULL )
     return aResult._retn();
 
   // find node
-  const SMDS_MeshNode* aNode = aMeshDS->FindNode(id);
+  const SMDS_MeshNode* aNode = aSMESHDS_Mesh->FindNode(id);
   if(!aNode)
     return aResult._retn();
 
@@ -4368,12 +4357,12 @@ SMESH::long_array* SMESH_Mesh_i::GetNodeInverseElements(const CORBA::Long id)
     _preMeshInfo->FullLoadFromFile();
 
   SMESH::long_array_var aResult = new SMESH::long_array();
-  SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS();
-  if ( aMeshDS == NULL )
+  SMESHDS_Mesh* aSMESHDS_Mesh = _impl->GetMeshDS();
+  if ( aSMESHDS_Mesh == NULL )
     return aResult._retn();
 
   // find node
-  const SMDS_MeshNode* aNode = aMeshDS->FindNode(id);
+  const SMDS_MeshNode* aNode = aSMESHDS_Mesh->FindNode(id);
   if(!aNode)
     return aResult._retn();
 
@@ -4415,16 +4404,17 @@ SMESH::NodePosition* SMESH_Mesh_i::GetNodePosition(CORBA::Long NodeID)
       case SMDS_TOP_EDGE:
         aNodePosition->shapeType = GEOM::EDGE;
         aNodePosition->params.length(1);
-        aNodePosition->params[0] = SMDS_EdgePositionPtr( pos )->GetUParameter();
+        aNodePosition->params[0] =
+          static_cast<SMDS_EdgePosition*>( pos )->GetUParameter();
         break;
-      case SMDS_TOP_FACE: {
-        SMDS_FacePositionPtr fPos = pos;
+      case SMDS_TOP_FACE:
         aNodePosition->shapeType = GEOM::FACE;
         aNodePosition->params.length(2);
-        aNodePosition->params[0] = fPos->GetUParameter();
-        aNodePosition->params[1] = fPos->GetVParameter();
+        aNodePosition->params[0] =
+          static_cast<SMDS_FacePosition*>( pos )->GetUParameter();
+        aNodePosition->params[1] =
+          static_cast<SMDS_FacePosition*>( pos )->GetVParameter();
         break;
-      }
       case SMDS_TOP_VERTEX:
         aNodePosition->shapeType = GEOM::VERTEX;
         break;
@@ -4499,12 +4489,12 @@ CORBA::Long SMESH_Mesh_i::GetShapeID(const CORBA::Long id)
   if ( _preMeshInfo )
     _preMeshInfo->FullLoadFromFile();
 
-  SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS();
-  if ( aMeshDS == NULL )
+  SMESHDS_Mesh* aSMESHDS_Mesh = _impl->GetMeshDS();
+  if ( aSMESHDS_Mesh == NULL )
     return -1;
 
   // try to find node
-  const SMDS_MeshNode* aNode = aMeshDS->FindNode(id);
+  const SMDS_MeshNode* aNode = aSMESHDS_Mesh->FindNode(id);
   if(aNode) {
     return aNode->getshapeId();
   }
@@ -4526,12 +4516,12 @@ CORBA::Long SMESH_Mesh_i::GetShapeIDForElem(const CORBA::Long id)
   if ( _preMeshInfo )
     _preMeshInfo->FullLoadFromFile();
 
-  SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS();
-  if ( aMeshDS == NULL )
+  SMESHDS_Mesh* aSMESHDS_Mesh = _impl->GetMeshDS();
+  if ( aSMESHDS_Mesh == NULL )
     return -1;
 
   // try to find element
-  const SMDS_MeshElement* elem = aMeshDS->FindElement(id);
+  const SMDS_MeshElement* elem = aSMESHDS_Mesh->FindElement(id);
   if(!elem)
     return -1;
 
@@ -4556,10 +4546,10 @@ CORBA::Long SMESH_Mesh_i::GetElemNbNodes(const CORBA::Long id)
   if ( _preMeshInfo )
     _preMeshInfo->FullLoadFromFile();
 
-  SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS();
-  if ( aMeshDS == NULL ) return -1;
+  SMESHDS_Mesh* aSMESHDS_Mesh = _impl->GetMeshDS();
+  if ( aSMESHDS_Mesh == NULL ) return -1;
   // try to find element
-  const SMDS_MeshElement* elem = aMeshDS->FindElement(id);
+  const SMDS_MeshElement* elem = aSMESHDS_Mesh->FindElement(id);
   if(!elem) return -1;
   return elem->NbNodes();
 }
@@ -4578,9 +4568,9 @@ CORBA::Long SMESH_Mesh_i::GetElemNode(const CORBA::Long id, const CORBA::Long in
   if ( _preMeshInfo )
     _preMeshInfo->FullLoadFromFile();
 
-  SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS();
-  if ( aMeshDS == NULL ) return -1;
-  const SMDS_MeshElement* elem = aMeshDS->FindElement(id);
+  SMESHDS_Mesh* aSMESHDS_Mesh = _impl->GetMeshDS();
+  if ( aSMESHDS_Mesh == NULL ) return -1;
+  const SMDS_MeshElement* elem = aSMESHDS_Mesh->FindElement(id);
   if(!elem) return -1;
   if( index>=elem->NbNodes() || index<0 ) return -1;
   return elem->GetNode(index)->GetID();
@@ -4598,9 +4588,9 @@ SMESH::long_array* SMESH_Mesh_i::GetElemNodes(const CORBA::Long id)
     _preMeshInfo->FullLoadFromFile();
 
   SMESH::long_array_var aResult = new SMESH::long_array();
-  if ( SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS() )
+  if ( SMESHDS_Mesh* aSMESHDS_Mesh = _impl->GetMeshDS() )
   {
-    if ( const SMDS_MeshElement* elem = aMeshDS->FindElement(id) )
+    if ( const SMDS_MeshElement* elem = aSMESHDS_Mesh->FindElement(id) )
     {
       aResult->length( elem->NbNodes() );
       for ( int i = 0; i < elem->NbNodes(); ++i )
@@ -4622,13 +4612,13 @@ CORBA::Boolean SMESH_Mesh_i::IsMediumNode(const CORBA::Long ide, const CORBA::Lo
   if ( _preMeshInfo )
     _preMeshInfo->FullLoadFromFile();
 
-  SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS();
-  if ( aMeshDS == NULL ) return false;
+  SMESHDS_Mesh* aSMESHDS_Mesh = _impl->GetMeshDS();
+  if ( aSMESHDS_Mesh == NULL ) return false;
   // try to find node
-  const SMDS_MeshNode* aNode = aMeshDS->FindNode(idn);
+  const SMDS_MeshNode* aNode = aSMESHDS_Mesh->FindNode(idn);
   if(!aNode) return false;
   // try to find element
-  const SMDS_MeshElement* elem = aMeshDS->FindElement(ide);
+  const SMDS_MeshElement* elem = aSMESHDS_Mesh->FindElement(ide);
   if(!elem) return false;
 
   return elem->IsMediumNode(aNode);
@@ -4648,11 +4638,11 @@ CORBA::Boolean SMESH_Mesh_i::IsMediumNodeOfAnyElem(const CORBA::Long idn,
   if ( _preMeshInfo )
     _preMeshInfo->FullLoadFromFile();
 
-  SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS();
-  if ( aMeshDS == NULL ) return false;
+  SMESHDS_Mesh* aSMESHDS_Mesh = _impl->GetMeshDS();
+  if ( aSMESHDS_Mesh == NULL ) return false;
 
   // try to find node
-  const SMDS_MeshNode* aNode = aMeshDS->FindNode(idn);
+  const SMDS_MeshNode* aNode = aSMESHDS_Mesh->FindNode(idn);
   if(!aNode) return false;
 
   SMESH_MesherHelper aHelper( *(_impl) );
@@ -4678,9 +4668,9 @@ CORBA::Long SMESH_Mesh_i::ElemNbEdges(const CORBA::Long id)
   if ( _preMeshInfo )
     _preMeshInfo->FullLoadFromFile();
 
-  SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS();
-  if ( aMeshDS == NULL ) return -1;
-  const SMDS_MeshElement* elem = aMeshDS->FindElement(id);
+  SMESHDS_Mesh* aSMESHDS_Mesh = _impl->GetMeshDS();
+  if ( aSMESHDS_Mesh == NULL ) return -1;
+  const SMDS_MeshElement* elem = aSMESHDS_Mesh->FindElement(id);
   if(!elem) return -1;
   return elem->NbEdges();
 }
@@ -4697,9 +4687,9 @@ CORBA::Long SMESH_Mesh_i::ElemNbFaces(const CORBA::Long id)
   if ( _preMeshInfo )
     _preMeshInfo->FullLoadFromFile();
 
-  SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS();
-  if ( aMeshDS == NULL ) return -1;
-  const SMDS_MeshElement* elem = aMeshDS->FindElement(id);
+  SMESHDS_Mesh* aSMESHDS_Mesh = _impl->GetMeshDS();
+  if ( aSMESHDS_Mesh == NULL ) return -1;
+  const SMDS_MeshElement* elem = aSMESHDS_Mesh->FindElement(id);
   if(!elem) return -1;
   return elem->NbFaces();
 }
@@ -4716,9 +4706,9 @@ SMESH::long_array* SMESH_Mesh_i::GetElemFaceNodes(CORBA::Long  elemId,
     _preMeshInfo->FullLoadFromFile();
 
   SMESH::long_array_var aResult = new SMESH::long_array();
-  if ( SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS() )
+  if ( SMESHDS_Mesh* aSMESHDS_Mesh = _impl->GetMeshDS() )
   {
-    if ( const SMDS_MeshElement* elem = aMeshDS->FindElement(elemId) )
+    if ( const SMDS_MeshElement* elem = aSMESHDS_Mesh->FindElement(elemId) )
     {
       SMDS_VolumeTool vtool( elem );
       if ( faceIndex < vtool.NbFaces() )
@@ -4829,9 +4819,9 @@ CORBA::Boolean SMESH_Mesh_i::IsPoly(const CORBA::Long id)
   if ( _preMeshInfo )
     _preMeshInfo->FullLoadFromFile();
 
-  SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS();
-  if ( aMeshDS == NULL ) return false;
-  const SMDS_MeshElement* elem = aMeshDS->FindElement(id);
+  SMESHDS_Mesh* aSMESHDS_Mesh = _impl->GetMeshDS();
+  if ( aSMESHDS_Mesh == NULL ) return false;
+  const SMDS_MeshElement* elem = aSMESHDS_Mesh->FindElement(id);
   if(!elem) return false;
   return elem->IsPoly();
 }
@@ -4848,9 +4838,9 @@ CORBA::Boolean SMESH_Mesh_i::IsQuadratic(const CORBA::Long id)
   if ( _preMeshInfo )
     _preMeshInfo->FullLoadFromFile();
 
-  SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS();
-  if ( aMeshDS == NULL ) return false;
-  const SMDS_MeshElement* elem = aMeshDS->FindElement(id);
+  SMESHDS_Mesh* aSMESHDS_Mesh = _impl->GetMeshDS();
+  if ( aSMESHDS_Mesh == NULL ) return false;
+  const SMDS_MeshElement* elem = aSMESHDS_Mesh->FindElement(id);
   if(!elem) return false;
   return elem->IsQuadratic();
 }
@@ -4867,7 +4857,7 @@ CORBA::Double SMESH_Mesh_i::GetBallDiameter(CORBA::Long id)
     _preMeshInfo->FullLoadFromFile();
 
   if ( const SMDS_BallElement* ball =
-       SMDS_Mesh::DownCast<SMDS_BallElement>( _impl->GetMeshDS()->FindElement( id )))
+       dynamic_cast<const SMDS_BallElement*>( _impl->GetMeshDS()->FindElement( id )))
     return ball->GetDiameter();
 
   return 0;
@@ -4885,11 +4875,11 @@ SMESH::double_array* SMESH_Mesh_i::BaryCenter(const CORBA::Long id)
     _preMeshInfo->FullLoadFromFile();
 
   SMESH::double_array_var aResult = new SMESH::double_array();
-  SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS();
-  if ( aMeshDS == NULL )
+  SMESHDS_Mesh* aSMESHDS_Mesh = _impl->GetMeshDS();
+  if ( aSMESHDS_Mesh == NULL )
     return aResult._retn();
 
-  const SMDS_MeshElement* elem = aMeshDS->FindElement(id);
+  const SMDS_MeshElement* elem = aSMESHDS_Mesh->FindElement(id);
   if(!elem)
     return aResult._retn();
 
@@ -4949,14 +4939,12 @@ SMESH_Mesh_i::MakeGroupsOfBadInputElements( int         theSubShapeID,
   {
     // compute error
     SMESH_ComputeErrorPtr error = sm->GetComputeError();
-    if ( error && error->HasBadElems() )
+    if ( error && !error->myBadElements.empty())
     {
       // sort bad elements by type
       vector< const SMDS_MeshElement* > elemsByType[ SMDSAbs_NbElementTypes ];
-      const list<const SMDS_MeshElement*>& badElems =
-        static_cast<SMESH_BadInputElements*>( error.get() )->myBadElements;
-      list<const SMDS_MeshElement*>::const_iterator elemIt  = badElems.begin();
-      list<const SMDS_MeshElement*>::const_iterator elemEnd = badElems.end();
+      list<const SMDS_MeshElement*>::iterator elemIt  = error->myBadElements.begin();
+      list<const SMDS_MeshElement*>::iterator elemEnd = error->myBadElements.end();
       for ( ; elemIt != elemEnd; ++elemIt )
       {
         const SMDS_MeshElement* elem = *elemIt;
@@ -5325,7 +5313,7 @@ SALOMEDS::TMPFile* SMESH_Mesh_i::GetVtkUgStream()
 {
   SALOMEDS::TMPFile_var SeqFile;
   if ( SMESHDS_Mesh* aMeshDS = _impl->GetMeshDS() ) {
-    SMDS_UnstructuredGrid* aGrid = aMeshDS->GetGrid();
+    SMDS_UnstructuredGrid* aGrid = aMeshDS->getGrid();
     if(aGrid) {
       vtkUnstructuredGridWriter* aWriter = vtkUnstructuredGridWriter::New();
       aWriter->WriteToOutputStringOn();
@@ -6124,24 +6112,6 @@ void SMESH_Mesh_i::convertMeshOrder (const TListOfListOfInt&     theIdsOrder,
   }
 }
 
-namespace // utils used by SMESH_MeshPartDS
-{
-  /*!
-   * \brief Class used to access to protected data of SMDS_MeshInfo
-   */
-  struct TMeshInfo : public SMDS_MeshInfo
-  {
-    void Add(const SMDS_MeshElement* e) { SMDS_MeshInfo::addWithPoly( e ); }
-  };
-  /*!
-   * \brief Element holing its ID only
-   */
-  struct TElemID : public SMDS_LinearEdge
-  {
-    TElemID(int ID) : SMDS_LinearEdge(0,0) { setID( ID ); }
-  };
-}
-
 //================================================================================
 //
 // Implementation of SMESH_MeshPartDS
@@ -6248,7 +6218,7 @@ SMDS_ElemIteratorPtr SMESH_MeshPartDS::elementGeomIterator(SMDSAbs_GeometryType
     SMDS_MeshElement::GeomFilter
     > TIter;
 
-  SMDSAbs_ElementType type = SMDS_MeshCell::ElemType( geomType );
+  SMDSAbs_ElementType type = SMDS_MeshCell::toSmdsType( geomType );
 
   return SMDS_ElemIteratorPtr( new TIter( _elements[type].begin(),
                                           _elements[type].end(),
@@ -6266,7 +6236,7 @@ SMDS_ElemIteratorPtr SMESH_MeshPartDS::elementEntityIterator(SMDSAbs_EntityType
     SMDS_MeshElement::EntityFilter
     > TIter;
 
-  SMDSAbs_ElementType type = SMDS_MeshCell::ElemType( entity );
+  SMDSAbs_ElementType type = SMDS_MeshCell::toSmdsType( entity );
 
   return SMDS_ElemIteratorPtr( new TIter( _elements[type].begin(),
                                           _elements[type].end(),
@@ -6293,10 +6263,10 @@ SMDS_ElemIteratorPtr SMESH_MeshPartDS::elementsIterator(SMDSAbs_ElementType type
 }
 // -------------------------------------------------------------------------------------
 #define _GET_ITER_DEFINE( iterType, methName, elem, elemType)                       \
-  iterType SMESH_MeshPartDS::methName() const                 \
+  iterType SMESH_MeshPartDS::methName( bool idInceasingOrder) const                 \
   {                                                                                 \
     typedef SMDS_SetIterator<const elem*, TIDSortedElemSet::const_iterator > TIter; \
-    return _meshDS ? _meshDS->methName() : iterType                 \
+    return _meshDS ? _meshDS->methName(idInceasingOrder) : iterType                 \
       ( new TIter( _elements[elemType].begin(), _elements[elemType].end() ));       \
   }
 // -------------------------------------------------------------------------------------
index c2181296c5aab928de37fd7ced292a0ee7d792e3..c7e753d89c3d5f9cda95af08eb166be2aa8b14c6 100644 (file)
@@ -1059,7 +1059,8 @@ void SMESH_PreMeshInfo::readSubMeshes(DriverMED_R_SMESHDS_Mesh* reader) const
             // -- Most probably a bad study was saved when there were
             // not fixed bugs in SMDS_MeshInfo
             if ( aPos->GetTypeOfPosition() == SMDS_TOP_FACE ) {
-              SMDS_FacePositionPtr fPos = aPos;
+              SMDS_FacePosition* fPos = const_cast<SMDS_FacePosition*>
+                ( static_cast<const SMDS_FacePosition*>( aPos ));
               fPos->SetUParameter( aUPos[ iNode ]);
               fPos->SetVParameter( aVPos[ iNode ]);
             }
@@ -1067,8 +1068,9 @@ void SMESH_PreMeshInfo::readSubMeshes(DriverMED_R_SMESHDS_Mesh* reader) const
           else {
             // ASSERT( aPos->GetTypeOfPosition() == SMDS_TOP_EDGE );-- issue 20182
             if ( aPos->GetTypeOfPosition() == SMDS_TOP_EDGE ) {
-              SMDS_EdgePositionPtr ePos = aPos;
-              ePos->SetUParameter( aUPos[ iNode ]);
+              SMDS_EdgePosition* fPos = const_cast<SMDS_EdgePosition*>
+                ( static_cast<const SMDS_EdgePosition*>( aPos ));
+              fPos->SetUParameter( aUPos[ iNode ]);
             }
           }
         }
index b9c2e393fbb0705525dafded7f630970be85ee6c..2c1beefc80eb6e720e49ee32047c042acddc7956 100644 (file)
@@ -3619,7 +3619,7 @@ bool StdMeshers_Cartesian_3D::Compute(SMESH_Mesh &         theMesh,
         for ( ; solidExp.More() && volIt->more(); solidExp.Next() )
         {
           const SMDS_MeshElement* vol = volIt->next();
-          sm1->RemoveElement( vol );
+          sm1->RemoveElement( vol, /*isElemDeleted=*/false );
           meshDS->SetMeshElementOnShape( vol, solidExp.Current() );
         }
       }
index 0b684862296ee8a1bf585377aae8389421c7ab10..b0d36a59ccb5bd25c9f7aa58a6a9006e4b6e2605 100644 (file)
@@ -549,7 +549,8 @@ const std::vector<UVPtStruct>& StdMeshers_FaceSide::GetUVPtStruct(bool   isXCons
           uvPt.normParam  = u_node->first;
           uvPt.x = uvPt.y = uvPt.normParam;
           // -- U ----------------------------------------------
-          SMDS_EdgePositionPtr epos = uvPt.node->GetPosition();
+          const SMDS_EdgePosition* epos =
+            dynamic_cast<const SMDS_EdgePosition*>(uvPt.node->GetPosition());
           if ( epos && uvPt.node->getshapeId() == myEdgeID[iE] ) {
             uvPt.param = epos->GetUParameter();
           }
index 403de38f6e22f4b259b0bec2d962dda786b1e81d..a32b65891b4552a5a867931658beefe3b322a184 100644 (file)
@@ -386,7 +386,7 @@ namespace
 
     // Find a node at any block corner
 
-    SMDS_NodeIteratorPtr nIt = meshDS->nodesIterator();
+    SMDS_NodeIteratorPtr nIt = meshDS->nodesIterator(/*idInceasingOrder=*/true);
     if ( !nIt->more() ) return error("Empty mesh");
 
     const SMDS_MeshNode* nCorner = 0;
index b5da1cd52f00bfad5478104d9436fc16a6dc6acb..949bd3a9073214bc786d6affa7d1840c79e433c3 100644 (file)
@@ -581,7 +581,7 @@ bool StdMeshers_Import_1D2D::Compute(SMESH_Mesh & theMesh, const TopoDS_Shape &
                 if ( Abs(u-f) < 2 * faceTol || Abs(u-l) < 2 * faceTol )
                   // duplicated node on vertex
                   return error("Source elements overlap one another");
-                tgtFaceSM->RemoveNode( n );
+                tgtFaceSM->RemoveNode( n, /*isNodeDeleted=*/false );
                 tgtMesh->SetNodeOnEdge( n, edges[iE], u );
                 break;
               }
@@ -634,7 +634,7 @@ bool StdMeshers_Import_1D2D::Compute(SMESH_Mesh & theMesh, const TopoDS_Shape &
 
           TopoDS_Edge geomEdge = TopoDS::Edge(bndShapes.back());
           helper.CheckNodeU( geomEdge, link._medium, u, projTol, /*force=*/true );
-          tgtFaceSM->RemoveNode( link._medium );
+          tgtFaceSM->RemoveNode( link._medium, /*isNodeDeleted=*/false );
           tgtMesh->SetNodeOnEdge( (SMDS_MeshNode*)link._medium, geomEdge, u );
         }
         else
@@ -747,7 +747,7 @@ bool StdMeshers_Import_1D2D::Compute(SMESH_Mesh & theMesh, const TopoDS_Shape &
           seamHelper.AddEdge( node1, node2 );
           if ( node2->getshapeId() == helper.GetSubShapeID() )
           {
-            tgtFaceSM->RemoveNode( node2 );
+            tgtFaceSM->RemoveNode( node2, /*isNodeDeleted=*/false );
             tgtMesh->SetNodeOnEdge( const_cast<SMDS_MeshNode*>( node2 ), seamEdge, n2->first );
           }
         }
index 4ea62de3e713f647726c06759061bbf5a421ff9f..196dbe7daf0fe38a41e2c5fcb0ae0619158e8163 100644 (file)
@@ -516,7 +516,8 @@ static bool fixCommonVertexUV (R2 &                 theUV,
         // check if node is medium
         if ( theCreateQuadratic && SMESH_MesherHelper::IsMedium( node, SMDSAbs_Edge ))
           continue;
-        SMDS_EdgePositionPtr epos = node->GetPosition();
+        const SMDS_EdgePosition* epos =
+          static_cast<const SMDS_EdgePosition*>(node->GetPosition());
         double u = epos->GetUParameter();
         if ( u < umin )
           umin = u;
@@ -534,10 +535,10 @@ static bool fixCommonVertexUV (R2 &                 theUV,
   }
   R2 uv0, uv1, uv2;
   uv0.x = thisUV.X();   uv0.y = thisUV.Y();
-  uv1.x = nextUV.X();   uv1.y = nextUV.Y();
+  uv1.x = nextUV.X();   uv1.y = nextUV.Y(); 
   uv2.x = thisUV.X();   uv2.y = thisUV.Y();
 
-  uv1.x *= theScaleX;   uv1.y *= theScaleY;
+  uv1.x *= theScaleX;   uv1.y *= theScaleY; 
 
   if ( fixOverlappedLinkUV( uv0, uv1, uv2 ))
   {
index f22b5fe67dad5aa45ba2e2d67c9aeecbb56192a1..0223a7a074cb9b2852fb11bc345510b3fbb8cc21 100644 (file)
@@ -234,7 +234,8 @@ void StdMeshers_Penta_3D::MakeNodes()
       aTNode.SetBaseNodeID(aNodeID);
       //
       if ( SMESH_Block::IsEdgeID (aSID)) {
-        SMDS_EdgePositionPtr epos = aNode->GetPosition();
+        const SMDS_EdgePosition* epos =
+          static_cast<const SMDS_EdgePosition*>(aNode->GetPosition());
         myBlock.ComputeParameters( epos->GetUParameter(), aS, aCoords );
       }
       else {
@@ -1464,9 +1465,11 @@ bool StdMeshers_Penta_3D::LoadIJNodes(StdMeshers_IJNodeMap & theIJNodes,
     node = nIt->next();
     if(myTool->IsMedium(node))
       continue;
-    SMDS_EdgePositionPtr pos = node->GetPosition();
-    if ( !pos )
+    const SMDS_EdgePosition* pos =
+      dynamic_cast<const SMDS_EdgePosition*>( node->GetPosition() );
+    if ( !pos ) {
       return false;
+    }
     double u = ( pos->GetUParameter() - f ) / range;
     vector<const SMDS_MeshNode*> & nVec = theIJNodes[ u ];
     nVec.resize( vsize, nullNode );
@@ -1485,9 +1488,11 @@ bool StdMeshers_Penta_3D::LoadIJNodes(StdMeshers_IJNodeMap & theIJNodes,
     node = nIt->next();
     if(myTool->IsMedium(node))
       continue;
-    SMDS_EdgePositionPtr pos = node->GetPosition();
-    if ( !pos )
+    const SMDS_EdgePosition* pos =
+      dynamic_cast<const SMDS_EdgePosition*>( node->GetPosition() );
+    if ( !pos ) {
       return false;
+    }
     sortedNodes.insert( make_pair( pos->GetUParameter(), node ));
   }
   loadedNodes.insert( nVecf[ vsize - 1 ] = smVft->GetNodes()->next() );
index f5807f09a192f848a28904cad3c1cbd6514297fe..9dde41365e3a12a664c5409d757d41c01b39da36 100644 (file)
@@ -1798,8 +1798,9 @@ bool StdMeshers_Prism_3D::computeWalls(const Prism_3D::TPrismTopo& thePrism)
       if ( myHelper->GetIsQuadratic() )
       {
         // fill myHelper with medium nodes built by quadAlgo
-        for ( SMDS_ElemIteratorPtr fIt = fSM->GetSubMeshDS()->GetElements(); fIt->more(); )
-          myHelper->AddTLinks( SMDS_Mesh::DownCast<SMDS_MeshFace>( fIt->next() ));
+        SMDS_ElemIteratorPtr fIt = fSM->GetSubMeshDS()->GetElements();
+        while ( fIt->more() )
+          myHelper->AddTLinks( dynamic_cast<const SMDS_MeshFace*>( fIt->next() ));
       }
     }
   }
@@ -4846,7 +4847,7 @@ TPCurveOnHorFaceAdaptor::TPCurveOnHorFaceAdaptor( const TSideFace*   sideFace,
         }
         if ( !C2d.IsNull() )
         {
-          double u = SMDS_EdgePositionPtr( n->GetPosition() )->GetUParameter();
+          double u = static_cast< const SMDS_EdgePosition* >( n->GetPosition() )->GetUParameter();
           if ( f <= u && u <= l )
           {
             uv = C2d->Value( u ).XY();
index 55a7214e8e9e1da2302b7c5af14bc58591eaeb18..2070ef108b407d2d8760e8dd820ace1654ca6318 100644 (file)
@@ -2209,7 +2209,8 @@ FindMatchingNodesOnFaces( const TopoDS_Face&     face1,
       SMDS_NodeIteratorPtr nIt = edgeSM->GetNodes();
       while ( nIt->more() ) {
         const SMDS_MeshNode* node = nIt->next();
-        SMDS_EdgePositionPtr pos = node->GetPosition();
+        const SMDS_EdgePosition* pos =
+          static_cast<const SMDS_EdgePosition*>(node->GetPosition());
         pos2nodes.insert( make_pair( pos->GetUParameter(), node ));
       }
       if ((int) pos2nodes.size() != edgeSM->NbNodes() )
@@ -2885,6 +2886,7 @@ namespace StdMeshers_ProjectionUtils
 
     double bc[3]; // barycentric coordinates
     int    nodeIDs[3]; // nodes of a delaunay triangle
+    const SMDS_FacePosition* pos;
 
     _delaunay.InitTraversal( nbSrcNodes );
 
@@ -2902,8 +2904,8 @@ namespace StdMeshers_ProjectionUtils
       tgtNode = n2n->second;
       tgtMesh->MoveNode( tgtNode, xyz.X(), xyz.Y(), xyz.Z() );
 
-      if ( SMDS_FacePositionPtr pos = tgtNode->GetPosition() )
-        pos->SetParameters( uvNew.X(), uvNew.Y() );
+      if (( pos = dynamic_cast< const SMDS_FacePosition* >( tgtNode->GetPosition() )))
+        const_cast<SMDS_FacePosition*>( pos )->SetParameters( uvNew.X(), uvNew.Y() );
 
       --nbSrcNodes;
     }
index ae15730cdaea772582799431007ff623522f2603..c0e53ceebc99d2c577aa1c7872bc7e8b4a7959be 100644 (file)
@@ -140,7 +140,7 @@ bool StdMeshers_Projection_1D2D::Compute(SMESH_Mesh& theMesh, const TopoDS_Shape
     {
       const SMDS_MeshElement* f = fIt->next();
       //if ( !f->IsQuadratic() ) continue;
-      nodes.assign( SMDS_MeshElement::iterator( f->interlacedNodesIterator() ),
+      nodes.assign( SMDS_MeshElement::iterator( f->interlacedNodesElemIterator() ),
                     SMDS_MeshElement::iterator() );
       nodes.push_back( nodes[0] );
       for ( size_t i = 2; i < nodes.size(); i += 2 )
@@ -149,8 +149,8 @@ bool StdMeshers_Projection_1D2D::Compute(SMESH_Mesh& theMesh, const TopoDS_Shape
         if ( idType.second == TopAbs_EDGE &&
              idType.first  != nodes[i-1]->getshapeId() )
         {
-          faceSubMesh->RemoveNode( nodes[i-1] );
-          meshDS->SetNodeOnEdge( nodes[i-1], idType.first );
+          faceSubMesh->RemoveNode( nodes[i-1], /*isDeleted=*/false );
+          meshDS->SetNodeOnEdge( (SMDS_MeshNode*) nodes[i-1], idType.first );
           posFixer.SetSubShape( idType.first );
           posFixer.CheckNodeU( TopoDS::Edge( posFixer.GetSubShape() ),
                                nodes[i-1], dummyU=0., tol, /*force=*/true );
index 68ae8ea47ab88aecafeb96edb8de92a096058ffc..0686b165a77c6301498028dd42455674b24afa52 100644 (file)
@@ -371,7 +371,8 @@ namespace {
         if ( node->GetPosition()->GetTypeOfPosition() != SMDS_TOP_EDGE )
           RETURN_BAD_RESULT("Bad node position type: node " << node->GetID() <<
                             " pos type " << node->GetPosition()->GetTypeOfPosition());
-        SMDS_EdgePositionPtr pos = node->GetPosition();
+        const SMDS_EdgePosition* pos =
+          static_cast<const SMDS_EdgePosition*>(node->GetPosition());
         u2nodes.insert( make_pair( pos->GetUParameter(), node ));
         seamNodes.insert( node );
       }
@@ -1586,7 +1587,8 @@ bool StdMeshers_Projection_2D::Compute(SMESH_Mesh& theMesh, const TopoDS_Shape&
           break;
         }
         case  SMDS_TOP_EDGE:   {
-          SMDS_EdgePositionPtr pos = node->GetPosition();
+          const SMDS_EdgePosition* pos =
+            static_cast<const SMDS_EdgePosition*>(node->GetPosition());
           pos2nodes.insert( make_pair( pos->GetUParameter(), node ));
           break;
         }
index 4284c1b360d6a99eed50e0f1e37c3d8f23d7e780..43a6c4c093ac3d5c7e201dda3f2633dcdde651a9 100644 (file)
@@ -31,6 +31,7 @@
 
 #include "StdMeshers_ProjectionUtils.hxx"
 
+#include "SMDS_PolyhedralVolumeOfNodes.hxx"
 #include "SMDS_VolumeTool.hxx"
 #include "SMESHDS_Hypothesis.hxx"
 #include "SMESHDS_Mesh.hxx"
@@ -407,7 +408,8 @@ bool StdMeshers_Projection_3D::Compute(SMESH_Mesh& aMesh, const TopoDS_Shape& aS
                                  nodes[6],
                                  nodes[7], id, force3d); break;
     default: // polyhedron
-      const SMDS_MeshVolume * poly = tgtMeshDS->DownCast<SMDS_MeshVolume>( srcVol );
+      const SMDS_VtkVolume * poly =
+        dynamic_cast<const SMDS_VtkVolume*>( srcVol );
       if ( !poly )
         RETURN_BAD_RESULT("Unexpected volume type");
       if ( !poly->IsPoly())
index fd3a5bb10f8376a3dbb7789039c964905b7facd3..2e4ea50b8fb3effa05cc7ff8904de0bbbf3d0df4 100644 (file)
@@ -296,13 +296,12 @@ namespace
       SMESH_ComputeErrorPtr& err = sm->GetComputeError();
       if ( !err || err->IsOK() )
       {
-        SMESH_BadInputElements* badElems =
-          new SMESH_BadInputElements( mesh.GetMeshDS(),COMPERR_BAD_INPUT_MESH, msg, sm->GetAlgo() );
-        badElems->add( face1 );
-        badElems->add( face2 );
-        err.reset( badElems );
+        err = SMESH_ComputeError::New( COMPERR_BAD_INPUT_MESH, msg, sm->GetAlgo() );
+        err->myBadElements.push_back( face1 );
+        err->myBadElements.push_back( face2 );
       }
     }
+    //throw SALOME_Exception( msg.c_str() );
 
     return false; // == "algo fails"
   }
@@ -1036,7 +1035,7 @@ bool StdMeshers_QuadToTriaAdaptor::Compute(SMESH_Mesh& aMesh)
   vector<const SMDS_MeshNode*> FNodes(5);
   TColgp_SequenceOfPnt aContour;
 
-  SMDS_FaceIteratorPtr fIt = meshDS->facesIterator();
+  SMDS_FaceIteratorPtr fIt = meshDS->facesIterator(/*idInceasingOrder=*/true);
   while( fIt->more())
   {
     const SMDS_MeshElement* face = fIt->next();
index a9d275cfbc15723f8b14709e60e7440f0082d04e..ada3ab0ccc43d7e524949325cb589e543ffa13dc 100644 (file)
@@ -643,11 +643,9 @@ bool StdMeshers_Quadrangle_2D::computeQuadDominant(SMESH_Mesh&         aMesh,
               SMESH_ComputeErrorPtr& err = aMesh.GetSubMesh( aFace )->GetComputeError();
               if ( !err || err->IsOK() || err->myName < COMPERR_WARNING )
               {
-                SMESH_BadInputElements* badElems =
-                  new SMESH_BadInputElements( meshDS, COMPERR_WARNING,
-                                              "Bad quality quad created");
-                badElems->add( face );
-                err.reset( badElems );
+                err.reset( new SMESH_ComputeError( COMPERR_WARNING,
+                                                   "Bad quality quad created"));
+                err->myBadElements.push_back( face );
               }
             }
             --i;
@@ -820,11 +818,9 @@ bool StdMeshers_Quadrangle_2D::computeQuadDominant(SMESH_Mesh&         aMesh,
               SMESH_ComputeErrorPtr& err = aMesh.GetSubMesh( aFace )->GetComputeError();
               if ( !err || err->IsOK() || err->myName < COMPERR_WARNING )
               {
-                SMESH_BadInputElements* badElems =
-                  new SMESH_BadInputElements( meshDS, COMPERR_WARNING,
-                                              "Bad quality quad created");
-                badElems->add( face );
-                err.reset( badElems );
+                err.reset( new SMESH_ComputeError( COMPERR_WARNING,
+                                                   "Bad quality quad created"));
+                err->myBadElements.push_back( face );
               }
             }
             --i;
@@ -4672,11 +4668,9 @@ bool StdMeshers_Quadrangle_2D::check()
   {
     SMESH_subMesh* fSM = myHelper->GetMesh()->GetSubMesh( geomFace );
     SMESH_ComputeErrorPtr& err = fSM->GetComputeError();
-    SMESH_BadInputElements* badElems =
-      new SMESH_BadInputElements( meshDS, COMPERR_ALGO_FAILED,
-                                  "Inverted elements generated");
-    badElems->myBadElements.swap( badFaces );
-    err.reset( badElems );
+    err.reset ( new SMESH_ComputeError( COMPERR_ALGO_FAILED,
+                                        "Inverted elements generated"));
+    err->myBadElements.swap( badFaces );
 
     return !isOK;
   }
index 72cdff35f606d09c861ff43f409bcac402f22ddf..f68c3cbee37e2e41b524b0a17e7879744ebd4c9d 100644 (file)
@@ -27,7 +27,6 @@
 #include "SMDS_FaceOfNodes.hxx"
 #include "SMDS_FacePosition.hxx"
 #include "SMDS_MeshNode.hxx"
-#include "SMDS_PolygonalFaceOfNodes.hxx"
 #include "SMDS_SetIterator.hxx"
 #include "SMESHDS_Group.hxx"
 #include "SMESHDS_Hypothesis.hxx"
@@ -94,7 +93,6 @@
 #include <list>
 #include <queue>
 #include <string>
-#include <unordered_map>
 
 #ifdef _DEBUG_
 #define __myDEBUG
@@ -662,8 +660,7 @@ namespace VISCOUS_3D
     vector< _EdgesOnShape* > _eosConcaVer; // edges at concave VERTEXes of a FACE
     vector< _EdgesOnShape* > _eosC1; // to smooth together several C1 continues shapes
 
-    typedef std::unordered_map< const SMDS_MeshElement*, gp_XYZ > TFace2NormMap;
-    TFace2NormMap            _faceNormals; // if _shape is FACE
+    vector< gp_XYZ >         _faceNormals; // if _shape is FACE
     vector< _EdgesOnShape* > _faceEOS; // to get _faceNormals of adjacent FACEs
 
     Handle(ShapeAnalysis_Surface) _offsetSurf;
@@ -1101,23 +1098,24 @@ namespace VISCOUS_3D
    * We can't use SMDS_FaceOfNodes since it's impossible to set it's ID which is
    * needed because SMESH_ElementSearcher internaly uses set of elements sorted by ID
    */
-  struct _TmpMeshFace : public SMDS_PolygonalFaceOfNodes
+  struct _TmpMeshFace : public SMDS_MeshElement
   {
-    const SMDS_MeshElement* _srcFace;
-
+    vector<const SMDS_MeshNode* > _nn;
     _TmpMeshFace( const vector<const SMDS_MeshNode*>& nodes,
-                  int                                 ID,
-                  int                                 faceID=-1,
-                  const SMDS_MeshElement*             srcFace=0 ):
-      SMDS_PolygonalFaceOfNodes(nodes), _srcFace( srcFace ) { setID( ID ); setShapeID( faceID ); }
-    virtual SMDSAbs_EntityType  GetEntityType() const
-    { return _srcFace ? _srcFace->GetEntityType() : SMDSEntity_Quadrangle; }
-    virtual SMDSAbs_GeometryType GetGeomType()  const
-    { return _srcFace ? _srcFace->GetGeomType() : SMDSGeom_QUADRANGLE; }
+                  int id, int faceID=-1, int idInFace=-1):
+      SMDS_MeshElement(id), _nn(nodes) { setShapeId(faceID); setIdInShape(idInFace); }
+    virtual const SMDS_MeshNode* GetNode(const int ind) const { return _nn[ind]; }
+    virtual SMDSAbs_ElementType  GetType() const              { return SMDSAbs_Face; }
+    virtual vtkIdType GetVtkType() const                      { return -1; }
+    virtual SMDSAbs_EntityType   GetEntityType() const        { return SMDSEntity_Last; }
+    virtual SMDSAbs_GeometryType GetGeomType() const
+    { return _nn.size() == 3 ? SMDSGeom_TRIANGLE : SMDSGeom_QUADRANGLE; }
+    virtual SMDS_ElemIteratorPtr elementsIterator(SMDSAbs_ElementType) const
+    { return SMDS_ElemIteratorPtr( new SMDS_NodeVectorElemIterator( _nn.begin(), _nn.end()));}
   };
   //--------------------------------------------------------------------------------
   /*!
-   * \brief Class of temporary mesh quadrangle face storing _LayerEdge it's based on
+   * \brief Class of temporary mesh face storing _LayerEdge it's based on
    */
   struct _TmpMeshFaceOnEdge : public _TmpMeshFace
   {
@@ -1125,21 +1123,17 @@ namespace VISCOUS_3D
     _TmpMeshFaceOnEdge( _LayerEdge* le1, _LayerEdge* le2, int ID ):
       _TmpMeshFace( vector<const SMDS_MeshNode*>(4), ID ), _le1(le1), _le2(le2)
     {
-      myNodes[0]=_le1->_nodes[0];
-      myNodes[1]=_le1->_nodes.back();
-      myNodes[2]=_le2->_nodes.back();
-      myNodes[3]=_le2->_nodes[0];
-    }
-    const SMDS_MeshNode* n( size_t i ) const
-    {
-      return myNodes[ i ];
+      _nn[0]=_le1->_nodes[0];
+      _nn[1]=_le1->_nodes.back();
+      _nn[2]=_le2->_nodes.back();
+      _nn[3]=_le2->_nodes[0];
     }
     gp_XYZ GetDir() const // return average direction of _LayerEdge's, normal to EDGE
     {
-      SMESH_TNodeXYZ p0s( myNodes[0] );
-      SMESH_TNodeXYZ p0t( myNodes[1] );
-      SMESH_TNodeXYZ p1t( myNodes[2] );
-      SMESH_TNodeXYZ p1s( myNodes[3] );
+      SMESH_TNodeXYZ p0s( _nn[0] );
+      SMESH_TNodeXYZ p0t( _nn[1] );
+      SMESH_TNodeXYZ p1t( _nn[2] );
+      SMESH_TNodeXYZ p1s( _nn[3] );
       gp_XYZ  v0 = p0t - p0s;
       gp_XYZ  v1 = p1t - p1s;
       gp_XYZ v01 = p1s - p0s;
@@ -1150,10 +1144,10 @@ namespace VISCOUS_3D
     }
     gp_XYZ GetDir(_LayerEdge* le1, _LayerEdge* le2) // return average direction of _LayerEdge's
     {
-      myNodes[0]=le1->_nodes[0];
-      myNodes[1]=le1->_nodes.back();
-      myNodes[2]=le2->_nodes.back();
-      myNodes[3]=le2->_nodes[0];
+      _nn[0]=le1->_nodes[0];
+      _nn[1]=le1->_nodes.back();
+      _nn[2]=le2->_nodes.back();
+      _nn[3]=le2->_nodes[0];
       return GetDir();
     }
   };
@@ -2647,7 +2641,7 @@ bool _ViscousBuilder::makeLayer(_SolidData& data)
 
       // create a temporary face
       const SMDS_MeshElement* newFace =
-        new _TmpMeshFace( newNodes, --_tmpFaceID, face->GetShapeID(), face );
+        new _TmpMeshFace( newNodes, --_tmpFaceID, face->getshapeId(), face->getIdInShape() );
       proxySub->AddElement( newFace );
 
       // compute inflation step size by min size of element on a convex surface
@@ -3319,18 +3313,19 @@ void _ViscousBuilder::setShapeData( _EdgesOnShape& eos,
     {
       SMESHDS_SubMesh* smDS = sm->GetSubMeshDS();
       if ( !smDS ) return;
-      eos._faceNormals.reserve( smDS->NbElements() );
+      eos._faceNormals.resize( smDS->NbElements() );
 
-      double oriFactor = helper.IsReversedSubMesh( TopoDS::Face( eos._shape )) ? 1.: -1.;
       SMDS_ElemIteratorPtr eIt = smDS->GetElements();
-      for ( ; eIt->more(); )
+      for ( int iF = 0; eIt->more(); ++iF )
       {
         const SMDS_MeshElement* face = eIt->next();
-        gp_XYZ&                 norm = eos._faceNormals[face];
-        if ( !SMESH_MeshAlgos::FaceNormal( face, norm, /*normalized=*/true ))
-          norm.SetCoord( 0,0,0 );
-        norm *= oriFactor;
+        if ( !SMESH_MeshAlgos::FaceNormal( face, eos._faceNormals[iF], /*normalized=*/true ))
+          eos._faceNormals[iF].SetCoord( 0,0,0 );
       }
+
+      if ( !helper.IsReversedSubMesh( TopoDS::Face( eos._shape )))
+        for ( size_t iF = 0; iF < eos._faceNormals.size(); ++iF )
+          eos._faceNormals[iF].Reverse();
     }
     else // find EOS of adjacent FACEs
     {
@@ -3356,7 +3351,7 @@ void _ViscousBuilder::setShapeData( _EdgesOnShape& eos,
 bool _EdgesOnShape::GetNormal( const SMDS_MeshElement* face, gp_Vec& norm )
 {
   bool ok = false;
-  _EdgesOnShape* eos = 0;
+  const _EdgesOnShape* eos = 0;
 
   if ( face->getshapeId() == _shapeID )
   {
@@ -3370,9 +3365,9 @@ bool _EdgesOnShape::GetNormal( const SMDS_MeshElement* face, gp_Vec& norm )
   }
 
   if (( eos ) &&
-      ( ok = ( eos->_faceNormals.count( face ) )))
+      ( ok = ( face->getIdInShape() < (int) eos->_faceNormals.size() )))
   {
-    norm = eos->_faceNormals[ face ];
+    norm = eos->_faceNormals[ face->getIdInShape() ];
   }
   else if ( !eos )
   {
@@ -3610,7 +3605,7 @@ bool _ViscousBuilder::setEdgeData(_LayerEdge&         edge,
   {
     const SMDS_MeshNode* tgtNode = edge._nodes.back();
     if ( SMESHDS_SubMesh* sm = getMeshDS()->MeshElements( data._solid ))
-      sm->RemoveNode( tgtNode );
+      sm->RemoveNode( tgtNode , /*isNodeDeleted=*/false );
 
     // set initial position which is parameters on _sWOL in this case
     if ( eos.SWOLType() == TopAbs_EDGE )
@@ -5112,13 +5107,14 @@ bool _ViscousBuilder::smoothAndCheck(_SolidData& data,
           eos._edges[i]->Set( _LayerEdge::INTERSECTED ); // not to intersect
           eos._edges[i]->Block( data );                  // not to inflate
 
-          //if ( _EdgesOnShape* eof = data.GetShapeEdges( intFace->getshapeId() ))
+          if ( _EdgesOnShape* eof = data.GetShapeEdges( intFace->getshapeId() ))
           {
             // block _LayerEdge's, on top of which intFace is
             if ( const _TmpMeshFace* f = dynamic_cast< const _TmpMeshFace*>( intFace ))
             {
-              const SMDS_MeshElement* srcFace = f->_srcFace;
-              SMDS_ElemIteratorPtr        nIt = srcFace->nodesIterator();
+              const SMDS_MeshElement* srcFace =
+                eof->_subMesh->GetSubMeshDS()->GetElement( f->getIdInShape() );
+              SMDS_ElemIteratorPtr nIt = srcFace->nodesIterator();
               while ( nIt->more() )
               {
                 const SMDS_MeshNode* srcNode = static_cast<const SMDS_MeshNode*>( nIt->next() );
@@ -5785,7 +5781,7 @@ bool _Smoother1D::smoothAnalyticEdge( _SolidData&                    data,
           tgtNode->setXYZ( newPos.X(), newPos.Y(), newPos.Z() );
           dumpMove( tgtNode );
 
-          SMDS_FacePositionPtr pos = tgtNode->GetPosition();
+          SMDS_FacePosition* pos = static_cast<SMDS_FacePosition*>( tgtNode->GetPosition() );
           pos->SetUParameter( newUV.X() );
           pos->SetVParameter( newUV.Y() );
 
@@ -5897,7 +5893,7 @@ bool _Smoother1D::smoothAnalyticEdge( _SolidData&                    data,
         tgtNode->setXYZ( newPos.X(), newPos.Y(), newPos.Z() );
         dumpMove( tgtNode );
 
-        SMDS_FacePositionPtr pos = tgtNode->GetPosition();
+        SMDS_FacePosition* pos = static_cast<SMDS_FacePosition*>( tgtNode->GetPosition() );
         pos->SetUParameter( newUV.X() );
         pos->SetVParameter( newUV.Y() );
 
@@ -6505,10 +6501,10 @@ void _SolidData::PrepareEdgesToSmoothOnFace( _EdgesOnShape* eos, bool substitute
     {
       edge->Set( _LayerEdge::SMOOTHED_C1 );
       isCurved = true;
-      SMDS_FacePositionPtr fPos = edge->_nodes[0]->GetPosition();
+      SMDS_FacePosition* fPos = dynamic_cast<SMDS_FacePosition*>( edge->_nodes[0]->GetPosition() );
       if ( !fPos )
         for ( size_t iS = 0; iS < edge->_simplices.size()  &&  !fPos; ++iS )
-          fPos = edge->_simplices[iS]._nPrev->GetPosition();
+          fPos = dynamic_cast<SMDS_FacePosition*>( edge->_simplices[iS]._nPrev->GetPosition() );
       if ( fPos )
         edge->_curvature->_uv.SetCoord( fPos->GetUParameter(), fPos->GetVParameter() );
     }
@@ -6805,9 +6801,9 @@ void _ViscousBuilder::findCollisionEdges( _SolidData& data, SMESH_MesherHelper&
               ( f->_le2->IsOnEdge() && f->_le2->_2neibors->include( edge )))  continue;
         }
         dist1 = dist2 = Precision::Infinite();
-        if ( !edge->SegTriaInter( lastSegment, f->n(0), f->n(1), f->n(2), dist1, eps ))
+        if ( !edge->SegTriaInter( lastSegment, f->_nn[0], f->_nn[1], f->_nn[2], dist1, eps ))
           dist1 = Precision::Infinite();
-        if ( !edge->SegTriaInter( lastSegment, f->n(3), f->n(2), f->n(0), dist2, eps ))
+        if ( !edge->SegTriaInter( lastSegment, f->_nn[3], f->_nn[2], f->_nn[0], dist2, eps ))
           dist2 = Precision::Infinite();
         if (( dist1 > segLen ) && ( dist2 > segLen ))
           continue;
@@ -6815,7 +6811,7 @@ void _ViscousBuilder::findCollisionEdges( _SolidData& data, SMESH_MesherHelper&
         if ( edge->IsOnEdge() )
         {
           // skip perpendicular EDGEs
-          gp_Vec fSegDir  = SMESH_TNodeXYZ( f->n(0) ) - SMESH_TNodeXYZ( f->n(3) );
+          gp_Vec fSegDir  = SMESH_TNodeXYZ( f->_nn[0] ) - SMESH_TNodeXYZ( f->_nn[3] );
           bool isParallel = ( isLessAngle( eSegDir0, fSegDir, angle45 ) ||
                               isLessAngle( eSegDir1, fSegDir, angle45 ) ||
                               isLessAngle( eSegDir0, fSegDir.Reversed(), angle45 ) ||
@@ -8251,7 +8247,7 @@ void _LayerEdge::MoveNearConcaVer( const _EdgesOnShape*    eov,
     prevPosV = surface.Value( prevPosV.X(), prevPosV.Y() ).XYZ();
   }
 
-  SMDS_FacePositionPtr fPos;
+  SMDS_FacePosition* fPos;
   //double r = 1. - Min( 0.9, step / 10. );
   for ( set< _LayerEdge* >::iterator e = edges.begin(); e != edges.end(); ++e )
   {
@@ -8265,7 +8261,7 @@ void _LayerEdge::MoveNearConcaVer( const _EdgesOnShape*    eov,
 
     // set _curvature to make edgeF updated by putOnOffsetSurface()
     if ( !edgeF->_curvature )
-      if (( fPos = edgeF->_nodes[0]->GetPosition() ))
+      if (( fPos = dynamic_cast<SMDS_FacePosition*>( edgeF->_nodes[0]->GetPosition() )))
       {
         edgeF->_curvature = new _Curvature;
         edgeF->_curvature->_r = 0;
@@ -9486,7 +9482,7 @@ void _LayerEdge::SetNewLength( double len, _EdgesOnShape& eos, SMESH_MesherHelpe
       _pos.back().SetCoord( u, 0, 0 );
       if ( _nodes.size() > 1 && uvOK )
       {
-        SMDS_EdgePositionPtr pos = n->GetPosition();
+        SMDS_EdgePosition* pos = static_cast<SMDS_EdgePosition*>( n->GetPosition() );
         pos->SetUParameter( u );
       }
     }
@@ -9498,7 +9494,7 @@ void _LayerEdge::SetNewLength( double len, _EdgesOnShape& eos, SMESH_MesherHelpe
       _pos.back().SetCoord( uv.X(), uv.Y(), 0 );
       if ( _nodes.size() > 1 && uvOK )
       {
-        SMDS_FacePositionPtr pos = n->GetPosition();
+        SMDS_FacePosition* pos = static_cast<SMDS_FacePosition*>( n->GetPosition() );
         pos->SetUParameter( uv.X() );
         pos->SetVParameter( uv.Y() );
       }
@@ -9614,7 +9610,7 @@ void _LayerEdge::InvalidateStep( size_t curStep, const _EdgesOnShape& eos, bool
       TopLoc_Location loc;
       if ( eos.SWOLType() == TopAbs_EDGE )
       {
-        SMDS_EdgePositionPtr pos = n->GetPosition();
+        SMDS_EdgePosition* pos = static_cast<SMDS_EdgePosition*>( n->GetPosition() );
         pos->SetUParameter( nXYZ.X() );
         double f,l;
         Handle(Geom_Curve) curve = BRep_Tool::Curve( TopoDS::Edge( eos._sWOL ), loc, f,l);
@@ -9622,7 +9618,7 @@ void _LayerEdge::InvalidateStep( size_t curStep, const _EdgesOnShape& eos, bool
       }
       else
       {
-        SMDS_FacePositionPtr pos = n->GetPosition();
+        SMDS_FacePosition* pos = static_cast<SMDS_FacePosition*>( n->GetPosition() );
         pos->SetUParameter( nXYZ.X() );
         pos->SetVParameter( nXYZ.Y() );
         Handle(Geom_Surface) surface = BRep_Tool::Surface( TopoDS::Face(eos._sWOL), loc );
@@ -9987,12 +9983,12 @@ bool _ViscousBuilder::refine(_SolidData& data)
         SMDS_PositionPtr  lastPos = tgtNode->GetPosition();
         if ( isOnEdge )
         {
-          SMDS_EdgePositionPtr epos = lastPos;
+          SMDS_EdgePosition* epos = static_cast<SMDS_EdgePosition*>( lastPos );
           epos->SetUParameter( otherTgtPos.X() );
         }
         else
         {
-          SMDS_FacePositionPtr fpos = lastPos;
+          SMDS_FacePosition* fpos = static_cast<SMDS_FacePosition*>( lastPos );
           fpos->SetUParameter( otherTgtPos.X() );
           fpos->SetVParameter( otherTgtPos.Y() );
         }
@@ -10081,7 +10077,7 @@ bool _ViscousBuilder::refine(_SolidData& data)
                 u = helper.GetNodeU( geomEdge, node );
               pos = curve->Value( u ).Transformed(loc);
 
-              SMDS_EdgePositionPtr epos = node->GetPosition();
+              SMDS_EdgePosition* epos = static_cast<SMDS_EdgePosition*>( node->GetPosition() );
               epos->SetUParameter( u );
             }
             else
@@ -10091,7 +10087,7 @@ bool _ViscousBuilder::refine(_SolidData& data)
                 uv = helper.GetNodeUV( geomFace, node );
               pos = surface->Value( uv );
 
-              SMDS_FacePositionPtr fpos = node->GetPosition();
+              SMDS_FacePosition* fpos = static_cast<SMDS_FacePosition*>( node->GetPosition() );
               fpos->SetUParameter( uv.X() );
               fpos->SetVParameter( uv.Y() );
             }
@@ -10266,11 +10262,10 @@ bool _ViscousBuilder::refine(_SolidData& data)
     SMESH_ComputeErrorPtr& err = _mesh->GetSubMesh( data._solid )->GetComputeError();
     if ( !err || err->IsOK() )
     {
-      SMESH_BadInputElements* badElems =
-        new SMESH_BadInputElements( getMeshDS(), COMPERR_WARNING, "Bad quality volumes created" );
-      badElems->myBadElements.insert( badElems->myBadElements.end(),
-                                      degenVols.begin(),degenVols.end() );
-      err.reset( badElems );
+      err.reset( new SMESH_ComputeError( COMPERR_WARNING,
+                                         "Bad quality volumes created" ));
+      err->myBadElements.insert( err->myBadElements.end(),
+                                 degenVols.begin(),degenVols.end() );
     }
   }
 
@@ -10683,14 +10678,14 @@ bool _ViscousBuilder::shrink(_SolidData& theData)
                edge->Is( _LayerEdge::SHRUNK )) continue;
           if ( subEOS[iS]->SWOLType() == TopAbs_FACE )
           {
-            SMDS_FacePositionPtr pos = tgtNode->GetPosition();
+            SMDS_FacePosition* pos = static_cast<SMDS_FacePosition*>( tgtNode->GetPosition() );
             pos->SetUParameter( edge->_pos[0].X() );
             pos->SetVParameter( edge->_pos[0].Y() );
             p = surface->Value( edge->_pos[0].X(), edge->_pos[0].Y() );
           }
           else
           {
-            SMDS_EdgePositionPtr pos = tgtNode->GetPosition();
+            SMDS_EdgePosition* pos = static_cast<SMDS_EdgePosition*>( tgtNode->GetPosition() );
             pos->SetUParameter( edge->_pos[0].Coord( U_TGT ));
             p = BRepAdaptor_Curve( TopoDS::Edge( subEOS[iS]->_sWOL )).Value( pos->GetUParameter() );
           }
@@ -10885,7 +10880,7 @@ bool _ViscousBuilder::prepareEdgeToShrink( _LayerEdge&            edge,
     edge._pos[0].SetCoord( tgtUV.X(), tgtUV.Y(), 0 );
 
     // set UV of source node to target node
-    SMDS_FacePositionPtr pos = tgtNode->GetPosition();
+    SMDS_FacePosition* pos = static_cast<SMDS_FacePosition*>( tgtNode->GetPosition() );
     pos->SetUParameter( srcUV.X() );
     pos->SetVParameter( srcUV.Y() );
   }
@@ -10935,7 +10930,7 @@ bool _ViscousBuilder::prepareEdgeToShrink( _LayerEdge&            edge,
     edge._simplices[0]._nPrev = n2;
 
     // set U of source node to the target node
-    SMDS_EdgePositionPtr pos = tgtNode->GetPosition();
+    SMDS_EdgePosition* pos = static_cast<SMDS_EdgePosition*>( tgtNode->GetPosition() );
     pos->SetUParameter( uSrc );
   }
   return true;
@@ -10968,7 +10963,7 @@ void _ViscousBuilder::restoreNoShrink( _LayerEdge& edge ) const
       TopLoc_Location loc;
       Handle(Geom_Curve) curve = BRep_Tool::Curve( TopoDS::Edge( S ), loc, f, l );
       if ( curve.IsNull() ) return;
-      SMDS_EdgePositionPtr ePos = srcNode->GetPosition();
+      SMDS_EdgePosition* ePos = static_cast<SMDS_EdgePosition*>( srcNode->GetPosition() );
       p = curve->Value( ePos->GetUParameter() );
       break;
     }
@@ -11194,7 +11189,7 @@ bool _LayerEdge::SetNewLength2d( Handle(Geom_Surface)& surface,
     {
       return true;
     }
-    SMDS_FacePositionPtr pos = tgtNode->GetPosition();
+    SMDS_FacePosition* pos = static_cast<SMDS_FacePosition*>( tgtNode->GetPosition() );
     pos->SetUParameter( newUV.X() );
     pos->SetVParameter( newUV.Y() );
 
@@ -11208,7 +11203,7 @@ bool _LayerEdge::SetNewLength2d( Handle(Geom_Surface)& surface,
   {
     const TopoDS_Edge&      E = TopoDS::Edge( eos._sWOL );
     const SMDS_MeshNode*   n2 = _simplices[0]._nPrev;
-    SMDS_EdgePositionPtr tgtPos = tgtNode->GetPosition();
+    SMDS_EdgePosition* tgtPos = static_cast<SMDS_EdgePosition*>( tgtNode->GetPosition() );
 
     const double u2     = helper.GetNodeU( E, n2, tgtNode );
     const double uSrc   = _pos[0].Coord( U_SRC );
@@ -11328,7 +11323,7 @@ bool _SmoothNode::Smooth(int&                  nbBad,
     return false;
   }
 
-  SMDS_FacePositionPtr pos = _node->GetPosition();
+  SMDS_FacePosition* pos = static_cast<SMDS_FacePosition*>( _node->GetPosition() );
   pos->SetUParameter( newPos.X() );
   pos->SetVParameter( newPos.Y() );
 
@@ -11555,7 +11550,7 @@ void _Shrinker1D::Compute(bool set3D, SMESH_MesherHelper& helper)
       if ( !discret.IsDone() )
         return throw SALOME_Exception(LOCALIZED("GCPnts_AbscissaPoint failed"));
       double u = discret.Parameter();
-      SMDS_EdgePositionPtr pos = _nodes[i]->GetPosition();
+      SMDS_EdgePosition* pos = static_cast<SMDS_EdgePosition*>( _nodes[i]->GetPosition() );
       pos->SetUParameter( u );
       gp_Pnt p = C->Value( u );
       const_cast< SMDS_MeshNode*>( _nodes[i] )->setXYZ( p.X(), p.Y(), p.Z() );
@@ -11573,7 +11568,7 @@ void _Shrinker1D::Compute(bool set3D, SMESH_MesherHelper& helper)
     {
       if ( !_nodes[i] ) continue;
       double u = f * ( 1-_normPar[i] ) + l * _normPar[i];
-      SMDS_EdgePositionPtr pos = _nodes[i]->GetPosition();
+      SMDS_EdgePosition* pos = static_cast<SMDS_EdgePosition*>( _nodes[i]->GetPosition() );
       pos->SetUParameter( u );
     }
   }
@@ -11591,7 +11586,7 @@ void _Shrinker1D::RestoreParams()
     for ( size_t i = 0; i < _nodes.size(); ++i )
     {
       if ( !_nodes[i] ) continue;
-      SMDS_EdgePositionPtr pos = _nodes[i]->GetPosition();
+      SMDS_EdgePosition* pos = static_cast<SMDS_EdgePosition*>( _nodes[i]->GetPosition() );
       pos->SetUParameter( _initU[i] );
     }
   _done = false;
index 98a30fa229535cb0a2f6ff35011cf9df48fa9323..6cb97c538332e2cbdd489f8bcbff599781373c14 100644 (file)
@@ -110,7 +110,7 @@ namespace VISCOUS_2D
     // Proxy sub-mesh of an EDGE. It contains nodes in _uvPtStructVec.
     struct _EdgeSubMesh : public SMESH_ProxyMesh::SubMesh
     {
-      _EdgeSubMesh(const SMDS_Mesh* mesh, int index=0): SubMesh(mesh,index) {}
+      _EdgeSubMesh(int index=0): SubMesh(index) {}
       //virtual int NbElements() const { return _elements.size()+1; }
       virtual int NbNodes() const { return Max( 0, _uvPtStructVec.size()-2 ); }
       void SetUVPtStructVec(UVPtStructVec& vec) { _uvPtStructVec.swap( vec ); }
@@ -118,7 +118,7 @@ namespace VISCOUS_2D
     };
     _ProxyMeshOfFace(const SMESH_Mesh& mesh): SMESH_ProxyMesh(mesh) {}
     _EdgeSubMesh* GetEdgeSubMesh(int ID) { return (_EdgeSubMesh*) getProxySubMesh(ID); }
-    virtual SubMesh* newSubmesh(int index=0) const { return new _EdgeSubMesh( GetMeshDS(), index); }
+    virtual SubMesh* newSubmesh(int index=0) const { return new _EdgeSubMesh(index); }
   };
   //--------------------------------------------------------------------------------
   /*!
@@ -1998,7 +1998,7 @@ bool _ViscousBuilder2D::shrink()
         throw SALOME_Exception(SMESH_Comment("ViscousBuilder2D: not SMDS_TOP_EDGE node position: ")
                                << oldNode->GetPosition()->GetTypeOfPosition()
                                << " of node " << oldNode->GetID());
-      SMDS_EdgePositionPtr pos = oldNode->GetPosition();
+      SMDS_EdgePosition* pos = static_cast<SMDS_EdgePosition*>( oldNode->GetPosition() );
       pos->SetUParameter( nodeDataVec[iP].param );
 
       gp_Pnt newP = curve.Value( nodeDataVec[iP].param );