不了解Learnopengl.com中的漫射辐射教程中的captureViews

时间:2019-06-09 15:09:38

标签: c++ opengl glm-math

我正在https://learnopengl.com/PBR/IBL/Diffuse-irradiance中学习IBL。

该教程通过创建6个视图将等角矩形转换为立方体贴图。

视图是以下代码:

glm::mat4 captureViews[] = 
{
   glm::lookAt(glm::vec3(0.0f, 0.0f, 0.0f), glm::vec3( 1.0f,  0.0f,  0.0f), glm::vec3(0.0f, -1.0f,  0.0f)),
   glm::lookAt(glm::vec3(0.0f, 0.0f, 0.0f), glm::vec3(-1.0f,  0.0f,  0.0f), glm::vec3(0.0f, -1.0f,  0.0f)),
   glm::lookAt(glm::vec3(0.0f, 0.0f, 0.0f), glm::vec3( 0.0f,  1.0f,  0.0f), glm::vec3(0.0f,  0.0f,  1.0f)),
   glm::lookAt(glm::vec3(0.0f, 0.0f, 0.0f), glm::vec3( 0.0f, -1.0f,  0.0f), glm::vec3(0.0f,  0.0f, -1.0f)),
   glm::lookAt(glm::vec3(0.0f, 0.0f, 0.0f), glm::vec3( 0.0f,  0.0f,  1.0f), glm::vec3(0.0f, -1.0f,  0.0f)),
   glm::lookAt(glm::vec3(0.0f, 0.0f, 0.0f), glm::vec3( 0.0f,  0.0f, -1.0f), glm::vec3(0.0f, -1.0f,  0.0f))
};

我不了解glm::lookAt的第三个参数。

glm::lookAt的第三个参数是up向量。我认为captureViews应该是:

// zero is    [0, 0, 0]
// right is   [1, 0, 0]
// left is    [-1, 0, 0]
// up is      [0, 1, 0]
// down is    [0, -1, 0]
// back is    [0, 0, 1]
// forward is [0, 0, -1]
glm::mat4 captureViews[] = 
{
   glm::lookAt(zero, right, up),
   glm::lookAt(zero, left, up),
   glm::lookAt(zero, up, back),
   glm::lookAt(zero, down, forward),
   glm::lookAt(zero, back, up),
   glm::lookAt(zero, forward, up)
};

但是我完全错了。我不了解本教程的up向量中的魔术。

有人可以帮我解释一下吗?

1 个答案:

答案 0 :(得分:1)

使用立方体贴图纹理时,必须将3维方向矢量转换为相对于地图一侧的2维纹理坐标。

规范的相关部分是OpenGL 4.6 API Core Profile Specification, 8.13 Cube Map Texture Selection,第253页:

  

采样立方体贴图纹理时,将处理(s t r)纹理坐标   作为从立方体中心发出的方向向量(rx ry rz)q坐标将被忽略。在纹理应用时,内插的每个片段方向向量会根据最大量值坐标方向(长轴方向)选择立方体贴图的二维图像之一。如果两个或多个坐标具有相同的幅度,则实现可以定义规则以消除这种情况的歧义。该规则必须是确定性的,并且仅取决于(rx ry rz)。表8.19中的目标列说明了主轴方向如何映射到特定立方体贴图目标的二维图像。   使用表8.19中指定的由主轴方向确定的sctcma,更新后的(s t)   计算如下:

s = 1/2 * (s_c / |m_a| + 1)
t = 1/2 * (t_c / |m_a| + 1)


Major Axis Direction|        Target             |sc |tc |ma |
--------------------+---------------------------+---+---+---+
       +rx          |TEXTURE_CUBE_MAP_POSITIVE_X|−rz|−ry| rx|
       −rx          |TEXTURE_CUBE_MAP_NEGATIVE_X| rz|−ry| rx|
       +ry          |TEXTURE_CUBE_MAP_POSITIVE_Y| rx| rz| ry|
       −ry          |TEXTURE_CUBE_MAP_NEGATIVE_Y| rx|−rz| ry|
       +rz          |TEXTURE_CUBE_MAP_POSITIVE_Z| rx|−ry| rz|
       −rz          |TEXTURE_CUBE_MAP_NEGATIVE_Z|−rx|−ry| rz|
--------------------+---------------------------+---+---+---+

sc对应于u coordiante和tcv相关。因此tc必须朝着视图空间向上的方向


查看表格的第一行:

+rx | TEXTURE_CUBE_MAP_POSITIVE_X | −rz | −ry | rx

这意味着,对于立方体贴图的X +侧(右侧),对应于切线和双法线的方向为

sc = (0, 0, -1)
tc = (0, -1, 0)

这与表glm::mat4 captureViews[]的第一行完全匹配:

glm::lookAt(glm::vec3(0.0f, 0.0f, 0.0f), glm::vec3(1.0f, 0.0f, 0.0f), glm::vec3(0.0f, -1.0f, 0.0f))

因为主要方向是由视线给出的,所以视线就是从视线位置到目标(los = target - eye)的方向,所以(1,0,0)。
向上向量(或ts)是(0,-1,0)。
sc由视线和向上矢量(0,0,-1)的叉积给出。