这更像是一种肮脏的本性,但无论如何。我需要能够检测到在OpenGl中以四边形显示的图像中单击的位置。四边形的尺寸为5000x5000,渲染为0,0。从我所看到的,这是从窗口中间呈现的。这会在轴的左下角呈现四边形。为了解决这个问题,而不是改变四边形的顶点,因为我需要平移以便在绘制四边形之前进行变换。
因此,为了使四边形在启动时居中,我按GL.Translate(-2500,-2500),0)进行平移。
现在鼠标坐标相对于窗口的左上角,所以我将它们分成一小部分,例如Mouse.X / Width Mouse.Y / Height
这就是iffy的地方。我知道我需要乘以5000,但我还需要以某种方式加入平底锅。
我不确定这是否重要,但这就是我的Ortho矩阵的设置方式:
GL.Ortho(-G_.MapSize * 1.5 ^ ZoomFactor, G_.MapSize * 1.5 ^ ZoomFactor, G_.MapSize * 1.5 ^ ZoomFactor, -G_.MapSize * 1.5 ^ ZoomFactor, -1, 1)
答案 0 :(得分:1)
GL具有清晰的物体空间锥形,夹子空间,标准化设备坐标和窗口空间。您对glOrtho()
和glTranslate()
的使用意味着您使用旧的固定功能,其中眼睛空间也是明确定义的。
如果要将窗口sapce点(如鼠标坐标)映射回对象空间,则需要反转gl执行的计算。顶点的转换管道如下:
glDepthRange
进一步转换,之后可能转换为某种整数表示。如果您有一个给定的2D鼠标位置,您可以简单地反转该方案:
修改强>
由于该操作很常见,因此还有一些实用程序功能可以实现此功能。当您使用GL的矩阵堆栈时,最简单的解决方案就是使用GLu库中的gluUnproject()
。您所需要的只是点的3D窗口坐标,以及在绘制对象时使用的矩阵和视口设置,可以使用各种glGetDoublev()
函数使用glGet
查询。有full example at the old NeHe site。
使用现代GL,您必须自己完成所有这些。但是,流行的GLM库还有一个类似于GLU的glm::unProject
方法。
答案 1 :(得分:0)
这只是我评论的扩展,这是unProjecting鼠标坐标到世界坐标的工作代码。它几乎是derhass所说的一个实际例子。 调用函数:
Dim modelViewMatrix As Matrix4
Dim projectionMatrix As Matrix4
Dim viewport(4) As Integer
GL.GetFloat(GetPName.ModelviewMatrix, modelViewMatrix)
GL.GetFloat(GetPName.ProjectionMatrix, projectionMatrix)
GL.GetInteger(GetPName.Viewport, viewport)
Dim cords As Vector4 = GF.UnProject(projectionMatrix, modelViewMatrix, New Size(viewport(2), viewport(3)), New Vector2(e.Position.X, e.Position.Y))
功能:
Public Function UnProject(ByRef projection As Matrix4, ByVal view As Matrix4, ByVal viewport As Size, ByVal mouse As Vector2) As Vector4
Dim vec As Vector4
vec.X = 2.0F * mouse.X / CSng(viewport.Width) - 1
vec.Y = -(2.0F * mouse.Y / CSng(viewport.Height) - 1)
vec.Z = 0
vec.W = 1.0F
Dim viewInv As Matrix4 = Matrix4.Invert(view)
Dim projInv As Matrix4 = Matrix4.Invert(projection)
Vector4.Transform(vec, projInv, vec)
Vector4.Transform(vec, viewInv, vec)
If vec.W > Single.Epsilon OrElse vec.W < Single.Epsilon Then
vec.X /= vec.W
vec.Y /= vec.W
vec.Z /= vec.W
End If
Return vec
End Function