通过2个gluUnproject调用获取世界坐标中的鼠标以创建ray [英] get mouse in world coordinates with 2 gluUnproject calls to create ray

查看:102
本文介绍了通过2个gluUnproject调用获取世界坐标中的鼠标以创建ray的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我尝试使用许多人似乎找到的好方法,用不同的z值两次调用gluUnproject,然后尝试从这两个向量计算射线的方向向量.

I try to use what many people seem to find a good way, I call gluUnproject 2 times with different z-values and then try to calculate the direction vector for the ray from these 2 vectors.

我阅读了这个问题,并尝试将其中的结构用于我自己的代码:

I read this question and tried to use the structure there for my own code:

        glGetFloat(GL_MODELVIEW_MATRIX, modelBuffer);
        glGetFloat(GL_PROJECTION_MATRIX, projBuffer);
        glGetInteger(GL_VIEWPORT, viewBuffer);

        gluUnProject(mouseX, mouseY, 0.0f, modelBuffer, projBuffer, viewBuffer, startBuffer);
        gluUnProject(mouseX, mouseY, 1.0f, modelBuffer, projBuffer, viewBuffer, endBuffer);

        start = vecmath.vector(startBuffer.get(0), startBuffer.get(1), startBuffer.get(2));
        end = vecmath.vector(endBuffer.get(0), endBuffer.get(1), endBuffer.get(2));

        direction = vecmath.vector(end.x()-start.x(), end.y()-start.y(), end.z()-start.z());

但是这只会返回同构的剪辑坐标(我相信),因为它们在每个轴上的范围从-1到1.

But this only returns the Homogeneous Clip Coordinates (I believe), since they only range from -1 to 1 on every axis.

如何实际获取可用来创建射线的坐标?

How to actually get coordinates from which I can create a ray?

编辑:这是构造矩阵的方式:

This is how I construct the matrices:

Matrix projectionMatrix = vecmath.perspectiveMatrix(60f, aspect, 0.1f,
            100f);
//The matrix of the camera = viewMatrix
setTransformation(vecmath.lookatMatrix(eye, center, up));
//And every object sets a ModelMatrix in it's display method  
Matrix modelMatrix = parentMatrix.mult(vecmath
                    .translationMatrix(translation));
modelMatrix = modelMatrix.mult(vecmath.rotationMatrix(1, 0, 1, angle));

此函数现在的外观:

private void calcMouseInWorldPosition(float mouseX, float mouseY, Matrix proj, Matrix view) {
    Vector start = vecmath.vector(0, 0, 0);
    Vector end = vecmath.vector(0, 0, 0);

    FloatBuffer modelBuffer = BufferUtils.createFloatBuffer(16);
    modelBuffer.put(view.asArray());
    modelBuffer.rewind();
    FloatBuffer projBuffer = BufferUtils.createFloatBuffer(16);
    projBuffer.put(proj.asArray());
    projBuffer.rewind();

    FloatBuffer startBuffer = BufferUtils.createFloatBuffer(16);
    FloatBuffer endBuffer = BufferUtils.createFloatBuffer(16);
    IntBuffer viewBuffer = BufferUtils.createIntBuffer(16);

     //The two calls for projection and modelView matrix are disabled here,   
       as I use my own matrices in this case
//  glGetFloat(GL_MODELVIEW_MATRIX, modelBuffer);
//  glGetFloat(GL_PROJECTION_MATRIX, projBuffer);
    glGetInteger(GL_VIEWPORT, viewBuffer);

    //I know this is really ugly and bad, but I know that the height and width is always 600  
    // and this is just for testing purposes 
    mouseY = 600 - mouseY;

    gluUnProject(mouseX, mouseY, 0.0f, modelBuffer, projBuffer, viewBuffer, startBuffer);
    gluUnProject(mouseX, mouseY, 1.0f, modelBuffer, projBuffer, viewBuffer, endBuffer);

    start = vecmath.vector(startBuffer.get(0), startBuffer.get(1), startBuffer.get(2));
    end = vecmath.vector(endBuffer.get(0), endBuffer.get(1), endBuffer.get(2));

    direction = vecmath.vector(end.x()-start.x(), end.y()-start.y(), end.z()-start.z());

}

我正在尝试使用自己的投影和视图矩阵,但这似乎只能给出奇怪的结果.
使用GlGet ...的东西,我可以在右上角单击以下内容:
开始:(0.97333336,-0.98,-1.0)
结束:(0.97333336,-0.98,1.0)

I'm trying to use my own projection and view matrix, but this only seems to give weirder results.
With the GlGet... stuff I get this for a click in the upper right corner:
start: (0.97333336, -0.98, -1.0)
end: (0.97333336, -0.98, 1.0)

使用我自己的东西时,我得到的位置是相同的:
开始:(-2.4399707,-0.55425626,-14.202201)
结束:(-2.4399707,-0.55425626,-16.198204)

When I use my own stuff I get this for the same position:
start: (-2.4399707, -0.55425626, -14.202201)
end: (-2.4399707, -0.55425626, -16.198204)

现在我实际上需要一个modelView矩阵,而不仅仅是视图矩阵,但是我不知道应该如何获取它,因为它在每个对象的每次显示调用中都被更改并重新创建.
但这真的是问题吗?在教程中,他说"将向量与投影矩阵相乘.我们可以向后乘以该矩阵的逆." 在下一步中,他再次与视图矩阵的逆相乘,所以我认为这是我应该做的真的吗?

Now I actually need a modelView matrix instead of just the view matrix, but I don't know how I am supposed to get it, since it is altered and created anew in every display call of every object.
But is this really the problem? In this tutorial he says "Normally, to get into clip space from eye space we multiply the vector by a projection matrix. We can go backwards by multiplying by the inverse of this matrix." and in the next step he multiplies again by the inverse of the view matrix, so I thought this is what I should actually do?


在这里,我尝试了user42813的建议:

EDIT 3:
Here I tried what user42813 suggested:

    Matrix view = cam.getTransformation();
    view = view.invertRigid();

    mouseY = height - mouseY - 1;

    //Here I only these values, because the Z and W values would be 0  
    //following your suggestion, so no use adding them here
    float tempX = view.get(0, 0) * mouseX + view.get(1, 0) * mouseY;
    float tempY = view.get(0, 1) * mouseX + view.get(1, 1) * mouseY;
    float tempZ = view.get(0, 2) * mouseX + view.get(1, 2) * mouseY;

    origin = vecmath.vector(tempX, tempY, tempZ);
    direction = cam.getDirection();

但是现在方向和原点值始终相同:
来源:(-0.04557252,-0.0020000197,-0.9989586)
方向:(-0.04557252,-0.0020000197,-0.9989586)

But now the direction and origin values are always the same:
origin: (-0.04557252, -0.0020000197, -0.9989586)
direction: (-0.04557252, -0.0020000197, -0.9989586)

推荐答案

好吧,我终于设法解决了这个问题,也许这会对某人有所帮助.
我为此找到了一些公式,并使用我得到的坐标(从-1到1:

Ok I finally managed to work this out, maybe this will help someone.
I found some formula for this and did this with the coordinates that I was getting, which ranged from -1 to 1:

    float tempX = (float) (start.x() * 0.1f * Math.tan(Math.PI * 60f / 360));
    float tempY = (float) (start.y() * 0.1f * Math.tan(Math.PI * 60f / 360) * height / width);
    float tempZ = -0.1f;

    direction = vecmath.vector(tempX, tempY, tempZ); //create new vector with these x,y,z
    direction = view.transformDirection(direction); 
    //multiply this new vector with the INVERSED viewMatrix
    origin = view.getPosition(); //set the origin to the position values of the matrix (the right column)

这篇关于通过2个gluUnproject调用获取世界坐标中的鼠标以创建ray的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆