[英]OpenGL 3D Selection
我正在嘗試創建一個3D機器人,在點擊某些身體部位時應執行某些操作。 我已經成功(有點)實施了揀選,如果你點擊任何x平面部分,它會記錄一個命中,但不是其他任何地方。 也就是說,它沒有注冊深度,如果你點擊它的方頭,你只能通過點擊頭部的正面(面向你)來注冊命中。 顯然,我並不完全理解挑選和選擇,我正在努力將我對2D選擇的了解轉錄為3D(我的老師和搖滾一樣有用),但是我遺漏了一些東西,或者沒有改變與深度相關的東西。 誰能幫我嗎? 以下是相關功能。
void processHits (GLint hits, GLuint buffer[])
{
unsigned int i, j;
GLint n, *ptr;
printf ("hits = %d\n", hits);
ptr = (GLint *) buffer;
//For each hit.
for (i = 0; i < hits; i++)
{
n = *ptr; //Number of names under current hit.
ptr+=3; //Bypass three integers: n, z1, z2.
printf ("hit %d has %d name(s)\n", i, n);
//For each name.
for (j = 0; j < n; j++)
{
if(*ptr==1) printf ("Body hit.\n");
else if(*ptr==2) printf ("Right shoulder hit.\n");
else if(*ptr==3) printf ("Left shoulder hit.\n");
else if(*ptr==4) printf ("Left arm hit.\n");
else if(*ptr==5) printf ("Right arm hit.\n");
else if(*ptr==6) printf ("Left leg hit.\n");
else if(*ptr==7) printf ("Right leg hit.\n");
else if(*ptr==8) printf ("Right foot hit.\n");
else if(*ptr==9) printf ("Left foot hit.\n");
else if(*ptr==10) printf ("Neck hit.\n");
else if(*ptr==11) printf ("Head hit.\n");
else printf ("Nothing hit.\n");
ptr++;
}
printf ("\n");
}
}
void selection(int mouse_x, int mouse_y)
{
GLuint buffer[512]; //Set up a selection buffer.
GLint hits; //The number of objects we selected.
GLint viewport[4]; //Viewport size. [0] Is <x>, [1] Is <y>, [2] Is <length>, [3] Is <width>.
glGetIntegerv(GL_VIEWPORT, viewport); //Sets the array <viewport> to size and location of screen relative to window.
glSelectBuffer(512, buffer); //Tell OpenGL to use our array for selection.
glRenderMode(GL_SELECT); //Puts OpenGL in selection mode. Nothing will be drawn. Object IDs and extents stored in buffer.
glInitNames(); //Initializes name stack.
glPushName(0); //Push an entry onto the stack.
glMatrixMode(GL_PROJECTION); //Selects the projection matrix.
glPushMatrix(); //Push the projection matrix.
glLoadIdentity(); //Resets matrix.
//This creates a matrix that will zoom up to a small portion of the screen, where the mouse is.
gluPickMatrix((GLdouble) mouse_x, (GLdouble) (viewport[3]-mouse_y), 0.01, 0.01, viewport);
gluPerspective(45.0f, (GLfloat) (viewport[2]-viewport[0])/(GLfloat) (viewport[3]-viewport[1]), 0.1f, 100.0f);
glMatrixMode(GL_MODELVIEW); //Select the modelview matrix.
drawObjects(GL_SELECT); //Render the targets to the selection buffer.
glMatrixMode(GL_PROJECTION); //Select the projection matrix.
glPopMatrix(); //Pop the projection matrix.
glMatrixMode(GL_MODELVIEW); //Select the modelview matrix.
hits = glRenderMode(GL_RENDER);
processHits (hits, buffer);
//printf("%d ", hits);
//Post redisplay message.
glutPostRedisplay();
}
void mouse(int button, int state, int x, int y)
{
if (button == GLUT_LEFT_BUTTON && state == GLUT_DOWN)
{
selection(x, y);
}
}
你要求的並不完全清楚。 如果你的意思是你只獲得了最前面的對象的命中記錄,那就是那種預期。 剔除的多邊形不會產生任何命中記錄。 如果你想要通常被剔除的多邊形的命中記錄,你將需要使用glDisable(GL_CULL_FACE);
在選擇模式下進行繪圖時。 這可以防止多邊形被剔除,因此它們可以生成命中記錄。
在此處閱讀使用Back Buffer選擇對象選擇。 我實施了一次,效果很好。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.