CFx SDK Documentation  2023 SP0
FMContourIntersectors.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 #ifndef __FM_CONTOUR_INTERSECTORS_H__
24 #define __FM_CONTOUR_INTERSECTORS_H__
25 
27 #include "Contours/FM_IContour2D.h"
28 #include "FMProfile2D.h"
29 
30 namespace FacetModeler
31 {
32 
33  // Intersection of contours with user-defined IDs of the contours
34  class FMGEOMETRY_API IntersectionWithIDs : public Intersection
35  {
36  public:
37  IntersectionWithIDs() : uContourA(0), uContourB(0) { };
38 
40  : Intersection(rI), uContourA(uIDA), uContourB(uIDB) { };
41 
43  double dPA, OdUInt32 uIDB, double dPB, Types eIT=eitNone )
44  : Intersection(rPt, dPA, dPB, eIT), uContourA( uIDA ), uContourB( uIDB ) { };
45 
47 
48  static bool lessIDParamA( const IntersectionWithIDs& rI1, const IntersectionWithIDs& rI2 );
49  static bool lessIDParamB( const IntersectionWithIDs& rI1, const IntersectionWithIDs& rI2 );
50 
51  public:
52  OdUInt32 uContourA; // ID of the first contour
53  OdUInt32 uContourB; // ID of the second contour
54  };
55 
56 
57 
58 
59  class Crossing
60  {
61  public:
62 
64  {
65  public:
66  ContourLink() { };
67  ContourLink( OdUInt32 uID, double dP, double dD )
68  : uContourID(uID), dParam( dP ), dDistance( dD ) { };
69 
70  inline bool operator < ( const ContourLink & rB ) const
71  {
72  return (uContourID < rB.uContourID)
73  ||( (uContourID == rB.uContourID) && ( dParam < rB.dParam ) );
74  };
75 
76  public:
78  double dParam;
79  double dDistance;
80  };
81 
82  OdGePoint2d ptPoint; // center of the crossing
83 
84  std::vector< ContourLink > vecLinks; // contour links
85  };
86 
87 
88 
89  // This helper class is used for fast contour/profile intersections
90 
91  class FMGEOMETRY_API ContourIntersector
92  {
93  public:
94 
95  // some definitions
96 
97  struct SegmentUID
98  {
99  SegmentUID() { };
101  : uGroupIdx( uG ), uContourIdx( uC ), uSegmentIdx( uS ) { };
102 
103  bool operator < ( const SegmentUID & rB ) const;
104 
108  };
109 
110 
111 
112 
113  // SegmentBound1D class
114  // The class represents 1-D bound of a segment. It is used in contour intersection code.
116  public:
118  :m_eType(eNone)
119  { };
120 
121  enum eBoundType {
122  eNone = 0, eStart, eEnd, eLastBound
123  };
124 
125  SegmentBound1D( eBoundType eType, double dValue, OdUInt32 uG, OdUInt32 uC, OdUInt32 uS )
126  :m_dValue(dValue)
127  ,m_eType(eType)
128  ,m_UID( uG, uC, uS )
129  { };
130 
131 
132  // comparison of the bounds. Used in bound sorting
133  static bool less( const SegmentBound1D& A, const SegmentBound1D& B)
134  {
135  return A.value() < B.value();
136  }
137 
138  inline double value() const { return m_dValue; };
139  inline eBoundType type() const { return m_eType; };
140 
141  inline const SegmentUID & segmentUID() const { return m_UID; };
142 
143  private:
144  double m_dValue; // position
145  eBoundType m_eType; // start/end
146 
147  SegmentUID m_UID; // Group, Contour, Segment
148  };
149 
150 
151  // type of intersections to look for
153  {
154  eIntNone = 0,
155  eIntMiddle2Middle = 0x01, // interior parts of some segments intersect
156  eIntNode2Node = 0x02, // boundary points of some segments intersect
157  eIntNode2Middle = 0x04, // boundary points of some segment(s) touch interior of some other
158 
159  // ToDo...
160  //eIntSkipTouches = 0x10, // reject touches in node2node and node2middle
161  //eIntNode2NodeST = eIntNode2Node|eIntSkipTouches,
162  //eIntNode2MiddleST = eIntNode2Middle|eIntSkipTouches,
163 
164  eIntSkipZeroLength= 0x20,// reject self-intersections with zero (<tol) distance
165  eIntAny = 0x0F // look for all crossings
166  };
167 
168 
169  public:
170 
172 
174 
175  // Clear all groups and set tolerance
176  void reset( const OdGeTol & gTol = FMGeGbl::gTol );
177 
178  void reserveGroups( OdUInt32 iNumGroups );
179 
180  // Add a new group of contours and reserve memory, if uReservedContours>0
181  // bSelfIntersecting defines whether self-intersections of the group are searched for or not
182  // returns group index
183  OdUInt32 addGroup( bool bSelfIntersecting = false, OdUInt32 uReservedContours = 0 );
184 
185  inline OdUInt32 numGroups() const { return (OdUInt32)m_vecGroups.size(); };
186 
187  // Add contour/profile to an intersection group.
188  // Intersection points on the contour will have uContourA or uContourB = uID
189  // Contours from rProfile are added with auto-incremented IDs, starting from uFirstID
190  // Contours from 0 group are intersected with all contours.
191  // Contours from other groups are intersected with different groups only
192  Result addContour( const IContour2D & rContour, OdUInt32 uID, OdUInt32 uGroup = 0 );
193  Result addProfile( const Profile2D & rProfile, OdUInt32 uFirstID, OdUInt32 uGroup = 0 );
194 
195  // Appends intersection points to vecPoints.
196  // Returns number of intersections.
197  OdUInt32 getIntersections( std::vector< IntersectionWithIDs > & vecPoints, bool bOrderByGroups = true );
198 
199  // Looks for intersections and returns true, iff the specified type of intersection
200  // was found.
201  // Default: find any intersection
202  bool hasIntersections( int eLookFor = eIntAny );
203 
204  // Appends Crossings to the vecCrossings
205  // Crossings are unique and contain links to all possible segments.
206  OdUInt32 getAllCrossings( std::vector< Crossing > & vecCrossings, double dMergeTol = 0 );
207 
208  private:
209 
210  struct ContourRec
211  {
212  ContourRec( const IContour2D & rContour, OdUInt32 uContourID, OdUInt32 uGroupID );
213  // This method should be called manually to release pContour, if necessary.
214  // It is not included in destructor to fasten std::vector operations
215  void Done( );
216 
217  inline const IContour2D & contour() const { return *pContour; };
218 
219  OdUInt32 uContourID; // ID of the contour
220  OdUInt32 uGroupID; // Group ID
221  const IContour2D * pContour; // Contour ( original or a caching copy of original )
222  const IContour2D * pOrigContour; // Original contour
223  };
224 
225  struct GroupRec
226  {
227  GroupRec() : bSelfIntersecting(false) { };
228 
229  void Done( );
230 
231  bool bSelfIntersecting;
232  std::vector< ContourRec > vecContours;
233  };
234 
235 
236  OdGeTol m_gTol; // tolerance of intersection
237 
238  // Vectors of contours
239  std::vector< GroupRec > m_vecGroups;
240 
241  // helper class for getAllCrossings( )
242  class SegmentCrossing;
243 
244  bool m_bOrderByGroup;
245 
246  private:
247 
248  void resetGroup( OdUInt32 uGroup );
249 
251  // Stages of getIntersections:
252 
253  // Stage 1: find good direction for projection of segments
254  OdGeVector2d findMainDirection( ) const;
255 
256  // Stage 2: get and sort segment bounds using selected direction
257  void fillSegmentBounds( const OdGeVector2d& vMainDir, std::vector< SegmentBound1D > & vecBounds, double dAddTol = 0 ) const;
258 
259  // returns total number of segments
260  OdUInt32 getSegmentCount( ) const;
261 
262 
263  // Stage 2b: try to remove some useless segments from the bounds list.
264  // the bounds aren't actually removed, but its type is set to eNone.
265  // returns number of useful bounds
266  OdUInt32 removeUselessBounds( std::vector< SegmentBound1D > & vecBounds ) const;
267 
268  bool createCrossing( SegmentCrossing & rCross, Crossing & rDest, const double dTol ) const;
269 
270 
271  // skips segment joints. returns true, if there are valid intersections
272  // if dZeroTol >= 0 it also skips self-intersections with zero distance along contour
273  bool skipJoints( const SegmentUID & rUID1, const SegmentUID & rUID2,
274  IntersectionWithIDs * aIPs, OdUInt32 iXNum, const double dZeroTol = -1.0 );
275 
276  // updates contour parameters and IDs.
277  // returns number of valid intersections
278  OdUInt32 postprocessIntersections( const SegmentUID & rUID1, const SegmentUID & rUID2,
279  IntersectionWithIDs * aIPs, OdUInt32 iXNum );
280  };
281 
282 
283 };
284 
285 #endif //__FM_CONTOUR_INTERSECTORS_H__
false
Definition: DimVarDefs.h:165
unsigned int OdUInt32
bool operator<(const OdString &s1, const OdString &s2)
Definition: OdString.h:1284
static bool less(const SegmentBound1D &A, const SegmentBound1D &B)
SegmentBound1D(eBoundType eType, double dValue, OdUInt32 uG, OdUInt32 uC, OdUInt32 uS)
OdUInt32 getAllCrossings(std::vector< Crossing > &vecCrossings, double dMergeTol=0)
OdUInt32 getIntersections(std::vector< IntersectionWithIDs > &vecPoints, bool bOrderByGroups=true)
ContourIntersector(const OdGeTol &gTol=FMGeGbl::gTol)
OdUInt32 addGroup(bool bSelfIntersecting=false, OdUInt32 uReservedContours=0)
void reset(const OdGeTol &gTol=FMGeGbl::gTol)
bool hasIntersections(int eLookFor=eIntAny)
void reserveGroups(OdUInt32 iNumGroups)
Result addProfile(const Profile2D &rProfile, OdUInt32 uFirstID, OdUInt32 uGroup=0)
Result addContour(const IContour2D &rContour, OdUInt32 uID, OdUInt32 uGroup=0)
std::vector< ContourLink > vecLinks
IntersectionWithIDs(const OdGePoint2d &rPt, OdUInt32 uIDA, double dPA, OdUInt32 uIDB, double dPB, Types eIT=eitNone)
static bool lessIDParamB(const IntersectionWithIDs &rI1, const IntersectionWithIDs &rI2)
static bool lessIDParamA(const IntersectionWithIDs &rI1, const IntersectionWithIDs &rI2)
IntersectionWithIDs(const Intersection &rI, OdUInt32 uIDA, OdUInt32 uIDB)
IntersectionWithIDs & swapParams()
Definition: GeTol.h:49
SegmentUID(OdUInt32 uG, OdUInt32 uC, OdUInt32 uS)
static FMGEOMETRY_API_STATIC OdGeTol gTol
Definition: FMGeometry.h:156