Three.js - 如果对象相交则剪切平面?
Three.js - Clip plane if object intersects?
我正在使用 PlaneGeometry
作为水,并在其上添加了一艘船(gltf 模型)。问题是,当船稍微停在水中时,水会显示在船内,即使船是漂浮的。有没有办法在船(或其他models/objects)运动时与水相交?
浮动效果是用sin函数制作的,应用于y-coordinate。可以用同样的原理让gltf model(ship)在任意坐标轴上移动
示例:
position.y = Math.sin(ship.userData.initFloating + t) * 0.15;
Three.js 中的每个 material 都有 an AlphaMap property 可用于更改网格的不透明度。因此,您可以绘制一个黑色矩形,船将在不透明度为 0 的位置“切出”水平面的那部分。
我假设您的船会移动,因此您的纹理也需要移动这个黑色矩形。要解决这个问题,您可以使用 HTML <canvas>
元素来绘制和移动黑色矩形。然后你可以使用 THREE.CanvasTexture
将 <canvas>
变成你飞机 alpha 的纹理。
const drawingCanvas = document.getElementById( 'drawing-canvas' );
const canvasTexture = new THREE.CanvasTexture( drawingCanvas );
const waterMaterial = new THREE.MeshBasicMaterial({
transparent: true,
alphaMap: squareTexture
});
请参阅 this working demo 了解如何在 3D 场景中使用 2D canvas 作为纹理。当您在 top-left 正方形上绘制时,您会看到它被应用于立方体。您可以复制此方法,但不是将其分配给 material.map
,而是在 material.alphaMap
.
上使用它
您可以检查每一帧船体顶点的位置,如果 PlaneGeometry 上有足够的点,您可以将船体内部表面的所有顶点移动到最近船体顶点的 y 坐标.这可能也可以通过自定义着色器来完成,这可能是一种更有效的解决方案。
@Marquizzo 关于 alpha 通道的想法也可能是一个更好的解决方案,因为您真的不想像我假设的那样模拟水的位移,而只是简单地摆脱船内水的显示。在这种情况下,我会在船上方放置一个正交相机,将近距和远距剪裁平面设置为尽可能靠近平面,并使用 alpha 通道或 alpha 通道内的 CanvasTexture 作为渲染目标。这样,您将获得实时 alpha 贴图,该贴图也会对船的摇晃、俯仰和起伏做出反应。
我正在使用 PlaneGeometry
作为水,并在其上添加了一艘船(gltf 模型)。问题是,当船稍微停在水中时,水会显示在船内,即使船是漂浮的。有没有办法在船(或其他models/objects)运动时与水相交?
浮动效果是用sin函数制作的,应用于y-coordinate。可以用同样的原理让gltf model(ship)在任意坐标轴上移动
示例:
position.y = Math.sin(ship.userData.initFloating + t) * 0.15;
Three.js 中的每个 material 都有 an AlphaMap property 可用于更改网格的不透明度。因此,您可以绘制一个黑色矩形,船将在不透明度为 0 的位置“切出”水平面的那部分。
我假设您的船会移动,因此您的纹理也需要移动这个黑色矩形。要解决这个问题,您可以使用 HTML <canvas>
元素来绘制和移动黑色矩形。然后你可以使用 THREE.CanvasTexture
将 <canvas>
变成你飞机 alpha 的纹理。
const drawingCanvas = document.getElementById( 'drawing-canvas' );
const canvasTexture = new THREE.CanvasTexture( drawingCanvas );
const waterMaterial = new THREE.MeshBasicMaterial({
transparent: true,
alphaMap: squareTexture
});
请参阅 this working demo 了解如何在 3D 场景中使用 2D canvas 作为纹理。当您在 top-left 正方形上绘制时,您会看到它被应用于立方体。您可以复制此方法,但不是将其分配给 material.map
,而是在 material.alphaMap
.
您可以检查每一帧船体顶点的位置,如果 PlaneGeometry 上有足够的点,您可以将船体内部表面的所有顶点移动到最近船体顶点的 y 坐标.这可能也可以通过自定义着色器来完成,这可能是一种更有效的解决方案。 @Marquizzo 关于 alpha 通道的想法也可能是一个更好的解决方案,因为您真的不想像我假设的那样模拟水的位移,而只是简单地摆脱船内水的显示。在这种情况下,我会在船上方放置一个正交相机,将近距和远距剪裁平面设置为尽可能靠近平面,并使用 alpha 通道或 alpha 通道内的 CanvasTexture 作为渲染目标。这样,您将获得实时 alpha 贴图,该贴图也会对船的摇晃、俯仰和起伏做出反应。