Drawing XYZ axis

Hi,

I’m trying to draw a set of XYZ axis in the corner of the screen which will show the orientation. I want these to rotate when the rest of my scene rotates, but to stay in the same position when I translate my scene. i can draw the axis fine although when I move the scene they also move.

any suggestions much appreciated

Cheers

glRotate*(x…)
glRotate*(y…)
glRotate*(z…)

glPushMatrix()

glTranslate*(x,y,z)

Draw_Scene()

glPopMatrix()

Draw_XYZ_Axis()

Hi,

7 years later I try to do the same!
I want a little coordinate system in the left corner of my canvas that shows the current rotation of the world coordinate system. That means: only the rotating stuff is effecting the three drawn axis, whereas everything that is not related to rotating for instance translating or zooming should not do anything to the little coordinate system, so it stays forever there in the corner.
how would you realize it?. I am using webgl (opengl es 2.0).

cheeeers!

Take unit axis vectors, multiply by modelview, normalize (in case modelview has scales).

If your modelview doesn’t have scales or shears, you can just grab the axis vectors out of the upper-left 3x3. Same as multiply by unit vectors.

what? i thought this a beginner forum…
not i don’t have any scales or shears in my mvmatrix.

can someone explain in more detail pleae :o ?

thank you

Your modelview matrix:

R R R t
R R R t
R R R t
t t t t

Copy the R parts into a 3x3 matrix.
Multiply that matrix by vectors vec3(1,0,0), vec3(0,1,0), vec3(0,0,1). The results will be 3 vec3 vectors, rotated the way you want.
Also, you’ll note those vectors are identical with columns from the matrix. (that’s why Dark Photon mentioned you can simply use those columns)

Setup the projection to be orthographic or whatever, and set the viewport to cover only a small area from the bottom-left or wherever you want the axes to be drawn.

Draw 3 lines, starting from vec3(0,0,0) and ending with each of those 3 vectors you calculated before. Done :slight_smile:

P.S. if you had scales and shears, you’d simply have to normalize the 3 vectors (otherwise - if you’re just doing rotation and translation, they happen to be already normalized)

thank you for explaining that, now everything is much clearer!

that means i have to set multiple viewports?

Not really. It’s kinda like “okay gpu, now I’ll draw only on this rectangle”. Don’t forget to restore the viewport ASAP, though; nasties happen otherwise :slight_smile: .
The alternative would be to create a nice projection/modelview matrix that will transform everything to the specific corner. It’s preferable, but I can’t compose/recall the maths for it right now.

Don’t forget to restore the viewport ASAP

I’m failing setting up this steps… how do I set only a small area of the viewport and when to do it?

glViewport(0,0,100,100);

:smiley: yes it works!

thank you guys!!

now it’s time to celebrate this.

regards

Here’s a small OpenGL program that does what you want. Hope I’m not doing your homework for you. Sorry but my indentations got messed up during the cut and paste process.


//******************************************************************************
//********************       OpenGL Triad Demo          ************************
//********************     Max H - July 23, 2010        ************************

// This demo shows how to position a small triad in the lower left corner of
// the graphics window that rotates the same way as the objects in the scene.
// To keep the code to a minimum, no lighting or Z-buffering is used.
// To translate the objects, use h,H and v,V.
// To rotate the objects, use x,y,z and X,Y,Z.
// To scale object, use s, or S.
// Use Esc key to quit program.


#include <glut.h>
#include <stdlib.h>
#include <math.h>

float  xpos = 0.0, ypos = 0.0, xrot = 0.0, yrot = 0.0, zrot = 0.0, scal = 1.0;


// -----------------------------------------------------------------------------

void keyboard (unsigned char key, int x, int y) {

   switch (key) {

      case 'x':  xrot += 5.0;   glutPostRedisplay();  break;
      case 'y':  yrot += 5.0;   glutPostRedisplay();  break;
      case 'z':  zrot += 5.0;   glutPostRedisplay();  break;

      case 'X':  xrot -= 5.0;   glutPostRedisplay();  break;
      case 'Y':  yrot -= 5.0;   glutPostRedisplay();  break;
      case 'Z':  zrot -= 5.0;   glutPostRedisplay();  break;

      case 's':  scal *= 1.1;   glutPostRedisplay();  break;
      case 'S':  scal *= 0.9;   glutPostRedisplay();  break;

      case 'h':  xpos += 0.1;   glutPostRedisplay();  break;
      case 'H':  xpos -= 0.1;   glutPostRedisplay();  break;

      case 'v':  ypos += 0.1;   glutPostRedisplay();  break;
      case 'V':  ypos -= 0.1;   glutPostRedisplay();  break;

	  case  27:  exit (0);

      default :  printf ("   key = %c -> %d
", key, key);
   }
}

// -----------------------------------------------------------------------------

// Draws a 3D axis in the Z direction using two cylinders.

void Axis_3D (void)
{

    GLUquadric* cyl = gluNewQuadric();

    gluCylinder (cyl, 0.02, 0.02, 0.8, 16, 1);        // Body of axis.

	glColor3f (1,1,5);                                // Make arrow head white.
	glPushMatrix ();
       glTranslatef (0.0, 0.0, 0.8);
       gluCylinder  (cyl, 0.04, 0.001, 0.08, 12, 1);  // Cone at end of axis.
	glPopMatrix ();
}

// -----------------------------------------------------------------------------

void Triad_3D (void)
{
    GLUquadric* cyl = gluNewQuadric();

    glColor3f (0.3, 0.3, 1.0);    // Z axis in blue.
	Axis_3D ();

    glColor3f (0.3, 1.0, 0.3);    // Y axis is green.
	glPushMatrix ();
	   glRotatef (-90, 1,0,0);
       Axis_3D ();
	glPopMatrix ();

    glColor3f (1.0, 0.3, 0.3);    // X axis is red.
	glPushMatrix ();
	   glRotatef (90, 0,1,0);
       Axis_3D ();
	glPopMatrix ();
}

// -----------------------------------------------------------------------------

void Corner_Triad (void)
{
   glViewport     (0, 0, 150, 150);
   glMatrixMode   (GL_PROJECTION);
   glLoadIdentity ();
   gluPerspective (65.0, 1.0, 1.0, 20.0);
   glMatrixMode   (GL_MODELVIEW);
   glLoadIdentity ();

   glTranslatef (0, 0, -2);   // Place small triad between clipping planes.

   glRotatef (zrot, 0,0,1);   // Viewing rotations.
   glRotatef (yrot, 0,1,0);
   glRotatef (xrot, 1,0,0);

   Triad_3D ();
}

// -----------------------------------------------------------------------------

void display (void)
{
   glViewport     (0, 0, 800, 600);
   glMatrixMode   (GL_PROJECTION);
   glLoadIdentity ();
   gluPerspective (65.0, 1.33, 1.0, 20.0);
   glMatrixMode   (GL_MODELVIEW);

   glClear (GL_COLOR_BUFFER_BIT);

   glLoadIdentity ();

   glTranslatef (xpos, ypos, -3);  // Translations.

   glRotatef (zrot, 0,0,1);        // Rotations.
   glRotatef (yrot, 0,1,0);
   glRotatef (xrot, 1,0,0);

   glScalef (scal, scal, scal);    // Sizing.
   Triad_3D ();

   Corner_Triad ();

   glutSwapBuffers ();
}

// -----------------------------------------------------------------------------

int main (int argc, char** argv)
{
    glutInit               (&argc, argv);
    glutInitDisplayMode    (GLUT_DOUBLE | GLUT_RGB);
    glutInitWindowSize     (800, 600);
    glutInitWindowPosition (200, 100);
    glutCreateWindow       (argv[0]);
    glutDisplayFunc        (display);
    glutKeyboardFunc       (keyboard);
    glutMainLoop           ();
}

// -----------------------------------------------------------------------------
// -----------------------------------------------------------------------------

Y’all forgot the ‘x’ ‘y’ ‘z’ letters at the end of each vector line… :slight_smile:

RGB color coding is enough for a start.

A better version …


//******************************************************************************
//********************       OpenGL Triad Demo          ************************
//********************     Max H - July 25, 2010        ************************

// This demo shows how to position a small triad in the lower left corner of
// the graphics window that rotates the same way as the objects in the scene.
// To keep the code to a minimum, no lighting or Z-buffering is used.
// To translate the objects, use h,H and v,V.
// To rotate the objects, use x,y,z and X,Y,Z.
// To scale object, use s, or S.
// Use Esc key to quit program.


#include <glut.h>
#include <stdlib.h>
#include <math.h>

float  xpos = 0.0, ypos = 0.0, xrot = 0.0, yrot = 0.0, zrot = 0.0, scal = 1.0;


// -----------------------------------------------------------------------------

void keyboard (unsigned char key, int x, int y)
{
   switch (key) {

      case 'x':  xrot += 5.0;  break;
      case 'y':  yrot += 5.0;  break;
      case 'z':  zrot += 5.0;  break;

      case 'X':  xrot -= 5.0;  break;
      case 'Y':  yrot -= 5.0;  break;
      case 'Z':  zrot -= 5.0;  break;

      case 's':  scal *= 1.1;  break;
      case 'S':  scal *= 0.9;  break;

      case 'h':  xpos += 0.1;  break;
      case 'H':  xpos -= 0.1;  break;

      case 'v':  ypos += 0.1;  break;
      case 'V':  ypos -= 0.1;  break;

      case  27:  exit (0);

      default :  printf ("   key = %c -> %d
", key, key);
   }

   glutPostRedisplay();
}

// -----------------------------------------------------------------------------

// Draws a 3D axis in the Z direction using two cylinders.

void Axis_3D (void)
{
    GLUquadric* cyl = gluNewQuadric();

    gluCylinder (cyl, 0.02, 0.02, 0.8, 16, 1);        // Body of axis.

    glColor3f (1,1,1);                                // Make arrow head white.
    glPushMatrix ();
       glTranslatef (0.0, 0.0, 0.8);
       gluCylinder  (cyl, 0.04, 0.001, 0.1, 12, 1);   // Cone at end of axis.
    glPopMatrix ();
}

// -----------------------------------------------------------------------------

void Triad_3D (void)
{
    glColor3f           (0.3, 0.3, 1.0);    // Z axis in blue.
    glRasterPos3f       (0.0, 0.0, 1.1);
    glutBitmapCharacter (GLUT_BITMAP_HELVETICA_18, 'Z');
    Axis_3D ();

    glColor3f           (0.3, 1.0, 0.3);    // Y axis is green.
    glRasterPos3f       (0.0, 1.1, 0.0);
    glutBitmapCharacter (GLUT_BITMAP_HELVETICA_18, 'Y');
    glPushMatrix ();
       glRotatef (-90, 1,0,0);
       Axis_3D ();
    glPopMatrix ();

    glColor3f           (1.0, 0.3, 0.3);    // X axis is red.
    glRasterPos3f       (1.1, 0.0, 0.0);
    glutBitmapCharacter (GLUT_BITMAP_HELVETICA_18, 'X');
    glPushMatrix ();
       glRotatef (90, 0,1,0);
       Axis_3D ();
    glPopMatrix ();
}

// -----------------------------------------------------------------------------

void Corner_Triad (void)
{
   glViewport     (0, 0, 150, 150);
   glMatrixMode   (GL_PROJECTION);
   glLoadIdentity ();
   gluPerspective (65.0, 1.0, 1, 20);
   glMatrixMode   (GL_MODELVIEW);
   glLoadIdentity ();

   glTranslatef (0, 0, -3);   // Place small triad between clipping planes.

   glRotatef (zrot, 0,0,1);   // Viewing rotations.
   glRotatef (yrot, 0,1,0);
   glRotatef (xrot, 1,0,0);

   Triad_3D ();
}

// -----------------------------------------------------------------------------

void display (void)
{
   glViewport     (0, 0, 800, 600);
   glMatrixMode   (GL_PROJECTION);
   glLoadIdentity ();
   gluPerspective (65.0, 1.33, 1.0, 20.0);
   glMatrixMode   (GL_MODELVIEW);

   glClear (GL_COLOR_BUFFER_BIT);

   glLoadIdentity ();

   glTranslatef (xpos, ypos, -3);  // Translations.

   glRotatef (zrot, 0,0,1);        // Rotations.
   glRotatef (yrot, 0,1,0);
   glRotatef (xrot, 1,0,0);

   glScalef (scal, scal, scal);    // Sizing.
   Triad_3D ();

   Corner_Triad ();

   glutSwapBuffers ();
}

// -----------------------------------------------------------------------------

int main (int argc, char** argv)
{
    glutInit               (&argc, argv);
    glutInitDisplayMode    (GLUT_DOUBLE | GLUT_RGB);
    glutInitWindowSize     (800, 600);
    glutInitWindowPosition (200, 100);
    glutCreateWindow       (argv[0]);
    glutDisplayFunc        (display);
    glutKeyboardFunc       (keyboard);
    glutMainLoop           ();
}

// -----------------------------------------------------------------------------
// -----------------------------------------------------------------------------