plotboilerplate 1.20.2 → 1.21.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.esm.js +1985 -1368
- package/dist/index.esm.js.map +1 -1
- package/dist/index.esm.min.js +1 -1
- package/dist/index.esm.min.js.map +1 -1
- package/dist/plotboilerplate.browser.min.js +1 -1
- package/dist/plotboilerplate.browser.min.js.map +1 -1
- package/dist/plotboilerplate.js +1170 -541
- package/dist/plotboilerplate.min.js +1 -1
- package/package.json +1 -1
- package/src/cjs/BezierPath.d.ts +27 -49
- package/src/cjs/BezierPath.js +67 -234
- package/src/cjs/BezierPath.js.map +1 -1
- package/src/cjs/Bounds.d.ts +14 -1
- package/src/cjs/Bounds.js +21 -1
- package/src/cjs/Bounds.js.map +1 -1
- package/src/cjs/CubicBezierCurve.d.ts +70 -1
- package/src/cjs/CubicBezierCurve.js +130 -12
- package/src/cjs/CubicBezierCurve.js.map +1 -1
- package/src/cjs/Line.d.ts +2 -1
- package/src/cjs/Line.js +1 -0
- package/src/cjs/Line.js.map +1 -1
- package/src/cjs/PBText.d.ts +2 -1
- package/src/cjs/PBText.js +10 -9
- package/src/cjs/PBText.js.map +1 -1
- package/src/cjs/PlotBoilerplate.d.ts +4 -13
- package/src/cjs/PlotBoilerplate.js +61 -15
- package/src/cjs/PlotBoilerplate.js.map +1 -1
- package/src/cjs/Polygon.d.ts +35 -1
- package/src/cjs/Polygon.js +87 -1
- package/src/cjs/Polygon.js.map +1 -1
- package/src/cjs/VEllipse.js +1 -1
- package/src/cjs/VEllipse.js.map +1 -1
- package/src/cjs/Vector.d.ts +4 -4
- package/src/cjs/Vector.js +2 -2
- package/src/cjs/Vector.js.map +1 -1
- package/src/cjs/VertTuple.d.ts +2 -1
- package/src/cjs/VertTuple.js +4 -3
- package/src/cjs/VertTuple.js.map +1 -1
- package/src/cjs/Vertex.d.ts +14 -3
- package/src/cjs/Vertex.js +18 -3
- package/src/cjs/Vertex.js.map +1 -1
- package/src/cjs/draw.d.ts +154 -75
- package/src/cjs/draw.js +308 -137
- package/src/cjs/draw.js.map +1 -1
- package/src/cjs/drawgl.d.ts +87 -50
- package/src/cjs/drawgl.js +86 -31
- package/src/cjs/drawgl.js.map +1 -1
- package/src/cjs/drawutilssvg.d.ts +226 -53
- package/src/cjs/drawutilssvg.js +374 -92
- package/src/cjs/drawutilssvg.js.map +1 -1
- package/src/cjs/interfaces/DrawLib.d.ts +157 -79
- package/src/cjs/interfaces/DrawLib.js +6 -0
- package/src/cjs/interfaces/DrawLib.js.map +1 -1
- package/src/cjs/interfaces/core.d.ts +13 -2
- package/src/cjs/interfaces/core.js +1 -0
- package/src/cjs/interfaces/core.js.map +1 -1
- package/src/cjs/utils/creategui.js +16 -10
- package/src/cjs/utils/detectDarkMode.d.ts +10 -0
- package/src/cjs/utils/detectDarkMode.js +32 -0
- package/src/cjs/utils/detectDarkMode.js.map +1 -0
- package/src/esm/BezierPath.d.ts +27 -49
- package/src/esm/BezierPath.js +67 -234
- package/src/esm/BezierPath.js.map +1 -1
- package/src/esm/Bounds.d.ts +14 -1
- package/src/esm/Bounds.js +19 -1
- package/src/esm/Bounds.js.map +1 -1
- package/src/esm/CubicBezierCurve.d.ts +70 -1
- package/src/esm/CubicBezierCurve.js +130 -12
- package/src/esm/CubicBezierCurve.js.map +1 -1
- package/src/esm/Line.d.ts +2 -1
- package/src/esm/Line.js +1 -0
- package/src/esm/Line.js.map +1 -1
- package/src/esm/PBText.d.ts +2 -1
- package/src/esm/PBText.js +10 -9
- package/src/esm/PBText.js.map +1 -1
- package/src/esm/PlotBoilerplate.d.ts +4 -13
- package/src/esm/PlotBoilerplate.js +62 -16
- package/src/esm/PlotBoilerplate.js.map +1 -1
- package/src/esm/Polygon.d.ts +35 -1
- package/src/esm/Polygon.js +85 -1
- package/src/esm/Polygon.js.map +1 -1
- package/src/esm/VEllipse.js +1 -1
- package/src/esm/VEllipse.js.map +1 -1
- package/src/esm/Vector.d.ts +4 -4
- package/src/esm/Vector.js +2 -2
- package/src/esm/Vector.js.map +1 -1
- package/src/esm/VertTuple.d.ts +2 -1
- package/src/esm/VertTuple.js +4 -3
- package/src/esm/VertTuple.js.map +1 -1
- package/src/esm/Vertex.d.ts +14 -3
- package/src/esm/Vertex.js +18 -3
- package/src/esm/Vertex.js.map +1 -1
- package/src/esm/draw.d.ts +154 -75
- package/src/esm/draw.js +304 -135
- package/src/esm/draw.js.map +1 -1
- package/src/esm/drawgl.d.ts +87 -50
- package/src/esm/drawgl.js +86 -31
- package/src/esm/drawgl.js.map +1 -1
- package/src/esm/drawutilssvg.d.ts +226 -53
- package/src/esm/drawutilssvg.js +369 -92
- package/src/esm/drawutilssvg.js.map +1 -1
- package/src/esm/interfaces/DrawLib.d.ts +157 -79
- package/src/esm/interfaces/DrawLib.js +6 -0
- package/src/esm/interfaces/DrawLib.js.map +1 -1
- package/src/esm/interfaces/core.d.ts +13 -2
- package/src/esm/interfaces/core.js +1 -0
- package/src/esm/interfaces/core.js.map +1 -1
- package/src/esm/utils/detectDarkMode.d.ts +10 -0
- package/src/esm/utils/detectDarkMode.js +28 -0
- package/src/esm/utils/detectDarkMode.js.map +1 -0
- package/src/ts/BezierPath.ts +72 -241
- package/src/ts/Bounds.ts +25 -1
- package/src/ts/CubicBezierCurve.ts +139 -12
- package/src/ts/Line.ts +2 -1
- package/src/ts/PBText.ts +10 -9
- package/src/ts/PlotBoilerplate.ts +56 -19
- package/src/ts/Polygon.ts +91 -1
- package/src/ts/VEllipse.ts +2 -2
- package/src/ts/Vector.ts +4 -4
- package/src/ts/VertTuple.ts +4 -3
- package/src/ts/Vertex.ts +20 -4
- package/src/ts/draw.ts +311 -115
- package/src/ts/drawgl.ts +133 -71
- package/src/ts/drawutilssvg.ts +543 -121
- package/src/ts/interfaces/DrawLib.ts +219 -83
- package/src/ts/interfaces/core.ts +14 -2
- package/src/ts/utils/detectDarkMode.ts +30 -0
package/src/ts/BezierPath.ts
CHANGED
|
@@ -23,7 +23,9 @@
|
|
|
23
23
|
* @modified 2022-01-31 Added `BezierPath.getEvenDistributionVertices(number)`.
|
|
24
24
|
* @modified 2022-02-02 Added the `destroy` method.
|
|
25
25
|
* @modified 2022-02-02 Cleared the `toSVGString` function (deprecated). Use `drawutilssvg` instead.
|
|
26
|
-
* @
|
|
26
|
+
* @modified 2023-10-06 Adding the `BezierPath.toPathPoints()` method.
|
|
27
|
+
* @modified 2023-10-07 Adding the `BezierPath.fromCurve(CubicBezierCurve)` static function.
|
|
28
|
+
* @version 2.6.0
|
|
27
29
|
*
|
|
28
30
|
* @file BezierPath
|
|
29
31
|
* @public
|
|
@@ -139,10 +141,13 @@ export class BezierPath implements SVGSerializable {
|
|
|
139
141
|
* @name BezierPath
|
|
140
142
|
* @param {Vertex[]} pathPoints - An array of path vertices (no control points).
|
|
141
143
|
**/
|
|
142
|
-
private constructor(
|
|
144
|
+
private constructor() {
|
|
145
|
+
// pathPoints: Array<Vertex> | undefined | null) {
|
|
143
146
|
this.uid = UIDGenerator.next();
|
|
144
147
|
|
|
145
|
-
if (!pathPoints)
|
|
148
|
+
// if (!pathPoints) {
|
|
149
|
+
// pathPoints = [];
|
|
150
|
+
// }
|
|
146
151
|
this.totalArcLength = 0.0;
|
|
147
152
|
// Set this flag to true if you want the first point and
|
|
148
153
|
// last point of the path to be auto adjusted, too.
|
|
@@ -300,220 +305,6 @@ export class BezierPath implements SVGSerializable {
|
|
|
300
305
|
return this.bezierCurves[curveIndex];
|
|
301
306
|
}
|
|
302
307
|
|
|
303
|
-
/**
|
|
304
|
-
* Remove the end point of this path (which removes the last curve from this path).<br>
|
|
305
|
-
* <br>
|
|
306
|
-
* Please note that this function does never remove the first curve, thus the path
|
|
307
|
-
* cannot be empty after this call.
|
|
308
|
-
*
|
|
309
|
-
* @method removeEndPoint
|
|
310
|
-
* @instance
|
|
311
|
-
* @memberof BezierPath
|
|
312
|
-
* @return {boolean} Indicating if the last curve was removed.
|
|
313
|
-
**/
|
|
314
|
-
/*
|
|
315
|
-
BezierPath.prototype.removeEndPoint = function() {
|
|
316
|
-
if( this.bezierCurves.length <= 1 )
|
|
317
|
-
return false;
|
|
318
|
-
|
|
319
|
-
var newArray = [ this.bezierCurves.length-1 ];
|
|
320
|
-
for( var i = 0; i < this.bezierCurves.length-1; i++ ) {
|
|
321
|
-
newArray[i] = this.bezierCurves[i];
|
|
322
|
-
}
|
|
323
|
-
|
|
324
|
-
// Update arc length
|
|
325
|
-
this.totalArcLength -= this.bezierCurves[ this.bezierCurves.length-1 ].getLength();
|
|
326
|
-
this.bezierCurves = newArray;
|
|
327
|
-
return true;
|
|
328
|
-
}
|
|
329
|
-
*/
|
|
330
|
-
|
|
331
|
-
/**
|
|
332
|
-
* Remove the start point of this path (which removes the first curve from this path).<br>
|
|
333
|
-
* <br>
|
|
334
|
-
* Please note that this function does never remove the last curve, thus the path
|
|
335
|
-
* cannot be empty after this call.<br>
|
|
336
|
-
*
|
|
337
|
-
* @method removeStartPoint
|
|
338
|
-
* @instance
|
|
339
|
-
* @memberof BezierPath
|
|
340
|
-
* @return {boolean} Indicating if the first curve was removed.
|
|
341
|
-
**/
|
|
342
|
-
/*
|
|
343
|
-
BezierPath.prototype.removeStartPoint = function() {
|
|
344
|
-
|
|
345
|
-
if( this.bezierCurves.length <= 1 )
|
|
346
|
-
return false;
|
|
347
|
-
|
|
348
|
-
var newArray = [ this.bezierCurves.length-1 ];
|
|
349
|
-
for( var i = 1; i < this.bezierCurves.length; i++ ) {
|
|
350
|
-
|
|
351
|
-
newArray[i-1] = this.bezierCurves[i];
|
|
352
|
-
|
|
353
|
-
}
|
|
354
|
-
|
|
355
|
-
// Update arc length
|
|
356
|
-
this.totalArcLength -= this.bezierCurves[ 0 ].getLength();
|
|
357
|
-
this.bezierCurves = newArray;
|
|
358
|
-
|
|
359
|
-
return true;
|
|
360
|
-
}
|
|
361
|
-
*/
|
|
362
|
-
|
|
363
|
-
/**
|
|
364
|
-
* Removes a path point inside the path.
|
|
365
|
-
*
|
|
366
|
-
* This function joins the bezier curve at the given index with
|
|
367
|
-
* its predecessor, which means that the start point at the given
|
|
368
|
-
* curve index will be removed.
|
|
369
|
-
*
|
|
370
|
-
* @method joinAt
|
|
371
|
-
* @param {number} curveIndex - The index of the curve to be joined with its predecessor.
|
|
372
|
-
* @instance
|
|
373
|
-
* @memberof BezierPath
|
|
374
|
-
* @return {boolean} True if the passed index indicated an inner vertex and the two curves were joined.
|
|
375
|
-
**/
|
|
376
|
-
/*
|
|
377
|
-
BezierPath.prototype.joinAt = function( curveIndex ) {
|
|
378
|
-
|
|
379
|
-
if( curveIndex < 0 || curveIndex >= this.bezierCurves.length )
|
|
380
|
-
return false;
|
|
381
|
-
|
|
382
|
-
var leftCurve = this.bezierCurves[ curveIndex-1 ];
|
|
383
|
-
var rightCurve = this.bezierCurves[ curveIndex ];
|
|
384
|
-
|
|
385
|
-
// Make the length of the new handle double that long
|
|
386
|
-
var leftControlPoint = leftCurve.getStartControlPoint().clone();
|
|
387
|
-
leftControlPoint.sub( leftCurve.getStartPoint() );
|
|
388
|
-
leftControlPoint.multiplyScalar( 2.0 );
|
|
389
|
-
leftControlPoint.add( leftCurve.getStartPoint() );
|
|
390
|
-
|
|
391
|
-
var rightControlPoint = rightCurve.getEndControlPoint().clone();
|
|
392
|
-
rightControlPoint.sub( rightCurve.getEndPoint() );
|
|
393
|
-
rightControlPoint.multiplyScalar( 2.0 );
|
|
394
|
-
rightControlPoint.add( rightCurve.getEndPoint() );
|
|
395
|
-
|
|
396
|
-
var newCurve = new IKRS.CubicBezierCurve( leftCurve.getStartPoint(),
|
|
397
|
-
rightCurve.getEndPoint(),
|
|
398
|
-
leftControlPoint,
|
|
399
|
-
rightControlPoint
|
|
400
|
-
);
|
|
401
|
-
// Place into array
|
|
402
|
-
var newArray = [ this.bezierCurves.length - 1 ];
|
|
403
|
-
|
|
404
|
-
for( var i = 0; i < curveIndex-1; i++ )
|
|
405
|
-
newArray[ i ] = this.bezierCurves[i];
|
|
406
|
-
|
|
407
|
-
newArray[ curveIndex-1 ] = newCurve;
|
|
408
|
-
|
|
409
|
-
// Shift trailing curves left
|
|
410
|
-
for( var i = curveIndex; i+1 < this.bezierCurves.length; i++ )
|
|
411
|
-
newArray[ i ] = this.bezierCurves[ i+1 ];
|
|
412
|
-
|
|
413
|
-
this.bezierCurves = newArray;
|
|
414
|
-
this.updateArcLengths();
|
|
415
|
-
|
|
416
|
-
return true;
|
|
417
|
-
}
|
|
418
|
-
*/
|
|
419
|
-
|
|
420
|
-
/**
|
|
421
|
-
* Add a new inner curve point to the path.<br>
|
|
422
|
-
* <br>
|
|
423
|
-
* This function splits the bezier curve at the given index and given
|
|
424
|
-
* curve segment index.
|
|
425
|
-
*
|
|
426
|
-
* @method splitAt
|
|
427
|
-
* @param {number} curveIndex - The index of the curve to split.
|
|
428
|
-
* @param {nunber} segmentIndex - The index of the curve segment where the split should be performed.
|
|
429
|
-
* @instance
|
|
430
|
-
* @memberof BezierPath
|
|
431
|
-
* @return {boolean} True if the passed indices were valid and the path was split.
|
|
432
|
-
**/
|
|
433
|
-
/*
|
|
434
|
-
BezierPath.prototype.splitAt = function( curveIndex,
|
|
435
|
-
segmentIndex
|
|
436
|
-
) {
|
|
437
|
-
// Must be a valid curve index
|
|
438
|
-
if( curveIndex < 0 || curveIndex >= this.bezierCurves.length )
|
|
439
|
-
return false;
|
|
440
|
-
|
|
441
|
-
var oldCurve = this.bezierCurves[ curveIndex ];
|
|
442
|
-
|
|
443
|
-
// Segment must be an INNER point!
|
|
444
|
-
// (the outer points are already bezier end/start points!)
|
|
445
|
-
if( segmentIndex < 1 || segmentIndex-1 >= oldCurve.segmentCache.length )
|
|
446
|
-
return false;
|
|
447
|
-
|
|
448
|
-
// Make room for a new curve
|
|
449
|
-
for( var c = this.bezierCurves.length; c > curveIndex; c-- ) {
|
|
450
|
-
// Move one position to the right
|
|
451
|
-
this.bezierCurves[ c ] = this.bezierCurves[ c-1 ];
|
|
452
|
-
}
|
|
453
|
-
|
|
454
|
-
// Accumulate segment lengths
|
|
455
|
-
var u = 0;
|
|
456
|
-
for( var i = 0; i < segmentIndex; i++ )
|
|
457
|
-
u += oldCurve.segmentLengths[i];
|
|
458
|
-
//var tangent = oldCurve.getTangentAt( u );
|
|
459
|
-
var tangent = oldCurve.getTangent( u );
|
|
460
|
-
tangent = tangent.multiplyScalar( 0.25 );
|
|
461
|
-
|
|
462
|
-
var leftEndControlPoint = oldCurve.segmentCache[ segmentIndex ].clone();
|
|
463
|
-
leftEndControlPoint.sub( tangent );
|
|
464
|
-
|
|
465
|
-
var rightStartControlPoint = oldCurve.segmentCache[ segmentIndex ].clone();
|
|
466
|
-
rightStartControlPoint.add( tangent );
|
|
467
|
-
|
|
468
|
-
// Make the old existing handles a quarter that long
|
|
469
|
-
var leftStartControlPoint = oldCurve.getStartControlPoint().clone();
|
|
470
|
-
// move to (0,0)
|
|
471
|
-
leftStartControlPoint.sub( oldCurve.getStartPoint() );
|
|
472
|
-
leftStartControlPoint.multiplyScalar( 0.25 );
|
|
473
|
-
leftStartControlPoint.add( oldCurve.getStartPoint() );
|
|
474
|
-
|
|
475
|
-
var rightEndControlPoint = oldCurve.getEndControlPoint().clone();
|
|
476
|
-
// move to (0,0)
|
|
477
|
-
rightEndControlPoint.sub( oldCurve.getEndPoint() );
|
|
478
|
-
rightEndControlPoint.multiplyScalar( 0.25 );
|
|
479
|
-
rightEndControlPoint.add( oldCurve.getEndPoint() );
|
|
480
|
-
|
|
481
|
-
var newLeft = new CubicBezierCurve( oldCurve.getStartPoint(), // old start point
|
|
482
|
-
oldCurve.segmentCache[ segmentIndex ], // new end point
|
|
483
|
-
leftStartControlPoint, // old start control point
|
|
484
|
-
leftEndControlPoint // new end control point
|
|
485
|
-
);
|
|
486
|
-
var newRight = new CubicBezierCurve( oldCurve.segmentCache[ segmentIndex ], // new start point
|
|
487
|
-
oldCurve.getEndPoint(), // old end point
|
|
488
|
-
rightStartControlPoint, // new start control point
|
|
489
|
-
rightEndControlPoint // old end control point
|
|
490
|
-
);
|
|
491
|
-
|
|
492
|
-
// Insert split curve(s) at free index
|
|
493
|
-
this.bezierCurves[ curveIndex ] = newLeft;
|
|
494
|
-
this.bezierCurves[ curveIndex + 1 ] = newRight;
|
|
495
|
-
|
|
496
|
-
// Update total arc length, even if there is only a very little change!
|
|
497
|
-
this.totalArcLength -= oldCurve.getLength();
|
|
498
|
-
this.totalArcLength += newLeft.getLength();
|
|
499
|
-
this.totalArcLength += newRight.getLength();
|
|
500
|
-
|
|
501
|
-
return true;
|
|
502
|
-
};
|
|
503
|
-
*/
|
|
504
|
-
|
|
505
|
-
/*
|
|
506
|
-
insertVertexAt( t:number ) : void {
|
|
507
|
-
console.log('Inserting vertex at', t );
|
|
508
|
-
// Find the curve index
|
|
509
|
-
var u : number = 0;
|
|
510
|
-
var curveIndex : number = -1;
|
|
511
|
-
var localT : number = 0.0;
|
|
512
|
-
for( var i = 0; curveIndex == -1 && i < this.bezierCurves.length; i++ ) {
|
|
513
|
-
|
|
514
|
-
}
|
|
515
|
-
}; */
|
|
516
|
-
|
|
517
308
|
/**
|
|
518
309
|
* Move the whole bezier path by the given (x,y)-amount.
|
|
519
310
|
*
|
|
@@ -551,24 +342,6 @@ export class BezierPath implements SVGSerializable {
|
|
|
551
342
|
* @return {BezierPath} this for chaining.
|
|
552
343
|
**/
|
|
553
344
|
scale(anchor: Vertex, scaleFactor: number): BezierPath {
|
|
554
|
-
// var scaleFactors : XYCoords = { x : scaleFactor, y : scaleFactor };
|
|
555
|
-
// for (var i = 0; i < this.bezierCurves.length; i++) {
|
|
556
|
-
// var curve = this.bezierCurves[i];
|
|
557
|
-
// curve.getStartPoint().scale(scaleFactor, anchor);
|
|
558
|
-
// curve.getStartControlPoint().scale(scaleFactor, anchor);
|
|
559
|
-
// curve.getEndControlPoint().scale(scaleFactor, anchor);
|
|
560
|
-
// // Do NOT scale the end point here!
|
|
561
|
-
// // Don't forget that the curves are connected and on curve's end point
|
|
562
|
-
// // the the successor's start point (same instance)!
|
|
563
|
-
// }
|
|
564
|
-
|
|
565
|
-
// // Finally move the last end point (was not scaled yet)
|
|
566
|
-
// if (this.bezierCurves.length > 0 && !this.adjustCircular) {
|
|
567
|
-
// this.bezierCurves[this.bezierCurves.length - 1].getEndPoint().scale(scaleFactor, anchor);
|
|
568
|
-
// }
|
|
569
|
-
|
|
570
|
-
// this.updateArcLengths();
|
|
571
|
-
// return this;
|
|
572
345
|
return this.scaleXY({ x: scaleFactor, y: scaleFactor }, anchor);
|
|
573
346
|
}
|
|
574
347
|
|
|
@@ -1132,7 +905,7 @@ export class BezierPath implements SVGSerializable {
|
|
|
1132
905
|
* @return {BezierPath}
|
|
1133
906
|
**/
|
|
1134
907
|
clone(): BezierPath {
|
|
1135
|
-
var path: BezierPath = new BezierPath(undefined);
|
|
908
|
+
var path: BezierPath = new BezierPath(); // undefined);
|
|
1136
909
|
for (var i = 0; i < this.bezierCurves.length; i++) {
|
|
1137
910
|
path.bezierCurves.push(this.bezierCurves[i].clone());
|
|
1138
911
|
// Connect splines
|
|
@@ -1168,6 +941,10 @@ export class BezierPath implements SVGSerializable {
|
|
|
1168
941
|
* This function should invalidate any installed listeners and invalidate this object.
|
|
1169
942
|
* After calling this function the object might not hold valid data any more and
|
|
1170
943
|
* should not be used.
|
|
944
|
+
*
|
|
945
|
+
* @method destroy
|
|
946
|
+
* @instance
|
|
947
|
+
* @memberof BezierPath
|
|
1171
948
|
*/
|
|
1172
949
|
destroy() {
|
|
1173
950
|
for (var i = 0; i < this.bezierCurves.length; i++) {
|
|
@@ -1176,6 +953,42 @@ export class BezierPath implements SVGSerializable {
|
|
|
1176
953
|
this.isDestroyed = true;
|
|
1177
954
|
}
|
|
1178
955
|
|
|
956
|
+
/**
|
|
957
|
+
* Convert this path to an array of path points that can be drawn by the default DrawLib
|
|
958
|
+
* implementations.
|
|
959
|
+
*
|
|
960
|
+
* @method toPathPoints
|
|
961
|
+
* @instance
|
|
962
|
+
* @memberof BezierPath
|
|
963
|
+
* @return {Array<XYCoords>}
|
|
964
|
+
*/
|
|
965
|
+
toPathPoints(): Array<XYCoords> {
|
|
966
|
+
if (this.bezierCurves.length === 0) {
|
|
967
|
+
return [];
|
|
968
|
+
}
|
|
969
|
+
if (this.bezierCurves.length === 1) {
|
|
970
|
+
return [
|
|
971
|
+
this.bezierCurves[0].startPoint,
|
|
972
|
+
this.bezierCurves[0].startControlPoint,
|
|
973
|
+
this.bezierCurves[0].endControlPoint,
|
|
974
|
+
this.bezierCurves[0].endPoint
|
|
975
|
+
];
|
|
976
|
+
}
|
|
977
|
+
const arr: Array<XYCoords> = [];
|
|
978
|
+
arr.push(this.bezierCurves[0].startPoint);
|
|
979
|
+
arr.push(this.bezierCurves[0].startControlPoint);
|
|
980
|
+
for (var i = 1; i < this.bezierCurves.length; i++) {
|
|
981
|
+
arr.push(this.bezierCurves[i - 1].endControlPoint);
|
|
982
|
+
arr.push(this.bezierCurves[i - 1].endPoint);
|
|
983
|
+
arr.push(this.bezierCurves[i].startPoint);
|
|
984
|
+
arr.push(this.bezierCurves[i].startControlPoint);
|
|
985
|
+
}
|
|
986
|
+
arr.push(this.bezierCurves[0].endControlPoint);
|
|
987
|
+
arr.push(this.bezierCurves[0].endPoint);
|
|
988
|
+
|
|
989
|
+
return arr;
|
|
990
|
+
}
|
|
991
|
+
|
|
1179
992
|
/**
|
|
1180
993
|
* Create a JSON string representation of this bézier curve.
|
|
1181
994
|
*
|
|
@@ -1215,6 +1028,21 @@ export class BezierPath implements SVGSerializable {
|
|
|
1215
1028
|
return BezierPath.fromArray(obj);
|
|
1216
1029
|
}
|
|
1217
1030
|
|
|
1031
|
+
/**
|
|
1032
|
+
* Construct a new path with a single curve. Adding more curves is always possible.
|
|
1033
|
+
*
|
|
1034
|
+
* @method fromCurve
|
|
1035
|
+
* @param {CubicBezierCurve} curve - The curve to construct a new path from.
|
|
1036
|
+
* @static
|
|
1037
|
+
* @memberof BezierPath
|
|
1038
|
+
* @return {BezierPath} The constructed bezier path instance.
|
|
1039
|
+
*/
|
|
1040
|
+
static fromCurve(curve: CubicBezierCurve): BezierPath {
|
|
1041
|
+
const path = new BezierPath(); // []);
|
|
1042
|
+
path.addCurve(curve);
|
|
1043
|
+
return path;
|
|
1044
|
+
}
|
|
1045
|
+
|
|
1218
1046
|
/**
|
|
1219
1047
|
* Create a BezierPath instance from the given array.
|
|
1220
1048
|
*
|
|
@@ -1225,16 +1053,19 @@ export class BezierPath implements SVGSerializable {
|
|
|
1225
1053
|
* @memberof BezierPath
|
|
1226
1054
|
* @return {BezierPath} The bezier path instance retrieved from the array data.
|
|
1227
1055
|
**/
|
|
1228
|
-
static fromArray(obj: any) {
|
|
1229
|
-
if (!Array.isArray(obj))
|
|
1056
|
+
static fromArray(obj: any): BezierPath {
|
|
1057
|
+
if (!Array.isArray(obj)) {
|
|
1058
|
+
throw "[BezierPath.fromArray] Passed object must be an array.";
|
|
1059
|
+
}
|
|
1230
1060
|
|
|
1231
1061
|
const arr: Array<any> = obj as Array<Array<Vertex>>; // FORCE?
|
|
1232
1062
|
|
|
1233
|
-
if (arr.length < 1)
|
|
1063
|
+
if (arr.length < 1) {
|
|
1234
1064
|
throw "[BezierPath.fromArray] Passed array must contain at least one bezier curve (has " + arr.length + ").";
|
|
1065
|
+
}
|
|
1235
1066
|
|
|
1236
1067
|
// Create an empty bezier path
|
|
1237
|
-
var bPath: BezierPath = new BezierPath(undefined);
|
|
1068
|
+
var bPath: BezierPath = new BezierPath(); // undefined);
|
|
1238
1069
|
var lastCurve: CubicBezierCurve | null = null;
|
|
1239
1070
|
for (var i = 0; i < arr.length; i++) {
|
|
1240
1071
|
// Convert object (or array?) to bezier curve
|
|
@@ -1352,7 +1183,7 @@ export class BezierPath implements SVGSerializable {
|
|
|
1352
1183
|
*/
|
|
1353
1184
|
static fromReducedList(pointArray: Array<number>, adjustCircular?: boolean): BezierPath {
|
|
1354
1185
|
// Convert to object
|
|
1355
|
-
var bezierPath: BezierPath = new BezierPath(null); // No points yet
|
|
1186
|
+
var bezierPath: BezierPath = new BezierPath(); // null); // No points yet
|
|
1356
1187
|
|
|
1357
1188
|
var startPoint: Vertex = new Vertex();
|
|
1358
1189
|
var startControlPoint: Vertex;
|
package/src/ts/Bounds.ts
CHANGED
|
@@ -8,12 +8,14 @@
|
|
|
8
8
|
* @modified 2022-02-01 Added the `toString` function.
|
|
9
9
|
* @modified 2022-10-09 Added the `fromDimension` function.
|
|
10
10
|
* @modified 2022-11-28 Added the `clone` method.
|
|
11
|
-
* @
|
|
11
|
+
* @modified 2023-09-29 Added the `randomPoint` method.
|
|
12
|
+
* @version 1.7.0
|
|
12
13
|
**/
|
|
13
14
|
|
|
14
15
|
import { Polygon } from "./Polygon";
|
|
15
16
|
import { XYCoords, IBounds, XYDimension } from "./interfaces";
|
|
16
17
|
import { Vertex } from "./Vertex";
|
|
18
|
+
import { VertTuple } from "./VertTuple";
|
|
17
19
|
|
|
18
20
|
/**
|
|
19
21
|
* @classdesc A bounds class with min and max values. Implementing IBounds.
|
|
@@ -97,6 +99,28 @@ export class Bounds implements IBounds, XYDimension {
|
|
|
97
99
|
return new Vertex(this.min.x + (this.max.x - this.min.x) / 2.0, this.min.y + (this.max.y - this.min.y) / 2);
|
|
98
100
|
}
|
|
99
101
|
|
|
102
|
+
/**
|
|
103
|
+
* Generate a random point inside this bounds object. Safe areas at the border to avoid
|
|
104
|
+
* included.
|
|
105
|
+
*
|
|
106
|
+
* @method randomPoint
|
|
107
|
+
* @instance
|
|
108
|
+
* @memberof Bounds
|
|
109
|
+
* @param {horizontalSafeArea} - (optional) The horizonal (left and right) safe area. No vertex will be created here. Can be used as percent in (0.0 ... 0.1) interval.
|
|
110
|
+
* @param {verticalSafeArea} - (optional) The vertical (top and bottom) safe area. No vertex will be created here. Can be used as percent in (0.0 ... 0.1) interval
|
|
111
|
+
* @returns {Vertex} A pseudo random point inside these bounds.
|
|
112
|
+
*/
|
|
113
|
+
randomPoint(horizontalSafeArea: number = 0, verticalSafeArea: number = 0): Vertex {
|
|
114
|
+
// Check if the safe areas are meant as percent
|
|
115
|
+
const absHorizontalSafeArea =
|
|
116
|
+
horizontalSafeArea > 0 && horizontalSafeArea < 1 ? this.width * horizontalSafeArea : horizontalSafeArea;
|
|
117
|
+
const absVerticalSafeArea = verticalSafeArea > 0 && verticalSafeArea < 1 ? this.height * verticalSafeArea : verticalSafeArea;
|
|
118
|
+
return new Vertex(
|
|
119
|
+
this.min.x + absHorizontalSafeArea + Math.random() * (this.width - 2 * absHorizontalSafeArea),
|
|
120
|
+
this.min.y + absVerticalSafeArea + Math.random() * (this.height - 2 * absVerticalSafeArea)
|
|
121
|
+
);
|
|
122
|
+
}
|
|
123
|
+
|
|
100
124
|
/**
|
|
101
125
|
* Convert these bounds to a human readable form.
|
|
102
126
|
*
|
|
@@ -21,7 +21,9 @@
|
|
|
21
21
|
* @modified 2022-02-02 Added the `destroy` method.
|
|
22
22
|
* @modified 2022-02-02 Cleared the `toSVGPathData` function (deprecated). Use `drawutilssvg` instead.
|
|
23
23
|
* @modified 2022-10-17 The `CubicBezierCurve` class now implements the new `PathSegment` interface.
|
|
24
|
-
* @
|
|
24
|
+
* @modified 2023-09-30 Added the function `CubicbezierCurve.getSubCurve(number,number)` – similar to `getSubCurveAt(...)` but with absolute position parameters.
|
|
25
|
+
* @modified 2023-10-07 Added the `trimEnd`, `trimEndAt`, `trimStart`, `trimStartAt` methods.
|
|
26
|
+
* @version 2.8.0
|
|
25
27
|
*
|
|
26
28
|
* @file CubicBezierCurve
|
|
27
29
|
* @public
|
|
@@ -523,6 +525,96 @@ export class CubicBezierCurve implements PathSegment {
|
|
|
523
525
|
return new Vertex(tX, tY);
|
|
524
526
|
}
|
|
525
527
|
|
|
528
|
+
/**
|
|
529
|
+
* Trim off a start section of this curve. The position parameter `uValue` is the absolute position on the
|
|
530
|
+
* curve in `[0...arcLength]`.
|
|
531
|
+
* The remaining curve will be the one in the bounds `[uValue,1]` (so `[0.0,uValue]` is cut off).
|
|
532
|
+
*
|
|
533
|
+
* Note this function just converts the absolute parameter to a relative one and call `trimStartAt`.
|
|
534
|
+
*
|
|
535
|
+
* @method trimStart
|
|
536
|
+
* @instance
|
|
537
|
+
* @memberof CubicBezierCurve
|
|
538
|
+
* @param {number} uValue - The absolute position parameter where to cut off the head curve.
|
|
539
|
+
* @returns {CubicBezierCurve} `this` for chanining.
|
|
540
|
+
*/
|
|
541
|
+
trimStart(uValue: number): CubicBezierCurve {
|
|
542
|
+
return this.trimStartAt(this.convertU2T(uValue));
|
|
543
|
+
}
|
|
544
|
+
|
|
545
|
+
/**
|
|
546
|
+
* Trim off a start section of this curve. The position parameter `t` is the relative position in [0..1].
|
|
547
|
+
* The remaining curve will be the one in the bounds `[uValue,1]` (so `[0.0,uValue]` is cut off).
|
|
548
|
+
*
|
|
549
|
+
* @method trimStartAt
|
|
550
|
+
* @instance
|
|
551
|
+
* @memberof CubicBezierCurve
|
|
552
|
+
* @param {number} t - The relative position parameter where to cut off the head curve.
|
|
553
|
+
* @returns {CubicBezierCurve} `this` for chanining.
|
|
554
|
+
*/
|
|
555
|
+
trimStartAt(t: number): CubicBezierCurve {
|
|
556
|
+
const subCurbePoints = CubicBezierCurve.utils.getSubCurvePointsAt(this, t, 1.0);
|
|
557
|
+
this.startPoint.set(subCurbePoints[0]);
|
|
558
|
+
this.startControlPoint.set(subCurbePoints[2]);
|
|
559
|
+
this.endPoint.set(subCurbePoints[1]);
|
|
560
|
+
this.endControlPoint.set(subCurbePoints[3]);
|
|
561
|
+
this.updateArcLengths();
|
|
562
|
+
return this;
|
|
563
|
+
}
|
|
564
|
+
|
|
565
|
+
/**
|
|
566
|
+
* Trim off the end of this curve. The position parameter `uValue` is the absolute position on the
|
|
567
|
+
* curve in `[0...arcLength]`.
|
|
568
|
+
* The remaining curve will be the one in the bounds `[0,uValue]` (so `[1.0-uValue,1.0]` is cut off).
|
|
569
|
+
*
|
|
570
|
+
* Note this function just converts the absolute parameter to a relative one and call `trimEndAt`.
|
|
571
|
+
*
|
|
572
|
+
* @method trimEnd
|
|
573
|
+
* @instance
|
|
574
|
+
* @memberof CubicBezierCurve
|
|
575
|
+
* @param {number} uValue - The absolute position parameter where to cut off the tail curve.
|
|
576
|
+
* @returns {CubicBezierCurve} `this` for chanining.
|
|
577
|
+
*/
|
|
578
|
+
trimEnd(uValue: number): CubicBezierCurve {
|
|
579
|
+
return this.trimEndAt(this.convertU2T(uValue));
|
|
580
|
+
}
|
|
581
|
+
|
|
582
|
+
/**
|
|
583
|
+
* Trim off the end of this curve. The position parameter `t` is the relative position in [0..1].
|
|
584
|
+
* The remaining curve will be the one in the bounds `[0,t]` (so `[1.0-t,1.0]` is cut off).
|
|
585
|
+
*
|
|
586
|
+
* @method trimEndAt
|
|
587
|
+
* @instance
|
|
588
|
+
* @memberof CubicBezierCurve
|
|
589
|
+
* @param {number} t - The relative position parameter where to cut off the tail curve.
|
|
590
|
+
* @returns {CubicBezierCurve} `this` for chanining.
|
|
591
|
+
*/
|
|
592
|
+
trimEndAt(t: number): CubicBezierCurve {
|
|
593
|
+
const subCurbePoints = CubicBezierCurve.utils.getSubCurvePointsAt(this, 0.0, t);
|
|
594
|
+
this.startPoint.set(subCurbePoints[0]);
|
|
595
|
+
this.startControlPoint.set(subCurbePoints[2]);
|
|
596
|
+
this.endPoint.set(subCurbePoints[1]);
|
|
597
|
+
this.endControlPoint.set(subCurbePoints[3]);
|
|
598
|
+
this.updateArcLengths();
|
|
599
|
+
return this;
|
|
600
|
+
}
|
|
601
|
+
|
|
602
|
+
/**
|
|
603
|
+
* Get a sub curve at the given start end end positions (values on the curve's length, between 0 and curve.arcLength).
|
|
604
|
+
*
|
|
605
|
+
* tStart >= tEnd is allowed, you will get a reversed sub curve then.
|
|
606
|
+
*
|
|
607
|
+
* @method getSubCurve
|
|
608
|
+
* @param {number} tStart – The start position of the desired sub curve (must be in [0..arcLength]).
|
|
609
|
+
* @param {number} tEnd – The end position if the desired cub curve (must be in [0..arcLength]).
|
|
610
|
+
* @instance
|
|
611
|
+
* @memberof CubicBezierCurve
|
|
612
|
+
* @return {CubicBezierCurve} The sub curve as a new curve.
|
|
613
|
+
**/
|
|
614
|
+
getSubCurve(uStart: number, uEnd: number): CubicBezierCurve {
|
|
615
|
+
return this.getSubCurveAt(this.convertU2T(uStart), this.convertU2T(uEnd));
|
|
616
|
+
}
|
|
617
|
+
|
|
526
618
|
/**
|
|
527
619
|
* Get a sub curve at the given start end end offsets (values between 0.0 and 1.0).
|
|
528
620
|
*
|
|
@@ -536,20 +628,22 @@ export class CubicBezierCurve implements PathSegment {
|
|
|
536
628
|
* @return {CubicBezierCurve} The sub curve as a new curve.
|
|
537
629
|
**/
|
|
538
630
|
getSubCurveAt(tStart: number, tEnd: number): CubicBezierCurve {
|
|
539
|
-
const startVec: Vector = new Vector(this.getPointAt(tStart), this.getTangentAt(tStart));
|
|
540
|
-
const endVec: Vector = new Vector(this.getPointAt(tEnd), this.getTangentAt(tEnd).inv());
|
|
631
|
+
// const startVec: Vector = new Vector(this.getPointAt(tStart), this.getTangentAt(tStart));
|
|
632
|
+
// const endVec: Vector = new Vector(this.getPointAt(tEnd), this.getTangentAt(tEnd).inv());
|
|
541
633
|
|
|
542
|
-
// Tangents are relative. Make absolute.
|
|
543
|
-
startVec.b.add(startVec.a);
|
|
544
|
-
endVec.b.add(endVec.a);
|
|
634
|
+
// // Tangents are relative. Make absolute.
|
|
635
|
+
// startVec.b.add(startVec.a);
|
|
636
|
+
// endVec.b.add(endVec.a);
|
|
545
637
|
|
|
546
|
-
// This 'splits' the curve at the given point at t.
|
|
547
|
-
startVec.scale(0.33333333 * (tEnd - tStart));
|
|
548
|
-
endVec.scale(0.33333333 * (tEnd - tStart));
|
|
638
|
+
// // This 'splits' the curve at the given point at t.
|
|
639
|
+
// startVec.scale(0.33333333 * (tEnd - tStart));
|
|
640
|
+
// endVec.scale(0.33333333 * (tEnd - tStart));
|
|
549
641
|
|
|
550
|
-
// Draw the bezier curve
|
|
551
|
-
// pb.draw.cubicBezier( startVec.a, endVec.a, startVec.b, endVec.b, '#8800ff', 2 );
|
|
552
|
-
return new CubicBezierCurve(startVec.a, endVec.a, startVec.b, endVec.b);
|
|
642
|
+
// // Draw the bezier curve
|
|
643
|
+
// // pb.draw.cubicBezier( startVec.a, endVec.a, startVec.b, endVec.b, '#8800ff', 2 );
|
|
644
|
+
// return new CubicBezierCurve(startVec.a, endVec.a, startVec.b, endVec.b);
|
|
645
|
+
const subCurbePoints = CubicBezierCurve.utils.getSubCurvePointsAt(this, tStart, tEnd);
|
|
646
|
+
return new CubicBezierCurve(subCurbePoints[0], subCurbePoints[1], subCurbePoints[2], subCurbePoints[3]);
|
|
553
647
|
}
|
|
554
648
|
|
|
555
649
|
/**
|
|
@@ -813,4 +907,37 @@ export class CubicBezierCurve implements PathSegment {
|
|
|
813
907
|
if (arr.length != 4) throw "Can only build from array with four elements.";
|
|
814
908
|
return new CubicBezierCurve(arr[0], arr[1], arr[2], arr[3]);
|
|
815
909
|
}
|
|
910
|
+
|
|
911
|
+
/**
|
|
912
|
+
* Helper utils.
|
|
913
|
+
*/
|
|
914
|
+
private static utils = {
|
|
915
|
+
/**
|
|
916
|
+
* Get the points of a sub curve at the given start end end offsets (values between 0.0 and 1.0).
|
|
917
|
+
*
|
|
918
|
+
* tStart >= tEnd is allowed, you will get a reversed sub curve then.
|
|
919
|
+
*
|
|
920
|
+
* @method getSubCurvePointsAt
|
|
921
|
+
* @param {CubicBezierCurve} curve – The curve to get the sub curve points from.
|
|
922
|
+
* @param {number} tStart – The start offset of the desired sub curve (must be in [0..1]).
|
|
923
|
+
* @param {number} tEnd – The end offset if the desired cub curve (must be in [0..1]).
|
|
924
|
+
* @instance
|
|
925
|
+
* @memberof CubicBezierCurve
|
|
926
|
+
* @return {CubicBezierCurve} The sub curve as a new curve.
|
|
927
|
+
**/
|
|
928
|
+
getSubCurvePointsAt: (curve: CubicBezierCurve, tStart: number, tEnd: number): [Vertex, Vertex, Vertex, Vertex] => {
|
|
929
|
+
const startVec: Vector = new Vector(curve.getPointAt(tStart), curve.getTangentAt(tStart));
|
|
930
|
+
const endVec: Vector = new Vector(curve.getPointAt(tEnd), curve.getTangentAt(tEnd).inv());
|
|
931
|
+
|
|
932
|
+
// Tangents are relative. Make absolute.
|
|
933
|
+
startVec.b.add(startVec.a);
|
|
934
|
+
endVec.b.add(endVec.a);
|
|
935
|
+
|
|
936
|
+
// This 'splits' the curve at the given point at t.
|
|
937
|
+
startVec.scale(0.33333333 * (tEnd - tStart));
|
|
938
|
+
endVec.scale(0.33333333 * (tEnd - tStart));
|
|
939
|
+
|
|
940
|
+
return [startVec.a, endVec.a, startVec.b, endVec.b];
|
|
941
|
+
}
|
|
942
|
+
};
|
|
816
943
|
}
|
package/src/ts/Line.ts
CHANGED
|
@@ -15,6 +15,7 @@
|
|
|
15
15
|
* @modified 2022-02-02 Added the `destroy` method.
|
|
16
16
|
* @modified 2022-10-09 Changed the actual return value of the `intersection` function to null (was undefined before).
|
|
17
17
|
* @modified 2022-10-17 Adding these methods from the `PathSegment` interface: getStartPoint, getEndPoint, revert.
|
|
18
|
+
* @modified 2023-09-25 Changed param type of `intersection()` from Line to VertTuple.
|
|
18
19
|
* @version 2.3.0
|
|
19
20
|
*
|
|
20
21
|
* @file Line
|
|
@@ -61,7 +62,7 @@ export class Line extends VertTuple<Line> implements SVGSerializable, PathSegmen
|
|
|
61
62
|
* @memberof Line
|
|
62
63
|
**/
|
|
63
64
|
// !!! DO NOT MOVE TO VertTuple
|
|
64
|
-
intersection(line:
|
|
65
|
+
intersection(line: VertTuple<any>): Vertex | null {
|
|
65
66
|
const denominator: number = this.denominator(line);
|
|
66
67
|
if (denominator == 0) {
|
|
67
68
|
return null;
|
package/src/ts/PBText.ts
CHANGED
|
@@ -2,7 +2,8 @@
|
|
|
2
2
|
* @author Ikaros Kappler
|
|
3
3
|
* @date 2021-11-16
|
|
4
4
|
* @modified 2022-02-02 Added the `destroy` method.
|
|
5
|
-
* @
|
|
5
|
+
* @modified 2023-09-25 Fixed a type error in the constructor. Nothing vital.
|
|
6
|
+
* @version 1.1.1
|
|
6
7
|
**/
|
|
7
8
|
|
|
8
9
|
import { UIDGenerator } from "./UIDGenerator";
|
|
@@ -127,14 +128,14 @@ export class PBText implements SVGSerializable, FontOptions {
|
|
|
127
128
|
this.uid = UIDGenerator.next();
|
|
128
129
|
this.text = text;
|
|
129
130
|
this.anchor = anchor ?? new Vertex();
|
|
130
|
-
this.color = options
|
|
131
|
-
this.fontFamily = options
|
|
132
|
-
this.fontSize = options
|
|
133
|
-
this.fontStyle = options
|
|
134
|
-
this.fontWeight = options
|
|
135
|
-
this.lineHeight = options
|
|
136
|
-
this.textAlign = options
|
|
137
|
-
this.rotation = options
|
|
131
|
+
this.color = options?.color;
|
|
132
|
+
this.fontFamily = options?.fontFamily;
|
|
133
|
+
this.fontSize = options?.fontSize;
|
|
134
|
+
this.fontStyle = options?.fontStyle;
|
|
135
|
+
this.fontWeight = options?.fontWeight;
|
|
136
|
+
this.lineHeight = options?.lineHeight;
|
|
137
|
+
this.textAlign = options?.textAlign;
|
|
138
|
+
this.rotation = options?.rotation;
|
|
138
139
|
}
|
|
139
140
|
|
|
140
141
|
/**
|