Point Cloud Library (PCL)  1.14.1-dev
opennurbs_nurbscurve.h
1 /* $NoKeywords: $ */
2 /*
3 //
4 // Copyright (c) 1993-2012 Robert McNeel & Associates. All rights reserved.
5 // OpenNURBS, Rhinoceros, and Rhino3D are registered trademarks of Robert
6 // McNeel & Associates.
7 //
8 // THIS SOFTWARE IS PROVIDED "AS IS" WITHOUT EXPRESS OR IMPLIED WARRANTY.
9 // ALL IMPLIED WARRANTIES OF FITNESS FOR ANY PARTICULAR PURPOSE AND OF
10 // MERCHANTABILITY ARE HEREBY DISCLAIMED.
11 //
12 // For complete openNURBS copyright information see <http://www.opennurbs.org>.
13 //
14 ////////////////////////////////////////////////////////////////
15 */
16 
17 ////////////////////////////////////////////////////////////////
18 //
19 // Definition of NURBS curve
20 //
21 ////////////////////////////////////////////////////////////////
22 
23 #if !defined(OPENNURBS_NURBSCURVE_INC_)
24 #define OPENNURBS_NURBSCURVE_INC_
25 
26 #include <pcl/pcl_exports.h>
27 
28 class ON_NurbsCurve;
29 class PCL_EXPORTS ON_CLASS ON_NurbsCurve : public ON_Curve
30 {
31  ON_OBJECT_DECLARE(ON_NurbsCurve);
32 
33 public:
34  /*
35  Description:
36  Use ON_NurbsCurve::New(...) instead of new ON_NurbsCurve(...)
37  Returns:
38  Pointer to an ON_NurbsCurve. Destroy by calling delete.
39  Remarks:
40  See static ON_Brep* ON_Brep::New() for details.
41  */
42  static ON_NurbsCurve* New();
43  static ON_NurbsCurve* New(
44  const ON_NurbsCurve& nurbs_curve
45  );
46  static ON_NurbsCurve* New(
47  const ON_BezierCurve& bezier_curve
48  );
49  static ON_NurbsCurve* New(
50  int dimension,
51  ON_BOOL32 bIsRational,
52  int order,
53  int cv_count
54  );
55 
58 
59  // Description:
60  // Create a NURBS curve equal to bezier with domain [0,1].
61  // Parameters:
62  // bezier_curve - [in]
64  const ON_BezierCurve& bezier_curve
65  );
66 
67  // Description:
68  // Create a NURBS curve with knot a cv memory allocated.
69  // Parameters:
70  // dimension - [in] (>= 1)
71  // bIsRational - [in] true to make a rational NURBS
72  // order - [in] (>= 2) The order=degree+1
73  // cv_count - [in] (>= order) number of control vertices
75  int dimension,
76  ON_BOOL32 bIsRational,
77  int order,
78  int cv_count
79  );
80 
81  // virtual ON_Object::SizeOf override
82  unsigned int SizeOf() const;
83 
84  // virtual ON_Object::DataCRC override
85  ON__UINT32 DataCRC(ON__UINT32 current_remainder) const;
86 
87  /*
88  Description:
89  See if this and other are same NURBS geometry.
90  Parameters:
91  other - [in] other NURBS curve
92  bIgnoreParameterization - [in] if true, parameterization
93  and orientaion are ignored.
94  tolerance - [in] tolerance to use when comparing
95  control points.
96  Returns:
97  true if curves are tne same.
98  */
99  bool IsDuplicate(
100  const ON_NurbsCurve& other,
101  bool bIgnoreParameterization,
102  double tolerance = ON_ZERO_TOLERANCE
103  ) const;
104 
105  // Description:
106  // Zeros all fields.
107  void Initialize(void);
108 
109  // Description:
110  // Create a NURBS curve with knot a cv memory allocated.
111  // Parameters:
112  // dimension - [in] (>= 1)
113  // bIsRational - [in] true to make a rational NURBS
114  // order - [in] (>= 2) The order=degree+1
115  // cv_count - [in] (>= order) number of control vertices
116  bool Create(
117  int dimension,
118  ON_BOOL32 bIsRational,
119  int order,
120  int cv_count
121  );
122 
123  // Description:
124  // Create a clamped uniform NURBS curve from a list
125  // of control points
126  // Parameters:
127  // dimension - [in] 1, 2 or 3
128  // order - [in] (>=2) order=degree+1
129  // point_count - [in] (>=order) number of control vertices
130  // point - [in] array of control vertex locations.
131  // knot_delta - [in] (>0.0) knot spacing
132  // Returns:
133  // true if successful
135  int dimension,
136  int order,
137  int point_count,
138  const ON_3dPoint* point,
139  double knot_delta = 1.0
140  );
141 
142  // Description:
143  // Create a periodic uniform NURBS curve from a list
144  // of control points
145  // Parameters:
146  // dimension - [in] 1, 2 or 3
147  // order - [in] (>=2) order=degree+1
148  // point_count - [in] (>=max(3,order-1)) number of distinct control vertices
149  // point - [in] array of distinct control vertex locations.
150  // knot_delta - [in] (>0.0) knot spacing
151  // Returns:
152  // true if successful
154  int dimension,
155  int order,
156  int point_count,
157  const ON_3dPoint* point,
158  double knot_delta = 1.0
159  );
160 
161  // Description:
162  // Deallocate knot and cv memory. Zeros all fields.
163  void Destroy();
164 
165  virtual ~ON_NurbsCurve();
166 
167  // Description:
168  // Call if memory used by ON_NurbsCurve becomes invalid.
170 
172 
173  // Description:
174  // Set NURBS curve equal to bezier with domain [0,1].
175  // Parameters:
176  // bezier_curve - [in]
178  const ON_BezierCurve& bezier_curve
179  );
180 
181  /////////////////////////////////////////////////////////////////
182  // ON_Object overrides
183 
184  /*
185  Description:
186  Tests an object to see if its data members are correctly
187  initialized.
188  Parameters:
189  text_log - [in] if the object is not valid and text_log
190  is not NULL, then a brief englis description of the
191  reason the object is not valid is appened to the log.
192  The information appended to text_log is suitable for
193  low-level debugging purposes by programmers and is
194  not intended to be useful as a high level user
195  interface tool.
196  Returns:
197  @untitled table
198  true object is valid
199  false object is invalid, uninitialized, etc.
200  Remarks:
201  Overrides virtual ON_Object::IsValid
202  */
203  ON_BOOL32 IsValid( ON_TextLog* text_log = NULL ) const;
204 
205  // Description:
206  // virtual ON_Object::Dump override
207  void Dump(
208  ON_TextLog& dump
209  ) const;
210 
211  // Description:
212  // virtual ON_Object::Write override
213  ON_BOOL32 Write(
214  ON_BinaryArchive& binary_archive
215  ) const;
216 
217  // Description:
218  // virtual ON_Object::Read override
219  ON_BOOL32 Read(
220  ON_BinaryArchive& binary_archive
221  );
222 
223  /////////////////////////////////////////////////////////////////
224  // ON_Geometry overrides
225 
226  // Description:
227  // virtual ON_Geometry::Dimension override
228  // Returns:
229  // value of m_dim
230  int Dimension() const;
231 
232  // Description:
233  // virtual ON_Geometry::GetBBox override
234  // Calculates axis aligned bounding box.
235  // Parameters:
236  // boxmin - [in/out] array of Dimension() doubles
237  // boxmax - [in/out] array of Dimension() doubles
238  // bGrowBox - [in] (default=false)
239  // If true, then the union of the input bbox and the
240  // object's bounding box is returned in bbox.
241  // If false, the object's bounding box is returned in bbox.
242  // Returns:
243  // true if object has bounding box and calculation was successful
244  ON_BOOL32 GetBBox( // returns true if successful
245  double* boxmin,
246  double* boxmax,
247  int bGrowBox = false
248  ) const;
249 
250  // Description:
251  // virtual ON_Geometry::Transform override.
252  // Transforms the NURBS curve.
253  //
254  // Parameters:
255  // xform - [in] transformation to apply to object.
256  //
257  // Remarks:
258  // When overriding this function, be sure to include a call
259  // to ON_Object::TransformUserData() which takes care of
260  // transforming any ON_UserData that may be attached to
261  // the object.
262  ON_BOOL32 Transform(
263  const ON_Xform& xform
264  );
265 
266  // virtual ON_Geometry::IsDeformable() override
267  bool IsDeformable() const;
268 
269  // virtual ON_Geometry::MakeDeformable() override
271 
272  // Description:
273  // virtual ON_Geometry::SwapCoordinates override.
274  // Swaps control vertex coordinate values with indices i and j.
275  // Parameters:
276  // i - [in] coordinate index
277  // j - [in] coordinate index
278  ON_BOOL32 SwapCoordinates(
279  int i,
280  int j
281  );
282 
283  /////////////////////////////////////////////////////////////////
284  // ON_Curve overrides
285 
286  // Description:
287  // virtual ON_Curve::Domain override.
288  // Returns:
289  // domain of the NURBS curve.
291 
292  // Description:
293  // virtual ON_Curve::SetDomain override.
294  // Set the domain of the curve
295  // Parameters:
296  // t0 - [in]
297  // t1 - [in] new domain will be [t0,t1]
298  // Returns:
299  // true if successful.
300  ON_BOOL32 SetDomain(
301  double t0,
302  double t1
303  );
304 
305  /*
306  Description:
307  If this curve is closed, then modify it so that
308  the start/end point is at curve parameter t.
309  Parameters:
310  t - [in] curve parameter of new start/end point. The
311  returned curves domain will start at t.
312  Returns:
313  true if successful.
314  Remarks:
315  Overrides virtual ON_Curve::ChangeClosedCurveSeam
316  */
318  double t
319  );
320 
321  // Description:
322  // virtual ON_Curve::SpanCount override.
323  // Get number of nonempty smooth (c-infinity) spans in curve
324  // Returns:
325  // Number of nonempty smooth (c-infinity) spans.
326  // Remarks:
327  // A nonempty span is bracked by knots m_knot[i] < m_knot[i+1]
328  // with m_order-2 <= i < m_cv_count-1.
329  int SpanCount() const;
330 
331  // Description:
332  // virtual ON_Curve::GetSpanVector override.
333  // Get number of parameters of distinct knots in NURBS curve's domain.
334  // Parameters:
335  // knot_values - [out] an array of length SpanCount()+1 is
336  // filled in with the distinct knot values in the list
337  /// (m_knot[m_order-2],...,m_knot[m_cv_count-1)
338  // Returns:
339  // true if successful
340  ON_BOOL32 GetSpanVector(
341  double* knot_values
342  ) const; //
343 
344  // Description:
345  // virtual ON_Curve::Degree override.
346  // Returns:
347  // m_order-1
348  int Degree() const;
349 
350  // Description:
351  // virtual ON_Curve::GetParameterTolerance override.
352  ON_BOOL32 GetParameterTolerance( // returns tminus < tplus: parameters tminus <= s <= tplus
353  double t,
354  double* tminus,
355  double* tplus
356  ) const;
357 
358  // Description:
359  // virtual ON_Curve::IsLinear override.
360  ON_BOOL32 IsLinear(
361  double tolerance = ON_ZERO_TOLERANCE
362  ) const;
363 
364  /*
365  Description:
366  Several types of ON_Curve can have the form of a polyline including
367  a degree 1 ON_NurbsCurve, an ON_PolylineCurve, and an ON_PolyCurve
368  all of whose segments are some form of polyline. IsPolyline tests
369  a curve to see if it can be represented as a polyline.
370  Parameters:
371  pline_points - [out] if not NULL and true is returned, then the
372  points of the polyline form are returned here.
373  t - [out] if not NULL and true is returned, then the parameters of
374  the polyline points are returned here.
375  Returns:
376  @untitled table
377  0 curve is not some form of a polyline
378  >=2 number of points in polyline form
379  */
381  ON_SimpleArray<ON_3dPoint>* pline_points = NULL,
382  ON_SimpleArray<double>* pline_t = NULL
383  ) const;
384 
385  // Description:
386  // virtual ON_Curve::IsArc override.
387  ON_BOOL32 IsArc(
388  const ON_Plane* plane = NULL,
389  ON_Arc* arc = NULL,
390  double tolerance = ON_ZERO_TOLERANCE
391  ) const;
392 
393  // Description:
394  // virtual ON_Curve::IsPlanar override.
395  ON_BOOL32 IsPlanar(
396  ON_Plane* plane = NULL,
397  double tolerance = ON_ZERO_TOLERANCE
398  ) const;
399 
400  // Description:
401  // virtual ON_Curve::IsInPlane override.
402  ON_BOOL32 IsInPlane(
403  const ON_Plane& test_plane,
404  double tolerance = ON_ZERO_TOLERANCE
405  ) const;
406 
407  // Description:
408  // virtual ON_Curve::IsClosed override.
409  // Returns:
410  // true if NURBS curve is closed. (Either curve has
411  // clamped end knots and euclidean location of start
412  // CV = euclidean location of end CV, or curve is
413  // periodic.)
414  ON_BOOL32 IsClosed() const;
415 
416  // Description:
417  // virtual ON_Curve::IsPeriodic override.
418  // Returns:
419  // true if NURBS curve is periodic (degree > 1,
420  // periodic knot vector, last degree many CVs
421  // are duplicates of first degree many CVs).
422  ON_BOOL32 IsPeriodic() const;
423 
424  /*
425  Description:
426  Search for a derivatitive, tangent, or curvature discontinuity.
427  Parameters:
428  c - [in] type of continity to test for. If ON::C1_continuous
429  t0 - [in] search begins at t0
430  t1 - [in] (t0 < t1) search ends at t1
431  t - [out] if a discontinuity is found, the *t reports the
432  parameter at the discontinuity.
433  hint - [in/out] if GetNextDiscontinuity will be called repeatedly,
434  passing a "hint" with initial value *hint=0 will increase the speed
435  of the search.
436  dtype - [out] if not NULL, *dtype reports the kind of discontinuity
437  found at *t. A value of 1 means the first derivative or unit tangent
438  was discontinuous. A value of 2 means the second derivative or
439  curvature was discontinuous.
440  cos_angle_tolerance - [in] default = cos(1 degree) Used only when
441  c is ON::G1_continuous or ON::G2_continuous. If the cosine
442  of the angle between two tangent vectors
443  is <= cos_angle_tolerance, then a G1 discontinuity is reported.
444  curvature_tolerance - [in] (default = ON_SQRT_EPSILON) Used only when
445  c is ON::G2_continuous or ON::Gsmooth_continuous.
446  ON::G2_continuous:
447  If K0 and K1 are curvatures evaluated
448  from above and below and |K0 - K1| > curvature_tolerance,
449  then a curvature discontinuity is reported.
450  ON::Gsmooth_continuous:
451  If K0 and K1 are curvatures evaluated from above and below
452  and the angle between K0 and K1 is at least twice angle tolerance
453  or ||K0| - |K1|| > (max(|K0|,|K1|) > curvature_tolerance,
454  then a curvature discontinuity is reported.
455  Returns:
456  true if a discontinuity was found on the interior of the interval (t0,t1).
457  Remarks:
458  Overrides ON_Curve::GetNextDiscontinuity.
459  */
461  ON::continuity c,
462  double t0,
463  double t1,
464  double* t,
465  int* hint=NULL,
466  int* dtype=NULL,
467  double cos_angle_tolerance=ON_DEFAULT_ANGLE_TOLERANCE_COSINE,
468  double curvature_tolerance=ON_SQRT_EPSILON
469  ) const;
470 
471  /*
472  Description:
473  Test continuity at a curve parameter value.
474  Parameters:
475  c - [in] continuity to test for
476  t - [in] parameter to test
477  hint - [in] evaluation hint
478  point_tolerance - [in] if the distance between two points is
479  greater than point_tolerance, then the curve is not C0.
480  d1_tolerance - [in] if the difference between two first derivatives is
481  greater than d1_tolerance, then the curve is not C1.
482  d2_tolerance - [in] if the difference between two second derivatives is
483  greater than d2_tolerance, then the curve is not C2.
484  cos_angle_tolerance - [in] default = cos(1 degree) Used only when
485  c is ON::G1_continuous or ON::G2_continuous. If the cosine
486  of the angle between two tangent vectors
487  is <= cos_angle_tolerance, then a G1 discontinuity is reported.
488  curvature_tolerance - [in] (default = ON_SQRT_EPSILON) Used only when
489  c is ON::G2_continuous or ON::Gsmooth_continuous.
490  ON::G2_continuous:
491  If K0 and K1 are curvatures evaluated
492  from above and below and |K0 - K1| > curvature_tolerance,
493  then a curvature discontinuity is reported.
494  ON::Gsmooth_continuous:
495  If K0 and K1 are curvatures evaluated from above and below
496  and the angle between K0 and K1 is at least twice angle tolerance
497  or ||K0| - |K1|| > (max(|K0|,|K1|) > curvature_tolerance,
498  then a curvature discontinuity is reported.
499  Returns:
500  true if the curve has at least the c type continuity at the parameter t.
501  Remarks:
502  Overrides ON_Curve::IsContinuous.
503  */
505  ON::continuity c,
506  double t,
507  int* hint = NULL,
508  double point_tolerance=ON_ZERO_TOLERANCE,
509  double d1_tolerance=ON_ZERO_TOLERANCE,
510  double d2_tolerance=ON_ZERO_TOLERANCE,
511  double cos_angle_tolerance=ON_DEFAULT_ANGLE_TOLERANCE_COSINE,
512  double curvature_tolerance=ON_SQRT_EPSILON
513  ) const;
514 
515  /*
516  Description:
517  Force the curve to start at a specified point.
518  Parameters:
519  start_point - [in]
520  Returns:
521  true if successful.
522  Remarks:
523  Some end points cannot be moved. Be sure to check return
524  code.
525  See Also:
526  ON_Curve::SetEndPoint
527  ON_Curve::PointAtStart
528  ON_Curve::PointAtEnd
529  */
530  //virtual
531  ON_BOOL32 SetStartPoint(
532  ON_3dPoint start_point
533  );
534 
535  /*
536  Description:
537  Force the curve to end at a specified point.
538  Parameters:
539  end_point - [in]
540  Returns:
541  true if successful.
542  Remarks:
543  Some end points cannot be moved. Be sure to check return
544  code.
545  See Also:
546  ON_Curve::SetStartPoint
547  ON_Curve::PointAtStart
548  ON_Curve::PointAtEnd
549  */
550  //virtual
551  ON_BOOL32 SetEndPoint(
552  ON_3dPoint end_point
553  );
554 
555  // Description:
556  // virtual ON_Curve::Reverse override.
557  // Reverse parameterizatrion by negating all knots
558  // and reversing the order of the control vertices.
559  // Remarks:
560  // Domain changes from [a,b] to [-b,-a]
561  ON_BOOL32 Reverse();
562 
563  // Description:
564  // virtual ON_Curve::Evaluate override.
565  ON_BOOL32 Evaluate( // returns false if unable to evaluate
566  double, // evaluation parameter
567  int, // number of derivatives (>=0)
568  int, // array stride (>=Dimension())
569  double*, // array of length stride*(ndir+1)
570  int = 0, // optional - determines which side to evaluate from
571  // 0 = default
572  // < 0 to evaluate from below,
573  // > 0 to evaluate from above
574  int* = 0 // optional - evaluation hint (int) used to speed
575  // repeated evaluations
576  ) const;
577 
578  /*
579  Parameters:
580  span_index - [in]
581  (0 <= span_index <= m_cv_count-m_order)
582  min_length -[in]
583  minimum length of a linear span
584  tolerance -[in]
585  distance tolerance to use when checking control points
586  between the span ends
587  Returns
588  true if the span is a non-degenrate line. This means:
589  - dimension = 2 or 3
590  - There are full multiplicity knots at each end of the span.
591  - The length of the the line segment from the span's initial
592  control point to the span's final control point is
593  >= min_length.
594  - The distance from the line segment to the interior control points
595  is <= tolerance and the projections of these points onto
596  the line increases monotonically.
597  */
599  int span_index,
600  double min_length,
601  double tolerance
602  ) const;
603 
605  int span_index,
606  double min_length,
607  double tolerance,
608  ON_Line* line
609  ) const;
610 
611  /*
612  Description:
613  Looks for problems caused by knots that are close together
614  or have mulitplicity >= order. If bRepair is true, the problems
615  are fixed. Does not change the domain.
616  Parameters:
617  knot_tolerance - [in] >= 0 When in doubt, use zero.
618  bRepair - [in] If true, then problems are repaired.
619  Otherwise this function looks for problemsn that
620  can be repaired, but does not modify the curve.
621  Returns:
622  True if bad knots were found and can be repaired.
623  See Also:
624  ON_NurbsCurve::RemoveShortSegments
625  */
627  double knot_tolerance=0.0,
628  bool bRepair = true
629  );
630 
631  // Description:
632  // virtual ON_Curve::Trim override.
633  ON_BOOL32 Trim( const ON_Interval& );
634 
635  // Description:
636  // Where possible, analytically extends curve to include domain.
637  // Parameters:
638  // domain - [in] if domain is not included in curve domain,
639  // curve will be extended so that its domain includes domain.
640  // Will not work if curve is closed. Original curve is identical
641  // to the restriction of the resulting curve to the original curve domain,
642  // Returns:
643  // true if successful.
644  bool Extend(
645  const ON_Interval& domain
646  );
647 
648  // Description:
649  // virtual ON_Curve::Split override.
650  //
651  // Split() divides the curve at the specified parameter. The parameter
652  // must be in the interior of the curve's domain. The pointers passed
653  // to ON_NurbsCurve::Split must either be NULL or point to an ON_NurbsCurve.
654  // If the pointer is NULL, then a curve will be created
655  // in Split(). You may pass "this" as one of the pointers to Split().
656  // For example,
657  //
658  // ON_NurbsCurve right_side;
659  // crv.Split( crv.Domain().Mid() &crv, &right_side );
660  //
661  // would split crv at the parametric midpoint, put the left side in crv,
662  // and return the right side in right_side.
663  ON_BOOL32 Split(
664  double split_param, // t = curve parameter to split curve at
665  ON_Curve*& left_result, // left portion returned here (must be an ON_NurbsCurve)
666  ON_Curve*& right_result // right portion returned here (must be an ON_NurbsCurve)
667  ) const;
668 
669  // Description:
670  // virtual ON_Curve::GetNurbForm override.
671  int GetNurbForm( // returns 0: unable to create NURBS representation
672  // with desired accuracy.
673  // 1: success - returned NURBS parameterization
674  // matches the curve's to wthe desired accuracy
675  // 2: success - returned NURBS point locus matches
676  // the curve's to the desired accuracy but, on
677  // the interior of the curve's domain, the
678  // curve's parameterization and the NURBS
679  // parameterization may not match to the
680  // desired accuracy.
681  ON_NurbsCurve& nurbsform,
682  double tolerance = 0.0,
683  const ON_Interval* subdomain = NULL // OPTIONAL subdomain of curve
684  ) const;
685 
686  // Description:
687  // virtual ON_Curve::HasNurbForm override.
688  int HasNurbForm( // returns 0: unable to create NURBS representation
689  // with desired accuracy.
690  // 1: success - returned NURBS parameterization
691  // matches the curve's to wthe desired accuracy
692  // 2: success - returned NURBS point locus matches
693  // the curve's to the desired accuracy but, on
694  // the interior of the curve's domain, the
695  // curve's parameterization and the NURBS
696  // parameterization may not match to the
697  // desired accuracy.
698  ) const;
699 
700  // Description:
701  // virtual ON_Curve::GetCurveParameterFromNurbFormParameter override
703  double nurbs_t,
704  double* curve_t
705  ) const;
706 
707  // Description:
708  // virtual ON_Curve::GetNurbFormParameterFromCurveParameter override
710  double curve_t,
711  double* nurbs_t
712  ) const;
713 
714 public:
715 
716  /////////////////////////////////////////////////////////////////
717  // Interface
718 
719  bool IsRational( // true if NURBS curve is rational
720  void
721  ) const;
722 
723  int CVSize( // number of doubles per control vertex
724  void // = IsRational() ? Dim()+1 : Dim()
725  ) const;
726 
727  int Order( // order = degree + 1
728  void
729  ) const;
730 
731  int CVCount( // number of control vertices
732  void
733  ) const;
734 
735  int KnotCount( // total number of knots in knot vector
736  void
737  ) const;
738 
739  /*
740  Description:
741  Expert user function to get a pointer to control vertex
742  memory. If you are not an expert user, please use
743  ON_NurbsCurve::GetCV( ON_3dPoint& ) or
744  ON_NurbsCurve::GetCV( ON_4dPoint& ).
745  Parameters:
746  cv_index - [in]
747  Returns:
748  Pointer to control vertex.
749  Remarks:
750  If the NURBS curve is rational, the format of the
751  returned array is a homogeneos rational point with
752  length m_dim+1. If the NURBS curve is not rational,
753  the format of the returned array is a nonrational
754  euclidean point with length m_dim.
755  See Also
756  ON_NurbsCurve::CVStyle
757  ON_NurbsCurve::GetCV
758  ON_NurbsCurve::Weight
759  */
760  double* CV(
761  int cv_index
762  ) const;
763 
764  /*
765  Description:
766  Returns the style of control vertices in the m_cv array.
767  Returns:
768  @untitled table
769  ON::not_rational m_is_rat is false
770  ON::homogeneous_rational m_is_rat is true
771  */
772  ON::point_style CVStyle() const;
773 
774 
775  double Weight( // get value of control vertex weight
776  int // CV index ( >= 0 and < CVCount() )
777  ) const;
778 
779  ON_BOOL32 SetWeight( // get value of control vertex weight
780  int, // CV index ( >= 0 and < CVCount() )
781  double
782  );
783 
784  ON_BOOL32 SetCV( // set a single control vertex
785  int, // CV index ( >= 0 and < CVCount() )
786  ON::point_style, // style of input point
787  const double* // value of control vertex
788  );
789 
790  ON_BOOL32 SetCV( // set a single control vertex
791  int, // CV index ( >= 0 and < CVCount() )
792  const ON_3dPoint& // value of control vertex
793  // If NURBS is rational, weight
794  // will be set to 1.
795  );
796 
797  ON_BOOL32 SetCV( // set a single control vertex
798  int, // CV index ( >= 0 and < CVCount() )
799  const ON_4dPoint& // value of control vertex
800  // If NURBS is not rational, euclidean
801  // location of homogeneous point will
802  // be used.
803  );
804 
805  ON_BOOL32 GetCV( // get a single control vertex
806  int, // CV index ( >= 0 and < CVCount() )
807  ON::point_style, // style to use for output point
808  double* // array of length >= CVSize()
809  ) const;
810 
811  ON_BOOL32 GetCV( // get a single control vertex
812  int, // CV index ( >= 0 and < CVCount() )
813  ON_3dPoint& // gets euclidean cv when NURBS is rational
814  ) const;
815 
816  ON_BOOL32 GetCV( // get a single control vertex
817  int, // CV index ( >= 0 and < CVCount() )
818  ON_4dPoint& // gets homogeneous cv
819  ) const;
820 
821  // Description:
822  // Set knot value.
823  // Parameters:
824  // knot_index - [in] 0 <= knot_index <= KnotCount()-1
825  // knot_value - [in]
826  // Remarks:
827  // m_knot[] must exist. Use ReserveKnotCapacity to
828  // allocate m_knot[].
829  // Returns:
830  // true if successful
831  // See Also:
832  // ON_NurbsCurve::ReserveKnotCapacity
833  bool SetKnot(
834  int knot_index,
835  double knot_value
836  );
837 
838  // Description:
839  // Get knot value.
840  // Parameters:
841  // knot_index - [in] 0 <= knot_index <= KnotCount()-1
842  // Returns:
843  // knot value = m_knot[knot_index]
844  // See Also:
845  // ON_NurbsCurve::SetKnot, ON_NurbsCurve::KnotMultiplicity
846  double Knot(
847  int knot_index
848  ) const;
849 
850  // Description:
851  // Get knot multiplicity.
852  // Parameters:
853  // knot_index - [in] 0 <= knot_index <= KnotCount()-1
854  // Returns:
855  // knot multiplicity = m_knot[knot_index]
856  // See Also:
857  // ON_NurbsCurve::SetKnot, ON_NurbsCurve::Knot,
858  // ON_NurbsCurve::InsertKnot
860  int knot_index
861  ) const;
862 
863  // Description:
864  // Get pointer to knot vector array.
865  // Returns:
866  // pointer to knot vector array (m_knot).
867  // See Also:
868  // ON_NurbsCurve::SetKnot, ON_NurbsCurve::Knot,
869  // ON_NurbsCurve::InsertKnot
870  const double* Knot() const;
871 
872  // Description:
873  // Make knot vector a clamped uniform knot vector
874  // based on the current values of m_order and m_cv_count.
875  // Does not change values of control vertices.
876  // Parameters:
877  // delta - [in] (>0.0) knot spacing.
878  // Returns:
879  // true if successful.
880  // Remarks:
881  // Allocates m_knot[] if it is not big enough.
882  // See Also:
883  // ON_MakeClampedUniformKnotVector
885  double delta = 1.0
886  );
887 
888  // Description:
889  // Make knot vector a periodic uniform knot vector
890  // based on the current values of m_order and m_cv_count.
891  // Does not change values of control vertices.
892  // Parameters:
893  // delta - [in] (>0.0) knot spacing.
894  // Returns:
895  // true if successful.
896  // Remarks:
897  // Allocates m_knot[] if it is not big enough.
898  // See Also:
899  // ON_MakePeriodicUniformKnotVector
901  double delta = 1.0
902  );
903 
904  bool IsClamped( // determine if knot vector is clamped
905  int = 2 // end to check: 0 = start, 1 = end, 2 = start and end
906  ) const;
907 
909  int // 0 = start, 1 = end
910  ) const;
911 
913  int // index (0 <= index < CVCount(dir)
914  ) const;
915 
916  bool GetGrevilleAbcissae( // see ON_GetGrevilleAbcissae() for details
917  double* // g[cv_count]
918  ) const;
919 
920  bool ZeroCVs(); // zeros control vertices and, if rational, sets weights to 1
921 
922  // Description:
923  // Clamp end knots. Does not modify control points.
924  // Parameters:
925  // end - [in] 0 = clamp start, 1 = clamp end, 2 = clamp start and end
926  // Returns:
927  // true if successful
928  bool ClampEnd(
929  int end
930  );
931 
932  // Description:
933  // Insert a knot and update cv locations.
934  // Parameters:
935  // knot_value - [in] m_knot[order-2] < knot_value < m_knot[m_cv_count-1]
936  // knot_multiplicity - [in] 1 to degree - includes multiplicity of existing knots.
937  // Remarks:
938  // Does not change parameterization or locus of curve.
939  // Returns:
940  // true if successful
941  bool InsertKnot(
942  double knot_value,
943  int knot_multiplicity
944  );
945 
946  bool MakeRational();
947 
949 
951  int desired_degree
952  );
953 
955  int desired_dimension
956  );
957 
958  bool Append( const ON_NurbsCurve& );
959 
960  /////////////////////////////////////////////////////////////////
961  // Tools for managing CV and knot memory
963  int // number of doubles to reserve
964  );
966  int // number of doubles to reserve
967  );
968 
969  //////////
970  // returns the length of the control polygon
971  double ControlPolygonLength() const;
972 
973  ////////
974  // Converts a span of the NURBS curve into a bezier. If
975  // the span is empty
976  // (m_knot[span_index+m_order-2] == m_knot[span_index+m_order-1]),
977  // then false is returned.
979  int, // span_index (0 <= span_index <= m_cv_count-m_order)
980  ON_BezierCurve& // bezier returned here
981  ) const;
982 
983  /*
984  Paramaters:
985  span_index - [in]
986  The index of a non-empty span to test.
987  span_index >= 0
988  span_index <= m_cv_count-m_order
989  m_knot[span_index+m_order-2] < m_knot[span_index+m_order-1]
990  Returns:
991  true if the span_index parameter is valid and the span is singular
992  (collapsed to a point).
993  false if the span is not singular or span_index does not identify
994  a non-empty span.
995  */
997  int span_index
998  ) const;
999 
1000  /*
1001  Returns:
1002  True if every span in the NURBS curve is singular.
1003  See Also:
1004  ON_NurbsCurve::RepairBadKnots()
1005  ON_NurbsCurve::RemoveShortSegments()
1006  */
1007  bool IsSingular() const;
1008 
1009  /*
1010  Paramaters:
1011  span_index - [in]
1012  The index of a non-empty span to remove.
1013  span_index >= 0
1014  span_index <= m_cv_count-m_order
1015  m_knot[span_index+m_order-2] < m_knot[span_index+m_order-1]
1016  Returns:
1017  True if the span was successfully removed.
1018  Remarks:
1019  The NURBS curve must have 2 or more spans (m_cv_count > m_order).
1020  Set m0 = mulitiplicity of the knot at m_knot[span_index+m_order-2]
1021  and m1 = mulitiplicity of the knot at m_knot[span_index+m_order-1].
1022  If (m0 + m1) < degree, then the degree-(m0+m1) cvs will be added
1023  to the NURBS curve. If (m0+m1) > degree, then (m0+m1)-degree cvs will
1024  be removed from the curve.
1025  See Also:
1026  ON_NurbsCurve::RepairBadKnots()
1027  ON_NurbsCurve::RemoveShortSegments()
1028  */
1030  int span_index
1031  );
1032 
1033  /*
1034  Returns:
1035  Number of spans removed.
1036  */
1038 
1039  ////////
1040  // Returns true if the NURBS curve has bezier spans
1041  // (all distinct knots have multiplitity = degree)
1042  bool HasBezierSpans() const;
1043 
1044  /*
1045  Description:
1046  Clamps ends and adds knots so the NURBS curve has bezier spans
1047  (all distinct knots have multiplitity = degree).
1048  Paremeters:
1049  bSetEndWeightsToOne - [in] If true and the first or last weight is
1050  not one, then the first and last spans are reparameterized so
1051  that the end weights are one.
1052  Returns:
1053  true if successful.
1054  */
1056  bool bSetEndWeightsToOne = false
1057  );
1058 
1059  /*
1060  Description:
1061  Use a combination of scaling and reparameterization to change
1062  the end weights to the specified values.
1063  Parameters:
1064  w0 - [in] weight for first cv
1065  w1 - [in] weight for last cv
1066  Returns:
1067  true if successful.
1068  See Also:
1069  ON_ChangeRationalNurbsCurveEndWeights
1070  Remarks:
1071  The domain, eucleanean locations of the control points,
1072  and locus of the curve do not change, but the weights,
1073  homogeneous cv values and internal knot values may change.
1074  If w0 and w1 are 1 and the curve is not rational, the
1075  curve is not changed.
1076  */
1077  bool ChangeEndWeights( double w0, double w1 );
1078 
1079  /*
1080  Description:
1081  Use a linear fractional transformation to reparameterize
1082  the NURBS curve. This does not change the curve's domain.
1083  Parameters:
1084  c - [in]
1085  reparameterization constant (generally speaking, c should be > 0).
1086  The control points and knots are adjusted so that
1087  output_nurbs(t) = input_nurbs(lambda(t)), where
1088  lambda(t) = c*t/( (c-1)*t + 1 ).
1089  Note that lambda(0) = 0, lambda(1) = 1, lambda'(t) > 0,
1090  lambda'(0) = c and lambda'(1) = 1/c.
1091  Returns:
1092  true if successful.
1093  Remarks:
1094  The cv and knot values are values are changed so that
1095  output_nurbs(t) = input_nurbs(lambda(t)).
1096  See Also:
1097  ON_ReparameterizeRationalNurbsCurve
1098  */
1099  bool Reparameterize( double c );
1100 
1101 
1102 
1103  /////////////////////////////////////////////////////////////////
1104  // Implementation
1105 public:
1106  // NOTE: These members are left "public" so that expert users may efficiently
1107  // create NURBS curves using the default constructor and borrow the
1108  // knot and CV arrays from their native NURBS representation.
1109  // No technical support will be provided for users who access these
1110  // members directly. If you can't get your stuff to work, then use
1111  // the constructor with the arguments and the SetKnot() and SetCV()
1112  // functions to fill in the arrays.
1113 
1114  int m_dim; // (>=1)
1115 
1116  int m_is_rat; // 1 for rational B-splines. (Rational control
1117  // vertices use homogeneous form.)
1118  // 0 for non-rational B-splines. (Control
1119  // verticies do not have a weight coordinate.)
1120 
1121  int m_order; // order = degree+1 (>=2)
1122 
1123  int m_cv_count; // number of control vertices ( >= order )
1124 
1125  // knot vector memory
1126 
1127  int m_knot_capacity; // If m_knot_capacity > 0, then m_knot[]
1128  // is an array of at least m_knot_capacity
1129  // doubles whose memory is managed by the
1130  // ON_NurbsCurve class using rhmalloc(),
1131  // onrealloc(), and rhfree().
1132  // If m_knot_capacity is 0 and m_knot is
1133  // not NULL, then m_knot[] is assumed to
1134  // be big enough for any requested operation
1135  // and m_knot[] is not deleted by the
1136  // destructor.
1137 
1138  double* m_knot; // Knot vector. ( The knot vector has length
1139  // m_order+m_cv_count-2. )
1140 
1141  // control vertex net memory
1142 
1143  int m_cv_stride; // The pointer to start of "CV[i]" is
1144  // m_cv + i*m_cv_stride.
1145 
1146  int m_cv_capacity; // If m_cv_capacity > 0, then m_cv[] is an array
1147  // of at least m_cv_capacity doubles whose
1148  // memory is managed by the ON_NurbsCurve
1149  // class using rhmalloc(), onrealloc(), and rhfree().
1150  // If m_cv_capacity is 0 and m_cv is not
1151  // NULL, then m_cv[] is assumed to be big enough
1152  // for any requested operation and m_cv[] is not
1153  // deleted by the destructor.
1154 
1155  double* m_cv; // Control points.
1156  // If m_is_rat is false, then control point is
1157  //
1158  // ( CV(i)[0], ..., CV(i)[m_dim-1] ).
1159  //
1160  // If m_is_rat is true, then the control point
1161  // is stored in HOMOGENEOUS form and is
1162  //
1163  // [ CV(i)[0], ..., CV(i)[m_dim] ].
1164  //
1165 };
1166 
1167 #endif
ON_BOOL32 GetCV(int, ON_3dPoint &) const
static ON_NurbsCurve * New(int dimension, ON_BOOL32 bIsRational, int order, int cv_count)
bool MakeRational()
ON_BOOL32 SwapCoordinates(int i, int j)
ON_BOOL32 IsClosed() const
bool IsSingular() const
double ControlPolygonLength() const
ON_BOOL32 SetCV(int, ON::point_style, const double *)
ON_BOOL32 SetCV(int, const ON_3dPoint &)
unsigned int SizeOf() const
bool Create(int dimension, ON_BOOL32 bIsRational, int order, int cv_count)
ON_NurbsCurve(const ON_NurbsCurve &)
ON_NurbsCurve & operator=(const ON_NurbsCurve &src)
bool ConvertSpanToBezier(int, ON_BezierCurve &) const
ON_NurbsCurve(int dimension, ON_BOOL32 bIsRational, int order, int cv_count)
bool IsDuplicate(const ON_NurbsCurve &other, bool bIgnoreParameterization, double tolerance=ON_ZERO_TOLERANCE) const
ON_BOOL32 IsPlanar(ON_Plane *plane=NULL, double tolerance=ON_ZERO_TOLERANCE) const
bool IsClamped(int=2) const
int KnotMultiplicity(int knot_index) const
ON_BOOL32 SetEndPoint(ON_3dPoint end_point)
bool MakePeriodicUniformKnotVector(double delta=1.0)
ON_BOOL32 GetCV(int, ON::point_style, double *) const
ON_BOOL32 Trim(const ON_Interval &)
ON_BOOL32 IsValid(ON_TextLog *text_log=NULL) const
bool GetGrevilleAbcissae(double *) const
void Dump(ON_TextLog &dump) const
void Initialize(void)
bool IncreaseDegree(int desired_degree)
bool InsertKnot(double knot_value, int knot_multiplicity)
bool ReserveKnotCapacity(int)
static ON_NurbsCurve * New(const ON_BezierCurve &bezier_curve)
double SuperfluousKnot(int) const
bool HasBezierSpans() const
int Order(void) const
ON_BOOL32 SetCV(int, const ON_4dPoint &)
ON_BOOL32 SetDomain(double t0, double t1)
ON_Interval Domain() const
bool SpanIsLinear(int span_index, double min_length, double tolerance, ON_Line *line) const
int SpanCount() const
ON_BOOL32 GetCurveParameterFromNurbFormParameter(double nurbs_t, double *curve_t) const
ON_BOOL32 GetCV(int, ON_4dPoint &) const
bool IsDeformable() const
ON_BOOL32 SetStartPoint(ON_3dPoint start_point)
bool MakeDeformable()
bool MakeClampedUniformKnotVector(double delta=1.0)
const double * Knot() const
bool SpanIsLinear(int span_index, double min_length, double tolerance) const
bool Append(const ON_NurbsCurve &)
void EmergencyDestroy()
ON_BOOL32 IsInPlane(const ON_Plane &test_plane, double tolerance=ON_ZERO_TOLERANCE) const
ON_BOOL32 Transform(const ON_Xform &xform)
int Dimension() const
int Degree() const
bool ClampEnd(int end)
ON_BOOL32 Read(ON_BinaryArchive &binary_archive)
bool ChangeDimension(int desired_dimension)
ON_BOOL32 GetBBox(double *boxmin, double *boxmax, int bGrowBox=false) const
virtual ~ON_NurbsCurve()
double Weight(int) const
bool Reparameterize(double c)
bool SetKnot(int knot_index, double knot_value)
bool Extend(const ON_Interval &domain)
ON_NurbsCurve & operator=(const ON_BezierCurve &bezier_curve)
ON_BOOL32 ChangeClosedCurveSeam(double t)
ON_BOOL32 IsArc(const ON_Plane *plane=NULL, ON_Arc *arc=NULL, double tolerance=ON_ZERO_TOLERANCE) const
int GetNurbForm(ON_NurbsCurve &nurbsform, double tolerance=0.0, const ON_Interval *subdomain=NULL) const
bool ChangeEndWeights(double w0, double w1)
ON_BOOL32 GetParameterTolerance(double t, double *tminus, double *tplus) const
static ON_NurbsCurve * New(const ON_NurbsCurve &nurbs_curve)
bool MakePiecewiseBezier(bool bSetEndWeightsToOne=false)
ON_BOOL32 Write(ON_BinaryArchive &binary_archive) const
bool IsContinuous(ON::continuity c, double t, int *hint=NULL, double point_tolerance=ON_ZERO_TOLERANCE, double d1_tolerance=ON_ZERO_TOLERANCE, double d2_tolerance=ON_ZERO_TOLERANCE, double cos_angle_tolerance=ON_DEFAULT_ANGLE_TOLERANCE_COSINE, double curvature_tolerance=ON_SQRT_EPSILON) const
bool GetNextDiscontinuity(ON::continuity c, double t0, double t1, double *t, int *hint=NULL, int *dtype=NULL, double cos_angle_tolerance=ON_DEFAULT_ANGLE_TOLERANCE_COSINE, double curvature_tolerance=ON_SQRT_EPSILON) const
int RemoveSingularSpans()
static ON_NurbsCurve * New()
int CVCount(void) const
bool CreateClampedUniformNurbs(int dimension, int order, int point_count, const ON_3dPoint *point, double knot_delta=1.0)
ON_NurbsCurve(const ON_BezierCurve &bezier_curve)
int IsPolyline(ON_SimpleArray< ON_3dPoint > *pline_points=NULL, ON_SimpleArray< double > *pline_t=NULL) const
bool SpanIsSingular(int span_index) const
ON_BOOL32 IsLinear(double tolerance=ON_ZERO_TOLERANCE) const
bool CreatePeriodicUniformNurbs(int dimension, int order, int point_count, const ON_3dPoint *point, double knot_delta=1.0)
bool IsRational(void) const
ON_BOOL32 Evaluate(double, int, int, double *, int=0, int *=0) const
double * CV(int cv_index) const
ON_BOOL32 GetNurbFormParameterFromCurveParameter(double curve_t, double *nurbs_t) const
ON::point_style CVStyle() const
bool RepairBadKnots(double knot_tolerance=0.0, bool bRepair=true)
ON_BOOL32 Split(double split_param, ON_Curve *&left_result, ON_Curve *&right_result) const
bool ReserveCVCapacity(int)
ON_BOOL32 IsPeriodic() const
ON_BOOL32 SetWeight(int, double)
double Knot(int knot_index) const
bool MakeNonRational()
ON_BOOL32 GetSpanVector(double *knot_values) const
(m_knot[m_order-2],...,m_knot[m_cv_count-1)
int KnotCount(void) const
ON_BOOL32 Reverse()
ON__UINT32 DataCRC(ON__UINT32 current_remainder) const
int HasNurbForm() const
double GrevilleAbcissa(int) const
bool RemoveSpan(int span_index)
int CVSize(void) const
#define PCL_EXPORTS
Definition: pcl_macros.h:325