Vertex和Fragment着色器中旋转矩阵的差异结果

时间:2014-09-18 09:49:57

标签: opengl-es glsl opengl-es-2.0 webgl

旋转矩阵有问题。它在Vertex和片段着色器中给出了不同的结果。

有两个对象。 首先是sphere.Sphere需要在片段着色器中旋转它的纹理。它工作正常,与GUI算法相匹配。使用完全相同的算法。

第二个对象是点(精灵)。它应该围绕球体旋转相同的角度。

我在片段和顶点着色器中使用下一个算法:

mat3 rotateX = mat3(
   1.0, 0, 0,
   0, cos(angles.x), -sin(angles.x),
   0, sin(angles.x), cos(angles.x)
   );

   mat3 rotateY = mat3(
   cos(angles.y), 0, sin(angles.y),
   0, 1, 0,
   -sin(angles.y), 0, cos(angles.y)
   );

   mat3 rotateZ = mat3(
   cos(angles.z), -sin(angles.z), 0,
   sin(angles.z), cos(angles.z), 0,
   0, 0, 1
   );

   float Fi = (-current.x) * M_PI;
   float Te = current.y * M_PI;

   vec3 coord;
   coord.x = sin(Te) * cos(Fi);
   coord.y = sin(Te) * sin(Fi);
   coord.z = cos(Te);

   coord = vec3(coord.x, coord.y, coord.z) * rotateX * rotateY * rotateZ;

我有以下问题。如果从任何一个轴进行旋转,一切都可以。如果通过两个或三个轴进行旋转,则球体和点将沿不同方向旋转。

其正常行为(起始位置和一个轴旋转): http://joxi.ru/JqkaVP3JTJA_Xelvbds

开始轮换之后: http://joxi.ru/qqoaVIwyTJBWeTcvy4A

我做错了什么?

使用WebGL(OpenGL ES2)。

1 个答案:

答案 0 :(得分:0)

我解决了这个问题。 只需要以相反的顺序乘以旋转矩阵。

用于片段旋转的着色器

   mat3 rotateX = mat3(
   1.0, 0, 0,
   0, cos(angles.x), -sin(angles.x),
   0, sin(angles.x), cos(angles.x)
   );

   mat3 rotateY = mat3(
   cos(angles.y), 0, sin(angles.y),
   0, 1, 0,
   -sin(angles.y), 0, cos(angles.y)
   );

   mat3 rotateZ = mat3(
   cos(angles.z), -sin(angles.z), 0,
   sin(angles.z), cos(angles.z), 0,
   0, 0, 1
   );

   float Fi = (-cUv.x + 0.25) * 2.0 * M_PI;
   float Te = cUv.y * M_PI;  

   vec3 coord;
   coord.x = sin(Te) * cos(Fi);
   coord.y = sin(Te) * sin(Fi);
   coord.z = cos(Te);

   coord = coord * rotateX * rotateY * rotateZ;

顶点旋转着色器

angles = -angles;

mat3 rotateX = mat3(
    1.0, 0, 0,
    0, cos(angles.x), -sin(angles.x),
    0, sin(angles.x), cos(angles.x)
);

mat3 rotateY = mat3(
    cos(angles.y), 0, sin(angles.y),
    0, 1, 0,
    -sin(angles.y), 0, cos(angles.y)
);

mat3 rotateZ = mat3(
    cos(angles.z), -sin(angles.z), 0,
    sin(angles.z), cos(angles.z), 0,
    0, 0, 1
);

float Fi = (-curPosition.x) * M_PI; //hor
float Te = (curPosition.y) * M_PI; //vert

vec3 coord;
coord.x = sin(Te) * cos(Fi);
coord.y = sin(Te) * sin(Fi);
coord.z = cos(Te);

return coord * rotateZ * rotateY * rotateX;