Point Cloud Library (PCL)  1.9.1-dev
opennurbs_nurbssurface.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 surface
20 //
21 ////////////////////////////////////////////////////////////////
22 
23 #if !defined(OPENNURBS_NURBSSURFACE_INC_)
24 #define OPENNURBS_NURBSSURFACE_INC_
25 
26 #include <pcl/pcl_exports.h>
27 
28 class ON_CLASS ON_TensorProduct
29 {
30  // Pure virtual tensor passed to ON_NurbsSurface::TensorProduct()
31 public:
33 
34  virtual
36 
37  // Evaluate() must define a function T:R^dimA X R^dimB -> R^Dimension()
38  // such that
39  //
40  // T(a*A0 + (1-a)*A1, B) = a*T(A0,B) + (1-a)*T(A1,B) and
41  // T(A, b*B0 + (1-b)*B1) = b*T(A,B0) + (1-b)*T(A,B1).
42  virtual
43  int DimensionA() const = 0; // dimension of A space
44 
45  virtual
46  int DimensionB() const = 0; // dimension of B space
47 
48  virtual
49  int DimensionC() const = 0; // dimension of range space
50 
51  virtual
52  bool Evaluate( double, // a
53  const double*, // A
54  double, // b
55  const double*, // B
56  double* // C
57  ) = 0;
58 
59 };
60 
61 class ON_Brep;
62 class ON_NurbsSurface;
63 
64 class PCL_EXPORTS ON_CLASS ON_NurbsSurface : public ON_Surface
65 {
66  ON_OBJECT_DECLARE(ON_NurbsSurface);
67 
68 public:
69  /*
70  Description:
71  Use ON_NurbsSurface::New(...) instead of new ON_NurbsSurface(...)
72  Returns:
73  Pointer to an ON_NurbsSurface. Destroy by calling delete.
74  Remarks:
75  See static ON_Brep* ON_Brep::New() for details.
76  */
77  static ON_NurbsSurface* New();
78  static ON_NurbsSurface* New(
79  const ON_NurbsSurface& nurbs_surface
80  );
81  static ON_NurbsSurface* New(
82  const ON_BezierSurface& bezier_surface
83  );
84  static ON_NurbsSurface* New(
85  int dimension,
86  ON_BOOL32 bIsRational,
87  int order0,
88  int order1,
89  int cv_count0,
90  int cv_count1
91  );
92 
94  ON_NurbsSurface(const ON_NurbsSurface& nurbs_surface);
95  ON_NurbsSurface(const ON_BezierSurface& bezier_surface);
97  int dimension, // dimension (>= 1)
98  ON_BOOL32 bIsRational, // true to make a rational NURBS
99  int order0, // order0 (>= 2)
100  int order1, // order1 (>= 2)
101  int cv_count0, // cv count0 (>= order0)
102  int cv_count1 // cv count1 (>= order1)
103  );
104 
105  // virtual ON_Object::SizeOf override
106  unsigned int SizeOf() const;
107 
108  // virtual ON_Object::DataCRC override
109  ON__UINT32 DataCRC(ON__UINT32 current_remainder) const;
110 
111  /*
112  Description:
113  See if this and other are same NURBS geometry.
114  Parameters:
115  other - [in] other NURBS surface
116  bIgnoreParameterization - [in] if true, parameterization
117  and orientaion are ignored.
118  tolerance - [in] tolerance to use when comparing
119  control points.
120  Returns:
121  true if curves are tne same.
122  */
123  bool IsDuplicate(
124  const ON_NurbsSurface& other,
125  bool bIgnoreParameterization,
126  double tolerance = ON_ZERO_TOLERANCE
127  ) const;
128 
129  void Initialize(void); // zeros all fields
130 
131  ON_BOOL32 Create(
132  int dim, // dimension (>= 1)
133  ON_BOOL32 is_rat, // true to make a rational NURBS
134  int order0, // order0 (>= 2)
135  int order1, // order1 (>= 2)
136  int cv_count0, // cv count0 (>= order0)
137  int cv_count1 // cv count1 (>= order1)
138  );
139 
140  /*
141  Description:
142  Create a ruled surface from two curves.
143  Parameters:
144  curveA - [in] (must have same NURBS form knots as curveB)
145  curveB - [in] (must have same NURBS form knots as curveA)
146  curveA_domain - [in] if not NULL, then this is a subdomain
147  of curveA to use for the ruled surface.
148  curveB_domain - [in] if not NULL, then this is a subdomain
149  of curveA to use for the ruled surface.
150  Returns:
151  @untitled table
152  0 failure
153  1 success - parameterization is exact
154  2 success - parameterization is not exact
155  Remarks:
156  The ruling parameter is the second surface parameter and
157  it is in the interval [0,1].
158  The true ruled surface has parameterization
159  srf(s,t) = (1.0-t)*curveA(s) + t*curveB(s).
160  The returned NURBS surface has parameterization
161  srf(s,t) = (1.0-t)*nurbs_curveA(s) + t*nurbs_curveB(s),
162  where nurbs_curveX is the NURBS form of curveX. If the
163  parameterization of nurbs_curveX does not match the
164  parameterization of curveX, then 2 is returned.
165  */
166  virtual
167  int CreateRuledSurface(
168  const ON_Curve& curveA,
169  const ON_Curve& curveB,
170  const ON_Interval* curveA_domain = NULL,
171  const ON_Interval* curveB_domain = NULL
172  );
173 
174  /*
175  Description:
176  Create a cone surface from a curve to a point.
177  Parameters:
178  apex_point - [in]
179  curve - [in]
180  curve_domain - [in] if not NULL, then this is a subdomain
181  of curve to use for the ruled surface.
182  Returns:
183  @untitled table
184  0 failure
185  1 success - parameterization is exact
186  2 success - parameterization is not exact
187  Remarks:
188  The ruling parameter is the second surface parameter and
189  it is in the interval [0,1].
190  The true cone surface has parameterization
191  srf(s,t) = (1.0-t)*curve(s) + t*apex_point.
192  The returned NURBS surface has parameterization
193  srf(s,t) = (1.0-t)*nurbs_curve(s) + t*apex_point,
194  where nurbs_curve is the NURBS form of curve. If the
195  parameterization of nurbs_curve does not match the
196  parameterization of curve, then 2 is returned.
197  */
198  int CreateConeSurface(
199  ON_3dPoint apex_point,
200  const ON_Curve& curve,
201  const ON_Interval* curve_domain = NULL
202  );
203 
204  /*
205  Description:
206  Collapse the side of a NURBS surface to a single point.
207  Parameters:
208  side - [in] 0 = south west,
209  1 = south east,
210  2 = north east,
211  3 = north west
212  point - [in] point to collapse to. If point is ON_unset_point,
213  the the current location of the start of the side
214  is used.
215  Returns:
216  True if successful.
217  Remarks:
218  If the surface is rational, the weights of the side control
219  points must be set before calling CollapseSide.
220  */
221  bool CollapseSide(
222  int side,
223  ON_3dPoint point = ON_unset_point
224  );
225 
226  void Destroy();
227 
228  virtual ~ON_NurbsSurface();
229 
230  void EmergencyDestroy(); // call if memory used by this class becomes invalid
231 
232  ON_NurbsSurface& operator=(const ON_NurbsSurface&);
233 
234  /*
235  Description:
236  Set NURBS surface equal to bezier surface with domain [0,1]x[0,1].
237  Parameters:
238  bezier_surface - [in]
239  */
240  ON_NurbsSurface& operator=(
241  const ON_BezierSurface& bezier_surface
242  );
243 
244  /////////////////////////////////////////////////////////////////
245  // ON_Object overrides
246 
247  /*
248  Description:
249  Tests an object to see if its data members are correctly
250  initialized.
251  Parameters:
252  text_log - [in] if the object is not valid and text_log
253  is not NULL, then a brief englis description of the
254  reason the object is not valid is appened to the log.
255  The information appended to text_log is suitable for
256  low-level debugging purposes by programmers and is
257  not intended to be useful as a high level user
258  interface tool.
259  Returns:
260  @untitled table
261  true object is valid
262  false object is invalid, uninitialized, etc.
263  Remarks:
264  Overrides virtual ON_Object::IsValid
265  */
266  ON_BOOL32 IsValid( ON_TextLog* text_log = NULL ) const;
267 
268  void Dump( ON_TextLog& ) const; // for debugging
269 
270  ON_BOOL32 Write(
271  ON_BinaryArchive& // open binary file
272  ) const;
273 
274  ON_BOOL32 Read(
275  ON_BinaryArchive& // open binary file
276  );
277 
278  /////////////////////////////////////////////////////////////////
279  // ON_Geometry overrides
280 
281  int Dimension() const;
282 
283  ON_BOOL32 GetBBox( // returns true if successful
284  double*, // minimum
285  double*, // maximum
286  ON_BOOL32 = false // true means grow box
287  ) const;
288 
289  ON_BOOL32 Transform(
290  const ON_Xform&
291  );
292 
293  // virtual ON_Geometry::IsDeformable() override
294  bool IsDeformable() const;
295 
296  // virtual ON_Geometry::MakeDeformable() override
297  bool MakeDeformable();
298 
299  ON_BOOL32 SwapCoordinates(
300  int, int // indices of coords to swap
301  );
302 
303  /////////////////////////////////////////////////////////////////
304  // ON_Surface overrides
305 
306  ON_BOOL32 SetDomain(
307  int dir, // 0 sets first parameter's domain, 1 gets second parameter's domain
308  double t0,
309  double t1
310  );
311 
312  ON_Interval Domain(
313  int // 0 gets first parameter's domain, 1 gets second parameter's domain
314  ) const;
315 
316 
317  /*
318  Description:
319  Get an estimate of the size of the rectangle that would
320  be created if the 3d surface where flattened into a rectangle.
321  Parameters:
322  width - [out] (corresponds to the first surface parameter)
323  height - [out] (corresponds to the first surface parameter)
324  Remarks:
325  overrides virtual ON_Surface::GetSurfaceSize
326  Returns:
327  true if successful.
328  */
329  ON_BOOL32 GetSurfaceSize(
330  double* width,
331  double* height
332  ) const;
333 
334  int SpanCount(
335  int // 0 gets first parameter's domain, 1 gets second parameter's domain
336  ) const; // number of smooth spans in curve
337 
338  ON_BOOL32 GetSpanVector( // span "knots"
339  int, // 0 gets first parameter's domain, 1 gets second parameter's domain
340  double* // array of length SpanCount() + 1
341  ) const; //
342 
343  int Degree( // returns maximum algebraic degree of any span
344  // ( or a good estimate if curve spans are not algebraic )
345  int // 0 gets first parameter's domain, 1 gets second parameter's domain
346  ) const;
347 
348  ON_BOOL32 GetParameterTolerance( // returns tminus < tplus: parameters tminus <= s <= tplus
349  int, // 0 gets first parameter, 1 gets second parameter
350  double, // t = parameter in domain
351  double*, // tminus
352  double* // tplus
353  ) const;
354 
355  /*
356  Description:
357  Test a surface to see if it is planar.
358  Parameters:
359  plane - [out] if not NULL and true is returned,
360  the plane parameters are filled in.
361  tolerance - [in] tolerance to use when checking
362  Returns:
363  true if there is a plane such that the maximum distance from
364  the surface to the plane is <= tolerance.
365  Remarks:
366  Overrides virtual ON_Surface::IsPlanar.
367  */
368  ON_BOOL32 IsPlanar(
369  ON_Plane* plane = NULL,
370  double tolerance = ON_ZERO_TOLERANCE
371  ) const;
372 
373  ON_BOOL32 IsClosed( // true if NURBS surface is closed (either surface has
374  int // dir // clamped end knots and euclidean location of start
375  ) const; // CV = euclidean location of end CV, or surface is
376  // periodic.)
377 
378  ON_BOOL32 IsPeriodic( // true if NURBS surface is periodic (degree > 1,
379  int // dir // periodic knot vector, last degree many CVs
380  ) const; // are duplicates of first degree many CVs.)
381 
382  ON_BOOL32 IsSingular( // true if surface side is collapsed to a point
383  int // side of parameter space to test
384  // 0 = south, 1 = east, 2 = north, 3 = west
385  ) const;
386 
387  /*
388  Description:
389  Search for a derivatitive, tangent, or curvature
390  discontinuity.
391  Parameters:
392  dir - [in] If 0, then "u" parameter is checked. If 1, then
393  the "v" parameter is checked.
394  c - [in] type of continity to test for.
395  t0 - [in] Search begins at t0. If there is a discontinuity
396  at t0, it will be ignored. This makes it
397  possible to repeatedly call GetNextDiscontinuity
398  and step through the discontinuities.
399  t1 - [in] (t0 != t1) If there is a discontinuity at t1 is
400  will be ingored unless c is a locus discontinuity
401  type and t1 is at the start or end of the curve.
402  t - [out] if a discontinuity is found, then *t reports the
403  parameter at the discontinuity.
404  hint - [in/out] if GetNextDiscontinuity will be called
405  repeatedly, passing a "hint" with initial value *hint=0
406  will increase the speed of the search.
407  dtype - [out] if not NULL, *dtype reports the kind of
408  discontinuity found at *t. A value of 1 means the first
409  derivative or unit tangent was discontinuous. A value
410  of 2 means the second derivative or curvature was
411  discontinuous. A value of 0 means teh curve is not
412  closed, a locus discontinuity test was applied, and
413  t1 is at the start of end of the curve.
414  cos_angle_tolerance - [in] default = cos(1 degree) Used only
415  when c is ON::G1_continuous or ON::G2_continuous. If the
416  cosine of the angle between two tangent vectors is
417  <= cos_angle_tolerance, then a G1 discontinuity is reported.
418  curvature_tolerance - [in] (default = ON_SQRT_EPSILON) Used
419  only when c is ON::G2_continuous. If K0 and K1 are
420  curvatures evaluated from above and below and
421  |K0 - K1| > curvature_tolerance, then a curvature
422  discontinuity is reported.
423  Returns:
424  Parametric continuity tests c = (C0_continuous, ..., G2_continuous):
425 
426  true if a parametric discontinuity was found strictly
427  between t0 and t1. Note well that all curves are
428  parametrically continuous at the ends of their domains.
429 
430  Locus continuity tests c = (C0_locus_continuous, ...,G2_locus_continuous):
431 
432  true if a locus discontinuity was found strictly between
433  t0 and t1 or at t1 is the at the end of a curve.
434  Note well that all open curves (IsClosed()=false) are locus
435  discontinuous at the ends of their domains. All closed
436  curves (IsClosed()=true) are at least C0_locus_continuous at
437  the ends of their domains.
438  */
439  bool GetNextDiscontinuity(
440  int dir,
441  ON::continuity c,
442  double t0,
443  double t1,
444  double* t,
445  int* hint=NULL,
446  int* dtype=NULL,
447  double cos_angle_tolerance=ON_DEFAULT_ANGLE_TOLERANCE_COSINE,
448  double curvature_tolerance=ON_SQRT_EPSILON
449  ) const;
450 
451  /*
452  Description:
453  Test continuity at a surface parameter value.
454  Parameters:
455  c - [in] continuity to test for
456  s - [in] surface parameter to test
457  t - [in] surface parameter to test
458  hint - [in] evaluation hint
459  point_tolerance - [in] if the distance between two points is
460  greater than point_tolerance, then the surface is not C0.
461  d1_tolerance - [in] if the difference between two first derivatives is
462  greater than d1_tolerance, then the surface is not C1.
463  d2_tolerance - [in] if the difference between two second derivatives is
464  greater than d2_tolerance, then the surface is not C2.
465  cos_angle_tolerance - [in] default = cos(1 degree) Used only when
466  c is ON::G1_continuous or ON::G2_continuous. If the cosine
467  of the angle between two normal vectors
468  is <= cos_angle_tolerance, then a G1 discontinuity is reported.
469  curvature_tolerance - [in] (default = ON_SQRT_EPSILON) Used only when
470  c is ON::G2_continuous. If K0 and K1 are curvatures evaluated
471  from above and below and |K0 - K1| > curvature_tolerance,
472  then a curvature discontinuity is reported.
473  Returns:
474  true if the surface has at least the c type continuity at the parameter t.
475  Remarks:
476  Overrides virtual ON_Surface::IsContinuous
477  */
478  bool IsContinuous(
479  ON::continuity c,
480  double s,
481  double t,
482  int* hint = NULL,
483  double point_tolerance=ON_ZERO_TOLERANCE,
484  double d1_tolerance=ON_ZERO_TOLERANCE,
485  double d2_tolerance=ON_ZERO_TOLERANCE,
486  double cos_angle_tolerance=ON_DEFAULT_ANGLE_TOLERANCE_COSINE,
487  double curvature_tolerance=ON_SQRT_EPSILON
488  ) const;
489 
490  ON_BOOL32 Reverse( // reverse parameterizatrion, Domain changes from [a,b] to [-b,-a]
491  int // dir 0 = "s", 1 = "t"
492  );
493 
494  ON_BOOL32 Transpose(); // transpose surface parameterization (swap "s" and "t")
495 
496  ON_BOOL32 Evaluate( // returns false if unable to evaluate
497  double, double, // evaluation parameter
498  int, // number of derivatives (>=0)
499  int, // array stride (>=Dimension())
500  double*, // array of length stride*(ndir+1)*(ndir+2)/2
501  int = 0, // optional - determines which quadrant to evaluate from
502  // 0 = default
503  // 1 from NE quadrant
504  // 2 from NW quadrant
505  // 3 from SW quadrant
506  // 4 from SE quadrant
507  int* = 0 // optional - evaluation hint (int[2]) used to speed
508  // repeated evaluations
509  ) const;
510 
511  /*
512  Description:
513  Get isoparametric curve.
514  Overrides virtual ON_Surface::IsoCurve.
515  Parameters:
516  dir - [in] 0 first parameter varies and second parameter is constant
517  e.g., point on IsoCurve(0,c) at t is srf(t,c)
518  1 first parameter is constant and second parameter varies
519  e.g., point on IsoCurve(1,c) at t is srf(c,t)
520 
521  c - [in] value of constant parameter
522  Returns:
523  Isoparametric curve.
524  */
525  ON_Curve* IsoCurve(
526  int dir,
527  double c
528  ) const;
529 
530  /*
531  Description:
532  Removes the portions of the surface outside of the specified interval.
533  Overrides virtual ON_Surface::Trim.
534 
535  Parameters:
536  dir - [in] 0 The domain specifies an sub-interval of Domain(0)
537  (the first surface parameter).
538  1 The domain specifies an sub-interval of Domain(1)
539  (the second surface parameter).
540  domain - [in] interval of the surface to keep. If dir is 0, then
541  the portions of the surface with parameters (s,t) satisfying
542  s < Domain(0).Min() or s > Domain(0).Max() are trimmed away.
543  If dir is 1, then the portions of the surface with parameters
544  (s,t) satisfying t < Domain(1).Min() or t > Domain(1).Max()
545  are trimmed away.
546  */
547  ON_BOOL32 Trim(
548  int dir,
549  const ON_Interval& domain
550  );
551 
552  /*
553  Description:
554  Where possible, analytically extends surface to include domain.
555  Parameters:
556  dir - [in] 0 new Domain(0) will include domain.
557  (the first surface parameter).
558  1 new Domain(1) will include domain.
559  (the second surface parameter).
560  domain - [in] if domain is not included in surface domain,
561  surface will be extended so that its domain includes domain.
562  Will not work if surface is closed in direction dir.
563  Original surface is identical to the restriction of the
564  resulting surface to the original surface domain,
565  Returns:
566  true if successful.
567  */
568  bool Extend(
569  int dir,
570  const ON_Interval& domain
571  );
572 
573 
574  /*
575  Description:
576  Splits (divides) the surface into two parts at the
577  specified parameter.
578  Overrides virtual ON_Surface::Split.
579 
580  Parameters:
581  dir - [in] 0 The surface is split vertically. The "west" side
582  is returned in "west_or_south_side" and the "east"
583  side is returned in "east_or_north_side".
584  1 The surface is split horizontally. The "south" side
585  is returned in "west_or_south_side" and the "north"
586  side is returned in "east_or_north_side".
587  c - [in] value of constant parameter in interval returned
588  by Domain(dir)
589  west_or_south_side - [out] west/south portion of surface returned here
590  east_or_north_side - [out] east/north portion of surface returned here
591 
592  Example:
593 
594  ON_NurbsSurface srf = ...;
595  int dir = 1;
596  ON_NurbsSurface* south_side = 0;
597  ON_NurbsSurface* north_side = 0;
598  srf.Split( dir, srf.Domain(dir).Mid() south_side, north_side );
599 
600  */
601  ON_BOOL32 Split(
602  int dir,
603  double c,
604  ON_Surface*& west_or_south_side,
605  ON_Surface*& east_or_north_side
606  ) const;
607 
608  /*
609  Description:
610  Offset surface.
611  Parameters:
612  offset_distance - [in] offset distance
613  tolerance - [in] Some surfaces do not have an exact offset that
614  can be represented using the same class of surface definition.
615  In that case, the tolerance specifies the desired accuracy.
616  max_deviation - [out] If this parameter is not NULL, the maximum
617  deviation from the returned offset to the true offset is returned
618  here. This deviation is zero except for cases where an exact
619  offset cannot be computed using the same class of surface definition.
620  Returns:
621  Offset surface.
622  */
623  ON_Surface* Offset(
624  double offset_distance,
625  double tolerance,
626  double* max_deviation = NULL
627  ) const;
628 
629  int GetNurbForm( // returns 0: unable to create NURBS representation
630  // with desired accuracy.
631  // 1: success - returned NURBS parameterization
632  // matches the surface's to wthe desired accuracy
633  // 2: success - returned NURBS point locus matches
634  // the surfaces's to the desired accuracy but, on
635  // the interior of the surface's domain, the
636  // surface's parameterization and the NURBS
637  // parameterization may not match to the
638  // desired accuracy.
640  double = 0.0 // tolerance
641  ) const;
642 
643  /////////////////////////////////////////////////////////////////
644  // Interface
645 
646  /*
647  Description:
648  Get the maximum length of a nurb surface's control polygon
649  rows and/or columns
650  Parameters:
651  dir - [in] 0 to get "u" direction length, 1 to get "v"
652  direction length
653  length - [out] maximum length of a polygon "row" in the
654  specified direction
655  Returns:
656  true if successful.
657  */
658  double ControlPolygonLength( int dir ) const;
659 
660 
661  bool IsRational( // true if NURBS surface is rational
662  void
663  ) const;
664 
665  int CVSize( // number of doubles per control vertex
666  void // = IsRational() ? Dim()+1 : Dim()
667  ) const;
668 
669  int Order( // order = degree + 1
670  int // dir 0 = "s", 1 = "t"
671  ) const;
672 
673  int CVCount( // number of control vertices
674  int // dir 0 = "s", 1 = "t"
675  ) const;
676 
677  int CVCount( // total number of control vertices
678  void
679  ) const;
680 
681  int KnotCount( // total number of knots in knot vector
682  int dir // dir 0 = "s", 1 = "t"
683  ) const;
684 
685  /*
686  Description:
687  Expert user function to get a pointer to control vertex
688  memory. If you are not an expert user, please use
689  ON_NurbsSurface::GetCV( ON_3dPoint& ) or
690  ON_NurbsSurface::GetCV( ON_4dPoint& ).
691  Parameters:
692  i - [in] (0 <= i < m_cv_count[0])
693  j - [in] (0 <= j < m_cv_count[1])
694  Returns:
695  Pointer to control vertex.
696  Remarks:
697  If the NURBS surface is rational, the format of the
698  returned array is a homogeneos rational point with
699  length m_dim+1. If the NURBS surface is not rational,
700  the format of the returned array is a nonrational
701  euclidean point with length m_dim.
702  See Also
703  ON_NurbsSurface::CVStyle
704  ON_NurbsSurface::GetCV
705  ON_NurbsSurface::Weight
706  */
707  double* CV(
708  int i,
709  int j
710  ) const;
711 
712  /*
713  Description:
714  Returns the style of control vertices in the m_cv array.
715  Returns:
716  @untitled table
717  ON::not_rational m_is_rat is false
718  ON::homogeneous_rational m_is_rat is true
719  */
720  ON::point_style CVStyle() const;
721 
722  double Weight( // get value of control vertex weight
723  int i, int j // CV index ( 0 <= i <= CVCount(0), 0 <= j <= CVCount(1)
724  ) const;
725 
726  ON_BOOL32 SetWeight( // get value of control vertex weight
727  int i, int j, // CV index ( 0 <= i <= CVCount(0), 0 <= j <= CVCount(1)
728  double weight
729  );
730 
731  ON_BOOL32 SetCV( // set a single control vertex
732  int i, int j, // CV index ( 0 <= i <= CVCount(0), 0 <= j <= CVCount(1)
733  ON::point_style, // style of input point
734  const double* cv // value of control vertex
735  );
736 
737  ON_BOOL32 SetCV( // set a single control vertex
738  int i, int j, // CV index ( 0 <= i <= CVCount(0), 0 <= j <= CVCount(1)
739  const ON_3dPoint& cv// value of control vertex
740  // If NURBS is rational, weight
741  // will be set to 1.
742  );
743 
744  ON_BOOL32 SetCV( // set a single control vertex
745  int i, int j, // CV index ( 0 <= i <= CVCount(0), 0 <= j <= CVCount(1)
746  const ON_4dPoint& cv// value of control vertex
747  );
748 
749  ON_BOOL32 SetCVRow( // Sets CV( *, row_index )
750  int row_index, // row_index >= 0 and < m_cv_count[1]
751  const ON_3dPoint& cv // value of control vertex
752  // If NURBS is rational, weight
753  // will be set to 1.
754  );
755 
756  ON_BOOL32 SetCVRow( // Sets CV( *, row_index )
757  int row_index, // row_index >= 0 and < m_cv_count[1]
758  int v_stride, // v stride
759  const double* v // v[] = values (same dim and is_rat as surface)
760  );
761 
762  ON_BOOL32 SetCVColumn( // Sets CV( col_index, * )
763  int col_index, // col_index >= 0 and < m_cv_count[0]
764  const ON_3dPoint& cv // value of control vertex
765  // If NURBS is rational, weight
766  // will be set to 1.
767  );
768 
769  ON_BOOL32 SetCVColumn( // Sets CV( col_index, * )
770  int col_index, // col_index >= 0 and < m_cv_count[0]
771  int v_stride, // v stride
772  const double* v // v[] = values (same dim and is_rat as surface)
773  );
774 
775  ON_BOOL32 GetCV( // get a single control vertex
776  int i, int j, // CV index ( 0 <= i <= CVCount(0), 0 <= j <= CVCount(1)
777  ON::point_style, // style to use for output point
778  double* cv // array of length >= CVSize()
779  ) const;
780 
781  ON_BOOL32 GetCV( // get a single control vertex
782  int i, int j, // CV index ( 0 <= i <= CVCount(0), 0 <= j <= CVCount(1)
783  ON_3dPoint& cv // gets euclidean cv when NURBS is rational
784  ) const;
785 
786  ON_BOOL32 GetCV( // get a single control vertex
787  int i, int j, // CV index ( 0 <= i <= CVCount(0), 0 <= j <= CVCount(1)
788  ON_4dPoint& cv // gets homogeneous cv
789  ) const;
790 
791  int SetKnot(
792  int dir, // dir 0 = "s", 1 = "t"
793  int knot_index, // knot index ( 0 to KnotCount - 1 )
794  double knot_value // value for knot
795  );
796 
797  double Knot(
798  int dir, // dir 0 = "s", 1 = "t"
799  int knot_index // knot index ( >= 0 and < Order + CV_count - 2 )
800  ) const;
801 
802  int KnotMultiplicity(
803  int dir, // dir 0 = "s", 1 = "t"
804  int knot_index // knot index ( >= 0 and < Order + CV_count - 2 )
805  ) const;
806 
807  const double* Knot( // knot[] array
808  int dir // dir 0 = "s", 1 = "t"
809  ) const;
810 
811  // Description:
812  // Make knot vector a clamped uniform knot vector
813  // based on the current values of m_order and m_cv_count.
814  // Does not change values of control vertices.
815  // Parameters:
816  // dir - [in] 0 = u knots, 1 = v knots
817  // delta - [in] (>0.0) knot spacing.
818  // Returns:
819  // true if successful.
820  // Remarks:
821  // Allocates m_knot[] if it is not big enough.
822  // See Also:
823  // ON_MakeClampedUniformKnotVector
824  bool MakeClampedUniformKnotVector(
825  int dir,
826  double delta = 1.0
827  );
828 
829  // Description:
830  // Make knot vector a periodic uniform knot vector
831  // based on the current values of m_order and m_cv_count.
832  // Does not change values of control vertices.
833  // Parameters:
834  // dir - [in] 0 = u knots, 1 = v knots
835  // delta - [in] (>0.0) knot spacing.
836  // Returns:
837  // true if successful.
838  // Remarks:
839  // Allocates m_knot[] if it is not big enough.
840  // See Also:
841  // ON_MakePeriodicUniformKnotVector
842  bool MakePeriodicUniformKnotVector(
843  int dir,
844  double delta = 1.0
845  );
846 
847 
848  bool IsClamped( // determine if knot vector is clamped
849  int dir, // dir 0 = "s", 1 = "t"
850  int end = 2 // end to check: 0 = start, 1 = end, 2 = start and end
851  ) const;
852 
853  double SuperfluousKnot(
854  int dir, // dir 0 = "s", 1 = "t"
855  int end // 0 = start, 1 = end
856  ) const;
857 
858  double GrevilleAbcissa(
859  int dir, // dir
860  int cv_index // index (0 <= index < CVCount(dir)
861  ) const;
862 
863  bool GetGrevilleAbcissae( // see ON_GetGrevilleAbcissa() for details
864  int dir, // dir
865  double* g // g[cv count]
866  ) const;
867 
868  bool SetClampedGrevilleKnotVector(
869  int dir, // dir
870  int g_stride, // g_stride
871  const double* g // g[], CVCount(dir) many Greville abcissa
872  );
873 
874  bool SetPeriodicGrevilleKnotVector(
875  int dir, // dir
876  int g_stride, // g_stride
877  const double* g // g[], Greville abcissa
878  );
879 
880  bool ZeroCVs(); // zeros all CVs (any weights set to 1);
881 
882  bool ClampEnd(
883  int dir, // dir 0 = "s", 1 = "t"
884  int end // 0 = clamp start, 1 = clamp end, 2 = clamp start and end
885  );
886 
887  bool InsertKnot(
888  int dir, // dir 0 = "s", 1 = "t"
889  double knot_value, // value of knot
890  int knot_multiplicity=1 // multiplicity of knot ( >= 1 and <= degree )
891  );
892 
893  bool MakeRational();
894 
895  bool MakeNonRational();
896 
897  bool IncreaseDegree(
898  int dir, // dir 0 = "s", 1 = "t"
899  int desired_degree // desired_degree
900  );
901 
902  bool ChangeDimension(
903  int desired_dimension // desired_dimension
904  );
905 
906  /*
907  Description:
908  If the surface is closed in direction dir, then modify it so that
909  the seam is at parameter t in the dir direction.
910  Parameters:
911  dir - [in] must be 0 or 1
912  t - [in] dir parameter of seam, must have Domain(dir).Includes(t).
913  The resulting surface domain in the dir direction will start at t.
914  Returns:
915  true if successful.
916  */
917  ON_BOOL32 ChangeSurfaceSeam(
918  int dir,
919  double t
920  );
921 
922 
923  // Creates a tensor product nurbs surface with srf(s,t) = T(A(s),B(t));
924  ON_BOOL32 TensorProduct(
925  const ON_NurbsCurve&, // A
926  const ON_NurbsCurve&, // B
927  ON_TensorProduct& // T
928  );
929 
930  /////////////////////////////////////////////////////////////////
931  // Tools for managing CV and knot memory
932  ON_BOOL32 ReserveKnotCapacity( // returns false if allocation fails
933  // does not change m_order or m_cv_count
934  int dir, // dir 0 = "s", 1 = "t"
935  int knot_array_capacity // minimum capacity of m_knot[] array
936  );
937  ON_BOOL32 ReserveCVCapacity( // returns false if allocation fails
938  // does not change m_order or m_cv_count
939  int cv_array_capacity // minimum capacity of m_cv[] array
940  );
941 
942  /*
943  Description:
944  Convert a NURBS surface bispan into a bezier surface.
945  Parameters:
946  span_index0 - [in] Specifies the "u" span and must satisfy
947  0 <= span_index0 <= m_cv_count[0]-m_order[0]
948  m_knot[0][span_index0+m_order[0]-2] < m_knot[0][span_index0+m_order[0]-1]
949  span_index1 - [in] Specifies the "v" span and must satisfy
950  0 <= span_index1 <= m_cv_count[1]-m_order[1]
951  m_knot[1][span_index1+m_order[1]-2] < m_knot[1][span_index1+m_order[1]-1]
952  bezier_surface - [out] bezier surface returned here
953  Returns:
954  true if successful
955  false if input is not valid
956  */
957  ON_BOOL32 ConvertSpanToBezier(
958  int span_index0,
959  int span_index1,
960  ON_BezierSurface& bezier_surface
961  ) const;
962 
963  /////////////////////////////////////////////////////////////////
964  // Implementation
965 public:
966  // NOTE: These members are left "public" so that expert users may efficiently
967  // create NURBS curves using the default constructor and borrow the
968  // knot and CV arrays from their native NURBS representation.
969  // No technical support will be provided for users who access these
970  // members directly. If you can't get your stuff to work, then use
971  // the constructor with the arguments and the SetKnot() and SetCV()
972  // functions to fill in the arrays.
973 
974  int m_dim; // (>=1)
975 
976  int m_is_rat; // 1 for rational B-splines. (Control vertices
977  // use homogeneous form.)
978  // 0 for non-rational B-splines. (Control
979  // verticies do not have a weight coordinate.)
980 
981  int m_order[2]; // order = degree+1 (>=2)
982 
983  int m_cv_count[2]; // number of control vertices ( >= order )
984 
985  // knot vector memory
986 
987  int m_knot_capacity[2]; // If m_knot_capacity > 0, then m_knot[]
988  // is an array of at least m_knot_capacity
989  // doubles whose memory is managed by the
990  // ON_NurbsSurface class using rhmalloc(),
991  // onrealloc(), and rhfree().
992  // If m_knot_capacity is 0 and m_knot is
993  // not NULL, then m_knot[] is assumed to
994  // be big enough for any requested operation
995  // and m_knot[] is not deleted by the
996  // destructor.
997 
998  double* m_knot[2]; // Knot vector. ( The knot vector has length
999  // m_order+m_cv_count-2. )
1000 
1001  // control vertex net memory
1002 
1003  int m_cv_stride[2]; // The pointer to start of "CV[i]" is
1004  // m_cv + i*m_cv_stride.
1005 
1006  int m_cv_capacity; // If m_cv_capacity > 0, then m_cv[] is an array
1007  // of at least m_cv_capacity doubles whose
1008  // memory is managed by the ON_NurbsSurface
1009  // class using rhmalloc(), onrealloc(), and rhfree().
1010  // If m_cv_capacity is 0 and m_cv is not
1011  // NULL, then m_cv[] is assumed to be big enough
1012  // for any requested operation and m_cv[] is not
1013  // deleted by the destructor.
1014 
1015  double* m_cv; // Control points.
1016  // If m_is_rat is false, then control point is
1017  //
1018  // ( CV(i)[0], ..., CV(i)[m_dim-1] ).
1019  //
1020  // If m_is_rat is true, then the control point
1021  // is stored in HOMOGENEOUS form and is
1022  //
1023  // [ CV(i)[0], ..., CV(i)[m_dim] ].
1024  //
1025 };
1026 
1027 
1028 class PCL_EXPORTS ON_CLASS ON_NurbsCage : public ON_Geometry
1029 {
1030  ON_OBJECT_DECLARE(ON_NurbsCage);
1031 
1032 public:
1033  ON_NurbsCage();
1034 
1035  ON_NurbsCage(
1036  int dim,
1037  bool is_rat,
1038  int order0,
1039  int order1,
1040  int order2,
1041  int cv_count0,
1042  int cv_count1,
1043  int cv_count2
1044  );
1045 
1046  ON_NurbsCage(
1047  const ON_BoundingBox& bbox,
1048  int order0,
1049  int order1,
1050  int order2,
1051  int cv_count0,
1052  int cv_count1,
1053  int cv_count2
1054  );
1055 
1056  ON_NurbsCage(
1057  const ON_3dPoint* box_corners, // array of 8 3d points
1058  int order0,
1059  int order1,
1060  int order2,
1061  int cv_count0,
1062  int cv_count1,
1063  int cv_count2
1064  );
1065 
1066  ON_NurbsCage( const ON_BezierCage& src );
1067 
1068  ~ON_NurbsCage();
1069 
1070  ON_NurbsCage(const ON_NurbsCage& src);
1071 
1072  ON_NurbsCage& operator=(const ON_NurbsCage& src);
1073 
1074  ON_NurbsCage& operator=(const ON_BezierCage& src);
1075 
1076 
1077  /*
1078  Description:
1079  Overrides the pure virtual ON_Object::IsValid function.
1080  Parameters:
1081  text_log - [in] If not null and the object is invalid,
1082  a brief description of the problem
1083  suitable for debugging C++ code
1084  is printed in this log.
1085  Returns:
1086  True if the orders are at least two, dimension is positive,
1087  knot vectors are valid, and the other fields are valid
1088  for the specified orders and dimension.
1089  */
1090  ON_BOOL32 IsValid(
1091  ON_TextLog* text_log = NULL
1092  ) const;
1093 
1094  /*
1095  Description:
1096  Overrides the pure virtual ON_Object::Dump function.
1097  Parameters:
1098  text_log - [in] A listing of the values of the members.
1099  */
1100  void Dump( ON_TextLog& text_log) const;
1101 
1102  /*
1103  Description:
1104  Overrides the pure virtual ON_Object::SizeOf function.
1105  Returns:
1106  An estimate of the amount of memory used by the class
1107  and its members.
1108  */
1109  unsigned int SizeOf() const;
1110 
1111  // virtual ON_Object::DataCRC override
1112  ON__UINT32 DataCRC(ON__UINT32 current_remainder) const;
1113 
1114  /*
1115  Description:
1116  Overrides the pure virtual ON_Object::Read function.
1117  Reads the definition of this class from an
1118  archive previously saved by ON_BezierVolue::Write.
1119  Parameters:
1120  archive - [in] target archive
1121  Returns:
1122  True if successful.
1123  */
1124  ON_BOOL32 Read(
1125  ON_BinaryArchive& archive
1126  );
1127 
1128  /*
1129  Description:
1130  Overrides the pure virtual ON_Object::Write function.
1131  Saves the definition of this class in serial binary
1132  form that can be read by ON_BezierVolue::Read.
1133  Parameters:
1134  archive - [in] target archive
1135  Returns:
1136  True if successful.
1137  */
1138  ON_BOOL32 Write(
1139  ON_BinaryArchive& archive
1140  ) const;
1141 
1142  /*
1143  Description:
1144  Overrides the pure virtual ON_Object::ObjectType function.
1145  Saves the definition of this class in serial binary
1146  form that can be read by ON_BezierVolue::Read.
1147  Parameters:
1148  archive - [in] target archive
1149  Returns:
1150  True if successful.
1151  */
1152  ON::object_type ObjectType() const;
1153 
1154  /*
1155  Description:
1156  Overrides the pure virtual ON_Object::DestroyRuntimeCache function.
1157  Saves the definition of this class in serial binary
1158  form that can be read by ON_BezierVolue::Read.
1159  Parameters:
1160  bDelete - [in] if true, the cache is deleted. If false, the
1161  pointers to the cache are set to zero; this is done when
1162  the cache memory was allocated from a pool that has
1163  been destroyed and an attempt to free the memory would
1164  result in a crash.
1165  Returns:
1166  True if successful.
1167  */
1168  void DestroyRuntimeCache(
1169  bool bDelete = true
1170  );
1171 
1172 
1173  /*
1174  Description:
1175  Overrides virtual ON_Geometry::Dimension function.
1176  Gets a tight bounding box with respect to the coordinate
1177  system specified by the frame parameter.
1178  Parameters:
1179  bbox - [in/out]
1180  bGrowBox - [in] If true, the input bbox is grown to include
1181  this object's bounding box.
1182  frame - [in] if not null, this specifies the coordinate system
1183  frame.
1184  Returns:
1185  True if successful.
1186  */
1187  int Dimension() const;
1188 
1189  /*
1190  Description:
1191  Overrides virtual ON_Geometry::GetBBox function.
1192  Gets the world axis aligned bounding box that contains
1193  the NURBS volume's control points. The NURBS volume
1194  maps the unit cube into this box.
1195  Parameters:
1196  boxmin - [in] array of Dimension() doubles
1197  boxmax - [in] array of Dimension() doubles
1198  bGrowBox = [in] if true and the input is a valid box
1199  then the input box is grown to
1200  include this object's bounding box.
1201  Returns:
1202  true if successful.
1203  */
1204  ON_BOOL32 GetBBox(
1205  double* boxmin,
1206  double* boxmax,
1207  int bGrowBox = false
1208  ) const;
1209 
1210  /*
1211  Description:
1212  Get tight bounding box.
1213  Parameters:
1214  tight_bbox - [in/out] tight bounding box
1215  bGrowBox -[in] (default=false)
1216  If true and the input tight_bbox is valid, then returned
1217  tight_bbox is the union of the input tight_bbox and the
1218  surface's tight bounding box.
1219  xform -[in] (default=NULL)
1220  If not NULL, the tight bounding box of the transformed
1221  surface is calculated. The surface is not modified.
1222  Returns:
1223  True if a valid tight_bbox is returned.
1224  */
1225  bool GetTightBoundingBox(
1226  ON_BoundingBox& tight_bbox,
1227  int bGrowBox = false,
1228  const ON_Xform* xform = 0
1229  ) const;
1230 
1231  /*
1232  Description:
1233  Overrides virtual ON_Geometry::Transform function.
1234  Transforms NURBS volume.
1235  Parameters:
1236  xform - [in]
1237  Returns:
1238  true if successful.
1239  */
1240  ON_BOOL32 Transform(
1241  const ON_Xform& xform
1242  );
1243 
1244  /*
1245  Description:
1246  Overrides virtual ON_Geometry::IsDeformable function.
1247  Returns:
1248  True because a NURBS volume can be accuratly modified
1249  with "squishy" transformations like projections,
1250  shears, an non-uniform scaling.
1251  */
1252  bool IsDeformable() const;
1253 
1254  /*
1255  Description:
1256  Overrides virtual ON_Geometry::MakeDeformable function.
1257  Returns:
1258  True because NURBS volumes are deformable.
1259  */
1260  bool MakeDeformable();
1261 
1262  /*
1263  Returns:
1264  True if the cage is a parallelogram within the tolerance.
1265  This means the cage can be used as a starting point
1266  for cage deformations.
1267  */
1268  bool IsParallelogram(double tolerance) const;
1269 
1270  bool Create(
1271  int dim,
1272  bool is_rat,
1273  int order0,
1274  int order1,
1275  int order2,
1276  int cv_count0,
1277  int cv_count1,
1278  int cv_count2
1279  );
1280 
1281  /*
1282  Description:
1283  Create a Nurbs volume with corners defined by a bounding box.
1284  Parameters:
1285  box_corners - [in] 8 points that define corners of the volume
1286 
1287  7______________6
1288  |\ |\
1289  | \ | \
1290  | \ _____________\
1291  | 4 | 5
1292  | | | |
1293  | | | |
1294  3---|----------2 |
1295  \ | \ |
1296  \ |z \ |
1297  y \ | \ |
1298  \0_____________\1
1299  x
1300 
1301  */
1302  bool Create(
1303  const ON_BoundingBox& bbox,
1304  int order0,
1305  int order1,
1306  int order2,
1307  int cv_count0,
1308  int cv_count1,
1309  int cv_count2
1310  );
1311 
1312  /*
1313  Description:
1314  Create a nurbs volume from a 3d box
1315  Parameters:
1316  box_corners - [in] 8 points that define corners of the volume
1317 
1318  7______________6
1319  |\ |\
1320  | \ | \
1321  | \ _____________\
1322  | 4 | 5
1323  | | | |
1324  | | | |
1325  3---|----------2 |
1326  \ | \ |
1327  \ |t \ |
1328  s \ | \ |
1329  \0_____________\1
1330  r
1331 
1332  */
1333  bool Create(
1334  const ON_3dPoint* box_corners,
1335  int order0,
1336  int order1,
1337  int order2,
1338  int cv_count0,
1339  int cv_count1,
1340  int cv_count2
1341  );
1342 
1343  void Destroy();
1344 
1345  void EmergencyDestroy(); // call if memory used by ON_NurbsCage becomes invalid
1346 
1347  ON_Interval Domain(
1348  int // dir 0 = "r", 1 = "s", 2 = "t"
1349  ) const;
1350 
1351  bool Reverse(
1352  int dir // dir 0 = "r", 1 = "s", 2 = "t"
1353  );
1354 
1355  bool Transpose(
1356  int dir0,
1357  int dir1
1358  );
1359 
1360  bool ClampEnd(
1361  int dir, // dir 0 = "r", 1 = "s", 2 = "t"
1362  int end // 0 = clamp start, 1 = clamp end, 2 = clamp start and end
1363  );
1364 
1365  bool InsertKnot(
1366  int dir, // dir 0 = "r", 1 = "s", 2 = "t"
1367  double knot_value, // value of knot
1368  int knot_multiplicity=1 // multiplicity of knot ( >= 1 and <= degree )
1369  );
1370 
1371  ON_BOOL32 IncreaseDegree(
1372  int dir, // dir 0 = "r", 1 = "s", 2 = "t"
1373  int desired_degree // desired_degree
1374  );
1375 
1376  ON_BOOL32 ChangeDimension(
1377  int desired_dimension // desired_dimension
1378  );
1379 
1380  /*
1381  Description:
1382  Evaluate the NURBS cage
1383  Parameters:
1384  r - [in]
1385  s - [in]
1386  t - [in] (r,s,t) = evaluation parameters
1387  der_count - [in] (>= 0)
1388  v_stride - [in] (>= m_dim)
1389  v - [out] An array of length v_stride*(der_count+1)(der_count+2)*(der_count+3)/6.
1390  The evaluation results are stored in this array.
1391 
1392  P = v[0],...,v[m_dim-1]
1393  Dr = v[v_stride],...
1394  Ds = v[2*v_stride],...
1395  Dt = v[3*v_stride],...
1396 
1397  In general, Dr^i Ds^j Dt^k is returned in v[n],...,v[n+m_dim-1], where
1398 
1399  d = (i+j+k)
1400  n = v_stride*( d*(d+1)*(d+2)/6 + (j+k)*(j+k+1)/2 + k)
1401 
1402  side - [in] specifies the span to use for the evaluation
1403  when r, s, or t is at a knot value.
1404  0 = default
1405  1 = from upper NE quadrant
1406  2 = from upper NW quadrant
1407  3 = from upper SW quadrant
1408  4 = from upper SE quadrant
1409  5 = from lower NE quadrant
1410  6 = from lower NW quadrant
1411  7 = from lower SW quadrant
1412  8 = from lower SE quadrant
1413  hint - [in/out] If a bunch of evaluations will be performed that
1414  tend to occur in the same region, then
1415  hint[3] can be used to speed the search for
1416  the evaluation span. The input value is
1417  used as a search hint and the output value
1418  records the span used for that evaluation.
1419  Example:
1420 
1421  int der_count = 2;
1422  int v_stride = dim;
1423  double v[v_stride*(der_count+1)*(der_count+2)*(der_count+3)/6];
1424  int side = 0;
1425  int hint[3]; hint[0] = 0; hint[1] = 0; hint[2] = 0;
1426  bool rc = cage.Evaluate(r,s,t,der_count,v_stride,v,side,hint);
1427 
1428  ON_3dPoint P = v;
1429 
1430  // first order partial derivatives
1431  ON_3dVector Dr = v + v_stride;
1432  ON_3dVector Ds = v + 2*v_stride;
1433  ON_3dVector Dt = v + 3*v_stride;
1434 
1435  // second order partial derivatives
1436  ON_3dVector Drr = v + 4*v_stride;
1437  ON_3dVector Drs = v + 5*v_stride;
1438  ON_3dVector Drt = v + 6*v_stride;
1439  ON_3dVector Dss = v + 7*v_stride;
1440  ON_3dVector Dst = v + 8*v_stride;
1441  ON_3dVector Dtt = v + 8*v_stride;
1442 
1443  Returns:
1444  True if successful
1445  See Also:
1446  ON_NurbsCage::PointAt
1447  */
1448  bool Evaluate(
1449  double r,
1450  double s,
1451  double t,
1452  int der_count,
1453  int v_stride,
1454  double* v,
1455  int side=0,
1456  int* hint=0
1457  ) const;
1458 
1459  /*
1460  Description:
1461  Evaluates bezer volume map.
1462  Parameters:
1463  rst - [in]
1464  Returns:
1465  Value of the nurbs volume map at (r,s,t).
1466  */
1467  ON_3dPoint PointAt(
1468  double r,
1469  double s,
1470  double t
1471  ) const;
1472 
1473  ON_NurbsSurface* IsoSurface(
1474  int dir,
1475  double c,
1476  ON_NurbsSurface* srf = 0
1477  ) const;
1478 
1479  bool Trim(
1480  int dir,
1481  const ON_Interval& domain
1482  );
1483 
1484  bool Extend(
1485  int dir,
1486  const ON_Interval& domain
1487  );
1488 
1489  /*
1490  Description:
1491  Evaluates bezer volume map.
1492  Parameters:
1493  rst - [in]
1494  Returns:
1495  Value of the nurbs volume map at (rst.x,rst.y,rst.z).
1496  */
1497  ON_3dPoint PointAt(
1498  ON_3dPoint rst
1499  ) const;
1500 
1501  bool IsRational() const;
1502 
1503  int CVSize() const;
1504 
1505  int Order(
1506  int dir // dir 0 = "r", 1 = "s", 2 = "t"
1507  ) const;
1508 
1509  int CVCount( // number of control vertices
1510  int // dir 0 = "r", 1 = "s", 2 = "t"
1511  ) const;
1512 
1513  int CVCount( // total number of control vertices
1514  void
1515  ) const;
1516 
1517  int KnotCount( // total number of knots in knot vector
1518  int dir // dir 0 = "r", 1 = "s", 2 = "t"
1519  ) const;
1520 
1521  int Degree(
1522  int dir
1523  ) const;
1524 
1525 
1526  int SpanCount(
1527  int dir // dir 0 = "r", 1 = "s", 2 = "t"
1528  ) const;
1529 
1530  bool GetSpanVector(
1531  int dir, // dir 0 = "r", 1 = "s", 2 = "t"
1532  double* span_vector
1533  ) const;
1534 
1535  /*
1536  Description:
1537  Expert user function to get a pointer to control vertex
1538  memory. If you are not an expert user, please use
1539  ON_NurbsCage::GetCV( ON_3dPoint& ) or
1540  ON_NurbsCage::GetCV( ON_4dPoint& ).
1541  Parameters:
1542  cv_index0 - [in] (0 <= cv_index0 < m_order[0])
1543  cv_index1 - [in] (0 <= cv_index1 < m_order[1])
1544  Returns:
1545  Pointer to control vertex.
1546  Remarks:
1547  If the Nurbs surface is rational, the format of the
1548  returned array is a homogeneos rational point with
1549  length m_dim+1. If the Nurbs surface is not rational,
1550  the format of the returned array is a nonrational
1551  euclidean point with length m_dim.
1552  See Also
1553  ON_NurbsCage::CVStyle
1554  ON_NurbsCage::GetCV
1555  ON_NurbsCage::Weight
1556  */
1557  double* CV(
1558  int i,
1559  int j,
1560  int k
1561  ) const;
1562 
1563  /*
1564  Description:
1565  Returns the style of control vertices in the m_cv array.
1566  Returns:
1567  @untitled table
1568  ON::not_rational m_is_rat is false
1569  ON::homogeneous_rational m_is_rat is true
1570  */
1571  ON::point_style CVStyle() const;
1572 
1573  double Weight( // get value of control vertex weight
1574  int i,
1575  int j,
1576  int k
1577  ) const;
1578 
1579  bool SetWeight( // get value of control vertex weight
1580  int i,
1581  int j,
1582  int k,
1583  double w
1584  );
1585 
1586  bool SetCV( // set a single control vertex
1587  int i,
1588  int j,
1589  int k,
1590  ON::point_style, // style of input point
1591  const double* // value of control vertex
1592  );
1593 
1594  // set a single control vertex
1595  // If NURBS is rational, weight
1596  // will be set to 1.
1597  bool SetCV(
1598  int i,
1599  int j,
1600  int k,
1601  const ON_3dPoint& point
1602  );
1603 
1604  // set a single control vertex
1605  // value of control vertex
1606  // If NURBS is not rational, euclidean
1607  // location of homogeneous point will
1608  // be used.
1609  bool SetCV(
1610  int i,
1611  int j,
1612  int k,
1613  const ON_4dPoint& hpoint
1614  );
1615 
1616  bool GetCV( // get a single control vertex
1617  int i,
1618  int j,
1619  int k,
1620  ON::point_style, // style to use for output point
1621  double* // array of length >= CVSize()
1622  ) const;
1623 
1624  bool GetCV( // get a single control vertex
1625  int i,
1626  int j,
1627  int k,
1628  ON_3dPoint& // gets euclidean cv when NURBS is rational
1629  ) const;
1630 
1631  bool GetCV( // get a single control vertex
1632  int i,
1633  int j,
1634  int k,
1635  ON_4dPoint& // gets homogeneous cv
1636  ) const;
1637 
1638  /*
1639  Parameters:
1640  dir - [in] 0 = "r", 1 = "s", 2 = "t"
1641  knot_index - [in] 0 <= knot_index < KnotCount(dir)
1642  knot_value - [in]
1643  Returns:
1644  True if dir and knot_index parameters were valid and knot value
1645  was set.
1646  */
1647  bool SetKnot(
1648  int dir,
1649  int knot_index,
1650  double knot_value
1651  );
1652 
1653  /*
1654  Parameters:
1655  dir - [in] 0 = "r", 1 = "s", 2 = "t"
1656  knot_index - [in] 0 <= knot_index < KnotCount(dir)
1657  Returns:
1658  Value of knot or ON_UNSET_VALUE if input parameters are not valid.
1659  */
1660  double Knot(
1661  int dir,
1662  int knot_index
1663  ) const;
1664 
1665  bool ZeroCVs(); // zeros control vertices and, if rational, sets weights to 1
1666 
1667  bool MakeRational();
1668 
1669  bool MakeNonRational();
1670 
1671  bool IsClosed( // true if NURBS cage is closed (either cage has
1672  int // dir // clamped end knots and euclidean location of start
1673  ) const; // CV = euclidean location of end CV, or cage is
1674  // periodic.)
1675 
1676  bool IsPeriodic( // true if NURBS cage is periodic (degree > 1,
1677  int // dir // periodic knot vector, last degree many CVs
1678  ) const; // are duplicates of first degree many CVs.)
1679 
1680  bool IsSingular( // true if cage side is collapsed to a point
1681  int // side of parameter space to test
1682  // 0 = south, 1 = east, 2 = north, 3 = west
1683  ) const;
1684 
1685  double GrevilleAbcissa(
1686  int dir, // dir
1687  int gindex // index (0 <= index < CVCount(dir)
1688  ) const;
1689 
1690  /////////////////////////////////////////////////////////////////
1691  // Tools for managing CV and knot memory
1692 
1693  /*
1694  Description:
1695  cv_capacity - [in] number of doubles to reserve
1696  */
1697  bool ReserveCVCapacity(
1698  int cv_capacity
1699  );
1700 
1701  bool ReserveKnotCapacity(
1702  int dir,
1703  int cv_capacity
1704  );
1705 
1706  /////////////////////////////////////////////////////////////////
1707  // Implementation
1708 public:
1709  // NOTE: These members are left "public" so that expert users may efficiently
1710  // create nurbs curves using the default constructor and borrow the
1711  // knot and CV arrays from their native NURBS representation.
1712  // No technical support will be provided for users who access these
1713  // members directly. If you can't get your stuff to work, then use
1714  // the constructor with the arguments and the SetKnot() and SetCV()
1715  // functions to fill in the arrays.
1716 
1717 
1718  int m_dim;
1719  bool m_is_rat;
1720  int m_order[3];
1721  int m_cv_count[3];
1722  int m_knot_capacity[3];
1723  double* m_knot[3];
1724  int m_cv_stride[3];
1726  double* m_cv;
1727 };
1728 
1729 ON_DECL
1730 bool ON_GetCageXform(
1731  const ON_NurbsCage& cage,
1732  ON_Xform& cage_xform
1733  );
1734 
1735 
1736 class PCL_EXPORTS ON_CLASS ON_MorphControl : public ON_Geometry
1737 {
1738  ON_OBJECT_DECLARE(ON_MorphControl);
1739 
1740 public:
1741  ON_MorphControl();
1742  ~ON_MorphControl();
1743  // C++ default copy construction and operator= work fine.
1744 
1745 
1746  void Destroy();
1747 
1748 
1749  /////////////////////////////////////////////////////////
1750  //
1751  // ON_Object virtual functions
1752  //
1753 
1754  void MemoryRelocate();
1755 
1756  ON_BOOL32 IsValid( ON_TextLog* text_log = NULL ) const;
1757 
1758  void Dump( ON_TextLog& ) const;
1759 
1760  unsigned int SizeOf() const;
1761 
1762  ON_BOOL32 Write(
1763  ON_BinaryArchive& archive
1764  ) const;
1765 
1766  ON_BOOL32 Read(
1767  ON_BinaryArchive& archive
1768  );
1769 
1770  ON::object_type ObjectType() const;
1771 
1772  void DestroyRuntimeCache( bool bDelete = true );
1773 
1774  /////////////////////////////////////////////////////////
1775  //
1776  // ON_Geometry virtual functions
1777  //
1778 
1779  int Dimension() const;
1780 
1781  ON_BOOL32 GetBBox(
1782  double* boxmin,
1783  double* boxmax,
1784  int bGrowBox = false
1785  ) const;
1786 
1787  bool GetTightBoundingBox(
1788  ON_BoundingBox& tight_bbox,
1789  int bGrowBox = false,
1790  const ON_Xform* xform = 0
1791  ) const;
1792 
1793  void ClearBoundingBox();
1794 
1795  ON_BOOL32 Transform(
1796  const ON_Xform& xform
1797  );
1798 
1799  ON_BOOL32 HasBrepForm() const;
1800 
1801  ON_Brep* BrepForm( ON_Brep* brep = NULL ) const;
1802 
1803 
1804  /*
1805  Returns:
1806  True if the target NURBS object is rational
1807  */
1808  bool IsRational() const;
1809 
1810  /*
1811  Description:
1812  Makes the target NURBS object rational.
1813  */
1814  bool MakeRational();
1815 
1816  /*
1817  Description:
1818  Makes the target NURBS object non-rational.
1819  */
1820  bool MakeNonRational();
1821 
1822  /*
1823  Returns:
1824  Number of control points in the target NURBS object.
1825  */
1826  int CVCount() const;
1827 
1828  int CVCount(int dir) const;
1829  int Order(int dir) const;
1830  const double* Knot(int dir) const;
1831  ON_3dex MaxCVIndex() const;
1832  const double* CV(ON_3dex) const;
1833  double Weight(ON_3dex) const;
1834 
1835  /////////////////////////////////////////////////////////
1836  //
1837  // Localizers
1838  //
1839 
1840  /*
1841  Description:
1842  Adds localizer with support near the controling NURBS object.
1843  Parameters:
1844  support_distance - [in] >= 0
1845  If the distance a point to the controls NURBS
1846  curve/surface/cage is less than or equal to support_distance,
1847  then MorphPoint() deformation has 100% effect.
1848 
1849  falloff_distance - [in] > 0
1850  If the distance a point to the controls NURBS
1851  curve/surface/cage is more than support_distance+falloff_distance,
1852  then MorphPoint() deformation does not move the point.
1853  As the distance varies from support_distance to
1854  support_distance+falloff_distance the deformation attenuates
1855  from 100% to 0%.
1856  */
1857  bool AddControlLocalizer(
1858  double support_distance,
1859  double falloff_distance
1860  );
1861 
1862  bool AddSphereLocalizer(
1863  ON_3dPoint center,
1864  double support_distance,
1865  double falloff_distance
1866  );
1867 
1868  bool AddCylinderLocalizer(
1869  ON_Line axis,
1870  double support_distance,
1871  double falloff_distance
1872  );
1873 
1874  bool AddBoxLocalizer(
1875  ON_BoundingBox bbox,
1876  double support_distance,
1877  double falloff_distance
1878  );
1879 
1880  bool AddPlaneLocalizer(
1881  const ON_Plane& plane,
1882  double support_distance,
1883  double falloff_distance
1884  );
1885 
1886  bool AddConvexPolygonLocalizer(
1887  const ON_SimpleArray<ON_Plane>& planes,
1888  double support_distance,
1889  double falloff_distance
1890  );
1891 
1892  /////////////////////////////////////////////////////////
1893  //
1894  //
1895 
1896  // Get a cage_morph that can be passed to Morph functions
1897  bool GetCageMorph( class ON_CageMorph& cage_morph ) const;
1898 
1899  bool IsIdentity( const ON_BoundingBox& bbox ) const;
1900 
1901  int m_varient; // 1= curve, 2 = surface, 3 = cage
1902 
1903  // The value of m_varient determines which nurbs object
1904  // controls the cage
1908 
1911  ON_Interval m_nurbs_surface_domain[2];
1912 
1915 
1916  // Rhino captive object ids
1918 
1919  // Use ON_GetCageXform to set m_cage_xform.
1920 
1921  // Used to localize the deformation
1923 
1924  // ON_SpaceMorphOptions
1928 };
1929 
1930 
1931 class PCL_EXPORTS ON_CLASS ON_CageMorph : public ON_SpaceMorph
1932 {
1933 public:
1934  ON_CageMorph();
1935  ~ON_CageMorph();
1936 
1937  bool IsIdentity( const ON_BoundingBox& bbox ) const;
1938 
1940 };
1941 
1942 
1943 // Description:
1944 // Get an ON_NurbsSurface definition of a quadrilateral.
1945 // Parameters:
1946 // P - [in]
1947 // Q - [in]
1948 // R - [in]
1949 // S - [in] corners in counter clockwise layer
1950 // nurbs_surface - [in] if this pointer is not NULL,
1951 // then this ON_NurbsSurface is used to return
1952 // the quadrilateral.
1953 // Returns:
1954 // An ON_NurbsSurface representation of the quadrilateral.
1955 ON_DECL
1956 ON_NurbsSurface* ON_NurbsSurfaceQuadrilateral(
1957  const ON_3dPoint& P,
1958  const ON_3dPoint& Q,
1959  const ON_3dPoint& R,
1960  const ON_3dPoint& S,
1961  ON_NurbsSurface* nurbs_surface = NULL
1962  );
1963 
1964 #if defined(ON_DLL_TEMPLATE)
1965 // This stuff is here because of a limitation in the way Microsoft
1966 // handles templates and DLLs. See Microsoft's knowledge base
1967 // article ID Q168958 for details.
1968 #pragma warning( push )
1969 #pragma warning( disable : 4231 )
1970 ON_DLL_TEMPLATE template class ON_CLASS ON_ClassArray<ON_NurbsCurve>;
1971 ON_DLL_TEMPLATE template class ON_CLASS ON_ObjectArray<ON_NurbsCurve>;
1972 ON_DLL_TEMPLATE template class ON_CLASS ON_SimpleArray<ON_NurbsCurve*>;
1973 ON_DLL_TEMPLATE template class ON_CLASS ON_ClassArray<ON_NurbsSurface>;
1974 ON_DLL_TEMPLATE template class ON_CLASS ON_ObjectArray<ON_NurbsSurface>;
1975 ON_DLL_TEMPLATE template class ON_CLASS ON_SimpleArray<ON_NurbsSurface*>;
1976 ON_DLL_TEMPLATE template class ON_CLASS ON_ClassArray<ON_NurbsCage>;
1977 ON_DLL_TEMPLATE template class ON_CLASS ON_ObjectArray<ON_NurbsCage>;
1978 ON_DLL_TEMPLATE template class ON_CLASS ON_SimpleArray<ON_NurbsCage*>;
1979 #pragma warning( pop )
1980 #endif
1981 
1982 #endif
const ON_MorphControl * m_control
ON_NurbsSurface m_nurbs_surface0
ON_ClassArray< ON_Localizer > m_localizers
ON_NurbsSurface m_nurbs_surface
ON_NurbsCurve m_nurbs_curve0
#define PCL_EXPORTS
Definition: pcl_macros.h:241
ON_Interval m_nurbs_curve_domain