我们都知道threejs通过add添加的子物体,父物体如果移动、旋转、缩放,子物体会跟随父物体。
const geometry = new THREE.BoxGeometry( 1, 1, 1 );
const material = new THREE.MeshBasicMaterial( {color: 0x00ff00} );
const parent = new THREE.Mesh( geometry, material );
that.scene.add( parent );
let child=new THREE.AxesHelper(10)
parent.add(child)
可以把子物体放在场景中呀,不放在父物体下,每帧让它同步父物体的位置不就行了。嗯。。。说的没错可以。
如果我有一个应用场景,父物体会旋转、缩放,只想让子物体大小为1,也不旋转呢?只跟随父物体移动,比如panel底下的特效、或者模型。销毁的时候不想单独调用子物体的销毁呢?
1.可使用attach添加子物体
parent.attach(child)
那我想让父物体持续移动呢,显然attach一次性的是不行的
2.可以通过矩阵Matrix4.invert 直接上代码
参考文档:three.js docshttps://threejs.org/docs/index.html?q=mat#api/zh/math/Matrix4
const geometry = new THREE.BoxGeometry( 1, 1, 1 );
const material = new THREE.MeshBasicMaterial( {color: 0x00ff00} );
const parent = new THREE.Mesh( geometry, material );
that.scene.add( parent );
let child=new THREE.AxesHelper(10)
parent.add(child)
function update() {
parent.rotation.x+=0.01; //任意旋转
parent.rotation.z+=0.01; //任意旋转
parent.position.x+=0.005; //任意位移
parent.scale.x+=0.001; //任意缩放
parent.scale.y+=0.005; //任意缩放
parent.scale.z+=0.001; //任意缩放
parent.updateMatrixWorld(true) //更新父物体及其后代的全局变换,如果没有这行不会立马更新而是在下一帧更新
let childMatrix = parent.matrix.clone(); //克隆父物体的矩阵
childMatrix.setPosition(0, 0, 0) //因为我需要子物体跟随父物体
childMatrix.invert(); //逆矩阵,把父物体旋转与缩放与位移反转,因为我上一行位置设置为0,位置不参与反转
child.matrix.copy(childMatrix); //把新的矩阵拷贝到子物体
child.matrixAutoUpdate = false; // 禁用自动更新矩阵
child.updateMatrixWorld(true) //更新子物体及其后代的全局变换
// 如果你需要设置世界矩阵
// child.matrixWorld.multiplyMatrices(child.parent.matrixWorld, child.matrix);
// 通知渲染器世界矩阵已更新
// child.matrixWorldNeedsUpdate = true;
}
演示视频:
演示截图: parent(绿色的方框)在移动缩放旋转;child(3条线)只跟随parent移动