前言
Threejs中常用的集合体Three.Geometry和Three.BufferGeometry区别与联系,需要注意从r125版本开始,THREE.Geometry已被废弃,能用THREE.Geometry实现的功能都可由THREE.BufferGeometry代替。
Three.Geometry
在旧版本的threejs中,主要是通过以下两个属性创建一个自定义的几何体:
- vertices: 该属性存储一个顶点数组,用来存储该几何体所有顶点的空间坐标
- faces:该属性是一个Face3类型数组,一个Face3的实例即一个三角形面片
利用 Three.Geometry创建几何体的代码如下:
// 创建构成几何体的顶点,共八个
const vertices = [
new THREE.Vector3(1, 3, 1), // THREE.Vector3(a, b, c)既可以表示一个点,也可以表示具备长度和方向的向量
new THREE.Vector3(1, 3, -1),
new THREE.Vector3(1, -1, 1),
new THREE.Vector3(1, -1, -1),
new THREE.Vector3(-1, 3, -1),
new THREE.Vector3(-1, 3, 1),
new THREE.Vector3(-1, -1, -1),
new THREE.Vector3(-1, -1, 1)
];
// 创建构成几何体的面,共八个面,十六个三角形
// faces中保存了由顶点构成的三角形面
const faces = [
new THREE.Face3(0, 2, 1), // THREE.Face3(a, b, c)表示在几何体中被使用到的三角面片。
new THREE.Face3(2, 3, 1), // a、b、c表示geometry.vertices中的点索引,将被自动创建三角形
new THREE.Face3(4, 6, 5), // ⭐ 顺时针是正面朝相机,否则背面
new THREE.Face3(6, 7, 5),
new THREE.Face3(4, 5, 1),
new THREE.Face3(5, 0, 1),
new THREE.Face3(7, 6, 2),
new THREE.Face3(6, 3, 2),
new THREE.Face3(5, 7, 0),
new THREE.Face3(7, 2, 0),
new THREE.Face3(1, 3, 4),
new THREE.Face3(3, 6, 4),
];
const geom = new THREE.Geometry();
geom.vertices = vertices;
geom.faces = faces;
geom.computeFaceNormals(); // 更新每个面的法向量,法向量用于决定不同光源下的颜色
Three.Geometry与Three.BufferGeometry转换
在旧版本中Three.Geometry与Three.BufferGeometry两种类型是可以相互转换的,方法如下:
// Three.BufferGeometry => Three.Geometry
const geom = new THREE.BufferGeometry()
geom.fromBufferGeomery(geom)
// Three.Geometry => Three.BufferGeometry
const geom = new THREE.Geometry()
geom.fromGeomery(geom)
Three.BufferGeometry
新版的Threejs中已经移除了Geometry类,转而使用效率更加优秀的BufferGeometry,BufferGeometry通过attributes与index属性新建几何体
- attributes属性:包括color(颜色)、normal(法向量)、position(顶点位置)、uv(像素位置)
BufferGeometry.attributes.position // 几何体顶点位置
BufferGeometry.attributes.color // 几何体顶点颜色
BufferGeometry.attributes.normal // 几何体顶点法向量
BufferGeometry.attributes.uv // 几何体顶点像素
几何体的创建可以参考官网例子
const geometry = new THREE.BufferGeometry();
// create a simple square shape. We duplicate the top left and bottom right
// vertices because each vertex needs to appear once per triangle.
const vertices = new Float32Array( [
-1.0, -1.0, 1.0,
1.0, -1.0, 1.0,
1.0, 1.0, 1.0,
1.0, 1.0, 1.0,
-1.0, 1.0, 1.0,
-1.0, -1.0, 1.0
] );
// itemSize = 3 because there are 3 values (components) per vertex
geometry.setAttribute( 'position', new THREE.BufferAttribute( vertices, 3 ) );
// geometry.setAttribute( 'color', new THREE.BufferAttribute( vertices, 3 ) );
// geometry.setAttribute( 'normal', new THREE.BufferAttribute( vertices, 3 ) );
const material = new THREE.MeshBasicMaterial( { color: 0xff0000 } );
const mesh = new THREE.Mesh( geometry, material );
这里以cube立方体的attributes说明position属性
一个cube几何体具有六个面,每个面默认由两个三角形构成,三角形由三个顶点构成(itemSize);六个面共计有12个三角形,count值为12×3=36,每个count有x,y,z三个维度的坐标,故array长度为36×3=108。
每个顶点同样具备颜色和法向属性,它们的组成也是一个长度为三的元组,不同的是它们分别表示RGB颜色和法向量。
- index属性 通过创建顶点索引生产几何体
以上述正方体为例,每个面需要两个三角形组成,共六个点,六个面需要36个点坐标,但实际上有许多点是重复的,可以通过创建索引的方式简化。
总结
- Three.Geometry 使用
- Three.Geometry与Three.BufferGeometry转换方法
- Three.BufferGeometry 使用 属性