Version: 8.3.0
StdMeshers_Prism_3D.hxx
Go to the documentation of this file.
1 // Copyright (C) 2007-2016 CEA/DEN, EDF R&D, OPEN CASCADE
2 //
3 // Copyright (C) 2003-2007 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
5 //
6 // This library is free software; you can redistribute it and/or
7 // modify it under the terms of the GNU Lesser General Public
8 // License as published by the Free Software Foundation; either
9 // version 2.1 of the License, or (at your option) any later version.
10 //
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 // Lesser General Public License for more details.
15 //
16 // You should have received a copy of the GNU Lesser General Public
17 // License along with this library; if not, write to the Free Software
18 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 //
20 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
21 //
22 
23 // SMESH SMESH : implementaion of SMESH idl descriptions
24 // File : StdMeshers_Prism_3D.hxx
25 // Module : SMESH
26 //
27 #ifndef _SMESH_Prism_3D_HXX_
28 #define _SMESH_Prism_3D_HXX_
29 
30 #include "SMESH_StdMeshers.hxx"
31 
32 #include "SMDS_MeshNode.hxx"
33 #include "SMDS_TypeOfPosition.hxx"
34 #include "SMESHDS_Mesh.hxx"
35 #include "SMESH_Algo.hxx"
36 #include "SMESH_Block.hxx"
37 #include "SMESH_Comment.hxx"
38 #include "SMESH_Mesh.hxx"
39 #include "SMESH_MesherHelper.hxx"
40 #include "SMESH_TypeDefs.hxx"
41 #include "SMESH_subMesh.hxx"
42 
43 #include <Adaptor2d_Curve2d.hxx>
44 #include <Adaptor3d_Curve.hxx>
45 #include <Adaptor3d_Surface.hxx>
46 #include <BRepAdaptor_Surface.hxx>
47 #include <TopTools_IndexedMapOfOrientedShape.hxx>
48 #include <TopoDS_Face.hxx>
49 #include <gp_Trsf.hxx>
50 #include <gp_XYZ.hxx>
51 
52 #include <vector>
53 
54 namespace Prism_3D
55 {
56  struct TNode;
57  struct TPrismTopo;
58 }
59 namespace StdMeshers_ProjectionUtils
60 {
61  class TrsfFinder3D;
62 }
63 class SMESHDS_SubMesh;
64 class TopoDS_Edge;
65 
66 typedef TopTools_IndexedMapOfOrientedShape TBlockShapes;
67 typedef std::vector<const SMDS_MeshNode* > TNodeColumn;
68 typedef std::map< double, TNodeColumn > TParam2ColumnMap;
69 typedef std::map< double, TNodeColumn >::const_iterator TParam2ColumnIt;
70 // map of bottom nodes to the column of nodes above them
71 // (the column includes the bottom nodes)
72 typedef std::map< Prism_3D::TNode, TNodeColumn > TNode2ColumnMap;
73 
74 
75 namespace Prism_3D
76 {
77  // ===============================================
81  struct TNode
82  {
84  mutable gp_XYZ myParams;
85 
86  gp_XYZ GetCoords() const { return gp_XYZ( myNode->X(), myNode->Y(), myNode->Z() ); }
87  gp_XYZ GetParams() const { return myParams; }
88  gp_XYZ& ChangeParams() const { return myParams; }
89  bool HasParams() const { return myParams.X() >= 0.0; }
92  bool IsNeighbor( const TNode& other ) const;
93 
94  TNode(const SMDS_MeshNode* node = 0): myNode(node), myParams(-1,-1,-1) {}
95  bool operator < (const TNode& other) const { return myNode->GetID() < other.myNode->GetID(); }
96  };
97  // ===============================================
101  typedef std::list< TFaceQuadStructPtr > TQuadList;
102 
103  struct TPrismTopo
104  {
105  TopoDS_Shape myShape3D;
106  TopoDS_Face myBottom;
107  TopoDS_Face myTop;
108  std::list< TopoDS_Edge > myBottomEdges;
109  std::vector< TQuadList> myWallQuads; // wall sides can be vertically composite
110  std::vector< int > myRightQuadIndex; // index of right neighbour wall quad
111  std::list< int > myNbEdgesInWires;
112 
114 
115  void Clear();
116  void SetUpsideDown();
117  };
118 }
119 
120 // ===============================================================
128 {
129  public:
134 
136 
143  bool Init(SMESH_MesherHelper* helper, const Prism_3D::TPrismTopo& prism);
144 
148  SMESH_ComputeErrorPtr GetError() const { return myError; }
149 
153  void Clear();
154 
159  int VerticalSize() const { return myParam2ColumnMaps[0].begin()->second.size(); }
160 
161  bool HasNotQuadElemOnTop() const { return myNotQuadOnTop; }
162 
168  const TNodeColumn* GetNodeColumn(const SMDS_MeshNode* node) const;
169 
176  const TParam2ColumnMap* GetParam2ColumnMap(const int baseEdgeID,
177  bool & isReverse) const
178  {
179  std::map< int, std::pair< TParam2ColumnMap*, bool > >::const_iterator i_mo =
180  myShapeIndex2ColumnMap.find( baseEdgeID );
181  if ( i_mo == myShapeIndex2ColumnMap.end() ) return 0;
182 
183  const std::pair< TParam2ColumnMap*, bool >& col_frw = i_mo->second;
184  isReverse = !col_frw.second;
185  return col_frw.first;
186  }
187 
193  bool HasNodeColumn(const SMDS_MeshNode* node) const
194  {
195  return myShapeIndex2ColumnMap.count( node->getshapeId() );
196  }
197 
203  bool GetLayersTransformation(std::vector<gp_Trsf> & trsf,
204  const Prism_3D::TPrismTopo& prism) const;
205 
210  SMESH_Mesh* Mesh() const { return myHelper->GetMesh(); }
211 
216  SMESHDS_Mesh* MeshDS() const { return Mesh()->GetMeshDS(); }
217 
223  SMESH_subMesh* SubMesh(const int shapeID) const
224  { return Mesh()->GetSubMesh( Shape( shapeID )); }
225 
231  SMESHDS_SubMesh* SubMeshDS(const int shapeID) const
232  { return SubMesh(shapeID)->GetSubMeshDS(); }
233 
239  const TopoDS_Shape& Shape(const int shapeID) const
240  { return myShapeIDMap( shapeID ); }
241 
247  int ShapeID(const TopoDS_Shape& shape) const
248  { return myShapeIDMap.FindIndex( shape ); }
249 
258  static bool IsForwardEdge(SMESHDS_Mesh* meshDS,
259  const TParam2ColumnMap& columnsMap,
260  const TopoDS_Edge & bottomEdge,
261  const int sideFaceID);
262 
263 private:
264 
265  // --------------------------------------------------------------------
273  // --------------------------------------------------------------------
275  {
276  typedef boost::shared_ptr<BRepAdaptor_Surface> PSurface;
277 
278  int myID;
279  // map used to find out real UV by it's normalized UV
282  TopoDS_Edge myBaseEdge;
283  std::map< int, PSurface > myShapeID2Surf;
284  // first and last normalized params and orientaion for each component or it-self
285  std::vector< std::pair< double, double> > myParams; // select my columns in myParamToColumnMap
287  std::vector< TSideFace* > myComponents;
289  public:
290  TSideFace( SMESH_Mesh& mesh,
291  const int faceID,
292  const Prism_3D::TQuadList& quadList,
293  const TopoDS_Edge& baseEdge,
294  TParam2ColumnMap* columnsMap,
295  const double first = 0.0,
296  const double last = 1.0);
297  TSideFace( SMESH_Mesh& mesh,
298  const std::vector< TSideFace* >& components,
299  const std::vector< std::pair< double, double> > & params);
300  TSideFace( const TSideFace& other );
301  ~TSideFace();
302  bool IsComplex() const
303  { return ( NbComponents() > 0 || myParams[0].first != 0. || myParams[0].second != 1. ); }
304  int FaceID() const { return myID; }
305  SMESH_Mesh* GetMesh() const { return myHelper.GetMesh(); }
306  TParam2ColumnMap* GetColumns() const { return myParamToColumnMap; }
307  gp_XY GetNodeUV(const TopoDS_Face& F, const SMDS_MeshNode* n, const SMDS_MeshNode* n2=0) const
308  { return ((SMESH_MesherHelper&) myHelper).SetSubShape(F), myHelper.GetNodeUV( F, n, n2 ); }
309  const TopoDS_Edge & BaseEdge() const { return myBaseEdge; }
310  int ColumnHeight() const {
311  if ( NbComponents() ) return GetComponent(0)->GetColumns()->begin()->second.size();
312  else return GetColumns()->begin()->second.size(); }
313  double GetColumns(const double U, TParam2ColumnIt & col1, TParam2ColumnIt& col2 ) const;
314  void GetNodesAtZ(const int Z, std::map<double, const SMDS_MeshNode* >& nodes ) const;
315  int NbComponents() const { return myComponents.size(); }
316  TSideFace* GetComponent(const int i) const { return myComponents.at( i ); }
317  void SetComponent(const int i, TSideFace* c)
318  { if ( myComponents[i] ) delete myComponents[i]; myComponents[i]=c; }
319  TSideFace* GetComponent(const double U, double& localU) const;
320  bool IsForward() const { return myIsForward; }
321  // boundary geometry for a face
322  Adaptor3d_Surface* Surface() const { return new TSideFace( *this ); }
323  bool GetPCurves(Adaptor2d_Curve2d* pcurv[4]) const;
324  Adaptor2d_Curve2d* HorizPCurve(const bool isTop, const TopoDS_Face& horFace) const;
325  Adaptor3d_Curve* HorizCurve(const bool isTop) const;
326  Adaptor3d_Curve* VertiCurve(const bool isMax) const;
327  TopoDS_Edge GetEdge( const int edge ) const;
328  int InsertSubShapes( TBlockShapes& shapeMap ) const;
329  // redefine Adaptor methods
330  gp_Pnt Value(const Standard_Real U,const Standard_Real V) const;
331  // debug
332  void dumpNodes(int nbNodes) const;
333  };
334 
335  // --------------------------------------------------------------------
339  // --------------------------------------------------------------------
341  {
343  public:
344  TVerticalEdgeAdaptor( const TParam2ColumnMap* columnsMap, const double parameter );
345  gp_Pnt Value(const Standard_Real U) const;
346  Standard_Real FirstParameter() const { return 0; }
347  Standard_Real LastParameter() const { return 1; }
348  // debug
349  void dumpNodes(int nbNodes) const;
350  };
351 
352  // --------------------------------------------------------------------
356  // --------------------------------------------------------------------
358  {
360  double myV;
361  public:
362  THorizontalEdgeAdaptor( const TSideFace* sideFace, const bool isTop)
363  :mySide(sideFace), myV( isTop ? 1.0 : 0.0 ) {}
364  gp_Pnt Value(const Standard_Real U) const;
365  Standard_Real FirstParameter() const { return 0; }
366  Standard_Real LastParameter() const { return 1; }
367  // debug
368  void dumpNodes(int nbNodes) const;
369  };
370 
371  // --------------------------------------------------------------------
375  // --------------------------------------------------------------------
377  {
378  std::map< double, gp_XY > myUVmap; // normalized parameter to UV on a horizontal face
379  public:
380  TPCurveOnHorFaceAdaptor( const TSideFace* sideFace,
381  const bool isTop,
382  const TopoDS_Face& horFace);
383  gp_Pnt2d Value(const Standard_Real U) const;
384  Standard_Real FirstParameter() const { return 0; }
385  Standard_Real LastParameter() const { return 1; }
386  };
387 
392 
393  // container of 4 side faces
395  // node columns for each base edge
396  std::vector< TParam2ColumnMap > myParam2ColumnMaps;
397  // to find a column for a node by edge SMESHDS Index
398  std::map< int, std::pair< TParam2ColumnMap*, bool > > myShapeIndex2ColumnMap;
399 
403  bool error(int error, const SMESH_Comment& comment = "") {
404  myError = SMESH_ComputeError::New(error,comment);
405  return myError->IsOK();
406  }
410  void faceGridToPythonDump(const SMESH_Block::TShapeID face,
411  const int nb=10);
412 
413 }; // class StdMeshers_PrismAsBlock
414 
415 // ===============================================
420 {
421  std::vector< TNodeColumn* > myBndColumns; // boundary nodes
422  std::vector< TNodeColumn* > myIntColumns; // internal nodes
423 
424  bool ComputeNodes( SMESH_MesherHelper& helper,
425  const double tol,
426  const bool allowHighBndError );
427 
428 private:
429 
430  gp_XYZ bndPoint( int iP, int z ) const
431  { return SMESH_TNodeXYZ( (*myBndColumns[ iP ])[ z ]); }
432 
433  gp_XYZ intPoint( int iP, int z ) const
434  { return SMESH_TNodeXYZ( (*myIntColumns[ iP ])[ z ]); }
435 
436  static bool projectIntPoints(const std::vector< gp_XYZ >& fromBndPoints,
437  const std::vector< gp_XYZ >& toBndPoints,
438  const std::vector< gp_XYZ >& fromIntPoints,
439  std::vector< gp_XYZ >& toIntPoints,
441  std::vector< gp_XYZ > * bndError);
442 
443  static void applyBoundaryError(const std::vector< gp_XYZ >& bndPoints,
444  const std::vector< gp_XYZ >& bndError1,
445  const std::vector< gp_XYZ >& bndError2,
446  const double r,
447  std::vector< gp_XYZ >& toIntPoints,
448  std::vector< double >& int2BndDist);
449 };
450 
451 // ===============================================
456 {
457 public:
458  StdMeshers_Prism_3D(int hypId, int studyId, SMESH_Gen* gen);
459  virtual ~StdMeshers_Prism_3D();
460 
461  virtual bool CheckHypothesis(SMESH_Mesh& aMesh,
462  const TopoDS_Shape& aShape,
464 
465  virtual bool Compute(SMESH_Mesh& aMesh, const TopoDS_Shape& aShape);
466 
467  virtual bool Evaluate(SMESH_Mesh & aMesh, const TopoDS_Shape & aShape,
468  MapShapeNbElems& aResMap);
469 
478  void ProjectTriangles() { myProjectTriangles = true; }
479 
485  static bool AddPrisms( std::vector<const TNodeColumn*> & nodeColumns,
486  SMESH_MesherHelper* helper);
487 
488  static bool IsApplicable(const TopoDS_Shape & aShape, bool toCheckAll);
489 
490  private:
491 
496  bool initPrism(Prism_3D::TPrismTopo& thePrism,
497  const TopoDS_Shape& theSolid,
498  const bool selectBottom = true);
499 
503  bool getWallFaces( Prism_3D::TPrismTopo& thePrism,
504  const int totalNbFaces);
505 
509  bool compute(const Prism_3D::TPrismTopo& thePrism);
510 
514  bool computeWalls(const Prism_3D::TPrismTopo& thePrism);
515 
519  TopoDS_Edge findPropagationSource( const TopoDS_Edge& E );
520 
527  bool assocOrProjBottom2Top( const gp_Trsf & bottomToTopTrsf,
528  const Prism_3D::TPrismTopo& thePrism);
529 
535  bool projectBottomToTop( const gp_Trsf & bottomToTopTrsf,
536  const Prism_3D::TPrismTopo& thePrism );
537 
541  double getSweepTolerance( const Prism_3D::TPrismTopo& thePrism );
542 
546  bool isSimpleBottom( const Prism_3D::TPrismTopo& thePrism );
547 
553  bool project2dMesh(const TopoDS_Face& source, const TopoDS_Face& target);
554 
561  bool setFaceAndEdgesXYZ( const int faceID, const gp_XYZ& params, int z );
562 
566  bool toSM( bool isOK );
567 
571  int shapeID( const TopoDS_Shape& S );
572 
573 private:
574 
578 
581 
582  std::vector<gp_XYZ> myShapeXYZ; // point on each sub-shape of the block
583 
584  // map of bottom nodes to the column of nodes above them
585  // (the column includes the bottom node)
587 
588  TopTools_IndexedMapOfShape* myPropagChains;
589 
590 }; // class StdMeshers_Prism_3D
591 
592 #endif