Math 顶点着色器世界变换,为什么要使用四维向量?

Math 顶点着色器世界变换,为什么要使用四维向量?,math,vector,directx,hlsl,Math,Vector,Directx,Hlsl,从本网站: 我们有以下代码片段: // transformations provided by the app, constant Uniform data float4x4 matWorldViewProj: WORLDVIEWPROJECTION; // the format of our vertex data struct VS_OUTPUT { float4 Pos : POSITION; }; // Simple Vertex Shader - carry out tran

从本网站:

我们有以下代码片段:

// transformations provided by the app, constant Uniform data
float4x4 matWorldViewProj: WORLDVIEWPROJECTION;

// the format of our vertex data
struct VS_OUTPUT
{
  float4 Pos  : POSITION;
};

// Simple Vertex Shader - carry out transformation
VS_OUTPUT VS(float4 Pos  : POSITION)
{
  VS_OUTPUT Out = (VS_OUTPUT)0;
  Out.Pos = mul(Pos,matWorldViewProj);
  return Out;
}

我的问题是:为什么struct VS_输出有一个4维向量作为其位置?位置不是只有x、y和z吗?

旋转由三维矩阵指定,平移由向量指定。通过将两种变换组合成一个4 x 3矩阵,可以在“单个”操作中执行这两种变换:

rx1 rx2 rx3 tx1
ry1 ry2 ry3 ty1
rz1 rz2 rz3 tz1
然而,由于这不是方形的,所以有各种各样的操作无法执行(其中一个是反转)。通过添加额外的行(不执行任何操作):

所有这些操作都成为可能(如果不容易的话)


正如Goz在中解释的那样,通过将“1”设为非单位值,矩阵将成为透视变换。

因为透视计算需要w坐标。从顶点着色器输出后,DirectX将执行透视除以w

基本上,如果你有32768,-32768,32768,65536作为你的输出顶点位置,那么在除以w之后你得到0.5,-0.5,0.5,1。此时,可以丢弃w,因为不再需要它。该信息随后通过视口矩阵传递,视口矩阵将其转换为可用的二维坐标

编辑:如果查看如何使用投影矩阵执行矩阵乘法,可以看到值如何放置在正确的位置

采用D3DXMatrixPerspectiveLH中指定的投影矩阵

2*zn/w  0       0              0
0       2*zn/h  0              0
0       0       zf/(zf-zn)     1
0       0       zn*zf/(zn-zf)  0
将其应用于随机的x,y,z,1(注意顶点位置w始终为1)顶点输入值,得到以下结果

x' = ((2*zn/w) * x) + (0 * y) + (0 * z) + (0 * w)
y' = (0 * x) + ((2*zn/h) * y) + (0 * z) + (0 * w)
z' = (0 * x) + (0 * y) + ((zf/(zf-zn)) * z) + ((zn*zf/(zn-zf)) * w)
w' = (0 * x) + (0 * y) + (1 * z) + (0 * w)
你马上就能看到w和z是不同的。w坐标现在只包含传递给投影矩阵的z坐标。z包含了更复杂的东西

所以。。假设我们的输入位置为(2,1,5,1),我们的zn(Z-Near)为1,zf(Z-Far)为10,w(宽度)为1,h(高度)为1

通过传递这些值,我们得到

x' = (((2 * 1)/1) * 2
y' = (((2 * 1)/1) * 1
z' = ((10/(10-1)  * 5 + ((10 * 1/(1-10)) * 1)
w' = 5
扩展我们得到的

x' = 4
y' = 2
z' = 4.4
w' = 5
然后我们执行最终的透视图分割,得到

x'' = 0.8
y'' = 0.4
z'' = 0.88
w'' = 1
现在我们有了最终的坐标位置。这假设x和y的范围为-1到1,z的范围为0到1。正如您所看到的,顶点在屏幕上

奇怪的是,如果| x'|或| y'|或| z'|大于| w'|或z'小于0,则顶点在屏幕外。此信息用于将三角形剪裁到屏幕上

无论如何,我认为这是一个相当全面的答案:D


Edit2:请注意,我使用的是行主矩阵。列主矩阵被转置。

剪裁是此过程的一个重要部分,因为它有助于可视化几何体发生的情况。剪裁阶段实质上会丢弃以原点为中心的2个单位立方体之外的基本体中的任何点(好的,您必须重建部分剪裁的基本体,但这并不重要)

可以构造一个直接将世界空间坐标映射到这样一个立方体的矩阵,但是从远平面到近平面的逐渐移动是线性的。也就是说,当距离观看者一英里时,一只脚(朝向观看者)的移动将导致与距离摄影机几英尺时,一只脚的移动相同的尺寸增加

然而,如果我们的向量(w)中有另一个坐标,我们可以将向量分量除以w,我们的原语将不会表现出上述行为,但我们仍然可以使它们最终位于上面2个单位的立方体中

有关更多说明,请参阅和

一个简单的答案是,如果你不告诉管道w是什么,那么你就没有给它足够的关于你的投影的信息。这可以直接验证,而不需要了解管道如何处理它


正如您可能知道的那样,4x4矩阵可以根据每个部分的功能划分为多个部分。在执行旋转或缩放操作时,左上角的3x3矩阵会发生更改。翻译时,第四列将被更改。如果您检查透视矩阵,它会改变矩阵的底行。如果你再看看矩阵向量乘法是如何完成的,你会发现矩阵的底行只影响向量的w分量。因此,如果你不告诉管道w,它就不会有你所有的信息。

啊,一个比我好得多的答案:)+1(这是我找到的一个包含更多信息的页面)这与为什么它是顶点着色器的4向量输出有关吗?它解释了为什么有4个向量,但你没有提到透视分割。。。
x'' = 0.8
y'' = 0.4
z'' = 0.88
w'' = 1