C++ 在OpenGl中获取返回错误值的模型坐标
我有一个小程序画了几个球体,然后我试着右键点击它们。单击鼠标右键后,它在近平面和远平面之间绘制一条线,单击鼠标时在鼠标下方。然而,它会产生奇怪的结果,比如说,这条线已经走了相当长的一段路。这条线的方向是右的,但是,这条线可能是沿着X向左10,或者沿着Y向右5(这些是随机的例子) 这是我的密码: 定位摄像机C++ 在OpenGl中获取返回错误值的模型坐标,c++,opengl,C++,Opengl,我有一个小程序画了几个球体,然后我试着右键点击它们。单击鼠标右键后,它在近平面和远平面之间绘制一条线,单击鼠标时在鼠标下方。然而,它会产生奇怪的结果,比如说,这条线已经走了相当长的一段路。这条线的方向是右的,但是,这条线可能是沿着X向左10,或者沿着Y向右5(这些是随机的例子) 这是我的密码: 定位摄像机 gluLookAt(mouse.getScrollY(), 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1
gluLookAt(mouse.getScrollY(), 0.0f, 0.0f,
0.0f, 0.0f, 0.0f,
0.0f, 0.0f, 1.0f);
glRotated(mouse.getAngleV(), 0.0f, -1.0f, 0.0f);
glRotated(mouse.getAngleH(), 0.0f, 0.0f, -1.0f);
mouse.getScrollY只是一个基于相机从原点向后滚动的距离的值
获取坐标
void Mouse::GetGLPos(int x, int y)
{
//init vars:
GLint viewport[4];
GLdouble modelview[16];
GLdouble projection[16];
GLfloat winX, winY;
GLdouble posX, posY, posZ;
GLdouble FposX, FposY, FposZ;
//get gl specs
glGetDoublev( GL_MODELVIEW_MATRIX, modelview ); //get Modelmatrix
glGetDoublev( GL_PROJECTION_MATRIX, projection ); //get projection matrix
glGetIntegerv( GL_VIEWPORT, viewport ); //get viewport values
//calculate the gl mouseposition
winX = (float)x;
winY = (float)viewport[3] - (float)y;
std::cout << "X "<< winX << " Y " << winY << endl;
gluUnProject( winX, winY, 0.0, modelview, projection, viewport, &posX, &posY, &posZ);
gluUnProject( winX, winY, 1.0, modelview, projection, viewport, &FposX, &FposY, &FposZ);
std::cout << "Near positions:" << posX << " | " << posY << " | " << posZ << endl;
std::cout << " Far positions:" << FposX << " | " << FposY << " | " << FposZ << endl << endl;
for (int i = 0; i <= 15; i++)
{
cout << modelview[i] << endl;
}
if (counter == 5)
{
counter = 0;
}
LinestoreNear[counter + 1] = Vec3(posX, posY, posZ);
LinestoreFar[counter + 1] = Vec3(FposX, FposY, FposZ);
counter ++;
mouseOgl[0] = posX;
mouseOgl[1] = posY;
mouseOgl[2] = posZ;
}
void鼠标::GetGLPos(int x,int y)
{
//初始化变量:
闪烁视口[4];
GLdouble modelview[16];
gl双投影[16];
GLfloat winX,winY;
GLdouble-posX,posY,posZ;
GLdouble-FposX,FposY,FposZ;
//获取gl规格
glGetDoublev(GL_MODELVIEW_MATRIX,MODELVIEW);//获取Modelmatrix
glGetDoublev(GL_投影_矩阵,投影);//获取投影矩阵
glGetIntegerv(GL_视口,视口);//获取视口值
//计算gl鼠标位置
winX=(float)x;
winY=(浮动)视口[3]-(浮动)y;
std::cout这里是您需要使用的过程的一个非常简短的概述
要获得正确的世界坐标,场景中的每个对象都需要一个4x4模型矩阵。模型矩阵包含将模型坐标转换为/转换为世界坐标的所有变换
即每次调用glTranslate时,必须按如下方式变换模型矩阵:
T = [ 1 0 0 x ]
[ 0 1 0 y ]
[ 0 0 1 z ]
[ 0 0 0 1 ]
M' = M * T
然后,可以使用变换后的模型矩阵获取世界空间坐标
但是,首先对坐标进行均匀化(或检查它们是否已经均匀化),即,如果它们还不是均匀坐标,只需设置w=1即可
如果您不在对象空间和世界空间之间转换坐标,那么您将获得您正在经历的行为,并且很容易在错误的阶段进行转换,因此请规划所需的步骤,您应该可以:)
希望这能有所帮助。终于有时间来验证你的结果了。它完全按照它应该的方式工作
使用LookAt
指定(GLU将为您计算这些矩阵)相机位置和旋转矩阵(间接地,通过“向上”和“视点”向量,但仍然会导致这些变换)。在指定两个额外的旋转矩阵之后-这意味着,您将围绕一个零点旋转一个世界(这已经被LookAt
)移动了)。对于您来说,这种旋转看起来就像相机围绕空间中的某个点旋转,保持恒定的距离。线条保持其位置,透视变换(如果有)会引入一些失真,和被远剪裁平面剪裁(这看起来像是在旋转过程中直线变得越来越短).从眼睛的视角到远平面的直线是一个点。但当我旋转相机时,直线位于错误的位置。因此,近平面的XYZ与远平面的XYZ不同,我在它们之间画了一条线。然后旋转相机,查看直线是否到达我单击的位置,以便单击,然后旋转相机并查看您r线?那没关系。请问[counter+1]附近的linestore怎么了
,不应该只是计数器
,因为您在这之后就增加了它吗?当您调用此函数时,您当前的modelview矩阵是什么?只是查看还是它也有一些建模组件?行存储不是问题,我已经尝试过了。它根据camara查看它的位置而变化。我认为模式我想Glulookat正在更新l视图矩阵,但我不是100%确定。通过进一步探索,如果其中一个XYZ 0记不住gluUnProject后面的数学(并且现在没有时间检查),则该行大致位于正确的位置,但正如我所记得的,你们在最终的对象空间中得到向量。后来你们像在世界空间中一样使用它,但它不是。你们需要得到逆视图矩阵,并用这个矩阵乘以得到的线位置。
T = [ 1 0 0 x ]
[ 0 1 0 y ]
[ 0 0 1 z ]
[ 0 0 0 1 ]
M' = M * T