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 poly curve (composite curve) 20 // 21 //////////////////////////////////////////////////////////////// 22 23 #if !defined(OPENNURBS_POLYCURVE_INC_) 24 #define OPENNURBS_POLYCURVE_INC_ 25 26 /* 27 Description: 28 An ON_PolyCurve is an ON_Curve represented by a sequence of 29 contiguous ON_Curve segments. A valid polycurve is represented 30 by an array m_segment of Count()>=1 curve objects and a strictly 31 increasing array m_t of Count()+1 parameter values. The i-th 32 curve segment, when considered as part of the polycurve, is affinely 33 reparamaterized from m_t[i] to m_t[i+1], i.e., m_segment[i].Domain()[0] 34 is mapped to m_t[i] and m_segment[i].Domain()[1] is mapped to m_t[i+1]. 35 */ 36 class ON_PolyCurve; 37 class ON_CLASS ON_PolyCurve : public ON_Curve 38 { 39 ON_OBJECT_DECLARE(ON_PolyCurve); 40 41 public: 42 // virtual ON_Object::DestroyRuntimeCache override 43 void DestroyRuntimeCache( bool bDelete = true ); 44 45 public: 46 ON_PolyCurve(); 47 ON_PolyCurve( int ); // int = initial capacity - use when a good estimate 48 // of the number of segments is known. 49 ON_PolyCurve(const ON_PolyCurve&); 50 51 void Destroy(); 52 53 virtual ~ON_PolyCurve(); 54 55 void EmergencyDestroy(); // call if memory used by ON_PolyCurve becomes invalid 56 57 ON_PolyCurve& operator=(const ON_PolyCurve&); 58 59 ///////////////////////////////////////////////////////////////// 60 // ON_Object overrides 61 62 // virtual ON_Object::SizeOf override 63 unsigned int SizeOf() const; 64 65 // virtual ON_Object::DataCRC override 66 ON__UINT32 DataCRC(ON__UINT32 current_remainder) const; 67 68 /* 69 Description: 70 Tests an object to see if its data members are correctly 71 initialized. 72 Parameters: 73 text_log - [in] if the object is not valid and text_log 74 is not NULL, then a brief englis description of the 75 reason the object is not valid is appened to the log. 76 The information appended to text_log is suitable for 77 low-level debugging purposes by programmers and is 78 not intended to be useful as a high level user 79 interface tool. 80 Returns: 81 @untitled table 82 true object is valid 83 false object is invalid, uninitialized, etc. 84 Remarks: 85 Overrides virtual ON_Object::IsValid 86 */ 87 ON_BOOL32 IsValid( ON_TextLog* text_log = NULL ) const; 88 89 /* 90 Description: 91 Tests an object to see if its data members are correctly 92 initialized. 93 Parameters: 94 bAllowGaps - [in] 95 If true, gaps are allowed between polycurve segments. 96 If false, gaps are not allowed between polycurve segments. 97 text_log - [in] if the object is not valid and text_log 98 is not NULL, then a brief englis description of the 99 reason the object is not valid is appened to the log. 100 The information appended to text_log is suitable for 101 low-level debugging purposes by programmers and is 102 not intended to be useful as a high level user 103 interface tool. 104 Returns: 105 @untitled table 106 true object is valid 107 false object is invalid, uninitialized, etc. 108 Remarks: 109 Overrides virtual ON_Object::IsValid 110 */ 111 bool IsValid( bool bAllowGaps, ON_TextLog* text_log ) const; 112 113 114 void Dump( ON_TextLog& ) const; // for debugging 115 116 ON_BOOL32 Write( 117 ON_BinaryArchive& // open binary file 118 ) const; 119 120 ON_BOOL32 Read( 121 ON_BinaryArchive& // open binary file 122 ); 123 124 ///////////////////////////////////////////////////////////////// 125 // ON_Geometry overrides 126 127 int Dimension() const; 128 129 ON_BOOL32 GetBBox( // returns true if successful 130 double*, // minimum 131 double*, // maximum 132 ON_BOOL32 = false // true means grow box 133 ) const; 134 135 /* 136 Description: 137 Get tight bounding box. 138 Parameters: 139 tight_bbox - [in/out] tight bounding box 140 bGrowBox -[in] (default=false) 141 If true and the input tight_bbox is valid, then returned 142 tight_bbox is the union of the input tight_bbox and the 143 curve's tight bounding box. 144 xform -[in] (default=NULL) 145 If not NULL, the tight bounding box of the transformed 146 curve is calculated. The curve is not modified. 147 Returns: 148 True if a valid tight_bbox is returned. 149 */ 150 bool GetTightBoundingBox( 151 ON_BoundingBox& tight_bbox, 152 int bGrowBox = false, 153 const ON_Xform* xform = 0 154 ) const; 155 156 ON_BOOL32 Transform( 157 const ON_Xform& 158 ); 159 160 // virtual ON_Geometry::IsDeformable() override 161 bool IsDeformable() const; 162 163 // virtual ON_Geometry::MakeDeformable() override 164 bool MakeDeformable(); 165 166 ON_BOOL32 SwapCoordinates( 167 int, int // indices of coords to swap 168 ); 169 170 // virtual ON_Geometry override 171 bool EvaluatePoint( const class ON_ObjRef& objref, ON_3dPoint& P ) const; 172 173 ///////////////////////////////////////////////////////////////// 174 // ON_Curve overrides 175 176 ON_Curve* DuplicateCurve() const; 177 178 ON_Interval Domain() const; 179 180 // Description: 181 // virtual ON_Curve::SetDomain override. 182 // Set the domain of the curve 183 // Parameters: 184 // t0 - [in] 185 // t1 - [in] new domain will be [t0,t1] 186 // Returns: 187 // true if successful. 188 ON_BOOL32 SetDomain( 189 double t0, 190 double t1 191 ); 192 193 bool ChangeDimension( 194 int desired_dimension 195 ); 196 197 /* 198 Description: 199 If this curve is closed, then modify it so that 200 the start/end point is at curve parameter t. 201 Parameters: 202 t - [in] curve parameter of new start/end point. The 203 returned curves domain will start at t. 204 Returns: 205 true if successful. 206 Remarks: 207 Overrides virtual ON_Curve::ChangeClosedCurveSeam 208 */ 209 ON_BOOL32 ChangeClosedCurveSeam( 210 double t 211 ); 212 213 int SpanCount() const; // number of smooth spans in curve 214 215 ON_BOOL32 GetSpanVector( // span "knots" 216 double* // array of length SpanCount() + 1 217 ) const; // 218 219 int Degree( // returns maximum algebraic degree of any span 220 // ( or a good estimate if curve spans are not algebraic ) 221 ) const; 222 223 ON_BOOL32 IsLinear( // true if curve locus is a line segment between 224 // between specified points 225 double = ON_ZERO_TOLERANCE // tolerance to use when checking linearity 226 ) const; 227 228 /* 229 Description: 230 Several types of ON_Curve can have the form of a polyline including 231 a degree 1 ON_NurbsCurve, an ON_PolylineCurve, and an ON_PolyCurve 232 all of whose segments are some form of polyline. IsPolyline tests 233 a curve to see if it can be represented as a polyline. 234 Parameters: 235 pline_points - [out] if not NULL and true is returned, then the 236 points of the polyline form are returned here. 237 t - [out] if not NULL and true is returned, then the parameters of 238 the polyline points are returned here. 239 Returns: 240 @untitled table 241 0 curve is not some form of a polyline 242 >=2 number of points in polyline form 243 */ 244 int IsPolyline( 245 ON_SimpleArray<ON_3dPoint>* pline_points = NULL, 246 ON_SimpleArray<double>* pline_t = NULL 247 ) const; 248 249 ON_BOOL32 IsArc( // ON_Arc.m_angle > 0 if curve locus is an arc between 250 // specified points 251 const ON_Plane* = NULL, // if not NULL, test is performed in this plane 252 ON_Arc* = NULL, // if not NULL and true is returned, then arc parameters 253 // are filled in 254 double = ON_ZERO_TOLERANCE // tolerance to use when checking 255 ) const; 256 257 ON_BOOL32 IsPlanar( 258 ON_Plane* = NULL, // if not NULL and true is returned, then plane parameters 259 // are filled in 260 double = ON_ZERO_TOLERANCE // tolerance to use when checking 261 ) const; 262 263 ON_BOOL32 IsInPlane( 264 const ON_Plane&, // plane to test 265 double = ON_ZERO_TOLERANCE // tolerance to use when checking 266 ) const; 267 268 ON_BOOL32 IsClosed( // true if curve is closed (either curve has 269 void // clamped end knots and euclidean location of start 270 ) const; // CV = euclidean location of end CV, or curve is 271 // periodic.) 272 273 ON_BOOL32 IsPeriodic( // true if curve is a single periodic segment 274 void 275 ) const; 276 277 /* 278 Description: 279 Search for a derivatitive, tangent, or curvature discontinuity. 280 Parameters: 281 c - [in] type of continity to test for. If ON::C1_continuous 282 t0 - [in] search begins at t0 283 t1 - [in] (t0 < t1) search ends at t1 284 t - [out] if a discontinuity is found, the *t reports the 285 parameter at the discontinuity. 286 hint - [in/out] if GetNextDiscontinuity will be called repeatedly, 287 passing a "hint" with initial value *hint=0 will increase the speed 288 of the search. 289 dtype - [out] if not NULL, *dtype reports the kind of discontinuity 290 found at *t. A value of 1 means the first derivative or unit tangent 291 was discontinuous. A value of 2 means the second derivative or 292 curvature was discontinuous. 293 cos_angle_tolerance - [in] default = cos(1 degree) Used only when 294 c is ON::G1_continuous or ON::G2_continuous. If the cosine 295 of the angle between two tangent vectors 296 is <= cos_angle_tolerance, then a G1 discontinuity is reported. 297 curvature_tolerance - [in] (default = ON_SQRT_EPSILON) Used only when 298 c is ON::G2_continuous or ON::Gsmooth_continuous. 299 ON::G2_continuous: 300 If K0 and K1 are curvatures evaluated 301 from above and below and |K0 - K1| > curvature_tolerance, 302 then a curvature discontinuity is reported. 303 ON::Gsmooth_continuous: 304 If K0 and K1 are curvatures evaluated from above and below 305 and the angle between K0 and K1 is at least twice angle tolerance 306 or ||K0| - |K1|| > (max(|K0|,|K1|) > curvature_tolerance, 307 then a curvature discontinuity is reported. 308 Returns: 309 true if a discontinuity was found on the interior of the interval (t0,t1). 310 Remarks: 311 Overrides ON_Curve::GetNextDiscontinuity. 312 */ 313 bool GetNextDiscontinuity( 314 ON::continuity c, 315 double t0, 316 double t1, 317 double* t, 318 int* hint=NULL, 319 int* dtype=NULL, 320 double cos_angle_tolerance=ON_DEFAULT_ANGLE_TOLERANCE_COSINE, 321 double curvature_tolerance=ON_SQRT_EPSILON 322 ) const; 323 324 /* 325 Description: 326 Test continuity at a curve parameter value. 327 Parameters: 328 c - [in] continuity to test for 329 t - [in] parameter to test 330 hint - [in] evaluation hint 331 point_tolerance - [in] if the distance between two points is 332 greater than point_tolerance, then the curve is not C0. 333 d1_tolerance - [in] if the difference between two first derivatives is 334 greater than d1_tolerance, then the curve is not C1. 335 d2_tolerance - [in] if the difference between two second derivatives is 336 greater than d2_tolerance, then the curve is not C2. 337 cos_angle_tolerance - [in] default = cos(1 degree) Used only when 338 c is ON::G1_continuous or ON::G2_continuous. If the cosine 339 of the angle between two tangent vectors 340 is <= cos_angle_tolerance, then a G1 discontinuity is reported. 341 curvature_tolerance - [in] (default = ON_SQRT_EPSILON) Used only when 342 c is ON::G2_continuous or ON::Gsmooth_continuous. 343 ON::G2_continuous: 344 If K0 and K1 are curvatures evaluated 345 from above and below and |K0 - K1| > curvature_tolerance, 346 then a curvature discontinuity is reported. 347 ON::Gsmooth_continuous: 348 If K0 and K1 are curvatures evaluated from above and below 349 and the angle between K0 and K1 is at least twice angle tolerance 350 or ||K0| - |K1|| > (max(|K0|,|K1|) > curvature_tolerance, 351 then a curvature discontinuity is reported. 352 Returns: 353 true if the curve has at least the c type continuity at the parameter t. 354 Remarks: 355 Overrides ON_Curve::IsContinuous. 356 */ 357 bool IsContinuous( 358 ON::continuity c, 359 double t, 360 int* hint = NULL, 361 double point_tolerance=ON_ZERO_TOLERANCE, 362 double d1_tolerance=ON_ZERO_TOLERANCE, 363 double d2_tolerance=ON_ZERO_TOLERANCE, 364 double cos_angle_tolerance=ON_DEFAULT_ANGLE_TOLERANCE_COSINE, 365 double curvature_tolerance=ON_SQRT_EPSILON 366 ) const; 367 368 ON_BOOL32 Reverse(); // reverse parameterizatrion 369 // Domain changes from [a,b] to [-b,-a] 370 371 /* 372 Description: 373 Force the curve to start at a specified point. 374 Parameters: 375 start_point - [in] 376 Returns: 377 true if successful. 378 Remarks: 379 Some start points cannot be moved. Be sure to check return 380 code. 381 See Also: 382 ON_Curve::SetEndPoint 383 ON_Curve::PointAtStart 384 ON_Curve::PointAtEnd 385 */ 386 // virtual 387 ON_BOOL32 SetStartPoint( 388 ON_3dPoint start_point 389 ); 390 391 /* 392 Description: 393 Force the curve to end at a specified point. 394 Parameters: 395 end_point - [in] 396 Returns: 397 true if successful. 398 Remarks: 399 Some end points cannot be moved. Be sure to check return 400 code. 401 See Also: 402 ON_Curve::SetStartPoint 403 ON_Curve::PointAtStart 404 ON_Curve::PointAtEnd 405 */ 406 //virtual 407 ON_BOOL32 SetEndPoint( 408 ON_3dPoint end_point 409 ); 410 411 ON_BOOL32 Evaluate( // returns false if unable to evaluate 412 double, // evaluation parameter 413 int, // number of derivatives (>=0) 414 int, // array stride (>=Dimension()) 415 double*, // array of length stride*(ndir+1) 416 int = 0, // optional - determines which side to evaluate from 417 // 0 = default 418 // < 0 to evaluate from below, 419 // > 0 to evaluate from above 420 int* = 0 // optional - evaluation hint (int) used to speed 421 // repeated evaluations 422 ) const; 423 424 // Description: 425 // virtual ON_Curve::Trim override. 426 // Removes portions of the curve outside the specified interval. 427 // Parameters: 428 // domain - [in] interval of the curve to keep. Portions of the 429 // curve before curve(domain[0]) and after curve(domain[1]) are 430 // removed. 431 // Returns: 432 // true if successful. 433 ON_BOOL32 Trim( 434 const ON_Interval& domain 435 ); 436 437 // Description: 438 // Where possible, analytically extends curve to include domain. 439 // Parameters: 440 // domain - [in] if domain is not included in curve domain, 441 // curve will be extended so that its domain includes domain. 442 // Will not work if curve is closed. Original curve is identical 443 // to the restriction of the resulting curve to the original curve domain, 444 // Returns: 445 // true if successful. 446 bool Extend( 447 const ON_Interval& domain 448 ); 449 450 // Description: 451 // virtual ON_Curve::Split override. 452 // Divide the curve at the specified parameter. The parameter 453 // must be in the interior of the curve's domain. The pointers 454 // passed to Split must either be NULL or point to an ON_Curve 455 // object of the same of the same type. If the pointer is NULL, 456 // then a curve will be created in Split(). You may pass "this" 457 // as one of the pointers to Split(). 458 // Parameters: 459 // t - [in] parameter in interval Domain(). 460 // left_side - [out] left portion of curve 461 // right_side - [out] right portion of curve 462 // Example: 463 // For example, if crv were an ON_NurbsCurve, then 464 // 465 // ON_NurbsCurve right_side; 466 // crv.Split( crv.Domain().Mid() &crv, &right_side ); 467 // 468 // would split crv at the parametric midpoint, put the left side 469 // in crv, and return the right side in right_side. 470 ON_BOOL32 Split( 471 double t, // t = curve parameter to split curve at 472 ON_Curve*& left_side, // left portion returned here 473 ON_Curve*& right_side // right portion returned here 474 ) const; 475 476 int GetNurbForm( // returns 0: unable to create NURBS representation 477 // with desired accuracy. 478 // 1: success - returned NURBS parameterization 479 // matches the curve's to wthe desired accuracy 480 // 2: success - returned NURBS point locus matches 481 // the curve's to the desired accuracy but, on 482 // the interior of the curve's domain, the 483 // curve's parameterization and the NURBS 484 // parameterization may not match to the 485 // desired accuracy. 486 ON_NurbsCurve&, 487 double = 0.0, 488 const ON_Interval* = NULL // OPTIONAL subdomain of polycurve 489 ) const; 490 491 int HasNurbForm( // returns 0: unable to create NURBS representation 492 // with desired accuracy. 493 // 1: success - returned NURBS parameterization 494 // matches the curve's to wthe desired accuracy 495 // 2: success - returned NURBS point locus matches 496 // the curve's to the desired accuracy but, on 497 // the interior of the curve's domain, the 498 // curve's parameterization and the NURBS 499 // parameterization may not match to the 500 // desired accuracy. 501 ) const; 502 503 // virtual ON_Curve::GetCurveParameterFromNurbFormParameter override 504 ON_BOOL32 GetCurveParameterFromNurbFormParameter( 505 double, // nurbs_t 506 double* // curve_t 507 ) const; 508 509 // virtual ON_Curve::GetNurbFormParameterFromCurveParameter override 510 ON_BOOL32 GetNurbFormParameterFromCurveParameter( 511 double, // curve_t 512 double* // nurbs_t 513 ) const; 514 515 ///////////////////////////////////////////////////////////////// 516 // Interface 517 518 int Count() const; // number of segment curves 519 520 // These operator[] functions return NULL if index is out of range 521 ON_Curve* operator[](int) const; 522 523 /* 524 Description: 525 Returns a pointer to a segment curve. 526 Parameters: 527 segment_index - [in] 0 based index (0 <= segment_index < Count() ) 528 Returns: 529 A pointer to the segment curve. Returns NULL if segment_index < 0 530 or segment_index >= Count(). 531 */ 532 ON_Curve* SegmentCurve( 533 int segment_index 534 ) const; 535 536 /* 537 Description: 538 Converts a polycurve parameter to a segment curve parameter. 539 Parameters: 540 polycurve_parameter - [in] 541 Returns: 542 Segment curve evaluation parameter or ON_UNSET_VALUE if the 543 segment curve parameter cannot be computed. 544 See Also: 545 ON_PolyCurve::PolyCurveParameter 546 */ 547 double SegmentCurveParameter( 548 double polycurve_parameter 549 ) const; 550 551 /* 552 Description: 553 Converts a segment curve parameter to a polycurve parameter. 554 Parameters: 555 segment_index - [in] 556 segmentcurve_parameter - [in] 557 Returns: 558 Polycurve evaluation parameter or ON_UNSET_VALUE if the 559 polycurve curve parameter cannot be computed. 560 See Also: 561 ON_PolyCurve::SegmentCurveParameter 562 */ 563 double PolyCurveParameter( 564 int segment_index, 565 double segmentcurve_parameter 566 ) const; 567 568 /* 569 Description: 570 Returns the polycurve subdomain assigned to a segment curve. 571 Parameters: 572 segment_index - [in] 0 based index (0 <= segment_index < Count() ) 573 Returns: 574 The polycurve subdomain assigned to a segment curve. 575 Returns ([ON_UNSET_VALUE,ON_UNSET_VALUE) if segment_index < 0 576 or segment_index >= Count(). 577 */ 578 ON_Interval SegmentDomain( 579 int segment_index 580 ) const; 581 582 /* 583 Description: 584 Find the segment used for evaluation at polycurve_parameter. 585 Parameters: 586 polycurve_parameter - [in] 587 Returns: 588 index of the segment used for evaluation at polycurve_parameter. 589 If polycurve_parameter < Domain.Min(), then 0 is returned. 590 If polycurve_parameter > Domain.Max(), then Count()-1 is returned. 591 */ 592 int SegmentIndex( 593 double polycurve_parameter 594 ) const; 595 596 /* 597 Description: 598 Find the segments with support on sub_domain. 599 Parameters: 600 sub_domain - [in] increasing interval 601 segment_index0 - [out] 602 segment_index1 - [out] segments with index i where 603 *segment_index0 <= i < *segment_index1 are the segments 604 with support on the sub_domain 605 Returns: 606 number of segments with support on sub_domain. 607 */ 608 int SegmentIndex( 609 ON_Interval sub_domain, 610 int* segment_index0, 611 int* segment_index1 612 ) const; 613 614 ON_Curve* FirstSegmentCurve() const; // returns NULL if count = 0 615 616 ON_Curve* LastSegmentCurve() const; // returns NULL if count = 0 617 618 /* 619 Description: 620 Search the curve for gaps between the sub curve segments. 621 Parameters: 622 segment_index0 - [in] 623 The search for gaps starts at with the comparing 624 the end of segment[segment_index0] and the start of 625 segment[segment_index0+1]. 626 Returns: 627 0: 628 No gaps were found. 629 i > segment_index0: 630 The end of polycuve segment[i-1] is not coincident 631 with the start of polycurve segment[i]. 632 */ 633 int FindNextGap( int segment_index0 ) const; 634 635 /* 636 Description: 637 Determine if there is a gap between the end of 638 segment[segment_index] and the start of segment[segment_index+1]. 639 Parameters: 640 segment_index - [in] 641 >= 0 642 Returns: 643 true: 644 segment_index was valid and there is a gap between 645 the end of segment[segment_index] and the start of 646 segment[segment_index+1]. 647 */ 648 bool HasGapAt( int segment_index ) const; 649 650 // Replace calls to HasGap() with FindNextGap(0) 651 ON_DEPRECATED int HasGap() const; 652 653 /* 654 Description: 655 Modify the one or both locations at the end of 656 segment[gap_index-1] and the start of segment[gap_index] 657 so they are coindicent. 658 Parameters: 659 gap_index - [in] 1 <= gap_index < Count() 660 If the locations at the end of segment[gap_index-1] and 661 the start of segment[gap_index] are not identical, then 662 an attempt is made to modify the segments so these 663 locations are closer. 664 ends_to_modify - [in] 665 0: (suggested) 666 The code will decide what segments to modify. 667 1: 668 modify the end location of segment[gap_index-1] 669 2: 670 modify the start location of segment[gap_index] 671 Returns: 672 True if a modification was performed and HasGap(gap_index-1) 673 returns 0 after the modification. 674 False if no modification was preformed because there 675 was no gap or because one could not be performed. 676 Remarks: 677 Note that passing the return value from FindNextGap() will 678 close the gap found by FindNextGap(). 679 */ 680 bool CloseGap( int gap_index, int segments_to_modify ); 681 682 /* 683 Description: 684 Searches for and closes all gaps that can be found. 685 Returns: 686 Number of gaps that were closed. 687 */ 688 int CloseGaps(); 689 690 void Reserve( int ); // make sure capacity is at least the specified count 691 692 // ON_Curve pointers added with Prepend(), Append(), PrependAndMatch(), AppendANdMatch(),and Insert() are deleted 693 // by ~ON_PolyCurve(). Use ON_CurveProxy( ON_Curve*) if you want 694 // the original curve segment to survive ~ON_PolyCurve(). 695 ON_BOOL32 Prepend( ON_Curve* ); // Prepend curve. 696 ON_BOOL32 Append( ON_Curve* ); // Append curve. 697 ON_BOOL32 Insert( 698 int, // segment_index, 699 ON_Curve* 700 ); 701 702 //PrependAndMatch() and AppendAndMatch() return false if this->IsCLosed() or 703 //this->Count() > 0 and curve is closed 704 ON_BOOL32 PrependAndMatch(ON_Curve*); //Prepend and match end of curve to start of polycurve 705 ON_BOOL32 AppendAndMatch(ON_Curve*); //Append and match start of curve to end of polycurve 706 707 ON_BOOL32 Remove(); // delete last segment and reduce count by 1 708 ON_BOOL32 Remove( int ); // delete specified segment and reduce count by 1 709 710 ////////// 711 // Use the HarvestSegment() function when you want to prevent a 712 // segment from being destroyed by ~ON_PolyCurve(). HarvestSegment() 713 // replaces the polycurve segment with a NULL. Count() and parameter 714 // information remains unchanged. 715 ON_Curve* HarvestSegment( int ); 716 717 /* 718 Returns: 719 True if a curve in the m_segment[] array is an ON_PolyCurve. 720 */ 721 bool IsNested() const; 722 723 /* 724 Description: 725 Same as RemoveNestingEx(). 726 Remarks: 727 RemoveNestingEx was added to avoid breaking the SDK. 728 */ 729 void RemoveNesting(); 730 731 /* 732 Description: 733 Removes the nested of polycurves. The result will have not 734 have an ON_PolyCurve as a segment but will have identical 735 locus and parameterization. 736 Returns: 737 True if a nested polycurve was removed. False 738 if no nested polycurves were found. 739 */ 740 bool RemoveNestingEx(); 741 742 /* 743 Returns: 744 True if the domains of the curves in the m_segment[] array exactly 745 match the domains of the segments specified in the m_t[] array. 746 Put another way, returns true if SegmentDomain(i) = SegmentCurve(i).Domain() 747 for every segment index. 748 */ 749 bool HasSynchronizedSegmentDomains() const; 750 751 /* 752 Description: 753 Sets the domain of the curve int the m_segment[] array to exactly 754 match the domain defined in the m_t[] array. This is not required, 755 but can simplify some coding situations. 756 Returns: 757 True if at least one segment was reparameterized. False if no 758 changes were made. 759 */ 760 bool SynchronizeSegmentDomains(); 761 762 763 764 765 ////////// 766 // Expert user function 767 // Sets the m_segment[index] to crv. 768 void SetSegment(int index, ON_Curve* crv); 769 770 ////////// 771 /* 772 Description: 773 Expert user function to set the m_t[] array. 774 Parameters: 775 t - [in] increasing array of SegmentCount()+1 parameters. 776 Returns 777 True if successful. 778 */ 779 bool SetParameterization( const double* t ); 780 781 /* 782 Description: 783 Lookup a parameter in the m_t array, optionally using a built in snap tolerance to 784 snap a parameter value to an element of m_t. 785 Parameters: 786 t - [in] parameter 787 index -[out] index into m_t such that if the function returns true then t is equal 788 to, or is within tolerance of m_t[index]. 789 if function returns false then the value of index is 790 791 @table 792 condition value of index 793 t<m_t[0] or m_t is empty -1 794 m_t[i] < t < m_t[i+1] i for 0<=i<=m_t.Count()-2 795 t>m_t[ m_t.Count()-1] m_t.Count()-1 796 797 bEnableSnap -[in] if true use tolerance when comparing to m_t values 798 Returns 799 true if the t is exactly equal to, or within tolerance of 800 (only if bEnableSnap==true) m_t[index]. 801 */ 802 bool ParameterSearch(double t, int& index, bool bEnableSnap) const; 803 804 /* 805 Returns: 806 Reference to m_segment. 807 */ 808 const ON_CurveArray& SegmentCurves() const; 809 810 /* 811 Returns: 812 Reference to m_t. 813 */ 814 const ON_SimpleArray<double>& SegmentParameters() const; 815 816 ///////////////////////////////////////////////////////////////// 817 // Implementation 818 private: 819 // The curves in this array are deleted by ~ON_PolyCurve(). 820 // Use ON_CurveProxy classes if you don't want ON_PolyCurve() 821 // to destroy the curve. 822 823 ON_CurveArray m_segment; // array of pointers to curves 824 // all have the same dimension 825 // and are contiguous to tolerance 826 827 ON_SimpleArray<double> m_t; // ON_PolyCurve segment parameterizations 828 }; 829 830 831 #endif 832