18

I have an object which I first want to rotate (about its own center) then translate it to some point. I have a glm::quat that holds the rotation and a glm::vec3 that holds the point to which it needs to be translated.

glm::vec3 position;
glm::quat orientation;
glm::mat4 modelmatrix; <-- want to combine them both in here

modelmatrix = glm::translate(glm::toMat4(orientation),position);

Then at my render function, I do.

pvm = projectionMatrix*viewMatrix*modelmatrix;
glUniformMatrix4fv(pvmMatrixUniformLocation, 1, GL_FALSE, glm::value_ptr(pvm));

..and render...

Unfortunately, the object just orbits around the origin when I apply a rotation (the farther the "position" from the origin, the larger the orbit).

When I apply for only the position it translates fine. When I apply only the rotation it stays at the origin and rotates about its center (as expected). So why does it go weird when I apply them both? Am I missing something basic?

genpfault
  • 51,148
  • 11
  • 85
  • 139
Jubei
  • 1,686
  • 1
  • 17
  • 28

1 Answers1

30

Because you're applying them in the wrong order. By doing glm::translate(glm::toMat4(orientation),position), you are doing the equivalent of this:

glm::mat4 rot = glm::toMat4(orientation);
glm::mat4 trans = glm::translate(glm::mat4(1.0f), position);
glm::mat4 final = rot * trans;

Note that the translation is on the right side of the matrix, not the left. This means that the translation happens first, then the rotation happens relative to the translation. So rotation happens in the space after translation.

You want the rotation to happen first. So reverse the order of the matrix multiplication.

Nicol Bolas
  • 449,505
  • 63
  • 781
  • 982
  • I was under the impression that glm::translate applies the translation to the 1st argument of the function. Thank you. – Jubei Mar 30 '12 at 02:03
  • 3
    @Jubei: It *does* apply the translation to the matrix. It right-multiplies it. That means the translation occurs *first*, when you want the rotation to happen first. – Nicol Bolas Mar 30 '12 at 02:10
  • Thanks for this answer, I've been stuck on this a while today, but even though I figured out what I was doing wrong I simply couldn't find any confirmation that this is how the functions are supposed to work. – Adam Goodwin Aug 14 '13 at 03:47
  • Why are the functions backwards like this? I think the intuitive meaning would be for the matrix you passed in to have the translation applied *afterwards*. Is there a specific reason for this choice? – Gary Allen Aug 03 '21 at 10:55