WebGL - 如何将矢量取消投影到屏幕 space
WebGL - how to unproject vector to screen space
我有一个奇怪的问题...它可能与 webGL 关系不大,而与直接 3D 几何和矩阵乘法关系较大..但这里是:
我正在使用第 3 方 javascript 库来执行 webGL 渲染。使用这个库,我想 'unproject' 3d space (x, y, z) 中的一个点到 HTML canvas 的 2d 屏幕 space在其上渲染场景。
该库不提供任何内置方法来执行此操作...并且它不是开源的...
不过,该库确实提供了两个有用的功能。一种用于检索当前相机的 'view' 和 'projection' 矩阵。另一个用于计算生命值——有点像射线投射。要计算命中点,请传入屏幕坐标 (Xs,Ys),如果它命中一个对象,它 returns 3D 世界-space 点 (Xw,Yw,Zw)
我希望有了这些信息,有人可以帮助我对从 (Xw,Yw,Zw) 到 (Xs, Ys) 的解决方案进行逆向工程 - 给定相机矩阵信息。
这是一些示例数据:
TestPoint =
{
ScreenCoordinateX: 1098,
ScreenCoordinateY: 998
}
HitPoint =
{
WorldCoordinateX: 12082.2,
WorldCoordinateY: 200.18,
WorldCoordinateZ: -5848
}
CameraViewMatrix =
{
0: -0.817419, 1: -0.130593, 2: 0.561045, 3: 0,
4: 0.57542, 5: -0.139804, 6: 0.805821, 7: 0,
8: -0.0267983, 9: 0.981529, 10: 0.189425, 11: 0,
12: 7844.46, 13: 6482.28, 14: -17852.8, 15: 1
}
CameraProjectionMatrix =
{
0: 1.9222, 1: 0, 2: 0, 3: 0,
4: 0, 5: 3.73205, 6: 0, 7: 0,
8: 0, 9: 0, 10: -1.58869, 11: -1,
12: 0, 13: 0, 14: -13901.6, 15: 0
}
在此先感谢您提供的任何帮助
取消项目还是项目?通常 unproject 意味着获取屏幕 space 位置(如鼠标)并将其转换为 3d 位置(如穿过平截头体的射线)。
要将矢量投影到屏幕 space,您需要一个 viewProjection 矩阵。在您的情况下,您只有一个视图和一个投影,因此将它们相乘得到一个 viewProjection,然后将您的向量乘以该矩阵。结果应该是一个 4d 向量。将 xyz 部分除以 w 部分。 (注意,一些库已经有一个除以 w 的矩阵 * 向量函数)。
您现在将拥有剪辑space 坐标(-1 到+1)。缩放到屏幕 space
zeroToOne = (clipSpace + 1) / 2
screenSpace = zeroToOne * screenDimension
There's examples here for positioning HTML text to match WebGL
我有一个奇怪的问题...它可能与 webGL 关系不大,而与直接 3D 几何和矩阵乘法关系较大..但这里是:
我正在使用第 3 方 javascript 库来执行 webGL 渲染。使用这个库,我想 'unproject' 3d space (x, y, z) 中的一个点到 HTML canvas 的 2d 屏幕 space在其上渲染场景。
该库不提供任何内置方法来执行此操作...并且它不是开源的...
不过,该库确实提供了两个有用的功能。一种用于检索当前相机的 'view' 和 'projection' 矩阵。另一个用于计算生命值——有点像射线投射。要计算命中点,请传入屏幕坐标 (Xs,Ys),如果它命中一个对象,它 returns 3D 世界-space 点 (Xw,Yw,Zw)
我希望有了这些信息,有人可以帮助我对从 (Xw,Yw,Zw) 到 (Xs, Ys) 的解决方案进行逆向工程 - 给定相机矩阵信息。
这是一些示例数据:
TestPoint =
{
ScreenCoordinateX: 1098,
ScreenCoordinateY: 998
}
HitPoint =
{
WorldCoordinateX: 12082.2,
WorldCoordinateY: 200.18,
WorldCoordinateZ: -5848
}
CameraViewMatrix =
{
0: -0.817419, 1: -0.130593, 2: 0.561045, 3: 0,
4: 0.57542, 5: -0.139804, 6: 0.805821, 7: 0,
8: -0.0267983, 9: 0.981529, 10: 0.189425, 11: 0,
12: 7844.46, 13: 6482.28, 14: -17852.8, 15: 1
}
CameraProjectionMatrix =
{
0: 1.9222, 1: 0, 2: 0, 3: 0,
4: 0, 5: 3.73205, 6: 0, 7: 0,
8: 0, 9: 0, 10: -1.58869, 11: -1,
12: 0, 13: 0, 14: -13901.6, 15: 0
}
在此先感谢您提供的任何帮助
取消项目还是项目?通常 unproject 意味着获取屏幕 space 位置(如鼠标)并将其转换为 3d 位置(如穿过平截头体的射线)。
要将矢量投影到屏幕 space,您需要一个 viewProjection 矩阵。在您的情况下,您只有一个视图和一个投影,因此将它们相乘得到一个 viewProjection,然后将您的向量乘以该矩阵。结果应该是一个 4d 向量。将 xyz 部分除以 w 部分。 (注意,一些库已经有一个除以 w 的矩阵 * 向量函数)。
您现在将拥有剪辑space 坐标(-1 到+1)。缩放到屏幕 space
zeroToOne = (clipSpace + 1) / 2
screenSpace = zeroToOne * screenDimension
There's examples here for positioning HTML text to match WebGL