为什么这个图像不是水平渐变?
Why this image is not an horizontal gradient?
这个问题不是我的问题,而是我们为什么会得到这个结果的问题。
此图像生成渲染两个立方体,使用此着色器:
片段:
uniform mat4 u_ModelMatrix;
uniform mat4 u_ViewMatrix;
uniform mat4 u_ProjectionMatrix;
in FS {
vec4 pos;
} fs;
out vec4 out_Color;
void main()
{
out_Color.rgb = vec3(u_ProjectionMatrix * u_ViewMatrix * fs.pos).xxx;
}
顶点:
layout (location = 0) in vec4 in_Pos;
uniform mat4 u_ModelMatrix;
uniform mat4 u_ViewMatrix;
uniform mat4 u_ProjectionMatrix;
out FS {
vec4 pos;
} fs;
void main()
{
fs.pos = u_ModelMatrix * in_Pos;
gl_Position = u_ProjectionMatrix * u_ViewMatrix * worldPos;
}
我的理解是,当我们通过乘以 MVP 得到 projected 片段坐标时,我们应该 vec3(u_ProjectionMatrix * u_ViewMatrix * fs.pos)
等于到 X 和 Y 的 window 屏幕,等于 Z 的深度。因此,使用 xxx
作为 rgb
应该显示绘制模型的水平渐变,中心全黑window(右边是负 X)和右边的全白。这是全局结果,但颜色不仅仅取决于 X,因为我们可以看到图像中的垂直线具有不同颜色的像素。为什么会这样?
投影矩阵将输入转换为剪辑 space。 Clip space 是齐次 space(实际上是射影 P^3 space),并且不保证轴上有任何边界。对于剪辑 space 中可见的任何点,x、y、z 轴必须小于 w 分量。
如果您需要 space 中的点,其中所有坐标都在 [-1,1] 范围内,您必须通过将剪辑 space 坐标除以 w 坐标来均化剪辑坐标。
... we should have vec3(u_ProjectionMatrix * u_ViewMatrix * fs.pos)
equals to the window screen in X and Y and equals to the depth in Z:
NDC = clipSpace.xyz / clipSpace.w;
这既不适用于剪辑 space 也不适用于 NDC space true,要获得屏幕坐标,必须执行视口变换,基本上变换 [-1, 1] space 到 [0, 宽度](或 [0, 高度])space。为此,您必须执行以下计算:
windowSpace = (NDC.xy + 1.0) * ([width, height] / 2.0)
这个问题不是我的问题,而是我们为什么会得到这个结果的问题。 此图像生成渲染两个立方体,使用此着色器:
片段:
uniform mat4 u_ModelMatrix;
uniform mat4 u_ViewMatrix;
uniform mat4 u_ProjectionMatrix;
in FS {
vec4 pos;
} fs;
out vec4 out_Color;
void main()
{
out_Color.rgb = vec3(u_ProjectionMatrix * u_ViewMatrix * fs.pos).xxx;
}
顶点:
layout (location = 0) in vec4 in_Pos;
uniform mat4 u_ModelMatrix;
uniform mat4 u_ViewMatrix;
uniform mat4 u_ProjectionMatrix;
out FS {
vec4 pos;
} fs;
void main()
{
fs.pos = u_ModelMatrix * in_Pos;
gl_Position = u_ProjectionMatrix * u_ViewMatrix * worldPos;
}
我的理解是,当我们通过乘以 MVP 得到 projected 片段坐标时,我们应该 vec3(u_ProjectionMatrix * u_ViewMatrix * fs.pos)
等于到 X 和 Y 的 window 屏幕,等于 Z 的深度。因此,使用 xxx
作为 rgb
应该显示绘制模型的水平渐变,中心全黑window(右边是负 X)和右边的全白。这是全局结果,但颜色不仅仅取决于 X,因为我们可以看到图像中的垂直线具有不同颜色的像素。为什么会这样?
投影矩阵将输入转换为剪辑 space。 Clip space 是齐次 space(实际上是射影 P^3 space),并且不保证轴上有任何边界。对于剪辑 space 中可见的任何点,x、y、z 轴必须小于 w 分量。
如果您需要 space 中的点,其中所有坐标都在 [-1,1] 范围内,您必须通过将剪辑 space 坐标除以 w 坐标来均化剪辑坐标。
... we should have
vec3(u_ProjectionMatrix * u_ViewMatrix * fs.pos)
equals to the window screen in X and Y and equals to the depth in Z:
NDC = clipSpace.xyz / clipSpace.w;
这既不适用于剪辑 space 也不适用于 NDC space true,要获得屏幕坐标,必须执行视口变换,基本上变换 [-1, 1] space 到 [0, 宽度](或 [0, 高度])space。为此,您必须执行以下计算:
windowSpace = (NDC.xy + 1.0) * ([width, height] / 2.0)