Three.JS对象剪辑?

Ala*_*lan 6 javascript three.js

我试图以类似于Unity的方式使用three.js来划分我的3D模型: 在此输入图像描述

我一直在玩相机控制器,当然我可以调整近/远场以剪切相机的方向,但是如果我想在X或Y平面上剪辑怎么办?我看了可能添加一个可以在该轴上滑动的大透明块,然后使用二进制操作来合并/减去它与对象相交的位置,但是这些工具最终会沿着新平面创建一个新网格,而不是实际沿着该平面移除所有内容.轴.

我是否需要使用多个视口,还是有更简单的方法?

dai*_*ign 18

可以在着色器中轻松完成剪切.使用一些计算你甚至可以有像剪裁区域这样的球体.在垂直于坐标系的平面处剪切是最容易的.在顶点着色器中计算像素的世界位置:

worldPosition = modelMatrix * vec4( position, 1.0 );
Run Code Online (Sandbox Code Playgroud)

在片段着色器中,如果超出剪裁限制,则丢弃像素的绘制:

if ( worldPosition.x > clippingLimitX ) {
    discard;
}
Run Code Online (Sandbox Code Playgroud)

然而,这将使网格在裁剪边缘处打开.要关闭它,请使用模板缓冲区.用显示背面的场景减少模板.然后使用显示剪裁正面的场景增加模板.这些场景中使用的材料不应该是可见的,因此禁用它们的颜色和深度写入:

new THREE.ShaderMaterial( { colorWrite: false, depthWrite: false, ... } );
Run Code Online (Sandbox Code Playgroud)

使用模板渲染位于剪切平面位置的平面.禁用模板后,剪裁正面.

renderer.autoClear = false;
renderer.clear();

var gl = renderer.context;

renderer.state.setStencilTest( true );

renderer.state.setStencilFunc( gl.ALWAYS, 1, 0xff );
renderer.state.setStencilOp( gl.KEEP, gl.KEEP, gl.INCR );
renderer.render( backStencilScene, camera );

renderer.state.setStencilFunc( gl.ALWAYS, 1, 0xff );
renderer.state.setStencilOp( gl.KEEP, gl.KEEP, gl.DECR );
renderer.render( frontStencilScene, camera );

renderer.state.setStencilFunc( gl.EQUAL, 1, 0xff );
renderer.state.setStencilOp( gl.KEEP, gl.KEEP, gl.KEEP );
renderer.render( capsScene, camera );

renderer.state.setStencilTest( false );

renderer.render( scene, camera );
Run Code Online (Sandbox Code Playgroud)

我做了一个演示,展示了如何同时在多个平面上剪辑:

http://daign.github.io/clipping-with-caps/

我没有使用内置的three.js剪裁平面,因为要使这个演示工作,我必须使用着色器渲染模板,该着色器确定剪裁平面是否背对着摄像机,并且仅在那些平面上剪辑对着镜头.

  • 真棒!您是否有关于如何在剪辑位置绘制"粗"线的建议.打开和关闭网格之间的中间物.谢谢! (2认同)

Wes*_*ley 15

现在支持剪辑.

这是要遵循的模式.根据您的使用情况进行调整.

var localPlane = new THREE.Plane( new THREE.Vector3( 0, - 1, 0 ), 1 );

var globalPlane = new THREE.Plane( new THREE.Vector3( 1, 0, 0 ), 1 );

renderer.clippingPlanes = [ globalPlane ];

renderer.localClippingEnabled = true;

var material = new THREE.MeshPhongMaterial( {
    clippingPlanes: [ localPlane ],
    clipShadows: true
} );
Run Code Online (Sandbox Code Playgroud)

看到这三个例子:

https://threejs.org/examples/webgl_clipping.html https://threejs.org/examples/webgl_clipping_advanced.html

three.js r.85

  • @RahulPillai 全局裁剪平面针对每个渲染器。局部剪裁平面是针对每种材质的。请参阅 https://trijs.org/docs/index.html#api/en/materials/Material.clippingPlanes。 (2认同)