【问题标题】:Three.js & OrbitControls.js - pan camera parallel to ground plane (like Google Earth)Three.js & OrbitControls.js - 平移相机平行于地平面(如谷歌地球)
【发布时间】:2014-10-03 18:57:16
【问题描述】:

我正在开发一个使用 OrbitControls.js 的简单 Three.js 演示。

我想更改 OrbitControls 中的平移行为。目前,当您平移相机时,它会在垂直于观察方向的平面中移动相机。我想改变它,使相机与地平面保持恒定距离并平行移动。 Google 地球使用类似的控制设置。

编辑:我应该首先提到这个细节,但我也希望您单击并开始拖动的点在整个拖动过程中保持在光标的正下方。鼠标移动和用户期望在屏幕上发生的事情之间需要有牢固的联系。否则,当我尝试在场景中移动时感觉好像我在“滑倒”。

谁能给我一个关于如何做到这一点的高级解释(使用或不使用 OrbitControls.js)?

【问题讨论】:

  • 您的“地平面”实际上是平面(例如平面,还是高度可变)?
  • 实际上是平的。它只是一个位于 (0,0,0) 的无限平面,向上向量为 (0,1,0)。
  • 哦,所以你只想在世界 X/Z 方向上平移,保持相机在一个固定的 Y 位置?
  • 正确。只有当我围绕目标点旋转相机或将相机推向目标点时,Y 位置才会改变。
  • 正确。但我不确定我们对“旋转相机”的定义是否相同。当您旋转时,相机会围绕目标点(通常在平面上)旋转并始终转向查看该目标点。

标签: three.js


【解决方案1】:

编辑:OrbitControls 现在支持平行于“地平面”的平移,这是默认设置。

要与屏幕空间平行平移(传统行为),请设置:

controls.screenSpacePanning = true;

还可以使用MapControls,它的 API 类似于 Google 地球。

three.js r.94

【讨论】:

  • 我试过了。它很接近,但似乎 panUp 是倒退的。另外,我应该提到这一点,但我希望您单击并拖动的点在整个拖动过程中保持在光标下方。它为用户提供了更自然、更触觉的体验。在发布这个问题后,我实际上想出了一个可行的解决方案。我应该将其添加到我的答案中吗?
  • 1.所谓的“向后”平移可以通过符号翻转来修复,但您需要检查各种操作系统下的行为——尤其是 OSX。 2. 当视图从上方垂直向下时,这种方法将点保持在光标附近。当视角为锐角时,将平移距离调整 cos(view-angle) 系数可能会得到您想要的结果。
  • @Shashank 如果您需要帮助,请在 SO 或 discourse.threejs.org 上提问。
  • 我得到了它的工作@WestLangley。我的错。如果还有其他问题,我肯定会发布一个问题。谢谢。
【解决方案2】:

前段时间我正在研究这个问题,即将 OrbitControls.js 改编为地图导航。

【讨论】:

  • 这看起来很完美,但不再适用于版本 75。投影内容已被弃用并导致错误。
【解决方案3】:

您应该将相机“向上”设置为 z 轴:

camera.up.set(0,0,1)

然后,OrbitControl 的主要问题是它的 panUp() 函数。应该修好了。

我的拉取请求:https://github.com/mrdoob/three.js/pull/12727

y ax 是相对于相机轴的,应该相对于世界上的一个固定平面。要定义预期的 y 轴,请根据世界 z 轴将相机 x 轴旋转 90°。

v.setFromMatrixColumn( objectMatrix, 0 ); // get X column of objectMatrix
v.applyAxisAngle( new THREE.Vector3( 0, 0, 1 ), Math.PI / 2 );
v.multiplyScalar( distance );
panOffset.add( v )

享受吧!

【讨论】:

  • 看起来MapControls 工作得很好,但是,如果你想在平移时使用Z 作为垂直轴,X-Y 作为水平面,你需要使用camera.up.set(0, 0, 1)。谢谢! ^^
【解决方案4】:

我想通了。以下是概述:

  1. 将 mousedown 事件存储在某处。
  2. 当鼠标移动时,获取新的 mousedown 事件。
  3. 对于这些点中的每一个,在平面上找到这些点击所在的点(您需要将这些点放入相机空间,将它们转换为世界空间,然后从相机发射一条射线穿过每个点,找到它们与平面的交点。This page 解释了射线与平面的交点测试)。
  4. 从世界空间结束交点减去世界空间开始交点得到偏移量。
  5. 从相机的目标点减去该偏移量就完成了!

在 OrbitControl.js 的情况下,相机始终注视目标点,并且它的位置是相对于该点的。因此,当您更改目标时,相机会随之移动。由于目标始终位于平面上,因此相机会平行于该平面移动(只要您在平移)。

【讨论】:

    猜你喜欢
    • 2012-04-10
    • 2011-06-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-12-17
    • 1970-01-01
    • 1970-01-01
    • 2017-03-15
    相关资源
    最近更新 更多