ThreeJS camera.lookAt() 没有效果,是不是我做错了什么

ThreeJS camera.lookAt() has no effect, is there something I'm doing wrong?

本文关键字:是不是 错了 什么 有效果 lookAt camera ThreeJS      更新时间:2023-09-26

在Three.js中,我希望相机指向3D空间中的某个点。

为此,我尝试使用 camera.lookAt 函数,如下所示:

camera.lookAt(new THREE.Vector3(-100,-100,0));

但是,我发现该电话没有任何效果。它什么都不做。我尝试更改矢量中的数字,当它应该改变时,我总是在屏幕上看到相同的外观。

我现在才发现,如果我删除代码中的THREE.TrackballControlscamera.lookAt()就会正常工作。我使用 THREE 的方式有问题吗?轨迹球控制?这就是我初始化它们的方式:

    controls = new THREE.TrackballControls( camera, renderer.domElement );
    controls.rotateSpeed = 10.0;
    controls.zoomSpeed = 1.2;
    controls.panSpeed = 0.2;
    controls.noZoom = false;
    controls.noPan = false;
    controls.staticMoving = true;
    controls.dynamicDampingFactor = 1.0;
    var radius = 5;
    controls.minDistance = radius * 1.1;
    controls.maxDistance = radius * 100;
    controls.keys = [ 65, 83, 68 ]; // [ rotateKey, zoomKey, panKey ]*/

然后在我的渲染函数中,我做了:

function render() {
  controls.update();
  renderer.render(scene, camera);
}

关于 Three.js 的文档非常稀缺,所以我想我会在这里问。我做错了什么吗?

查看THREE.TrackballControls的源代码,我发现我可以通过将trackballControls.target设置为我希望它看到的THREE.Vector3,然后重新渲染场景来使摄像机看起来我想要的位置。

是的,

请注意...似乎有三个。轨迹球控制或三个。当您实例化控件的实例时,OrbitControls 似乎会覆盖 camera.lookAt 函数,因为您正在传入相机。 您可能希望删除控件,然后执行 camera.lookAt() 或其他方式补间相机,以验证控件是否对相机具有覆盖效果。 我用谷歌搜索了一段时间,为什么camera.lookat()似乎没有效果。

在我看来,我们不应该弄乱原始代码。我找到了一种方法来实现查看任何特定点的目标。声明"control"变量后,只需执行以下两行代码:

// Assuming you know how to set the camera and myCanvas variables
control = new THREE.OrbitControls(camera, myCanvas);
// Later in your code
control.object.position.set(camX, camY, camZ);
control.target = new THREE.Vector3(targetX, targetY, targetZ);

请记住,这会将焦点的中心切换到您的新目标。换句话说,您的新目标将是相机所有旋转的中心。有些部分将很难看,因为您熟悉操作相机假设默认中心。尝试尽可能放大,您将了解我在说什么希望这有帮助。

我想通了。若要防止THREE.TrackballControlsTHREE.OrbitControls在初始化时重写camera.lookAt,需要更改将控件的 target 属性设置为等于camera.position向量和camera.getWorldDirection()向量的总,而不是当前使用 new THREE.Vector3()(默认为 (0, 0, 0))实现它的方式。

因此,对于THREE.TrackballControls,将第 39 行更改为:

this.target = new THREE.Vector3().addVectors(/*new line for readability*/
    object.position, object.getWorldDirection());

THREE.OrbitControls也是如此,在第36行。我实际上还没有在TrackballControls.js上测试过它,但它确实适用于OrbitControls.js.希望这有帮助。

这是一个替代解决方案:创建一个维度为 0 的对象(即立方体)。

var cameraTarget = new THREE.Mesh( new THREE.CubeGeometry(0,0,0));

在渲染函数中,将 camera.lookAt 设置为摄像机目标的位置。

function render() {
    camera.lookAt( cameraTarget.position );
    renderer.render( scene, camera );
}

然后只需根据需要移动相机目标。

我遇到了同样的问题,并且能够通过使用OrbitControls.target使其工作。下面是我在声明控制器后所做的。

    controller = new THREE.OrbitControls(camera, renderer.domElement);
    controller.addEventListener('change', renderer.domElement);
    controller.target = new THREE.Vector3(0, 1, 0);