@thednp/dommatrix 3.0.6 → 3.1.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/dommatrix.js CHANGED
@@ -2,8 +2,8 @@
2
2
  typeof exports === "object" && typeof module !== "undefined" ? module.exports = factory() : typeof define === "function" && define.amd ? define([], factory) : (global = typeof globalThis !== "undefined" ? globalThis : global || self, global.CSSMatrix = factory());
3
3
  })(this, function() {
4
4
  //#region src/index.ts
5
- /** A model for JSONMatrix */
6
- const JSON_MATRIX = {
5
+ /** The property names of a JSONMatrix, used for compatibility checks */
6
+ const JSON_KEYS = Object.keys({
7
7
  a: 1,
8
8
  b: 0,
9
9
  c: 0,
@@ -28,14 +28,14 @@
28
28
  m44: 1,
29
29
  is2D: true,
30
30
  isIdentity: true
31
- };
31
+ });
32
32
  /** Checks if an array is compatible with CSSMatrix */
33
33
  const isCompatibleArray = (array) => {
34
34
  return (array instanceof Float64Array || array instanceof Float32Array || Array.isArray(array) && array.every((x) => typeof x === "number")) && [6, 16].some((x) => array.length === x);
35
35
  };
36
36
  /** Checks if an object is compatible with CSSMatrix */
37
37
  const isCompatibleObject = (object) => {
38
- return typeof DOMMatrix !== "undefined" && object instanceof DOMMatrix || object instanceof CSSMatrix || typeof object === "object" && Object.keys(JSON_MATRIX).every((k) => object && k in object);
38
+ return typeof DOMMatrix !== "undefined" && object instanceof DOMMatrix || object instanceof CSSMatrix || typeof object === "object" && JSON_KEYS.every((k) => object && k in object);
39
39
  };
40
40
  /**
41
41
  * Creates a new mutable `CSSMatrix` instance given an array of 16/6 floating point values.
@@ -48,49 +48,62 @@
48
48
  * @return the resulted matrix.
49
49
  */
50
50
  const fromArray = (array) => {
51
- const m = new CSSMatrix();
52
- const a = Array.from(array);
53
- if (!isCompatibleArray(a)) throw TypeError(`CSSMatrix: "${a.join(",")}" must be an array with 6/16 numbers.`);
51
+ if (!isCompatibleArray(array)) throw TypeError(`CSSMatrix: "${Array.from(array).join(",")}" must be an array with 6/16 numbers.`);
54
52
  // istanbul ignore else @preserve
55
- if (a.length === 16) {
56
- const [m11, m12, m13, m14, m21, m22, m23, m24, m31, m32, m33, m34, m41, m42, m43, m44] = a;
57
- m.m11 = m11;
58
- m.a = m11;
59
- m.m21 = m21;
60
- m.c = m21;
61
- m.m31 = m31;
62
- m.m41 = m41;
63
- m.e = m41;
64
- m.m12 = m12;
65
- m.b = m12;
66
- m.m22 = m22;
67
- m.d = m22;
68
- m.m32 = m32;
69
- m.m42 = m42;
70
- m.f = m42;
71
- m.m13 = m13;
72
- m.m23 = m23;
73
- m.m33 = m33;
74
- m.m43 = m43;
75
- m.m14 = m14;
76
- m.m24 = m24;
77
- m.m34 = m34;
78
- m.m44 = m44;
79
- } else if (a.length === 6) {
80
- const [M11, M12, M21, M22, M41, M42] = a;
81
- m.m11 = M11;
82
- m.a = M11;
83
- m.m12 = M12;
84
- m.b = M12;
85
- m.m21 = M21;
86
- m.c = M21;
87
- m.m22 = M22;
88
- m.d = M22;
89
- m.m41 = M41;
90
- m.e = M41;
91
- m.m42 = M42;
92
- m.f = M42;
53
+ if (array.length === 16) {
54
+ const [m11, m12, m13, m14, m21, m22, m23, m24, m31, m32, m33, m34, m41, m42, m43, m44] = array;
55
+ return fromValues(m11, m12, m13, m14, m21, m22, m23, m24, m31, m32, m33, m34, m41, m42, m43, m44);
93
56
  }
57
+ const [M11, M12, M21, M22, M41, M42] = array;
58
+ return fromValues(M11, M12, 0, 0, M21, M22, 0, 0, 0, 0, 1, 0, M41, M42, 0, 1);
59
+ };
60
+ /**
61
+ * Creates a new mutable `CSSMatrix` instance given the 16 values of the matrix.
62
+ * This internal helper skips the validation and intermediate array steps of
63
+ * `fromArray` and is used by the fast paths of the library.
64
+ *
65
+ * @param m11 the `m11` value.
66
+ * @param m12 the `m12` value.
67
+ * @param m13 the `m13` value.
68
+ * @param m14 the `m14` value.
69
+ * @param m21 the `m21` value.
70
+ * @param m22 the `m22` value.
71
+ * @param m23 the `m23` value.
72
+ * @param m24 the `m24` value.
73
+ * @param m31 the `m31` value.
74
+ * @param m32 the `m32` value.
75
+ * @param m33 the `m33` value.
76
+ * @param m34 the `m34` value.
77
+ * @param m41 the `m41` value.
78
+ * @param m42 the `m42` value.
79
+ * @param m43 the `m43` value.
80
+ * @param m44 the `m44` value.
81
+ * @return the resulted matrix.
82
+ */
83
+ const fromValues = (m11, m12, m13, m14, m21, m22, m23, m24, m31, m32, m33, m34, m41, m42, m43, m44) => {
84
+ const m = new CSSMatrix();
85
+ m.m11 = m11;
86
+ m.a = m11;
87
+ m.m21 = m21;
88
+ m.c = m21;
89
+ m.m31 = m31;
90
+ m.m41 = m41;
91
+ m.e = m41;
92
+ m.m12 = m12;
93
+ m.b = m12;
94
+ m.m22 = m22;
95
+ m.d = m22;
96
+ m.m32 = m32;
97
+ m.m42 = m42;
98
+ m.f = m42;
99
+ m.m13 = m13;
100
+ m.m23 = m23;
101
+ m.m33 = m33;
102
+ m.m43 = m43;
103
+ m.m14 = m14;
104
+ m.m24 = m24;
105
+ m.m34 = m34;
106
+ m.m44 = m44;
94
107
  return m;
95
108
  };
96
109
  /**
@@ -101,24 +114,7 @@
101
114
  * @return the resulted matrix.
102
115
  */
103
116
  const fromMatrix = (m) => {
104
- if (isCompatibleObject(m)) return fromArray([
105
- m.m11,
106
- m.m12,
107
- m.m13,
108
- m.m14,
109
- m.m21,
110
- m.m22,
111
- m.m23,
112
- m.m24,
113
- m.m31,
114
- m.m32,
115
- m.m33,
116
- m.m34,
117
- m.m41,
118
- m.m42,
119
- m.m43,
120
- m.m44
121
- ]);
117
+ if (isCompatibleObject(m)) return fromValues(m.m11, m.m12, m.m13, m.m14, m.m21, m.m22, m.m23, m.m24, m.m31, m.m32, m.m33, m.m34, m.m41, m.m42, m.m43, m.m44);
122
118
  throw TypeError(`CSSMatrix: "${JSON.stringify(m)}" is not a DOMMatrix / CSSMatrix / JSON compatible object.`);
123
119
  };
124
120
  /**
@@ -139,8 +135,13 @@
139
135
  const str = String(source).replace(/\s/g, "");
140
136
  const m = new CSSMatrix();
141
137
  const invalidStringError = `CSSMatrix: invalid transform string "${source}"`;
142
- str.split(")").filter((f) => f).forEach((tf) => {
143
- const [prop, value] = tf.split("(");
138
+ const transformFn = /([\w-]+)\(([^)]*)\)/g;
139
+ let consumed = 0;
140
+ let match;
141
+ while (match = transformFn.exec(str)) {
142
+ const prop = match[1];
143
+ const value = match[2];
144
+ consumed += match[0].length;
144
145
  if (!value) throw TypeError(invalidStringError);
145
146
  const components = value.split(",").map((n) => n.includes("rad") ? parseFloat(n) * (180 / Math.PI) : parseFloat(n));
146
147
  const [x, y, z, a] = components;
@@ -192,7 +193,8 @@
192
193
  m[method](...axeValues);
193
194
  }
194
195
  else throw TypeError(invalidStringError);
195
- });
196
+ }
197
+ if (consumed !== str.length) throw TypeError(invalidStringError);
196
198
  return m;
197
199
  };
198
200
  /**
@@ -410,14 +412,16 @@
410
412
  return Skew(0, angle);
411
413
  };
412
414
  /**
413
- * Creates a new `CSSMatrix` resulted from the multiplication of two matrixes
414
- * and returns it. Both matrixes are not changed.
415
+ * Computes the multiplication of two matrixes and stores the result into the
416
+ * third matrix argument, which is also returned. Both source matrixes are
417
+ * not changed.
415
418
  *
416
419
  * @param m1 the first matrix.
417
420
  * @param m2 the second matrix.
421
+ * @param m the matrix to store the result into.
418
422
  * @return the resulted matrix.
419
423
  */
420
- const Multiply = (m1, m2) => {
424
+ const multiplyInto = (m1, m2, m) => {
421
425
  const m11 = m2.m11 * m1.m11 + m2.m12 * m1.m21 + m2.m13 * m1.m31 + m2.m14 * m1.m41;
422
426
  const m12 = m2.m11 * m1.m12 + m2.m12 * m1.m22 + m2.m13 * m1.m32 + m2.m14 * m1.m42;
423
427
  const m13 = m2.m11 * m1.m13 + m2.m12 * m1.m23 + m2.m13 * m1.m33 + m2.m14 * m1.m43;
@@ -434,24 +438,40 @@
434
438
  const m42 = m2.m41 * m1.m12 + m2.m42 * m1.m22 + m2.m43 * m1.m32 + m2.m44 * m1.m42;
435
439
  const m43 = m2.m41 * m1.m13 + m2.m42 * m1.m23 + m2.m43 * m1.m33 + m2.m44 * m1.m43;
436
440
  const m44 = m2.m41 * m1.m14 + m2.m42 * m1.m24 + m2.m43 * m1.m34 + m2.m44 * m1.m44;
437
- return fromArray([
438
- m11,
439
- m12,
440
- m13,
441
- m14,
442
- m21,
443
- m22,
444
- m23,
445
- m24,
446
- m31,
447
- m32,
448
- m33,
449
- m34,
450
- m41,
451
- m42,
452
- m43,
453
- m44
454
- ]);
441
+ m.m11 = m11;
442
+ m.a = m11;
443
+ m.m21 = m21;
444
+ m.c = m21;
445
+ m.m31 = m31;
446
+ m.m41 = m41;
447
+ m.e = m41;
448
+ m.m12 = m12;
449
+ m.b = m12;
450
+ m.m22 = m22;
451
+ m.d = m22;
452
+ m.m32 = m32;
453
+ m.m42 = m42;
454
+ m.f = m42;
455
+ m.m13 = m13;
456
+ m.m23 = m23;
457
+ m.m33 = m33;
458
+ m.m43 = m43;
459
+ m.m14 = m14;
460
+ m.m24 = m24;
461
+ m.m34 = m34;
462
+ m.m44 = m44;
463
+ return m;
464
+ };
465
+ /**
466
+ * Creates a new `CSSMatrix` resulted from the multiplication of two matrixes
467
+ * and returns it. Both matrixes are not changed.
468
+ *
469
+ * @param m1 the first matrix.
470
+ * @param m2 the second matrix.
471
+ * @return the resulted matrix.
472
+ */
473
+ const Multiply = (m1, m2) => {
474
+ return multiplyInto(m1, m2, new CSSMatrix());
455
475
  };
456
476
  /**
457
477
  * Creates and returns a new `DOMMatrix` compatible instance
@@ -500,6 +520,11 @@
500
520
  * * a 6/16 elements *Array*.
501
521
  */
502
522
  constructor(init) {
523
+ if (init) {
524
+ if (typeof init === "string" && init.length && init !== "none") return fromString(init);
525
+ if (Array.isArray(init) || init instanceof Float64Array || init instanceof Float32Array) return fromArray(init);
526
+ if (typeof init === "object") return fromMatrix(init);
527
+ }
503
528
  this.a = 1;
504
529
  this.b = 0;
505
530
  this.c = 0;
@@ -522,7 +547,6 @@
522
547
  this.m42 = 0;
523
548
  this.m43 = 0;
524
549
  this.m44 = 1;
525
- if (init) return this.setMatrixValue(init);
526
550
  return this;
527
551
  }
528
552
  /**
@@ -573,7 +597,31 @@
573
597
  * @return an *Array* representation of the matrix
574
598
  */
575
599
  toFloat32Array(is2D) {
576
- return Float32Array.from(toArray(this, is2D));
600
+ return is2D ? new Float32Array([
601
+ this.a,
602
+ this.b,
603
+ this.c,
604
+ this.d,
605
+ this.e,
606
+ this.f
607
+ ]) : new Float32Array([
608
+ this.m11,
609
+ this.m12,
610
+ this.m13,
611
+ this.m14,
612
+ this.m21,
613
+ this.m22,
614
+ this.m23,
615
+ this.m24,
616
+ this.m31,
617
+ this.m32,
618
+ this.m33,
619
+ this.m34,
620
+ this.m41,
621
+ this.m42,
622
+ this.m43,
623
+ this.m44
624
+ ]);
577
625
  }
578
626
  /**
579
627
  * Returns a *Float64Array* containing elements which comprise the matrix.
@@ -584,7 +632,31 @@
584
632
  * @return an *Array* representation of the matrix
585
633
  */
586
634
  toFloat64Array(is2D) {
587
- return Float64Array.from(toArray(this, is2D));
635
+ return is2D ? new Float64Array([
636
+ this.a,
637
+ this.b,
638
+ this.c,
639
+ this.d,
640
+ this.e,
641
+ this.f
642
+ ]) : new Float64Array([
643
+ this.m11,
644
+ this.m12,
645
+ this.m13,
646
+ this.m14,
647
+ this.m21,
648
+ this.m22,
649
+ this.m23,
650
+ this.m24,
651
+ this.m31,
652
+ this.m32,
653
+ this.m33,
654
+ this.m34,
655
+ this.m41,
656
+ this.m42,
657
+ this.m43,
658
+ this.m44
659
+ ]);
588
660
  }
589
661
  /**
590
662
  * Creates and returns a string representation of the matrix in `CSS` matrix syntax,
@@ -613,7 +685,28 @@
613
685
  toJSON() {
614
686
  const { is2D, isIdentity } = this;
615
687
  return {
616
- ...this,
688
+ a: this.a,
689
+ b: this.b,
690
+ c: this.c,
691
+ d: this.d,
692
+ e: this.e,
693
+ f: this.f,
694
+ m11: this.m11,
695
+ m12: this.m12,
696
+ m13: this.m13,
697
+ m14: this.m14,
698
+ m21: this.m21,
699
+ m22: this.m22,
700
+ m23: this.m23,
701
+ m24: this.m24,
702
+ m31: this.m31,
703
+ m32: this.m32,
704
+ m33: this.m33,
705
+ m34: this.m34,
706
+ m41: this.m41,
707
+ m42: this.m42,
708
+ m43: this.m43,
709
+ m44: this.m44,
617
710
  is2D,
618
711
  isIdentity
619
712
  };
@@ -641,7 +734,14 @@
641
734
  * @return The resulted matrix
642
735
  */
643
736
  translate(x, y, z) {
644
- return this.multiply(Translate(x, y ?? 0, z ?? 0));
737
+ const ty = y ?? 0;
738
+ const tz = z ?? 0;
739
+ const { m11, m12, m13, m14, m21, m22, m23, m24, m31, m32, m33, m34, m41, m42, m43, m44 } = this;
740
+ const n41 = x * m11 + ty * m21 + tz * m31 + m41;
741
+ const n42 = x * m12 + ty * m22 + tz * m32 + m42;
742
+ const n43 = x * m13 + ty * m23 + tz * m33 + m43;
743
+ const n44 = x * m14 + ty * m24 + tz * m34 + m44;
744
+ return fromValues(m11, m12, m13, m14, m21, m22, m23, m24, m31, m32, m33, m34, n41, n42, n43, n44);
645
745
  }
646
746
  /**
647
747
  * The scale method returns a new matrix which is this matrix post multiplied by
@@ -655,7 +755,10 @@
655
755
  * @return The resulted matrix
656
756
  */
657
757
  scale(x, y, z) {
658
- return this.multiply(Scale(x, y ?? x, z ?? 1));
758
+ const sy = y ?? x;
759
+ const sz = z ?? 1;
760
+ const { m41, m42, m43, m44 } = this;
761
+ return fromValues(this.m11 * x, this.m12 * x, this.m13 * x, this.m14 * x, this.m21 * sy, this.m22 * sy, this.m23 * sy, this.m24 * sy, this.m31 * sz, this.m32 * sz, this.m33 * sz, this.m34 * sz, m41, m42, m43, m44);
659
762
  }
660
763
  /**
661
764
  * The rotate method returns a new matrix which is this matrix post multiplied
@@ -710,7 +813,7 @@
710
813
  * @return The resulted matrix
711
814
  */
712
815
  skewX(angle) {
713
- return this.multiply(SkewX(angle));
816
+ return this.skew(angle, 0);
714
817
  }
715
818
  /**
716
819
  * Specifies a skew transformation along the `y-axis` by the given angle.
@@ -720,7 +823,7 @@
720
823
  * @return The resulted matrix
721
824
  */
722
825
  skewY(angle) {
723
- return this.multiply(SkewY(angle));
826
+ return this.skew(0, angle);
724
827
  }
725
828
  /**
726
829
  * Specifies a skew transformation along both the `x-axis` and `y-axis`.
@@ -731,7 +834,10 @@
731
834
  * @return The resulted matrix
732
835
  */
733
836
  skew(angleX, angleY) {
734
- return this.multiply(Skew(angleX, angleY));
837
+ const tX = angleX ? Math.tan(angleX * Math.PI / 180) : 0;
838
+ const tY = angleY ? Math.tan(angleY * Math.PI / 180) : 0;
839
+ const { m11, m12, m13, m14, m21, m22, m23, m24 } = this;
840
+ return fromValues(m11 + tY * m21, m12 + tY * m22, m13 + tY * m23, m14 + tY * m24, tX * m11 + m21, tX * m12 + m22, tX * m13 + m23, tX * m14 + m24, this.m31, this.m32, this.m33, this.m34, this.m41, this.m42, this.m43, this.m44);
735
841
  }
736
842
  /**
737
843
  * Modifies the current matrix by post-multiplying it with another matrix.
@@ -741,8 +847,7 @@
741
847
  * @return this matrix (modified)
742
848
  */
743
849
  multiplySelf(m2) {
744
- const result = Multiply(this, m2);
745
- Object.assign(this, result);
850
+ multiplyInto(this, m2, this);
746
851
  return this;
747
852
  }
748
853
  /**
@@ -755,7 +860,20 @@
755
860
  * @return this matrix (modified)
756
861
  */
757
862
  translateSelf(x, y, z) {
758
- return this.multiplySelf(Translate(x, y ?? 0, z ?? 0));
863
+ const ty = y ?? 0;
864
+ const tz = z ?? 0;
865
+ const { m11, m12, m13, m14, m21, m22, m23, m24, m31, m32, m33, m34, m41, m42, m43, m44 } = this;
866
+ const n41 = x * m11 + ty * m21 + tz * m31 + m41;
867
+ const n42 = x * m12 + ty * m22 + tz * m32 + m42;
868
+ const n43 = x * m13 + ty * m23 + tz * m33 + m43;
869
+ const n44 = x * m14 + ty * m24 + tz * m34 + m44;
870
+ this.m41 = n41;
871
+ this.e = n41;
872
+ this.m42 = n42;
873
+ this.f = n42;
874
+ this.m43 = n43;
875
+ this.m44 = n44;
876
+ return this;
759
877
  }
760
878
  /**
761
879
  * Modifies the current matrix by post-multiplying it with a scale matrix.
@@ -767,7 +885,25 @@
767
885
  * @return this matrix (modified)
768
886
  */
769
887
  scaleSelf(x, y, z) {
770
- return this.multiplySelf(Scale(x, y ?? x, z ?? 1));
888
+ const sy = y ?? x;
889
+ const sz = z ?? 1;
890
+ this.m11 *= x;
891
+ this.a *= x;
892
+ this.m12 *= x;
893
+ this.b *= x;
894
+ this.m13 *= x;
895
+ this.m14 *= x;
896
+ this.m21 *= sy;
897
+ this.c *= sy;
898
+ this.m22 *= sy;
899
+ this.d *= sy;
900
+ this.m23 *= sy;
901
+ this.m24 *= sy;
902
+ this.m31 *= sz;
903
+ this.m32 *= sz;
904
+ this.m33 *= sz;
905
+ this.m34 *= sz;
906
+ return this;
771
907
  }
772
908
  /**
773
909
  * Modifies the current matrix by post-multiplying it with a rotation matrix.
@@ -818,7 +954,7 @@
818
954
  * @return this matrix (modified)
819
955
  */
820
956
  skewXSelf(angle) {
821
- return this.multiplySelf(SkewX(angle));
957
+ return this.skewSelf(angle, 0);
822
958
  }
823
959
  /**
824
960
  * Modifies the current matrix by post-multiplying it with a skewY matrix.
@@ -828,7 +964,7 @@
828
964
  * @return this matrix (modified)
829
965
  */
830
966
  skewYSelf(angle) {
831
- return this.multiplySelf(SkewY(angle));
967
+ return this.skewSelf(0, angle);
832
968
  }
833
969
  /**
834
970
  * Modifies the current matrix by post-multiplying it with a skew matrix.
@@ -839,7 +975,30 @@
839
975
  * @return this matrix (modified)
840
976
  */
841
977
  skewSelf(angleX, angleY) {
842
- return this.multiplySelf(Skew(angleX, angleY));
978
+ const tX = angleX ? Math.tan(angleX * Math.PI / 180) : 0;
979
+ const tY = angleY ? Math.tan(angleY * Math.PI / 180) : 0;
980
+ const { m11, m12, m13, m14, m21, m22, m23, m24 } = this;
981
+ const n11 = m11 + tY * m21;
982
+ const n12 = m12 + tY * m22;
983
+ const n13 = m13 + tY * m23;
984
+ const n14 = m14 + tY * m24;
985
+ const n21 = tX * m11 + m21;
986
+ const n22 = tX * m12 + m22;
987
+ const n23 = tX * m13 + m23;
988
+ const n24 = tX * m14 + m24;
989
+ this.m11 = n11;
990
+ this.a = n11;
991
+ this.m12 = n12;
992
+ this.b = n12;
993
+ this.m13 = n13;
994
+ this.m14 = n14;
995
+ this.m21 = n21;
996
+ this.c = n21;
997
+ this.m22 = n22;
998
+ this.d = n22;
999
+ this.m23 = n23;
1000
+ this.m24 = n24;
1001
+ return this;
843
1002
  }
844
1003
  /**
845
1004
  * Transforms a specified vector using the matrix, returning a new