5

我已经能够找到我单击的地方的世界坐标,并且它还使用深度缓冲区检查它。为此,使用以下代码:

GLint viewport[4];
GLdouble modelview[16];
GLdouble projection[16];
GLfloat winX,winY;
glGetIntegerv(GL_VIEWPORT, viewport);
glGetDoublev(GL_MODELVIEW_MATRIX, modelview);
glGetDoublev(GL_PROJECTION_MATRIX, projection);

// obtain the Z position (not world coordinates but in range 0 - 1)
GLfloat z_cursor;
winX = (float)x_cursor;
winY = (float)viewport[3]-(float)y_cursor;
glReadPixels(winX, winY, 1, 1, GL_DEPTH_COMPONENT, GL_FLOAT, &z_cursor);

// obtain the world coordinates
GLdouble x, y, z;
gluUnProject(winX, winY, z_cursor, modelview, projection, viewport, &x, &y, &z);

x_cursor 和 y_cursor 是我的光标坐标。

到目前为止一切都很好,在打印 x,y,z 时它们似乎很好!

但是现在......在解析了包含所有多边形/三角形的文件之后。我把所有东西都放在了 openGL 显示列表中。所以我的程序基本上只是调用列表,并翻译/旋转它们。每个对象都有一个唯一的名称。所以我只保留列表,我不保留每个对象的点/三角形

我的问题 :

所以我有我点击位置的世界坐标,但我怎样才能确定哪个对象与该位置匹配!?

4

4 回答 4

4

如果您只想要对象 ID 并愿意容忍 2 倍透支:

1) 清除颜色和深度缓冲区

2) 用不同的纯色绘制所有对象(禁用光照和纹理),保持颜色 -> 对象 ID 映射。

3)在鼠标位置读取颜色缓冲区,注意颜色并在颜色图中查找。

4) 清除颜色和深度缓冲区并正常重新渲染场景。

于 2011-08-11T15:44:08.650 回答
1

我想你可能会感兴趣: http ://www.gpwiki.org/index.php/OpenGL:Tutorials:Picking

于 2011-08-11T15:29:49.127 回答
0

从眼睛的角度将光线投射到场景中。

使用矢量算法计算鼠标在近平面上单击的世界空间 xyz 位置。

这是您需要做的图表:

在此处输入图像描述

这比 unproject 更有效,因为 unproject 涉及矩阵求逆(这非常昂贵)

这正是您将用于将光线投射到场景中的过程,以便为点击的像素设置光线追踪器。(在光线追踪器中,您正在检索颜色,在这里您正在检索对象的 id)。

于 2012-11-27T01:55:44.160 回答
0

请参阅OpenGL 拾取教程。它包含一个完整的工作示例。但是,如果您只想选择离相机最近的对象(例如画在顶部的对象),似乎仍然可以改进代码。但是,您可以修改代码以获得此结果。

void list_hits(GLint hits, GLuint *names)
{
    int i; int bestmatch; GLuint bestdistance;
    if (hits < 1) {
      return;
    }
    bestmatch = 0;
    bestdistance = names[bestmatch*4+1]; // min distance to object.
    for (i = 1; i < hits; i++)
    {
        distance = names[i*4+1];
        if (distance < bestdistance) {
           bestmatch = i; bestdistance = distance;
        }
    }
    printf("Hit: %d.\n", bestmatch);
 }

警告:我以前做过这个,但是这个特定的代码没有经过测试。

于 2011-08-11T16:45:40.107 回答