Salome HOME
Fix unstable failure of SALOME_TESTS/Grids/smesh/bugs_05/F0
authoreap <eap@opencascade.com>
Tue, 23 May 2017 17:19:15 +0000 (20:19 +0300)
committereap <eap@opencascade.com>
Tue, 23 May 2017 17:19:15 +0000 (20:19 +0300)
src/SMESH/SMESH_Algo.cxx
src/SMESH/SMESH_MeshEditor.cxx
src/SMESHUtils/SMESH_Delaunay.cxx
src/StdMeshers/StdMeshers_FaceSide.cxx
src/StdMeshers/StdMeshers_Prism_3D.cxx
src/StdMeshers/StdMeshers_Prism_3D.hxx

index bb21f5c..4e4002e 100644 (file)
@@ -553,28 +553,35 @@ bool SMESH_Algo::IsStraight( const TopoDS_Edge & E,
   case GeomAbs_Hyperbola:
   case GeomAbs_Parabola:
     return false;
-  // case GeomAbs_BezierCurve:
-  // case GeomAbs_BSplineCurve:
-  // case GeomAbs_OtherCurve:
+    // case GeomAbs_BezierCurve:
+    // case GeomAbs_BSplineCurve:
+    // case GeomAbs_OtherCurve:
   default:;
   }
-  const double   f = curve.FirstParameter();
-  const double   l = curve.LastParameter();
-  const gp_Pnt  pf = curve.Value( f );
-  const gp_Pnt  pl = curve.Value( l );
-  const gp_Vec v1( pf, pl );
-  const double v1Len = v1.Magnitude();
-  if ( v1Len < std::numeric_limits< double >::min() )
+
+  // evaluate how far from a straight line connecting the curve ends
+  // stand internal points of the curve
+  double  f = curve.FirstParameter();
+  double  l = curve.LastParameter();
+  gp_Pnt pf = curve.Value( f );
+  gp_Pnt pl = curve.Value( l );
+  gp_Vec lineVec( pf, pl );
+  double lineLen2 = lineVec.SquareMagnitude();
+  if ( lineLen2 < std::numeric_limits< double >::min() )
     return false; // E seems closed
-  const double tol = Min( 10 * curve.Tolerance(), v1Len * 1e-2 );
+
+  double edgeTol = 10 * curve.Tolerance();
+  double lenTol2 = lineLen2 * 1e-4; 
+  double tol2 = Min( edgeTol * edgeTol, lenTol2 );
+
   const double nbSamples = 7;
   for ( int i = 0; i < nbSamples; ++i )
   {
-    const double  r = ( i + 1 ) / nbSamples;
-    const gp_Pnt pi = curve.Value( f * r + l * ( 1 - r ));
-    const gp_Vec vi( pf, pi );
-    const double  h = 0.5 * v1.Crossed( vi ).Magnitude() / v1Len;
-    if ( h > tol )
+    double  r = ( i + 1 ) / nbSamples;
+    gp_Pnt pi = curve.Value( f * r + l * ( 1 - r ));
+    gp_Vec vi( pf, pi );
+    double h2 = lineVec.Crossed( vi ).SquareMagnitude() / lineLen2;
+    if ( h2 > tol2 )
       return false;
   }
   return true;
index 1f343b1..c477e72 100644 (file)
@@ -7482,8 +7482,8 @@ void SMESH_MeshEditor::MergeNodes (TListOfListOfNodes & theGroupsOfNodes,
   }
 
   // Remove bad elements, then equal nodes (order important)
-  Remove( rmElemIds, false );
-  Remove( rmNodeIds, true );
+  Remove( rmElemIds, /*isNodes=*/false );
+  Remove( rmNodeIds, /*isNodes=*/true );
 
   return;
 }
@@ -7553,14 +7553,14 @@ bool SMESH_MeshEditor::applyMerge( const SMDS_MeshElement* elem,
     toRemove = true;
     nbResElems = 0;
 
-    if ( elem->IsQuadratic() && newElemDefs[0].myType == SMDSAbs_Face && nbNodes > 6 )
+    if ( newElemDefs[0].myIsQuad && newElemDefs[0].myType == SMDSAbs_Face && nbNodes > 6 )
     {
       // if corner nodes stick, remove medium nodes between them from uniqueNodes
       int nbCorners = nbNodes / 2;
       for ( int iCur = 0; iCur < nbCorners; ++iCur )
       {
-        int iPrev = ( iCur + 1 ) % nbCorners;
-        if ( curNodes[ iCur ] == curNodes[ iPrev ] ) // corners stick
+        int iNext = ( iCur + 1 ) % nbCorners;
+        if ( curNodes[ iCur ] == curNodes[ iNext ] ) // corners stick
         {
           int iMedium = iCur + nbCorners;
           vector< const SMDS_MeshNode* >::iterator i =
@@ -7711,11 +7711,9 @@ bool SMESH_MeshEditor::applyMerge( const SMDS_MeshElement* elem,
       //    |       |
       //    +---+---+
       //   0    7    3
-      if (( nbUniqueNodes == 7 && nbRepl == 2 && iRepl[1] != 8 ) &&
-          (( iRepl[0] == 1 && iRepl[1] == 4 && curNodes[1] == curNodes[0] ) ||
-           ( iRepl[0] == 2 && iRepl[1] == 5 && curNodes[2] == curNodes[1] ) ||
-           ( iRepl[0] == 3 && iRepl[1] == 6 && curNodes[3] == curNodes[2] ) ||
-           ( iRepl[0] == 3 && iRepl[1] == 7 && curNodes[3] == curNodes[0] )))
+      if ( nbUniqueNodes == 7 &&
+           iRepl[0] < 4       &&
+           ( nbRepl == 1 || iRepl[1] != 8 ))
       {
         toRemove = false;
       }
index 85f03a6..e53bfd8 100644 (file)
@@ -193,16 +193,21 @@ const BRepMesh_Triangle* SMESH_Delaunay::FindTriangle( const gp_XY&
     nodeUVs[1] = _triaDS->GetNode( nodeIDs[1] ).Coord();
     nodeUVs[2] = _triaDS->GetNode( nodeIDs[2] ).Coord();
 
-    SMESH_MeshAlgos::GetBarycentricCoords( uv,
-                                           nodeUVs[0], nodeUVs[1], nodeUVs[2],
-                                           bc[0], bc[1] );
-    if ( bc[0] >= 0 && bc[1] >= 0 && bc[0] + bc[1] <= 1 )
+    if ( _triaDS->GetNode( nodeIDs[0] ).Movability() == BRepMesh_Frontier &&
+         _triaDS->GetNode( nodeIDs[1] ).Movability() == BRepMesh_Frontier &&
+         _triaDS->GetNode( nodeIDs[2] ).Movability() == BRepMesh_Frontier )
     {
-      bc[2] = 1 - bc[0] - bc[1];
-      triaNodes[0] = nodeIDs[0] - 1;
-      triaNodes[1] = nodeIDs[1] - 1;
-      triaNodes[2] = nodeIDs[2] - 1;
-      return tria;
+      SMESH_MeshAlgos::GetBarycentricCoords( uv,
+                                             nodeUVs[0], nodeUVs[1], nodeUVs[2],
+                                             bc[0], bc[1] );
+      if ( bc[0] >= 0 && bc[1] >= 0 && bc[0] + bc[1] <= 1 )
+      {
+        bc[2] = 1 - bc[0] - bc[1];
+        triaNodes[0] = nodeIDs[0] - 1;
+        triaNodes[1] = nodeIDs[1] - 1;
+        triaNodes[2] = nodeIDs[2] - 1;
+        return tria;
+      }
     }
 
     // look for a neighbor triangle, which is adjacent to a link intersected
index 71677dc..b0d36a5 100644 (file)
@@ -1251,7 +1251,7 @@ gp_Pnt StdMeshers_FaceSide::Value3d(double U) const
   // check parametrization of curve
   if( !myIsUniform[i] )
   {
-    double aLen3dU = r * myEdgeLength[i] * ( myFirst[i]>myLast[i] ? -1. : 1.);
+    double aLen3dU = r * myEdgeLength[i] * ( myFirst[i] > myLast[i] ? -1. : 1. );
     GCPnts_AbscissaPoint AbPnt
       ( const_cast<GeomAdaptor_Curve&>( myC3dAdaptor[i]), aLen3dU, myFirst[i] );
     if( AbPnt.IsDone() ) {
index 939679f..ae8ccc4 100644 (file)
@@ -4962,7 +4962,8 @@ bool StdMeshers_Sweeper::ComputeNodesByTrsf( const double tol,
 
   // for each internal column find boundary nodes whose error to use for correction
   prepareTopBotDelaunay();
-  findDelaunayTriangles();
+  if ( !findDelaunayTriangles())
+    return false;
 
   // compute coordinates of internal nodes by projecting (transfroming) src and tgt
   // nodes towards the central layer
@@ -5390,11 +5391,11 @@ void StdMeshers_Sweeper::prepareTopBotDelaunay()
 //================================================================================
 /*!
  * \brief For each internal node column, find Delaunay triangles including it
- *        and Barycentric Coordinates withing the triangles. Fill in myTopBotTriangles
+ *        and Barycentric Coordinates within the triangles. Fill in myTopBotTriangles
  */
 //================================================================================
 
-void StdMeshers_Sweeper::findDelaunayTriangles()
+bool StdMeshers_Sweeper::findDelaunayTriangles()
 {
   const SMDS_MeshNode     *botNode, *topNode;
   const BRepMesh_Triangle *topTria;
@@ -5424,14 +5425,14 @@ void StdMeshers_Sweeper::findDelaunayTriangles()
     myTopBotTriangles[ colID ] = tbTrias;
   }
 
-#ifdef _DEBUG_
   if ( myBotDelaunay->NbVisitedNodes() < nbInternalNodes )
-    throw SALOME_Exception(LOCALIZED("Not all internal nodes found by Delaunay"));
-#endif
+    return false;
 
   myBotDelaunay.reset();
   myTopDelaunay.reset();
   myNodeID2ColID.Clear();
+
+  return true;
 }
 
 //================================================================================
index da4b055..62f0b9a 100644 (file)
@@ -453,7 +453,7 @@ private:
                            TNodeColumn& nodes );
 
   void prepareTopBotDelaunay();
-  void findDelaunayTriangles();
+  bool findDelaunayTriangles();
 
   std::vector< TZColumn >                 myZColumns; // Z distribution of boundary nodes