The Reshape Callback

Ok, so I had to go back and re-read the documentation to get this working.

The default reshape callback (the one you get if you don’t call glutReshapeFunc()) calls glViewport(0, 0, w, h) and doesn’t change the coordinate system. The default coordinate system (which won’t change unless you call gluOrtho2D()) has its origin in thelower left corner of the window.

Unfortunately, the coordinate system used for the mouse position has its origin in the upper left corner. That means that if you don’t have a reshape callback, or if you call gluOrtho2d(0, w, 0, h);, you’ll end up with mouse coordinates that are the opposite of drawing coordinates. To fix that, you need to do one of two things:

  1. Subtract the mouse y-coordinate from the height of the window
  2. Change your drawing coordinate system to match the mouse coordinate system

Luckily, option (2) also allows us to resize the window without stretching the drawing or moving it all over the screen. Use the following reshape callback:

void reshape(int w, int h)
{
    glViewport(0, 0, w, h);
    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
    gluOrtho2D(0, w, h, 0);
}

Don’t forget to register the callback in main() with glutReshapeFunc(reshape).

Here’s what the function does:

glViewport(0, 0, w, h);

Specifies that the viewport rectangle should occupy the entire window. The default reshape callback does the same thing.

glMatrixMode(GL_PROJECTION);

We’re about to specify 2D Orthographic projection. The default matrix mode is GL_MODELVIEW, so we need to switch.

glLoadIdentity();

Clear any existing projection matrix

gluOrtho2D(0, w, h, 0);

Specify the left, right, bottom, and top clipping planes. Note that the bottom clipping plane is h, not 0.

Comments are closed.