Original Post
Hi, I posted a while back about GL_POINTS and videocard problems. Seems not all cards support all point sizes. It was suggested on the list I try to use GL_QUADS instead of points, which I've done. But now I've lost the picking capability. Not sure what's happening, and could use some advice. I understand ray picking is better, but I'm not quite at that level yet. This is a slight var. of the Kilgard ex. editgrid.c, but instead of points I'm using glquads, but can't seem to pick them. Thank you for comments, advice.
/* Adapted from Mark J. Kilgard editgrid.c, 1997. */
#include <windows.h>
#include <stdlib.h>
#include <stdio.h>
#include <GL/glut.h>
#define DEBUG
int antialiasing = 0;
int gridSize = 20;
GLuint selectedPoint = ~0;
int winWidth, winHeight;
GLuint selectBuffer[64];
GLdouble modelMatrix[16], projMatrix[16];
GLint viewport[4];
/* 4nd order initial grid. 16 points (4 by 4). */
GLfloat grid4x4[4][4][3] =
{
{
{-2.0, -2.0, 0.0},
{-0.5, -2.0, 0.0},
{0.5, -2.0, 0.0},
{2.0, -2.0, 0.0}},
{
{-2.0, -0.5, 0.0},
{-0.5, -0.5, 0.0},
{0.5, -0.5, 0.0},
{2.0, -0.5, 0.0}},
{
{-2.0, 0.5, 0.0},
{-0.5, 0.5, 0.0},
{0.5, 0.5, 0.0},
{2.0, 0.5, 0.0}},
{
{-2.0, 2.0, 0.0},
{-0.5, 2.0, 0.0},
{0.5, 2.0, 0.0},
{2.0, 2.0, 0.0}}
};
GLfloat quadpoints [4][4][3] =
{
//top left
{
{ -1.2f, 1.1f, 0.0f}, // Top Left
{ -1.0f, 1.1f, 0.0f}, // Top Right
{ -1.0f, 0.9f, 0.0f}, // Bottom Right
{ -1.2f, 0.9f, 0.0f}}, // Bottom Left
//top right square
{
{ 1.0f, 1.1f, 0.0f},// Top Left
{1.2f, 1.1f, 0.0f},// Top Right
{1.2f, 0.9f, 0.0f},// Bottom Right
{1.0f, 0.9f, 0.0f}},//Bottom Left
//bottom right square
{
{1.0f, -1.2f, 0.0f}, // Top Left
{1.2f, -1.2f, 0.0f}, // Top Right
{1.2f, -1.4f, 0.0f}, // Bottom Right
{1.0f, -1.4f, 0.0f}}, // Bottom Left
//bottomleft square
{
{-1.2f, -1.2f, 0.0f}, // Top Left
{-1.0f, -1.2f, 0.0f}, // Top Right
{-1.0f, -1.4f, 0.0f}, // Bottom Right
{-1.2f, -1.4f, 0.0f}} // Bottom Left
};
GLfloat *quad = &quadpoints[0][0][0];
GLfloat *grid = &grid4x4[0][0][0];
int uSize = 4;
int vSize = 4;
void
setupMesh(void)
{
glEnable(GL_MAP2_VERTEX_3);
glMapGrid2f(gridSize, 0.0, 1.0, gridSize, 0.0, 1.0);
}
void
evaluateGrid(void)
{
glColor3f(1.0, 1.0, 1.0);
glMap2f(GL_MAP2_VERTEX_3, 0, 1, 3, uSize, 0, 1, uSize * 3, vSize, grid);
glEvalMesh2(GL_LINE, 0, gridSize, 0, gridSize);
}
void
drawQuadPoints(void)
{
int i;
glColor3f(1.0, 1.0, 0.0);
glBegin(GL_QUADS);
for (i = 0; i < uSize * vSize; i++) {
glVertex3fv(&quad[i * 3]);
}
glEnd();
}
void
selectQuadPoints(void)
{
int i;
for (i = 0; i < uSize * vSize; i++) {
glLoadName(i);
glBegin(GL_QUADS);
glVertex3fv(&quad[i * 3]);
glEnd();
}
}
void
display(void)
{
glClear(GL_COLOR_BUFFER_BIT);
evaluateGrid();
drawQuadPoints();
glutSwapBuffers();
}
void
ortho(void)
{
if (winWidth <= winHeight)
glOrtho(-4.0, 4.0, -4.0 * (GLfloat) winHeight / (GLfloat) winWidth,
4.0 * (GLfloat) winHeight / (GLfloat) winWidth, -4.0, 4.0);
else
glOrtho(-4.0 * (GLfloat) winWidth / (GLfloat) winHeight,
4.0 * (GLfloat) winWidth / (GLfloat) winHeight, -4.0, 4.0, -4.0, 4.0);
}
GLuint
pick(int x, int y)
{
int hits;
(void) glRenderMode(GL_SELECT);
glInitNames();
glPushName(~0);
glMatrixMode(GL_PROJECTION);
glPushMatrix();
glLoadIdentity();
gluPickMatrix(x, winHeight - y, 8.0, 8.0, viewport);
ortho();
glMatrixMode(GL_MODELVIEW);
selectQuadPoints();
glMatrixMode(GL_PROJECTION);
glPopMatrix();
glMatrixMode(GL_MODELVIEW);
hits = glRenderMode(GL_RENDER);
if (hits) {
#ifdef DEBUG
{
unsigned int i;
GLint names;
GLuint *ptr;
printf("hits = %d\n", hits);
ptr = (GLuint *) selectBuffer;
for (i = 0; i < hits; i++) { /* for each hit */
int j;
names = *ptr;
printf("number of names for hit = %d\n", *ptr);
ptr++;
printf(" z1 is %g;", (float) *ptr / 0xffffffff);
ptr++;
printf(" z2 is %g\n", (float) *ptr / 0xffffffff);
ptr++;
printf(" the name is ");
for (j = 0; j < names; j++) { /* For each name. */
printf("%d ", *ptr);
ptr++;
}
printf("\n");
}
}
#endif
return selectBuffer[3];
} else {
return ~0;
}
}
void
reshape(int w, int h)
{
glViewport(0, 0, w, h);
winWidth = w;
winHeight = h;
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
ortho();
glGetDoublev(GL_PROJECTION_MATRIX, projMatrix);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glGetDoublev(GL_MODELVIEW_MATRIX, modelMatrix);
viewport[0] = 0;
viewport[1] = 0;
viewport[2] = winWidth;
viewport[3] = winHeight;
}
void
mouse(int button, int state, int x, int y)
{
if (button == GLUT_LEFT_BUTTON) {
if (state == GLUT_DOWN) {
selectedPoint = pick(x, y);
} //else {
//selectedPoint = -1;
//}
}
}
void
motion(int x, int y)
{
GLdouble objx, objy, objz;
if (selectedPoint != ~0) {
gluUnProject(x, winHeight - y, 0.95,
modelMatrix, projMatrix, viewport,
&objx, &objy, &objz);
grid[selectedPoint * 3 + 0] = objx;
grid[selectedPoint * 3 + 1] = objy;
glutPostRedisplay();
}
}
int
main(int argc, char **argv)
{
glutInit(&argc, argv);
glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB);
glutCreateWindow("editgrid");
glutReshapeFunc(reshape);
glutDisplayFunc(display);
glutMouseFunc(mouse);
glutMotionFunc(motion);
glSelectBuffer(sizeof(selectBuffer), selectBuffer);
setupMesh();
glutMainLoop();
return 0; /* ANSI C requires main to return int. */
}