Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

chore(): Matrix util cleanup #8894

Merged
merged 16 commits into from May 9, 2023
Merged

chore(): Matrix util cleanup #8894

merged 16 commits into from May 9, 2023

Conversation

ShaMan123
Copy link
Contributor

@ShaMan123 ShaMan123 commented May 7, 2023

Motivation

continues #8881

Description

Matrix utils belong to utils, not to parser
It is wrong to have utils import from parser for the following:

  • utils should be pure as possible (parser should import utils, also for the day we make the parser not part of the main bundle, if that day comes)
  • these methods have value for more than just the parser

Changes

  • squash matrix files from parser into the matrix util file
  • use these methods across fabric

Gist

In Action

@github-actions
Copy link
Contributor

github-actions bot commented May 7, 2023

Build Stats

file / KB (diff) bundled minified
fabric 902.311 (0) 304.491 (0)

@github-actions
Copy link
Contributor

github-actions bot commented May 7, 2023

Coverage after merging matrix-cleanup into master will be

83.66%

Coverage Report
FileStmtsBranchesFuncsLinesUncovered Lines
index.node.ts7.69%100%0%14.29%17, 20, 23, 29, 32, 35
src
   ClassRegistry.ts100%100%100%100%
   Collection.ts94.71%94.64%86.67%97.09%101, 104, 207–208, 233–234
   CommonMethods.ts96.55%87.50%100%100%10
   Intersection.ts100%100%100%100%
   Observable.ts87.23%85.29%84.62%89.36%144–145, 170–171, 39–40, 48, 57, 91, 99
   Point.ts100%100%100%100%
   Shadow.ts98.36%95.65%100%100%178
   cache.ts97.06%90%100%100%57
   config.ts75%66.67%66.67%82.76%130, 138, 138, 138, 138, 138–140, 151–153
   constants.ts100%100%100%100%
   typedefs.ts100%100%100%100%
src/Pattern
   Pattern.ts92.21%91.89%90%93.33%116, 127, 136, 29, 92
src/brushes
   BaseBrush.ts100%100%100%100%
   CircleBrush.ts0%0%0%0%100, 102–104, 113, 113, 113, 115, 117, 119–121, 123–126, 133–134, 141, 143, 28–29, 37–41, 45–49, 56–59, 67–71, 73, 81, 81, 81, 81, 81–82, 84, 84, 84–87, 89, 97–98
   PatternBrush.ts97.06%87.50%100%100%21
   PencilBrush.ts91.01%82.35%100%93.75%122–123, 152, 152–154, 176, 176, 276, 280, 285–286, 68–69, 84–85
   SprayBrush.ts0%0%0%0%100–101, 103–104, 112, 112, 112, 112, 112–113, 115–116, 123–124, 126, 128–132, 141, 145–146, 146, 154, 154, 154–157, 159–162, 166–167, 169, 171–174, 177, 184–185, 187, 189–190, 192, 199–200, 202–203, 206, 206, 213, 213, 217, 22–23, 25–27, 27, 27–29, 33, 42, 49, 56, 63, 70, 89–91, 99
src/canvas
   Canvas.ts78.87%77.54%81.67%79.41%1001–1002, 1002, 1002–1004, 1006–1007, 1007, 1007, 1009, 1017, 1017, 1017–1019, 1019, 1019, 1025–1026, 1034–1035, 1035, 1035–1036, 1041, 1043, 1074–1076, 1079–1080, 1084–1085, 1198–1200, 1203–1204, 1277, 1396, 1519, 1589, 162, 187, 297–298, 301–305, 310, 333–334, 339–344, 364, 364, 364–365, 365, 365–366, 37, 374, 379–380, 380, 380–381, 383, 392, 398–399, 399, 399, 41, 442, 450, 454, 454, 454–455, 457, 539–540, 540, 540–541, 547, 547, 547–549, 569, 571, 571, 571–572, 572, 572, 575, 575, 575–576, 579, 588–589, 591–592, 594, 594–595, 597–598, 610–611, 611, 611–612, 614–619, 625, 632, 669, 669, 669, 671, 673–678, 684, 690, 690, 690–691, 693, 696, 701, 714, 742, 742, 800–801, 801, 801–802, 804, 807–808, 808, 808–809, 811–812, 815, 815–817, 820–821, 891, 903, 910, 931, 963, 984–985
   SelectableCanvas.ts94.39%91.16%94.55%96.63%1113, 1113–1114, 1117, 1137, 1137, 1195, 1248–1249, 1270, 1278, 1403, 1405, 1407–1408, 512, 692–693, 695–696, 696, 696, 745–746, 807–808, 861–863, 895, 900–901, 928–929
   StaticCanvas.ts96.85%92.86%100%98.61%1113–1114, 1114, 1114–1115, 1235, 1245, 1299–1300, 1303, 1338–1339, 1416, 1425, 1425, 1429, 1429, 1476–1477, 321–322, 339, 770, 782–783
   TextEditingManager.ts100%100%100%100%
src/color
   Color.ts92.16%86.49%100%94.29%330–331, 335–336, 339–340, 58, 88–89, 89, 91, 91, 91–92, 94–95
   color_map.ts100%100%100%100%
   constants.ts100%100%100%100%
   util.ts100%100%100%100%
src/controls
   Control.ts93.90%88.89%90.91%97.73%235, 322, 322, 357
   changeWidth.ts100%100%100%100%
   commonControls.ts100%100%100%100%
   controlRendering.ts81.63%78%100%84.78%106, 111, 121, 121, 45, 50, 61, 61, 65–72, 81–82
   drag.ts100%100%100%100%
   polyControl.ts5.97%0%0%11.11%100, 105, 119, 119, 119, 119, 119, 121–124, 124, 127, 134, 17, 25–29, 29, 29, 29, 29, 29, 29, 29, 50–56, 56, 56, 56, 56, 58, 63–64, 66, 76, 82–83, 83, 83–84, 88–90, 90, 90, 90, 90, 92
   rotate.ts19.57%12.50%50%21.43%41, 45, 51, 51, 51–52, 55–57, 59, 59, 59, 59, 59–61, 61, 61–63, 65, 65, 65–67, 67, 67–68, 73, 73, 73–74, 76, 78, 80–81
   scale.ts93.57%92.94%100%93.67%129–130, 132–134, 148–149, 181–183, 42
   scaleSkew.ts78.79%64.29%100%85.71%27, 29, 29, 29, 31, 33, 35
   skew.ts91.03%79.31%100%97.67%130–131, 162–163, 170, 176, 178
   util.ts100%100%100%100%
   wrapWithFireEvent.ts100%100%100%100%
   wrapWithFixedAnchor.ts100%100%100%100%
src/env
   browser.ts84.21%77.78%50%100%14, 17
   index.ts100%100%100%100%
   node.ts76.92%50%66.67%88.24%27, 31–32, 32, 32
src/filters
   BaseFilter.ts21.93%22.81%32%19.05%106–109, 109, 109–110, 116, 116, 116–119, 137, 155, 169–174, 178–179, 179, 179–182, 182, 182, 182, 182–184, 190,

Copy link
Contributor Author

@ShaMan123 ShaMan123 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

cleanup done!
ready

src/util/misc/angleSkewConversion.ts Outdated Show resolved Hide resolved
src/util/misc/matrix.ts Show resolved Hide resolved
@ShaMan123 ShaMan123 requested a review from asturur May 7, 2023 06:02
Comment on lines 145 to 161
export function calcRotateMatrix(
{ angle = 0 }: TRotateMatrixArgs = {},
x = 0,
y = 0
): TMat2D {
const angleRadiant = degreesToRadians(angle),
cosValue = cos(angleRadiant),
sinValue = sin(angleRadiant);
return [
cosValue,
sinValue,
-sinValue,
cosValue,
x - (cosValue * x - sinValue * y),
y - (sinValue * x + cosValue * y),
];
}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The parser calcRotateMatrix and the old calcRotateMatrix are the only one i don't want to mix.
I m not sure the pivot point in our geometry is identical to the one in the svg context.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I will add a test comparing this and rotatePoint

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

take a look at 5d36428 with critical eyes

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i m not worried about that use case.
Those matrices were the building block of calcTransformMatrix.
I would like to have the calcRotateMatrix used for calcTransformMatrix, different from the function that has to only serve the SVG parsing abilities.

Is ok if the svg parser call the old calcRotateMatrix and then adds the missin 2 values and we name that parseSVGRotateTransformAttribute.

I don't know of svg notations that may need different operation to the one that we have and that are identical to the one we were already using, so scale/skew/translate do not bother me.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't really understand
I think I proved it is identical to how we use origin and since there aren't other use cases seems ok.
But I understand the mistrust.
I do think it is useful outside the parsing context.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i just want the pivot point, that was part of the svg parsing and nothing else, to stay part of the svg parsing.
I don't want to mix them up because we save a bunch of code and because if we pass 0,0 at the pivot point then the function is functionally he same.
Let's leave the previous calcRotateMatrix and the svg one divided.
We may want to change the svg parsing code independently from the canvas code.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I still don't get your point. As a standalone util it is great, isn't it?
Are you worried it does more calculations than before? Is that the point?

We may want to change the svg parsing code independently from the canvas code.

Then we change it accordingly.

I have encountered a number of times the need of this util and had to use rotatePoint to figure out the translation. That is why I want it exposed.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Well the 4 addition and 4 multiplication are also unwelcome an extra point to have divided in 2 stages that is all i m asking.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

can I just have an early return instead if the origin is 0,0?

@ShaMan123 ShaMan123 requested a review from asturur May 7, 2023 10:57
Copy link
Contributor Author

@ShaMan123 ShaMan123 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

added
multiplyTransformMatricesFromEnd renamed
multiplyTransformMatricesFromStart removed
multiplyTransformMatrices2 - do you a good name for it?

to multiply a chain of matrices

src/util/misc/matrix.ts Outdated Show resolved Hide resolved
src/util/misc/matrix.ts Outdated Show resolved Hide resolved
Comment on lines -90 to -93
return matrices.reduce(
(acc, matrix) => multiplyTransformMatrices(acc, matrix),
iMatrix
);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

we are changing a reduce to reduce right here nad i don't understand why.
I m incline to say don't touche the current transformation code at all, is not a cleanup anymore at that point

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree.
Touched it and became uneasy but the math is correct and I double checked that there is a test to cover it.
This proves it is all right: https://en.wikipedia.org/wiki/Matrix_multiplication#Associativity

Notice the args order passed to multiplyTransformMatrices

(product: TMat2D, curr) =>
curr ? multiplyTransformMatrices(curr, product, is2x2) : product,
iMatrix
);
Copy link
Member

@asturur asturur May 8, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

maybe i don't understan reduceRigth but it seems to me we are inverting changing the order of multiplication of matrices.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is the right order.
All tests pass.
https://en.wikipedia.org/wiki/Matrix_multiplication#Associativity

Notice the args order passed to multiplyTransformMatrices

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i know the result doesn't change because i know you know math. ( on top of that i know that property too ).
I opened the article anyway to see if maybe there was explained a mathematical property that was the reason for this change, but i couldn't find one.

So i don't know why you think that is the most correct order.
Why do you think is important to change it? I always have express preferences for don't touch what is not getting measurably better and i think you know it by now.

( apart that given the flawed float system of js, changing mutliplication order of floats ( the one inside the matrices ) isn't exactly the same thing. It could be, but sometimes it won't be)
( and apart that most of developers, inclding me, when they see reduceRight, they have to go and check how ti differs from reduce )

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is how it is done mathmatically
Because of Associativity it doesn't matter. I wasn't sure at the time of writing but now I am.
So it can be turned into reduce but IMO this is the correct manner.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

added a test and renamed

Copy link
Contributor Author

@ShaMan123 ShaMan123 May 9, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I will better explain.
Without Associativity it would matter.
Meaning, that using reduce (and not reduceRight) multiplies left to right and is correct only because of Associativity.
Multiplying using reduceRight is how matrix multiplication is defined

Copy link
Contributor Author

@ShaMan123 ShaMan123 May 9, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It is confusing but this is how we do it in fabric using concatation of multiplyTransformMatrices

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

after much thinking i will write you what i think.
I think that even removed any personal preference, the rule of no gain no change should be easy to agree with for everyone.
There is no gain here ( just minor losses ) ( i can't even find references about one order being more canon that the other ) and just the will to have this change.
This was hours ago, now you take this reduceRight and you keep it, my time and mood is not worth this change.
When i get to this point i the never want to talk about it anymore so please help me there.

Copy link
Member

@asturur asturur left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

  • multiplyTransformMatrices2 doesn't seems a good name.
  • multiplyTransformMatrices2 uses reduce and not reduceRight
  • calcRotateMatrix does not get the extra calculation

Started as a cleanup is drifing away from that concept

@ShaMan123
Copy link
Contributor Author

multiplyTransformMatrices2

what name do you suggest?
multiplyTransformMatrixArray?

@asturur
Copy link
Member

asturur commented May 8, 2023

multiplyTransformMatrices2

what name do you suggest? multiplyTransformMatrixArray?

That works for me

@ShaMan123 ShaMan123 requested a review from asturur May 8, 2023 13:02
asturur
asturur previously approved these changes May 9, 2023
@asturur asturur merged commit d0d0cfb into master May 9, 2023
16 of 17 checks passed
@asturur asturur deleted the matrix-cleanup branch May 9, 2023 08:48
@asturur asturur mentioned this pull request May 19, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

2 participants