CGAffineTransform 连接两个矩阵与将一个矩阵应用于另一个矩阵

Dan*_*e P 5 cgaffinetransform swift

在下面的这个例子中,为什么第一个矩阵等于第三个,而不是第二个?

let t1 = CGAffineTransform(scaleX: 2, y: 2)
    .concatenating(CGAffineTransform(translationX: 50, y: 50))

let t2 = CGAffineTransform(scaleX: 2, y: 2).translatedBy(x: 50, y: 50)

let t3 = CGAffineTransform(translationX: 50, y: 50).scaledBy(x: 2, y: 2)
Run Code Online (Sandbox Code Playgroud)

rma*_*ddy 5

为了避免与名称混淆,我将变量从重命名tNrN

\n\n
let r1 = CGAffineTransform(scaleX: 2, y: 2)\n    .concatenating(CGAffineTransform(translationX: 50, y: 50))\n\nlet r2 = CGAffineTransform(scaleX: 2, y: 2).translatedBy(x: 50, y: 50)\n\nlet r3 = CGAffineTransform(translationX: 50, y: 50).scaledBy(x: 2, y: 2)\n
Run Code Online (Sandbox Code Playgroud)\n\n

确实看起来倒退了。而且这些方法的文档并没有真正清楚地说明除函数之外的任何数学运算concatenating

\n\n

正如您在文档中看到的concatenating

\n\n
\n

一个新的仿射变换矩阵。即t\xe2\x80\x99 = t1*t2。

\n
\n\n

在变量的示例代码中,r1这是scale * translate.

\n\n

这部分似乎很清楚。

\n\n

至于translatedByscaledBy函数需要查看 Objective-C 头文件中CGAffineTransformTranslate和对应的函数CGAffineTransformScale

\n\n

CGAffineTransformTranslate你看看评论:

\n\n
\n

将 t 翻译 (tx, ty) 并返回结果:\n t' = [ 1 0 0 1 tx ty ] * t

\n
\n\n

CGAffineTransformScale你看:

\n\n
\n

按 (sx, sy) 缩放 t 并返回结果:\n t' = [ sx 0 0 sy 0 0 ] * t

\n
\n\n

该信息告诉我们,let r = t.translatedBy(t2)相当于t' = t2 * t。当然scaledByrotatedBy是相似的。

\n\n

这意味着您的代码中的这一行:

\n\n
let r3 = CGAffineTransform(translationX: 50, y: 50).scaledBy(x: 2, y: 2)\n
Run Code Online (Sandbox Code Playgroud)\n\n

是相同的:

\n\n
let r3 = CGAffineTransform(scaleX: 2, y: 2).concatenating(CGAffineTransform(translationX: 50, y: 50))\n
Run Code Online (Sandbox Code Playgroud)\n\n

并不是:

\n\n
let r3 = CGAffineTransform(translationX: 50, y: 50).concatenating(CGAffineTransform(scaleX: 2, y: 2))\n
Run Code Online (Sandbox Code Playgroud)\n\n

这就是为什么在您的示例代码中,r1等于r3。像英语一样阅读第二两行会导致矩阵以相反的顺序连接的想法。

\n