【问题标题】:Confused about order of operation when using a Matrix in XNA, C#在 XNA、C# 中使用矩阵时对操作顺序感到困惑
【发布时间】:2012-01-29 19:03:38
【问题描述】:

这里有两段不同的代码

这就是我的开始

Vector2 hold = Vector2.Transform(pos1, mat1);
Matrix inv = Matrix.Invert(mat2);
Vector2 pos2 = Vector2.Transform(hold, inv);

这就是我被告知的简化版

Matrix matrix1to2 = mat1 * Matrix.Invert(mat2);
Vector2 pos2 = Vector2.Transform(pos1, matrix1to2);

我不明白的是,为什么简化版的第一行不是

Matrix matrix1to2 = Matrix.Invert(mat2)*mat1;

因为在矩阵顺序中,右边的东西会首先生效,而在原来的情况下,我们首先将 mat1 相乘

编辑: 下图显示了所需的操作顺序

http://www.riemers.net/images/Tutorials/XNA/Csharp/Series2D/mat1.png

教程说要创建你使用的这个转换;

Matrix carriageMat = Matrix.CreateTranslation(0, -carriage.Height, 0) * Matrix.CreateScale(playerScaling) 
* Matrix.CreateTranslation(xPos, yPos, 0) * Matrix.Identity;

如果顺序是从左到右,为什么会这样?

【问题讨论】:

  • 我认为这是一个gamedev.stackexchange.com 的问题。您将在那里获得更多反馈。
  • 谢谢,我会试试的。那我应该关闭它吗?
  • 如果你愿意。可能会有一些版主来到这里。

标签: c# vector matrix xna


【解决方案1】:

因为按照矩阵顺序,右边的东西会先生效 在原始文件中,我们首先将 mat1 相乘

其实是“左边的东西”先生效。矩阵以您阅读它们的相同顺序应用于顶点(假设您习惯于拉丁语言)。

在 XNA 中,您通常按 SRT(缩放、旋转、平移)顺序执行转换。这样,在移动到世界空间之前,对象将围绕它自己的原点进行缩放和旋转(在自己的轴上旋转)。

例如:如果我想将一个对象旋转 Pi / 2,沿 X 轴移动 100 个单位,我可能会使用:

var rotate = Matrix.CreateRotationY(MathHelper.PiOver2);
var translate = Matrix.CreateTranslation(new Vector3(100,0,0));

var worldMatrix = rotate * translate;

相反,如果我想将对象向右移动 100 个单位,然后围绕世界原点 (0,0,0) 旋转它以获得一种轨道效果(而不是像第一个那样旋转)例如),我会使用

var worldMatrix = translate * rotate;

您还可以在其轴上旋转对象,沿世界 X 轴移动 100 个单位,围绕世界原点的轨道:

var worldMatrix = rotateSpin * translate * rotateOrbit;

其中rotateSpinrotateOrbit 是旋转矩阵,分别定义了你的自旋(围绕物体原点的旋转)和轨道(围绕世界原点的旋转)。请注意,操作影响服务顶点的顺序是从左到右。

【讨论】:

  • 大卫,我看到的关于矩阵顺序的每一次讨论,都提到了首先应用 right 上的操作。例如gamedev.stackexchange.com/a/29265/45120“先缩放对象,再旋转,再平移:L = T * R * S”。请解释有什么不同,例如从左到右。
  • 例如,查看所引用的 Riemer 图,并将其与所讨论的公式进行比较,所讨论的 first 变换位于图像 (1) 和 (2 );这是XY位置的变化。在公式中(最后忽略对象的恒等变换矩阵),这是 last 矩阵Matrix.CreateTranslation(xPos, yPos, 0)。仅在y中的车厢高度变换是最终的变化,图像(3)变为(4),由第一个矩阵Matrix.CreateTranslation(0, -carriage.Height, 0)完成
  • ... 因此,恕我直言,更好的解释是 both 方法——(应用一个 mult,然后应用第二个 mult)vs (将两个矩阵相乘,然后应用组合)“工作方式相同”:它们可以被认为是“执行第二个操作,然后执行第一个操作”。因此,您按照希望它们生效的相反顺序应用它们。当“简化”一个有效的多步骤公式时,您不要更改它们的顺序,正如您正确所说。但是当考虑你最终会得到什么时,从右到左思考。
  • @ToolmakerSteve 这取决于您的代码和 API 中使用的约定。例如,GLSL 中的矩阵的应用顺序与 HLSL 中使用的顺序相反,因为矩阵是转置的(行优先与列优先)。在所有 XNA 文档中(大约六年前这个问题就是这个问题),矩阵按照我在答案中指定的顺序应用。矩阵是关联的,但不是可交换的。 (我想 - 自从我上 8 年级几何学以来已经有一段时间了。)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-12-18
  • 1970-01-01
  • 2017-10-19
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多