Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/three.js/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Three.js 3.Object3D:如何禁用对象而不是材质的光线投射?_Three.js - Fatal编程技术网

Three.js 3.Object3D:如何禁用对象而不是材质的光线投射?

Three.js 3.Object3D:如何禁用对象而不是材质的光线投射?,three.js,Three.js,因此,常识似乎是将对象的材质可见性设置为false 因此,当我有无数的对象共享相同的材质时,这就不起作用了。但根据他们的数据,我想禁用其中一些 与 我可以隐藏它们,但它们仍然是可选的 Object.Material.visible = false 隐藏所有对象,因为它们的共享材质设置为不可见 这能做到吗 我没有创建这些对象,因此没有机会创建多个材质。我只能处理共享相同材质且需要隐藏的对象解决方案1:手动筛选光线投射候选对象和结果 看起来没有任何内置字段可以实现您想要的效果,但是您应该能够通过手

因此,常识似乎是将对象的材质可见性设置为false

因此,当我有无数的对象共享相同的材质时,这就不起作用了。但根据他们的数据,我想禁用其中一些

我可以隐藏它们,但它们仍然是可选的

Object.Material.visible = false
隐藏所有对象,因为它们的共享材质设置为不可见

这能做到吗

我没有创建这些对象,因此没有机会创建多个材质。我只能处理共享相同材质且需要隐藏的对象

解决方案1:手动筛选光线投射候选对象和结果 看起来没有任何内置字段可以实现您想要的效果,但是您应该能够通过手动过滤要光线投射的对象列表来实现类似的行为。下面是一个如何做到这一点的想法:

// scene with lots of nested objects
const scene, raycaster;

// ...

// Gather up which objects to try to raycast against based on
// a set of conditions
const raycastList = [];
scene.traverse(c => {
    if (c.isMesh && !c.disableRaycast) {
        raycastList.push(c);
    }
});

// raycast against only the items in the array
const intersections = raycaster.raycastObjects(raycastList);
如果要基于父对象
disableRaycast
字段进行过滤,则可以创建一个自定义遍历函数,用于跟踪父对象禁用状态并提前停止遍历

如果您已经知道哪些对象应该或不应该提前进行光线投射,您可以预先创建该列表并保留它

编辑

解决方案2:重写并生成自定义网格.raycast()函数 如果您无权修改光线投射代码,则可以创建一个“DeactivateableRaycastMesh”类,该类实现自定义光线投射方法,并允许您启用或禁用它是否返回光线投射命中

class DeactivateableRaycastMesh extends THREE.Mesh {

    constructor(...args) {
        super(...args);
        this.raycastEnabled = true;
    }

    raycast(...args) {
        if (!this.raycastEnabled) return;
        super.raycast(...args);
    }

}
如果您在每个网格上都需要此功能,而不仅仅是在您创建的网格上,那么您可以修改
THREE.mesh.prototype
,将上述功能添加到所有网格中。但是,不建议这样做

const originalRaycast = THREE.Mesh.prototype.raycast;
THREE.Mesh.prototype.raycast = function(...args) {
    if (!this.raycastEnabled) return;
    originalRaycast.call(this, ...args);
}

从光源上看,(对象或材质的)可见性似乎不会影响光线投射。根据您的最终目标,您可以向对象添加自定义字段,然后在光线投射后过滤交点,或者维护您知道要进行光线投射的对象的单独列表。我没有访问权限。我可以改变场景图中的现有对象!没有访问权限,我的意思是我不会在我的代码库中调用raycaster。我试图改变一个场景的现有应用程序的基础上三个。但是disableRaycast听起来可能很有趣!如果你不需要修改raycast逻辑,那么你可以看看我在上面编辑的文章中包含的第二个解决方案,它应该能提供你所说的行为。
const originalRaycast = THREE.Mesh.prototype.raycast;
THREE.Mesh.prototype.raycast = function(...args) {
    if (!this.raycastEnabled) return;
    originalRaycast.call(this, ...args);
}