本文介绍了OpenGL使用不同轴的多次旋转来变换对象的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在构建一个建模程序,我想对自己空间中的对象进行转换,然后将该单个对象分配给一个组,以围绕该组旋转的另一个轴旋转.但是,我还希望能够在对象合并后在其自己的空间中进行转换.

I am building a modeling program and I'd like to do transformations on objects in their own space and then assign that single object to a group to rotate around another axis which the group rotates around. However, I'd also like to be able to do transformations in the object's own space when it's combined.

操纵单个对象,然后选择对象的中心.

Manipulating the individual object, I pick the object's center.

glm::mat4 transform;
transform = glm::translate(transform, - obj.meshCenter);
glm::mat4 transform1;
transform1 = glm::translate(transform1, obj.meshCenter);
obj.rotation =  transform1*obj.thisRot*transform;

然后我将其发送给着色器,

I then send this off to the shader,

glUniformMatrix4fv(modelLoc, 1, GL_FALSE, glm::value_ptr(obj.translation*obj.rotation*objscale);

我现在想绕另一个轴旋转该对象,比如说(5,0,0)轴为45度.

I would now like to rotate this object around another axis, say an axis of (5,0,0) of 45 degrees.

我现在有:

glm::mat4 groupR;
groupR = glm::rotate(groupR,glm::degrees(45.0f),glm::vec3(5,0,0));
obj.groupRotation = groupR;
glUniformMatrix4fv(modelLoc, 1, GL_FALSE,
glm::value_ptr(obj.groupRotation*obj.translation*obj.rotation*objscale)

我现在将对象从其本地空间移到了组空间.与Group的旋转结合使用时,我现在在操作对象自身空间中的转换时遇到了一些困难.像这样将groupR轴设置为(0,1,0)时,我获得的成功有限:

I've now moved the object from it's local space to the Group space.I'm having a bit of difficulty now operating tranformations in the object's own space when combined with the Group's rotation.I've had limited success when I set the groupR axis to (0,1,0) like so:

///Translating object in its own space///
glm::mat4 R = obj.groupRotation;
obj.translation = glm::inverse(R) * obj.translate * R;

这里的问题是,仅当R的旋转轴(组的旋转)等于(0,1,0)时,才可以在其自己的空间中正确平移对象.

the problem here is that this will only translate the object correctly in it's own space if the axis of rotation of R (Group's rotation) is equal to (0,1,0):

///Rotating object in its own space///
glm::mat4 R = obj.groupRotation;
obj.rotation = glm::inverse(R) * obj.rot * R;

同样,旋转不正确.我在想,也许我必须撤消groupR的轴平移?然后在某个地方重新应用?

Again, the rotations are incorrect. I'm thinking that maybe I have to undo the groupR's axis translation? and then re-apply it somewhere?

推荐答案

假设我们有一个可以移动,旋转和缩放的对象,并且我们定义了一个转换矩阵,如下所示:

Let's assume we have an object that is moved, rotated and scaled, and we define a transformation matrix as follows:

glm::mat4 objTrans ...; // translation
glm::mat4 objRot ...;   // roation
glm::mat4 objScale ...; // scaling

glm::mat4 objMat = objTrans * objRot * objScale;

我们有要在对象上运行的旋转矩阵.在这种情况下,我们可以绕Z轴旋转:

And we have rotation matrix that we want to run on the object. In this case we have rotation around the Z-axis:

foat angle ...; // rotation angle

glm::mat4 rotMat = glm::rotate( angle, glm::vec3( 0.0, 0.0, 1.0 ) );

我们可以多次轮换处理此信息.首先,我们要旋转对象的局部轴:

We have several rotations we can do with this information.First we want to rotate the object on its local axis:

glm::mat4 modelMat = objMat * rotMat;

围绕地球原点的旋转可以这样执行:

A Rotation around the worlds origin can be performed like this:

glm::mat4 modelMat = rotMat * objMat;

要在世界坐标系中绕对象的原点旋转,我们必须消除对象的旋转:

In order to rotate around the origin of the object in the world coordinate system, we must eliminate the rotation of the object:

glm::mat4 modelMat = objMat * (glm::inverse(objRot) * rotMat * objRot);

围绕地球原点相对于对象的旋转,您必须执行相反的操作:

A Rotation around the worlds origin in relation to the object you have to do the opposite:

glm::mat4 modelMat = (objRot * rotMat * glm::inverse(objRot)) * objMat;

如果您具有对象的完整转换矩阵,但不知道旋转部分,则可以轻松确定它.

If you have a complete transformations matrix for an object and you do not know the rotation part, then it can be easily determined.

请注意,转换矩阵通常如下所示:

Note that a transformation matrix usually looks like this:

( X-axis.x, X-axis.y, X-axis.z, 0 )
( Y-axis.x, Y-axis.y, Y-axis.z, 0 )
( Z-axis.x, Z-axis.y, Z-axis.z, 0 )
( trans.x,  trans.y,  trans.z,  1 )

要生成仅旋转矩阵,您必须提取归一化的轴矢量:

To generate a rotation only matrix you have to extract the normalized axis vectors:

glm::mat4 a ...; // any matrix
glm::vec3 x = glm::normalize( a[0][0], a[0][1], a[0][2] );
glm::vec3 y = glm::normalize( a[1][0], a[1][1], a[1][2] );
glm::vec3 z = glm::normalize( a[2][0], a[2][1], a[2][2] );

glm::mat4 r;
r[0][0] = x[0]; r[0][1] = x[1]; r[0][2] = x[2]; r[0][3] = 0.0f;
r[1][0] = y[0]; r[1][1] = y[1]; r[1][2] = y[2]; r[0][3] = 0.0f;
r[2][0] = z[0]; r[2][1] = z[1]; r[2][2] = z[2]; r[0][3] = 0.0f;
r[3][0] = 0.0f; r[3][1] = 0.0f; r[3][2] = 0.0f; r[0][3] = 1.0f;

这篇关于OpenGL使用不同轴的多次旋转来变换对象的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

09-02 12:56