Sign in to follow this  

ortho2d view changed on re-display

This topic is 1593 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Hi,

I'm trying out a zooming in-and-out with orthogonal projection. The following program changes the orthogonal projection between -200...200 by -200..200 (largest) to -100...100 by -100...100 (smallest). 4 triangles are drawn.

Everything seems to work fine if I let the program run on its own. (I don't care about aspect ratio for now.) But then I noticed something.

If I force a redisplay by covering my opengl program's window *completely* with another window, I notice that frequently the objects (the 4 triangles) drawn have been scaled. The scaling can be quite random. Furthermore, if the program's window is only partially covered and then revealed, everything would be fine and the 4 triangles are not scaled. The random scaling occurs only when the program's window is *fully* covered by another window. The same problem also occurs if I minimize and then maximize the program's window.

However I notice that the display is fine if I just drag and move the program's window around.

Can someone explain what's happening? I'm sure I'm missing something very important here.

#include <GL/freeglut.h>
         
const int M = 400;      // window is M-by-M
float x = M/2, y = M/2; // gluOrtho2d is set to -x....x by -y...y.
         
const float abs_d = 50; // speed of zooming
float d = -abs_d;       // velocity of zooming
         
int prev_time;
         
void display()
{
    // Calculate new x, y for new ortho2d viewing volume
    int curr_time = glutGet(GLUT_ELAPSED_TIME);
    float elapsed_time = (curr_time - prev_time) / 1000.0;
    prev_time = curr_time;
    if (elapsed_time <= 0) return;    
    float dt = elapsed_time; // shorthand
    x += d * dt;
    y += d * dt;
         
    if (x < 100) 
    {
        d = abs_d; // switch to zoom out 
        x = 100; y = 100;
    }
    else if (x > M/2) 
    {
        d = -abs_d; // switch to zoom in
        x = M/2; y = M/2;
    }
         
    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
    gluOrtho2D(-x, x, -y, y);
         
    // Draw 4 triangles
    glClear(GL_COLOR_BUFFER_BIT);
         
    glBegin(GL_TRIANGLES);
         
    glColor3f(1.0f, 0.0f, 0.0f);
    glVertex2f(0, 0);
    glVertex2f(-100, 0);
    glVertex2f(-100, 100);
         
    glColor3f(0.0f, 1.0f, 0.0f);
    glVertex2f(100, 0);
    glVertex2f(180, 0);
    glVertex2f(50, -100);
         
    glColor3f(0.0f, 0.0f, 1.0f);
    glVertex2f(-50, 0);
    glVertex2f(0, -100);
    glVertex2f(0, -150);
         
    glColor3f(0.5f, 0.5f, 0.5f);
    glVertex2f(100, 150);
    glVertex2f(50, 120);
    glVertex2f(100, 70);
         
    glEnd();        
    glutSwapBuffers();
}
         
void timer_callback(int x)
{
     glutPostRedisplay();
     glutTimerFunc(50, timer_callback, 0);
}
         
int main(int argc, char ** argv)
{
     glutInit(&argc, argv);
     glutInitWindowPosition(0, 0);
     glutInitWindowSize(M, M);
     glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGBA);
     glutCreateWindow("test");
     glClearColor(1.0, 1.0, 1.0, 0.0);
     glutDisplayFunc(display);
         
     glutTimerFunc(50, timer_callback, 0);
     prev_time = glutGet(GLUT_ELAPSED_TIME);
     glEnable(GL_SMOOTH);
     glutMainLoop();
         
     return 0;
}

Share this post


Link to post
Share on other sites

Maybe the projection and model-view matrices are being confused? I see you're setting the projection matrix in the display function - I set my model-view matrix there, and set the projection matrix only when changing the window size. From the sound of what triggers the bug, it sounds like checking your window resize callback might be a good idea :)

Share this post


Link to post
Share on other sites

This topic is 1593 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this