OpenGL rotation d'une texture 2D

Mise à JOUR

Voir en bas pour la mise à jour.


J'ai été à la recherche de beaucoup de choses autour de l'internet et j'ai trouvé quelques tutoriels qui expliquent ce que je suis en train de réaliser, mais je ne peux pas le faire fonctionner, le tutoriel est incomplète ou n'est pas applicable sur mon code.

Je suis en train d'essayer quelque chose d'aussi simple que la rotation d'une image 2D autour de son origine (au centre).

- Je utiliser xd, xa, yd et yEnd pour inverser la texture qui est soit 0 ou 1.

C'est ce à quoi ressemble le code

GameRectangle dest = destination;
Vector2 position = dest.getPosition();

glEnable(GL_TEXTURE_2D);

glBindTexture(GL_TEXTURE_2D, this->image);

//If the rotation isn't 0 we'll rotate it
if (rotation != 0)
{
    glMatrixMode(GL_TEXTURE);

    glLoadIdentity();
    glTranslatef(0.5, 0.5, 0);
    glRotatef(rotation, 0, 0, 1);

    glMatrixMode(GL_PROJECTION);
}

glBegin(GL_QUADS);
glTexCoord2d(xStart,yStart);
glVertex2f(position.x, position.y);

glTexCoord2d(xEnd,yStart);
glVertex2f(position.x + this->bounds.getWidth(), position.y);

glTexCoord2d(xEnd,yEnd); 
glVertex2f(position.x + this->bounds.getWidth(), position.y + this->bounds.getHeight());

glTexCoord2d(xStart,yEnd);
glVertex2f(position.x, position.y + this->bounds.getHeight());

glEnd();

glDisable(GL_TEXTURE_2D);

//Reset the rotation so next object won't be rotated
glMatrixMode(GL_TEXTURE);

glLoadIdentity();
glRotatef(0, 0, 0, 1);

glMatrixMode(GL_PROJECTION);

Ce code va afficher l'image dans sa taille d'origine et il va tourner, mais il la fera tourner dans le coin supérieur gauche qui recadre l'image de beaucoup. En appelant GameRectangle.getOrigin (), je peux facilement obtenir le centre du rectangle, mais je ne sais pas où l'utiliser.

Peu si mettre:

 glTranslatef(-0.5, -0.5, 0);

Après j'appelle le:

 glRotatef(0.5, 0.5, 0);

Il tournera à partir du centre, mais il va étirer l'image si elle n'est pas une parfaite rotation de 90 degrés.

Mise à JOUR


Après avoir essayé à peu près tout est possible, j'ai obtenu le résultat que je cherchais.

Mais je ne sais pas si c'est la meilleure approche. Veuillez me dire si il ya quelque chose de mal avec mon code.

Comme je l'ai mentionné dans un commentaire ci-dessus, j'utilise la même image plusieurs fois et de le faire avec des valeurs différentes, donc je ne peux pas sauver quoi que ce soit à l'image réelle. Donc, je dois réinitialiser les valeurs à chaque fois après que j'ai rendu.

J'ai changé mon code de cette fonction:

//Store the position temporary
GameRectangle dest = destination;
Vector2 position = dest.getPosition();

glEnable(GL_TEXTURE_2D);

glBindTexture(GL_TEXTURE_2D, this->image);

glTranslatef(dest.getOrigin().x, dest.getOrigin().y, 0);
glRotatef(rotation, 0, 0, 1);

glBegin(GL_QUADS);
glTexCoord2d(xStart,yStart);
glVertex2f(-dest.getWidth()/2, -dest.getHeight()/2);

glTexCoord2d(xEnd,yStart);
glVertex2f(dest.getWidth()/2, -dest.getHeight()/2);

glTexCoord2d(xEnd,yEnd); 
glVertex2f(dest.getWidth()/2, dest.getHeight()/2);

glTexCoord2d(xStart,yEnd);
glVertex2f(-dest.getWidth()/2, dest.getHeight()/2);

glEnd();

//Reset the rotation and translation
glRotatef(-rotation,0,0,1);
glTranslatef(-dest.getOrigin().x, -dest.getOrigin().y, 0);

glDisable(GL_TEXTURE_2D);

Rotation de la texture avec le quad c'est aspirée, il n'a pas d'allongement ou de la culture. Cependant, les bords sont un peu irréguliers si l'image est carrée remplie, mais je suppose que je ne peux pas éviter que avec antialiasing.

  • Voulez-vous vraiment à la rotation de la texture et de ne pas le quad? En tout cas, si vous êtes déjà à l'aide de l'OpenGL matrices, vous devez utiliser la matrice de la pile, c'est à dire, glPushMatrix et glPopMatrix, au lieu de la réinitialisation de la matrice à la fin de votre code.
  • Si juste en tournant le quad est assez je suppose que c'est ce que voulez. Sera que la rotation de la texture avec le quad et comment faire tourner le quad correctement?
  • Aussi, je ne sais pas où appeler glPushMatrix() et glPopMatrix(), si jamais je les ai mis, je n'obtenez pas le résultat souhaité, il tourne toutes les images ou pas d'images. Je ne sais pas si cela fait une différence, mais j'en tire la même image plusieurs fois mais avec des valeurs différentes pour la rotation etc, donc je ne peux pas sauver quoi que ce soit à l'image réelle.
  • En général, avant de modifier la matrice, vous faites quelque chose comme cela: glMatrixMode(...); glPushMatrix(); doStuff(); glPopMatrix(); Avez-vous essayé permettant le filtrage via glTexEnv et voir si ça aide avec vos bords irréguliers?
  • Mon "moteur" ressemble beaucoup au XNA framework où j'appelle le rendu.begin() qui ne: glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glPushMatrix(); glOrtho(0, frameWidth, frameHeight, 0, -1, 1); et puis le rendu.end() qui n': glPopMatrix(); SDL_GL_SwapBuffers(); Et entre les deux je dessine chaque objet individuel. J'ai donc utiliser glPopMatrix et PushMatrix(), mais pas tout à fait comme vous l'avez suggéré. Désolé, mais je ne sais rien à propos de glTexEnv, mais je l'ai fait essayer glEnable(GL_POLYGON_SMOOTH) qui fixe les bords irréguliers mais dessine alors un blanc/transparent ligne diagonale à travers mes quads. :S
  • En fait je voulais dire glTexParameter, de sorte que vous pouvez activer Mip-Mapping ou au moins linéaire filtrage. Si vous faites un glPushMatrix dans la mise à jour de votre code juste avant la glTranslatef et glPopMatrix après glEnd, vous n'avez pas besoin de "défaire" de votre rotation, ainsi que l'économie de plusieurs inutile d'opérations en virgule flottante. Il pourrait ne pas être un problème maintenant, mais il peut se transformer en un peu plus vite 😀
  • J'ai réussi à obtenir le push et pop pour fonctionner correctement, merci!

InformationsquelleAutor Orujimaru | 2012-02-16