安卓:矩阵 - >什么是间preconcat和postconcat不同? [英] Android: Matrix -> what is the different between preconcat and postconcat?

查看:1983
本文介绍了安卓:矩阵 - >什么是间preconcat和postconcat不同?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我使用矩阵来缩放和旋转位图。现在,我想知道什么之间preconcat和放大器的区别; postconcat是,以上precisely之间的区别:

I'm using Matrix to scale and rotate Bitmaps. Now I'm wondering what the difference between preconcat & postconcat is, or more precisely the difference between:

  • <一个href="http://developer.android.com/reference/android/graphics/Matrix.html#postRotate%28float%29">postRotate
  • <一个href="http://developer.android.com/reference/android/graphics/Matrix.html#$p$pRotate%28float%29">$p$pRotate
  • <一个href="http://developer.android.com/reference/android/graphics/Matrix.html#setRotate%28float%29">setRotate
  • postRotate
  • preRotate
  • setRotate

从我能找出迄今setRotate始终覆盖整个矩阵,同时用preRotate和postRotate我可以申请多次更改矩阵(如:缩放+旋转)。但是,无论是使用postRotate或preRotate没有造成任何不同的结果,因为我用他们的情况。

From what I could figure out so far setRotate always overwrites the whole matrix, while with preRotate and postRotate I can apply multiple changes to a matrix (e.g. scaling + rotation). However, either using postRotate or preRotate didn't cause any different results for the cases I used them.

推荐答案

在回答你的问题是没有真正具体到Android;它的图形和数学问题。有很多理论在这个答案 - you've被警告!对于一个肤浅的回答你的问题,跳到底部。同时,由于这是这样一个啰嗦的长篇大论,我可能有一个错字或两个使事情不清楚。我提前道歉,如果是这样的话。

The answer to your question isn't really specific to Android; it's a graphics and math question. There's lots of theory in this answer--you've been warned! For a superficial answer to your question, skip to the bottom. Also, because this is such a long-winded tirade, I might have a typo or two making things unclear. I apologize in advance if that's the case.

在计算机图形学中,我们可以重新present像素(或3D,顶点)作为载体。如果你的屏幕为640×480,这里有一个二维矢量在屏幕的中间点(原谅我的以次充好的标记):

In computer graphics, we can represent pixels (or in 3D, vertices) as vectors. If your screen is 640x480, here's a 2D vector for the point in the middle of your screen (forgive my shoddy markup):

[320]
[240]
[  1]

我来解释为什么1是很重要的更新版本。转换往往是再presented使用矩阵的,因为它是那么非常简单(并且非常有效)链他们在一起,像你提到的。要通过1.5倍缩放点之上,可以左乘以下列矩阵的那样:

I'll explain why the 1 is important later. Transformations are often represented using matrices because it's then very simple (and very efficient) to chain them together, like you mentioned. To scale the point above by a factor of 1.5, you can left-multiply it by the following matrix:

[1.5   0   0]
[  0 1.5   0]
[  0   0   1]

您会得到这个新点:

[480]
[360]
[  1]

这将重新presents原点,按1.5的相对缩小到屏幕的角落(0,0)。这是很重要的:缩放总是与相对于原点完成。如果你想扩展与其他一些点作为中心(如精灵的中间),你需要包装的规模的翻译,并从原点。下面是基质把我们的原点到原点:

Which represents the original point, scaled by 1.5 relative to the corner of your screen (0, 0). This is important: scaling is always done with respect to the origin. If you want to scale with some other point as your center (such as the middle of a sprite), you need to "wrap" the scale in translations to and from the origin. Here's the matrix to translate our original point to the origin:

[1  0  -320]
[0  1  -240]
[0  0     1]

生成:

[320*1 + 1*-320]   [0]
[240*1 + 1*-240] = [0]
[     1*1      ]   [1]

您将辨别出上面的位移身份矩阵在右上角坐标耳光。这就是为什么1(下称同质坐标)是必要的:以腾出空间给这些坐标,从而使得可以使用乘法平移。否则将必须是由矩阵加法,这是更直观的人类psented重新$ P $,但会使图形卡甚至更复杂的比他们已经是

You'll recognize the above as the identity matrix with the displacement coordinates slapped in the upper-right corner. That's why the 1 (the "homogenous coordinate") is necessary: to make room for these coordinates, thus making it possible to translate using multiplication. Otherwise it would have to be represented by matrix addition, which is more intuitive to humans, but would make graphics cards even more complicated than they already are.

现在,矩阵乘法一般是不可交换的的,所以当,并称转型(由乘法的你的矩阵),你需要指定无论你左乘或右乘法。它使不同的是什么命令你的转换是链接起来,通过右键乘以你的矩阵(使用 preRotate())你表明旋转一步应该发生的的一切,你刚才问的其他转换。这可能是你想要的,但通常并非如此。

Now, matrix multiplication generally isn't commutative, so when "adding" a transformation (by multiplying your matrix) you need to specify whether you're left-multiplying or right-multiplying. The difference it makes is what order your transformations are chained in. By right-multiplying your matrix (using preRotate()) you're indicating that the rotation step should happen before all the other transformations that you've just asked for. This might be what you want, but it usually isn't.

通常,也没关系。如果你只有一个转换,例如,它从来没有重要的:)有时候,你的转换可以发生在任何顺序具有同等效力,如缩放和旋转 - 我的线性代数是生疏,但我认为,在这种情况下,矩阵乘法实际上是可交换的,因为规模矩阵是对称的,也就是说,它反映本身横跨对角线。但实际上,只是想想而已:如果我按顺时针方向旋转了一些图片10度,然后将其扩展到200%,它的外观一样的,如果我第一比例,然后将其转动

Often, it doesn't matter. If you only have one transformation, for example, it never matters :) Sometimes, your transformations can happen in either order with the same effect, such as scaling and rotation--my linear algebra is rusty, but I believe that in this case the matrix multiplication actually is commutative because the scale matrix is symmetric, that is, it mirrors itself across the diagonal. But really, just think about it: If I rotate some picture 10 degrees clockwise and then scale it to 200%, it looks the same as if I scaled it first, then rotated it.

如果你正在做一些怪异的化合物转换,你会开始注意到的差异。我的建议是坚持使用 postRotate()

If you were doing some weirder compound transformations, you'd begin to notice a discrepancy. My advice is to stick with postRotate().

这篇关于安卓:矩阵 - &GT;什么是间preconcat和postconcat不同?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆