当鼠标移动太快时,变换对象将不起作用

时间:2018-05-16 07:54:54

标签: three.js

我写了一个控件来转换对象,但是当我将鼠标移动得太快时,它就无法工作。

我该如何解决这个问题?

这是我的代码:https://jsbin.com/vajunal/edit?html,output

这是主要代码:

    var a = 2 * x / this.canvas.width - 1;
    var b = 1 - 2 * y / this.canvas.height;
    this.raycaster.setFromCamera(new THREE.Vector2(a, b), this.camera);
    const intersects = this.raycaster.intersectObject(this.helpPlane);
    if (intersects.length == 0) {
        return;
    }
    var pos = intersects[0].point;
    this.helpPlane.position.set(pos.x, pos.y, pos.z)
    this.object.position.set(pos.x, pos.y, pos.z);

1 个答案:

答案 0 :(得分:0)

发生这种情况的原因是鼠标离开"辅助平面"在两个mousemove事件之间。为了捕捉鼠标的任何运动,你需要使辅助平面无限大。一种解决方案可以是使用THREE.Plane而不是平面网格来计算世界空间中的鼠标位置。请参阅此codepen以获取如何执行此操作的示例:https://codepen.io/usefulthink/pen/XqYqRL(其中包含更多文档)。

简而言之,这就是程序:

// --- somewhere outside:
const ray = new THREE.Ray();
const target = new THREE.Vector3();
const xzPlane = new THREE.Plane(new THREE.Vector3(0, 1, 0), 0);

// --- mousemove-handler:
const mouse = new THREE.Vector2();
renderer.domElement.addEventListener("mousemove", ev => {
  const { offsetWidth: w, offsetHeight: h } = ev.target;
  mouse.x = 2 * ev.clientX / w - 1;
  mouse.y = 1 - 2 * ev.clientY / h;
});

// --- in the animation-loop:
// Compute the ray from the camera through the cursor-position and intersect
// with the xz-plane.
ray.origin.setFromMatrixPosition(camera.matrixWorld);
ray.direction.set(mouse.x, mouse.y, 0.5).unproject(camera);
ray.direction.sub(ray.origin).normalize();

ray.intersectPlane(xzPlane, target);

// `target` now contains the world-space coordinates of the mouse-cursor

这可以处理整个场景中直到地平线的鼠标移动。现在,如果您想支持其他移动方向,则需要以不同的方式配置xzPlane,例如通过计算mousedown处理程序中的移动平面。

另请查看three.js附带的TransformControls,可能已经是您正在寻找的内容:https://threejs.org/examples/?q=trans#misc_controls_transform

另一个注意事项:mousemove事件通常与动画循环不同步,并且可能比渲染更频繁地​​发生。通常希望将所有昂贵的操作(如光线投射)放入主动画循环中,并仅将最后看到的鼠标位置存储在mousemove事件的处理程序中。但这可能只是一个小问题,对你所看到的问题没什么贡献。