将形状旋转到 1 到 2 弧度之间的任何位置会重置其旋转
Rotating a shape to anywhere between 1 and 2 radians resets its rotation
我目前正在使用 GLM 在 OpenGL 中转换形状。但是,当形状的旋转介于 1 到 2 弧度之间时,表示旋转的矩阵值将设置回它们在单位矩阵中的值。我目前正在将模型矩阵输出到控制台,这有助于找出它转回 0 弧度旋转的确切时刻。这是:
抱歉,如果它难以理解,我已经尝试对其进行注释,因为否则看起来会很烦人。有需要的直接上图link
控制台中每行的第一个值是作为单个值的旋转,以弧度表示。然后,输出形状的模型矩阵。
上传它的视频很烦人,但我相信你可以想象它 - 它只是一个正常旋转一段时间的形状,直到旋转达到一个弧度,此时它会重置为正常旋转。然后,当它达到两个弧度时,它又恢复正常,就好像从来没有问题一样。
变形相关的代码如下:
// NOTE: the variables 'active_translation, active_rotation, and active_scaling' are the values the user gives to translate, rotate, and scale the shape
// In this case, 'active_rotation' is equal to ~0.02 (1 degree in radians) every frame
void defshape::apply_transformations() {
// Create an identity matrix to store the applied transformations
glm::mat4 applied_transformation = glm::mat4(1.0f);
// Add the active translation to the stored transformations variable
applied_transformation = glm::translate(applied_transformation, active_translation);
// Apply the rotation to the mat4. For the sake of this example, I've only showed the Z axis line to simplify it as it's the only one being affected.
applied_transformation = glm::rotate(applied_transformation, active_rotation.z, glm::vec3(0, 0, 1));
// Add the active scale to the stored transformations variable
applied_transformation = glm::scale(applied_transformation, active_scaling);
// Apply these changes to the renderer by setting its model matrix and then updating it
renderer_handle->model_matrix = applied_transformation;
renderer_handle->update_renderer();
// Reset the translation of the model matrix back to 0
// This step ensures that the object rotates around its local origin, rather than the world space origin
applied_transformation = glm::translate(applied_transformation, glm::vec3(0.0f));
// Then apply this change to the renderer's model matrix
renderer_handle->model_matrix = applied_transformation;
renderer_handle->update_renderer();
}
这可能与 GLM 有关,还是我的代码有问题?
已解决 - 这个问题与我的项目特定的代码块有关,这可能就是它如此独特的原因。
具体来说,我犯了一个关于通过 glm 旋转时影响哪些轴的错误。我第一次编码的方式是这样的:
// Variable to store the affected rotation axes
glm::vec3 _active_rotation_axes = glm::vec3(0, 0, 0);
// Get the affected axes for rotation
// 'active_rotation' stores the rotation values for each axis
_active_rotation_axes.x = (active_rotation.x != 0) ? 1 : 0;
_active_rotation_axes.y = (active_rotation.y != 0) ? 1 : 0;
_active_rotation_axes.z = (active_rotation.z != 0) ? 1 : 0;
// Keep in mind the above code is partly pseudocode, as I have simplified it heavily and typed it directly into the answer.
然后变量_active_rotation_axes
被这样使用:
if (_active_rotation_axes.x != 0) applied_transformation = glm::rotate(applied_transformation, active_rotation.x, glm::vec3(_active_rotation_axes.x, 0, 0));
if (_active_rotation_axes.y != 0) applied_transformation = glm::rotate(applied_transformation, active_rotation.y, glm::vec3(0, _active_rotation_axes.y, 0));
if (_active_rotation_axes.z != 0) applied_transformation = glm::rotate(applied_transformation, active_rotation.z, glm::vec3(0, 0, _active_rotation_axes.z));
这导致了我遇到的问题, 虽然我仍然不知道确切原因。
无论如何,最后我要做的就是删除第一个代码块,并将第二个代码块更改为以下代码,它直接检查 active_rotation
而不是现在不存在的变量 _active_rotation_axes
:
if (active_rotation.x != 0) applied_transformation = glm::rotate(applied_transformation, active_rotation.x, glm::vec3(1, 0, 0));
if (active_rotation.y != 0) applied_transformation = glm::rotate(applied_transformation, active_rotation.y, glm::vec3(0, 1, 0));
if (active_rotation.z != 0) applied_transformation = glm::rotate(applied_transformation, active_rotation.z, glm::vec3(0, 0, 1));
真的,我应该从一开始就这样做,因为它明显更加高效和简单。
我目前正在使用 GLM 在 OpenGL 中转换形状。但是,当形状的旋转介于 1 到 2 弧度之间时,表示旋转的矩阵值将设置回它们在单位矩阵中的值。我目前正在将模型矩阵输出到控制台,这有助于找出它转回 0 弧度旋转的确切时刻。这是:
控制台中每行的第一个值是作为单个值的旋转,以弧度表示。然后,输出形状的模型矩阵。
上传它的视频很烦人,但我相信你可以想象它 - 它只是一个正常旋转一段时间的形状,直到旋转达到一个弧度,此时它会重置为正常旋转。然后,当它达到两个弧度时,它又恢复正常,就好像从来没有问题一样。
变形相关的代码如下:
// NOTE: the variables 'active_translation, active_rotation, and active_scaling' are the values the user gives to translate, rotate, and scale the shape
// In this case, 'active_rotation' is equal to ~0.02 (1 degree in radians) every frame
void defshape::apply_transformations() {
// Create an identity matrix to store the applied transformations
glm::mat4 applied_transformation = glm::mat4(1.0f);
// Add the active translation to the stored transformations variable
applied_transformation = glm::translate(applied_transformation, active_translation);
// Apply the rotation to the mat4. For the sake of this example, I've only showed the Z axis line to simplify it as it's the only one being affected.
applied_transformation = glm::rotate(applied_transformation, active_rotation.z, glm::vec3(0, 0, 1));
// Add the active scale to the stored transformations variable
applied_transformation = glm::scale(applied_transformation, active_scaling);
// Apply these changes to the renderer by setting its model matrix and then updating it
renderer_handle->model_matrix = applied_transformation;
renderer_handle->update_renderer();
// Reset the translation of the model matrix back to 0
// This step ensures that the object rotates around its local origin, rather than the world space origin
applied_transformation = glm::translate(applied_transformation, glm::vec3(0.0f));
// Then apply this change to the renderer's model matrix
renderer_handle->model_matrix = applied_transformation;
renderer_handle->update_renderer();
}
这可能与 GLM 有关,还是我的代码有问题?
已解决 - 这个问题与我的项目特定的代码块有关,这可能就是它如此独特的原因。
具体来说,我犯了一个关于通过 glm 旋转时影响哪些轴的错误。我第一次编码的方式是这样的:
// Variable to store the affected rotation axes
glm::vec3 _active_rotation_axes = glm::vec3(0, 0, 0);
// Get the affected axes for rotation
// 'active_rotation' stores the rotation values for each axis
_active_rotation_axes.x = (active_rotation.x != 0) ? 1 : 0;
_active_rotation_axes.y = (active_rotation.y != 0) ? 1 : 0;
_active_rotation_axes.z = (active_rotation.z != 0) ? 1 : 0;
// Keep in mind the above code is partly pseudocode, as I have simplified it heavily and typed it directly into the answer.
然后变量_active_rotation_axes
被这样使用:
if (_active_rotation_axes.x != 0) applied_transformation = glm::rotate(applied_transformation, active_rotation.x, glm::vec3(_active_rotation_axes.x, 0, 0));
if (_active_rotation_axes.y != 0) applied_transformation = glm::rotate(applied_transformation, active_rotation.y, glm::vec3(0, _active_rotation_axes.y, 0));
if (_active_rotation_axes.z != 0) applied_transformation = glm::rotate(applied_transformation, active_rotation.z, glm::vec3(0, 0, _active_rotation_axes.z));
这导致了我遇到的问题, 虽然我仍然不知道确切原因。
无论如何,最后我要做的就是删除第一个代码块,并将第二个代码块更改为以下代码,它直接检查 active_rotation
而不是现在不存在的变量 _active_rotation_axes
:
if (active_rotation.x != 0) applied_transformation = glm::rotate(applied_transformation, active_rotation.x, glm::vec3(1, 0, 0));
if (active_rotation.y != 0) applied_transformation = glm::rotate(applied_transformation, active_rotation.y, glm::vec3(0, 1, 0));
if (active_rotation.z != 0) applied_transformation = glm::rotate(applied_transformation, active_rotation.z, glm::vec3(0, 0, 1));
真的,我应该从一开始就这样做,因为它明显更加高效和简单。