CFx SDK Documentation  2023 SP0
FMMdlSlicerBaseImpl.h
Go to the documentation of this file.
1 // Copyright (C) 2002-2015, Open Design Alliance (the "Alliance").
3 // All rights reserved.
4 //
5 // This software and its documentation and related materials are owned by
6 // the Alliance. The software may only be incorporated into application
7 // programs owned by members of the Alliance, subject to a signed
8 // Membership Agreement and Supplemental Software License Agreement with the
9 // Alliance. The structure and organization of this software are the valuable
10 // trade secrets of the Alliance and its suppliers. The software is also
11 // protected by copyright law and international treaty provisions. Application
12 // programs incorporating this software must include the following statement
13 // with their copyright notices:
14 //
15 // This application incorporates Teigha(R) software pursuant to a license
16 // agreement with Open Design Alliance.
17 // Teigha(R) Copyright (C) 2002-2015 by Open Design Alliance.
18 // All rights reserved.
19 //
20 // By use of this software, its documentation or related materials, you
21 // acknowledge and accept the above terms.
23 
24 #ifndef AECSLICERBASEIMPL_H_INCLUDED
25 #define AECSLICERBASEIMPL_H_INCLUDED
26 
27 #include "FMProfile3D.h"
28 #include "FMGeometry.h"
29 #include "FMGeometryDebug.h"
30 #include "Modeler/FMMdlBody.h"
31 #include "Modeler/FMMdlFace.h"
32 #include "Modeler/FMMdlEdge.h"
33 #include "Modeler/FMMdlIterators.h"
34 #include "Contours/FMEdgeGraph.h"
35 #include "Contours/FMEdgeGraph.h"
37 
38 #include "Ge/GePlane.h"
39 #include "Ge/GeLineSeg3d.h"
40 #include <UInt32Array.h>
41 #include "Si/SiSpatialIndex.h"
42 #include "Si/SiShapePlane.h"
43 #include "Ge/GeLine3d.h"
44 #include "FMDebugDraw.h"
45 //#include "../sampleapplications/TADebugTx/Debug.h"
46 
47 template<typename _Tv>
49 {
50  template<typename _Td>
51  struct _Node
52  {
53  _Node* pNext;
54  _Node* pPrev;
55  _Td data;
56 
57  _Node()
58  {
59  pNext = NULL;
60  pPrev = NULL;
61  }
62  };
63 
64  typedef _Node<_Tv> Node;
65 
66  Node* m_pFirstNode;
67  int m_iNodeCount;
68 
69 public:
70  class iterator
71  {
72  friend class cycled_list<_Tv>;
73 
74  Node* m_pCurrentNode;
75 
76  iterator(Node* pNode)
77  {
78  m_pCurrentNode = pNode;
79  }
80 
81  public:
82  iterator(const iterator& it)
83  {
84  m_pCurrentNode = it.m_pCurrentNode;
85  }
86 
87  void move_forward()
88  {
89  m_pCurrentNode = m_pCurrentNode->pNext;
90  }
91 
93  {
94  m_pCurrentNode = m_pCurrentNode->pPrev;
95  }
96 
97  bool operator == (const iterator& it) const
98  {
99  return m_pCurrentNode == it.m_pCurrentNode;
100  }
101 
102  bool operator != (const iterator& it) const
103  {
104  return m_pCurrentNode != it.m_pCurrentNode;
105  }
106 
107  const _Tv& data() const
108  {
109  return m_pCurrentNode->data;
110  }
111 
112  _Tv& data()
113  {
114  return m_pCurrentNode->data;
115  }
116 
117  const _Tv& next_node_data()
118  {
119  return m_pCurrentNode->pNext->data;
120  }
121 
122  const _Tv& prev_node_data()
123  {
124  return m_pCurrentNode->pPrev->data;
125  }
126 
127  _Tv get()
128  {
129  return m_pCurrentNode->data;
130  }
131 
132  iterator next() const
133  {
134  return iterator(m_pCurrentNode->pNext);
135  }
136  };
137 
138 public:
140  {
141  m_iNodeCount = 0;
142  m_pFirstNode = NULL;
143  }
144 
146  {
147  clear();
148  }
149 
150  bool empty() const
151  {
152  return m_iNodeCount == 0;
153  }
154 
155  void clear()
156  {
157  m_iNodeCount = 0;
158  if(m_pFirstNode == NULL)
159  return;
160 
161  Node* pDeleteNode = m_pFirstNode->pNext;
162  while(pDeleteNode != m_pFirstNode)
163  {
164  pDeleteNode = pDeleteNode->pNext;
165  delete pDeleteNode->pPrev;
166  }
167 
168  delete m_pFirstNode;
169  m_pFirstNode = NULL;
170  }
171 
172  int size() const
173  {
174  return m_iNodeCount;
175  }
176 
177  void push_back(const _Tv& value)
178  {
179  m_iNodeCount++;
180 
181  Node* pNewNode = new Node();
182  pNewNode->data = value;
183 
184  if(m_pFirstNode == NULL)
185  {
186  m_pFirstNode = pNewNode;
187  pNewNode->pPrev = m_pFirstNode;
188  pNewNode->pNext = m_pFirstNode;
189  return;
190  }
191 
192  Node* pLastNode = m_pFirstNode->pPrev;
193 
194  pLastNode->pNext = pNewNode;
195  m_pFirstNode->pPrev = pNewNode;
196 
197  pNewNode->pPrev = pLastNode;
198  pNewNode->pNext = m_pFirstNode;
199  }
200 
201  void delete_range(const iterator& beg, const iterator& end)
202  {
203  if(beg == end)
204  throw OdError(OD_T("delete_range() parameters equal"));
205 
206  Node* pBeginNode = beg.m_pCurrentNode;
207  Node* pEndNode = end.m_pCurrentNode;
208 
209  if(pBeginNode->pNext == pEndNode)
210  {
211  return; // no inner nodes
212  }
213 
214  Node* pCurrentNode = pEndNode->pPrev;
215  do
216  {
217  m_iNodeCount--;
218  if(pCurrentNode == m_pFirstNode)
219  m_pFirstNode = pBeginNode;
220 
221  pCurrentNode = pCurrentNode->pPrev;
222  delete pCurrentNode->pNext;
223  }
224  while (pCurrentNode != pBeginNode);
225 
226  pEndNode->pPrev = pBeginNode;
227  pBeginNode->pNext = pEndNode;
228  }
229 
231  {
232  if(empty())
233  throw OdError(OD_T("begin() cannot create iterator for empty cycled list"));
234 
235  return iterator(m_pFirstNode);
236  }
237 };
238 
239 
240 namespace FacetModeler
241 {
242 
243  class SlicerBaseImpl;
244 
246  {
247  struct SegmentPoint
248  {
249  OdGePoint3d pt;
250  double mergeLineParam;
251  OdUInt32 ownerSegmentId;
252 
253  SegmentPoint(): mergeLineParam(0.0), ownerSegmentId(0)
254  {}
255 
256  SegmentPoint(const OdGePoint3d& point, OdUInt32 segmentId) : mergeLineParam(0.0)
257  {
258  pt = point;
259  ownerSegmentId = segmentId;
260  }
261 
262  inline bool operator < ( const SegmentPoint& segPoint ) const
263  {
264  return mergeLineParam < segPoint.mergeLineParam;
265  }
266  };
267  //FELIX_CHANGE_BEGIN
268  //DESKTOP-123542
269  //typedef OdArray<SegmentPoint, OdMemoryAllocator<SegmentPoint> > SegmentPointsArray;
270  using SegmentPointsArray = std::vector< SegmentPoint >;
271  //FELIX_CHANGE_END
272 
273  struct SegmentPointLess
274  {
275  inline bool operator() ( const SegmentPoint& pt1, const SegmentPoint& pt2 ) const
276  {
277  return pt1.mergeLineParam < pt2.mergeLineParam;
278  }
279  };
280 
281  private:
282  SegmentPointsArray m_segmentPoints;
283  OdGePoint3d m_ptPreviousPoint;
284  OdUInt32Array m_inSegments;
285 
286  OdUInt32 m_segmentsIdBase;
287  OdArray<const Edge*> m_segmentTags;
288 
289  public:
291  {
292  //FELIX_CHANGE_BEGIN
293  //DESKTOP-123542
294  /*
295  m_segmentPoints.reserve(1024);
296  */
297  //FELIX_CHANGE_END
298  m_segmentsIdBase = 0;
299  }
300 
301  void PushSegment(const OdGePoint3d& ptStart, const OdGePoint3d& ptEnd, const Edge* tag = 0)
302  {
303  OdUInt32 segmentId = MakeSegmentId();
304  m_segmentTags.push_back(tag);
305  //FELIX_CHANGE_BEGIN
306  //DESKTOP-123542
307  /*
308  m_segmentPoints.push_back(SegmentPoint(ptStart, segmentId));
309  m_segmentPoints.push_back(SegmentPoint(ptEnd, segmentId));
310  */
311  m_segmentPoints.emplace_back( ptStart, segmentId );
312  m_segmentPoints.emplace_back( ptEnd, segmentId );
313  //FELIX_CHANGE_END
314  }
315 
316  void MergeSegmentsAndAddToEdgeGraph(const OdGeLine3d& mergeLine, SlicerBaseImpl* pGraph, const OdGeTol& tol)
317  {
318  if(m_segmentPoints.empty())
319  return;
320 
321  #ifdef _DEBUG
322  CheckIsAllSegmentsOnMergeLine(mergeLine, tol);
323  #endif
324 
325  CalculatePointsParamAlongMergeLine(mergeLine, tol);
326  //SortSegmentPointsAlongMergeLine(); // !!!!!!
327  MergeSegments(pGraph, tol);
328  }
329 
330  void Clear()
331  {
332  m_segmentPoints.clear();
333  m_segmentsIdBase = 0;
334  m_inSegments.clear();
335  m_segmentTags.clear();
336  }
337 
338  private:
339  OdUInt32 MakeSegmentId()
340  {
341  return (m_segmentsIdBase++);
342  }
343 
344  #ifdef _DEBUG
345  void CheckIsAllSegmentsOnMergeLine(const OdGeLine3d& mergeLine, const OdGeTol& tol)
346  {
347  for(OdUInt32 iPoint = 0; iPoint < m_segmentPoints.size(); iPoint++)
348  {
349  const SegmentPoint& point = m_segmentPoints[iPoint];
350  //DEBUG_DRAW(point.pt, 0);
351 
352  ODA_ASSERT_ONCE(mergeLine.isOn(point.pt, tol));
353  }
354  }
355  #endif
356 
357  void CalculatePointsParamAlongMergeLine(const OdGeLine3d& mergeLine, const OdGeTol& tol)
358  {
359  const OdUInt32 pointsCount = m_segmentPoints.size();
360  for(OdUInt32 iPoint = 0; iPoint < pointsCount; iPoint++)
361  {
362  SegmentPoint& point = m_segmentPoints[iPoint];
363  point.mergeLineParam = mergeLine.paramOf(point.pt, tol);
364  }
365  }
366 
367  void SortSegmentPointsAlongMergeLine()
368  {
369  std::sort( m_segmentPoints.begin(), m_segmentPoints.end(), SegmentPointLess() );
370  }
371 
372  void MergeSegments(SlicerBaseImpl* pGraph, const OdGeTol& tol);
373 
374  bool IsOnSegment() const
375  {
376  return (!m_inSegments.empty());
377  }
378 
379  bool CanExtractCurrentSegment(const OdGePoint3d& currentPoint, const OdGeTol& tol)
380  {
381  if(!IsOnSegment())
382  return false;
383 
384  if(m_ptPreviousPoint.isEqualTo(currentPoint, tol))
385  return false;
386 
387  return true;
388  }
389 
390  void UpdateInSegmentsArray(OdUInt32 currentPtSegmentId)
391  {
392  if(!m_inSegments.contains(currentPtSegmentId))
393  {
394  m_inSegments.append(currentPtSegmentId);
395  }
396  else
397  {
398  m_inSegments.remove(currentPtSegmentId);
399  }
400  }
401  };
402 
403 
404  class SlicerBaseImpl : public EdgeGraph
405  {
406  protected:
408  {
410  double m_param;
411  const Edge* m_pEdge;
413 
415  {}
416 
417  inline bool operator < ( const Intersection& intersection2 ) const {
418  return m_param < intersection2.m_param;
419  }
420  };
422 
423  struct ParamLess
424  {
425  inline bool operator() ( const Intersection& intersection1, const Intersection& intersection2 ) const {
426  return intersection1.m_param < intersection2.m_param;
427  }
428  };
429 
431  {
435  };
436 
438  {
442  eExclude*/
443  };
444 
446  {
449  const Edge* pEdge;
450  int m_typeExclude; // 0 - not excluded, 1 - start exclude, 2 - end exclude
452  };
454 
455  protected:
463 
468 
472  double m_eq;
473 
474  public:
476 
477  void collect_segments( const Face* pFace );
478 
479  void reserveBuffers( size_t nFaces );
480 
481  const OdGeTol& tolerance() const { return m_tol; }
482 
483  void setTolerance( const OdGeTol& tol ) { m_tol = tol; }
484 
485  void set_cut_plane( const OdGePlane& cutPlane );
486 
487  void build_results(Profile2D* pResInclBndry,
488  Profile2D* pResExclCoBndry,
489  Profile2D* pResExclOpBndry,
490  Profile2D* pResExclBndry,
491  FaceConstPtrArray* pCoincidingFaces,
492  FaceConstPtrArray* pOppositeFaces,
493  bool bUseReverseEdgeAtMerge,
494  OdArray<const Edge*>* sourceEdges = 0);
495 
496  public:
497  void AddEdgeToGraph(const OdGePoint3d& ptStart, const OdGePoint3d& ptEnd, const Edge* tag = 0);
498 
499  protected:
501 
503  const OdGePlane& cut_plane() const;
504 
507 
509 
511 
512  bool extractSegment( const OdGePoint3d*& pStart, const OdGePoint3d*& pEnd, bool& bInside );
513 
515 
517 
519 
521 
522  void exclude_faces( Profile2D& excludedProfile, FaceConstPtrArray& excludeFaces, OdArray<const Edge*>* pSourceEdges = NULL );
523  void exclude_opposite_faces( Profile2D& excludedProfile, FaceConstPtrArray& excludeFaces, OdArray<const Edge*>* pSourceEdges = NULL );
524 
526 
527  void ClassifyLoopVertices(Edge* pFirstLoopEdge);
528 
530 
532 
534 
536 
537  bool ExtractSegmentFromVertex(VtxInPlanePosCycledList::iterator& itBase);
538 
539  VtxInPlanePosCycledList::iterator FindOnSegmentStartVertex(VtxInPlanePosCycledList::iterator& itBase);
540 
541  VtxInPlanePosCycledList::iterator FindOnSegmentEndVertex(VtxInPlanePosCycledList::iterator& itBase);
542 
543  bool VertexOnIntersectionLine(const VtxInPlanePosCycledList::iterator& itVtx) const;
544 
545  const OdGePoint3d& VertexPoint(const VtxInPlanePosCycledList::iterator& itVtx) const;
546 
547  bool IsIntersectionOnVertex(VtxInPlanePosCycledList::iterator& itVtx);
548 
549  bool IsIntersectionOnEdge(VtxInPlanePosCycledList::iterator& itVtx);
550 
552 
554 
555  void AddIntersection(const OdGePoint3d& ptIntersection, const Edge* pEdge, int bOnIntersectionSeg = 0);
556 
557  void CollectEdgeForEdgeGraph(const OdGePoint3d& ptStart, const OdGePoint3d& ptEnd, const Edge* tag = 0);
558 
560 
561 #ifdef _DEBUG
562  void DebugDrawIntersections() const;
563 #endif
564  };
565 }
566 
567 #endif //AECSLICERBASEIMPL_H_INCLUDED
#define ODA_ASSERT_ONCE(exp)
Definition: DebugStuff.h:51
tol
Definition: DimVarDefs.h:2287
#define NULL
Definition: GsProperties.h:177
#define OD_T(x)
unsigned int OdUInt32
bool operator<(const OdString &s1, const OdString &s2)
Definition: OdString.h:1284
void PushSegment(const OdGePoint3d &ptStart, const OdGePoint3d &ptEnd, const Edge *tag=0)
void MergeSegmentsAndAddToEdgeGraph(const OdGeLine3d &mergeLine, SlicerBaseImpl *pGraph, const OdGeTol &tol)
VtxInPlanePosCycledList::iterator FindOnSegmentStartVertex(VtxInPlanePosCycledList::iterator &itBase)
void AddIntersectionFromEdge(const VertexInPlanePosition &vtxData)
cycled_list< VertexInPlanePosition > VtxInPlanePosCycledList
void collect_segments(const Face *pFace)
bool IsIntersectionOnVertex(VtxInPlanePosCycledList::iterator &itVtx)
void reserveBuffers(size_t nFaces)
void setTolerance(const OdGeTol &tol)
void exclude_opposite_faces(Profile2D &excludedProfile, FaceConstPtrArray &excludeFaces, OdArray< const Edge * > *pSourceEdges=NULL)
VtxInPlanePosCycledList m_classifiedVertices
void CollectEdgeForEdgeGraph(const OdGePoint3d &ptStart, const OdGePoint3d &ptEnd, const Edge *tag=0)
void build_results(Profile2D *pResInclBndry, Profile2D *pResExclCoBndry, Profile2D *pResExclOpBndry, Profile2D *pResExclBndry, FaceConstPtrArray *pCoincidingFaces, FaceConstPtrArray *pOppositeFaces, bool bUseReverseEdgeAtMerge, OdArray< const Edge * > *sourceEdges=0)
IntersResult IntersectCutPlaneToCurrentFacePlane(double tol)
const OdGePlane & cut_plane() const
void AddIntersectionFromVertex(const VertexInPlanePosition &vtxData)
VtxInPlanePosCycledList::iterator FindOnSegmentEndVertex(VtxInPlanePosCycledList::iterator &itBase)
void set_cut_plane(const OdGePlane &cutPlane)
SlicerBaseImpl::Intersection * FindNextDifferentIntersection(SlicerBaseImpl::Intersection *pIntBase)
const OdGeTol & tolerance() const
const OdGePlane & current_face_plane() const
bool ExtractSegmentFromVertex(VtxInPlanePosCycledList::iterator &itBase)
void exclude_faces(Profile2D &excludedProfile, FaceConstPtrArray &excludeFaces, OdArray< const Edge * > *pSourceEdges=NULL)
bool VertexOnIntersectionLine(const VtxInPlanePosCycledList::iterator &itVtx) const
SlicerBaseImpl::Intersection * FindIntersectionEnterInside()
bool IsIntersectionOnEdge(VtxInPlanePosCycledList::iterator &itVtx)
void ClassifyLoopVertices(Edge *pFirstLoopEdge)
IntersResult IntersectCutPlaneToFacePlane(const Face *f) const
bool IntersectionsCoincident(const SlicerBaseImpl::Intersection *pInt1, const SlicerBaseImpl::Intersection *pInt2)
void AddEdgeToGraph(const OdGePoint3d &ptStart, const OdGePoint3d &ptEnd, const Edge *tag=0)
const OdGePoint3d & VertexPoint(const VtxInPlanePosCycledList::iterator &itVtx) const
bool extractSegment(const OdGePoint3d *&pStart, const OdGePoint3d *&pEnd, bool &bInside)
SlicerBaseImpl::VertexHalfPlaneSign ClassifyPointAboutIntersectionLine(const OdGePoint3d &ptToClassify)
void AddIntersection(const OdGePoint3d &ptIntersection, const Edge *pEdge, int bOnIntersectionSeg=0)
OdArray< Intersection, OdMemoryAllocator< Intersection > > IntersectionArray
void clear()
Definition: OdArray.h:979
bool empty() const
Definition: OdArray.h:901
void push_back(const T &value)
Definition: OdArray.h:987
bool contains(const T &value, size_type start=0) const
Definition: OdArray.h:1043
size_type append(const T &value)
Definition: OdArray.h:1215
bool remove(const T &value, size_type start=0)
Definition: OdArray.h:1577
double paramOf(const OdGePoint3d &point, const OdGeTol &tol=OdGeContext::gTol) const
bool isOn(const OdGePlane &plane, const OdGeTol &tol=OdGeContext::gTol) const
bool isEqualTo(const OdGePoint3d &point, const OdGeTol &tol=OdGeContext::gTol) const
Definition: GeTol.h:49
iterator(const iterator &it)
bool operator==(const iterator &it) const
bool operator!=(const iterator &it) const
const _Tv & data() const
void delete_range(const iterator &beg, const iterator &end)
int size() const
void push_back(const _Tv &value)
bool empty() const
GLfloat f
Definition: gles2_ext.h:564
GLint GLenum GLsizei GLsizei GLint GLsizei const void * data
Definition: gles2_ext.h:110
GLsizei const GLfloat * value
Definition: gles2_ext.h:302
bool operator<(const Intersection &intersection2) const
bool operator()(const Intersection &intersection1, const Intersection &intersection2) const