Search code examples
copenglglutvertex-array

Draw a series of points with vertex array : nothing displayed


I'm trying for exercise to do the following: there is an array of points, expressed through couples of GLfloats.The user should click in a point in the window to make another points appear.When a point is added, the window shall be redrawn and the points shall display connected with a line.So the user shall be able to draw lines clicking on some locations of the windows.
In this code whenever there's a click I push a point in the vector, but the points is not added, so I just see the gray window (APPLE_GRAY defined in header) without the points.

#include <OpenGL/OpenGL.h>
#include <GLUT/GLUT.h>
#include <stdio.h>
#include <stdlib.h>
#include "utility.h"

const int width=500;
const int height=500;

GLfloat* points;
size_t size=100;
int count=0;

void pushPoint(GLfloat x, GLfloat y)
{
    count++;
    if(count>size)
    {
        size+=100;
        points=(GLfloat*)realloc(points,2*size*sizeof(GLfloat));
    }
    points[2*count-2]=x;
    points[2*count-1]=y;
}

void init()
{
    points=(GLfloat*)malloc(2*size*sizeof(GLfloat));
    glutInitDisplayMode(GLUT_RGB | GLUT_DOUBLE | GLUT_DEPTH);
    glLoadIdentity();
    glOrtho(0, width, height, 0, 0, 1);
    glViewport(0, 0, 500, 500);
    glEnable(GL_DEPTH_TEST);
    glMatrixMode(GL_PROJECTION);
}

void display()
{
    glClearColor(APPLE_GRAY);
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    glColor4f(RED);
    glEnableClientState(GL_VERTEX_ARRAY);
    glVertexPointer(2, GL_FLOAT, 0, points);
    glDrawElements(GL_LINE_LOOP,count,GL_FLOAT,points);
    glFlush();
    glDisableClientState(GL_VERTEX_ARRAY);
}

void mouse(int button, int state, int x, int y)
{
    if(state)
    {
        pushPoint(x, y);
        glutPostRedisplay();
    }
}

void motion(int x, int y)
{
}

int main(int argc, char** argv)
{
    glutInit(&argc, argv);
    glutInitWindowPosition(100, 100);
    glutInitWindowSize(width,height);
    glutCreateWindow("Test");
    glutDisplayFunc(display);
    glutMouseFunc(mouse);
    glutMotionFunc(motion);
    init();
    glutMainLoop();
    return 0;
}

Solution

  • Again, glutInitDisplayMode() needs to be called before glutCreateWindow().

    GL_FLOAT is not a valid value for type in glDrawElements(). Also, points is not an index array.

    Use glDrawArrays():

    #include <GL/glut.h>
    
    const int width=500;
    const int height=500;
    
    GLfloat* points;
    size_t size=100;
    int count=0;
    
    void pushPoint(GLfloat x, GLfloat y)
    {
        count++;
        if(count>size)
        {
            size+=100;
            points=(GLfloat*)realloc(points,2*size*sizeof(GLfloat));
        }
        points[2*count-2]=x;
        points[2*count-1]=y;
    }
    
    void init()
    {
        points=(GLfloat*)malloc(2*size*sizeof(GLfloat));
        glMatrixMode(GL_PROJECTION);
        glLoadIdentity();
        glOrtho(0, width, height, 0, 0, 1);
        glEnable(GL_DEPTH_TEST);
    }
    
    void display()
    {
        glClearColor(0,0,0,0);
        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
        glColor3ub(255,0,0);
        glEnableClientState(GL_VERTEX_ARRAY);
        glVertexPointer(2, GL_FLOAT, 0, points);
        glDrawArrays(GL_LINE_LOOP,0,count);
        glDisableClientState(GL_VERTEX_ARRAY);
        glutSwapBuffers();
    }
    
    void mouse(int button, int state, int x, int y)
    {
        if(state)
        {
            pushPoint(x, y);
            glutPostRedisplay();
        }
    }
    
    int main(int argc, char** argv)
    {
        glutInit(&argc, argv);
        glutInitWindowPosition(100, 100);
        glutInitWindowSize(width,height);
        glutInitDisplayMode(GLUT_RGB | GLUT_DOUBLE | GLUT_DEPTH);
        glutCreateWindow("Test");
        glutDisplayFunc(display);
        glutMouseFunc(mouse);
        init();
        glutMainLoop();
        return 0;
    }