本文在前节的基础上,介绍three.js其它的内置几何体。
一、准备代码
// 引入Three.js库的全部功能,并将其命名为THREE
import * as THREE from 'three';
// 引入交互控制器
import {OrbitControls} from 'three/examples/jsm/controls/OrbitControls.js';
// 创建一个场景
const scene = new THREE.Scene();
// 创建一个透视相机,参数分别为视野角度、视口宽高比、近端距离、远端距离
const camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
// 创建一个WebGL渲染器
const renderer = new THREE.WebGLRenderer();
// 设置渲染器的大小为窗口的宽度和高度
renderer.setSize(window.innerWidth, window.innerHeight);
// 将渲染器的canvas元素添加到HTML文档中的body标签中
document.body.appendChild(renderer.domElement);
//------------- 下面放创建几何体的代码 -----------------------
const geometry = new THREE.BoxGeometry(1, 1, 1);
const material = new THREE.MeshBasicMaterial({ color: 0x00ff00 });
const myGeometry = new THREE.Mesh(geometry, material);
scene.add(myGeometry);
//--------------- 创建几何体代码结束 --------------------------
// 创建一个平行光源
const directionalLight = new THREE.DirectionalLight(0xffffff, 1);
directionalLight.position.set(1, 1, 1).normalize(); // 设置光源的方向
scene.add(directionalLight);
const controls = new OrbitControls(camera, renderer.domElement);
camera.position.z = 5;
// 创建一个动画函数
function animate() {
// 请求下一帧动画
requestAnimationFrame(animate);
// 更新 OrbitControls
controls.update();
myGeometry.rotation.x += 0.01;
myGeometry.rotation.y += 0.01;
// 渲染场景
renderer.render(scene, camera);
}
animate()
在上面的示例代码里,注释部分 下面放创建几何体的代码到 创建几何体代码结束之间是放后续示例代码的位置。
示例中使用了一个平行光源,关于光源的使用方法在后续章节详细介绍。
二、 three.js 更多几何体的介绍
1. 胶囊几何体(CapsuleGeometry)
2.1.1 胶囊几何体说明
胶囊几何体是一种有球形顶端和圆柱形部分组合的几何体。
其构造函数:
THREE.CapsuleGeometry(radiusTop, radiusBottom, height, radialSegments, heightSegments, cappedTop, cappedBottom, thetaStart, thetaLength)
参数说明:
- radiusTop: 胶囊体顶部的半径;
- radiusBottom: 胶囊体底部的半径;
- height: 胶囊体的总高度;
- radialSegments(径向分段数): 胶囊体周围的圆柱部分的分段数;
- heightSegments(高度分段数): 胶囊体的高度上的分段数;
- cappedTop(是否有顶部): 一个布尔值,指示是否有胶囊体的顶部;
- cappedBottom(是否有底部): 一个布尔值,指示是否有胶囊体的底部;
- thetaStart(起始角度): 胶囊体的起始角度,用弧度表示;
- thetaLength(角度范围): 胶囊体的角度范围,用弧度表示。
2.1.2 示例代码
const geometry = new THREE.CapsuleGeometry( 1, 1, 4, 8 );
const material = new THREE.MeshPhongMaterial( {color: 0x00ff00} );
const myGeometry = new THREE.Mesh( geometry, material ); scene.add( myGeometry );
运行效果:
本示例中使用了一个新的材质 : MeshPhongMaterial,这种材质基于 Phong 反射模型,用于模拟物体表面的光照和阴影。 关于材质的具体使用方式也在后续章节详细介绍。
通过增加 radialSegments 分段数,可以看到球体变得更圆滑:
2. 圆锥体(ConeGeometry)
2.2.1 圆锥体介绍
圆锥体是一种具有尖顶和圆锥底部的几何体。 构造函数如下:
THREE.ConeGeometry(radius, height, radialSegments, heightSegments, openEnded, thetaStart, thetaLength)
其参数说明:
- radius: 圆锥体底部的半径;
- height: 圆锥体的总高度;
- radialSegments(径向分段数): 圆锥体周围的圆环部分的分段数;
- heightSegments(高度分段数): 圆锥体的高度上的分段数;
- openEnded(是否开口): 一个布尔值,指示圆锥体是否是开口的,如果为 true,则表示开口;
- thetaStart(起始角度): 圆锥体的起始角度,用弧度表示;
- thetaLength(角度范围): 圆锥体的角度范围,用弧度表示。
2.2.2 示例代码
const geometry = new THREE.ConeGeometry( 1, 1, 20, 40 );
const material = new THREE.MeshPhongMaterial( {color: 0x00ff00} );
const myGeometry = new THREE.Mesh( geometry, material ); scene.add( myGeometry );
运行效果:
3. 十二面体(DodecahedronGeometry )
2.3.1 十二面体简介
十二面体是一种具有 12 个面的多面体。DodecahedronGeometry 的构造函数的参数如下:
THREE.DodecahedronGeometry(radius, detail)
参数说明:
- radius(半径): 十二面体的外接球的半径;
- detail(细分层级): 控制几何体的细分层级,可以是整数值,表示将每个三角面细分为更小的三角形的次数。默认值为 0。
当detail值非0时,几何体每个面会被分成更多的三角形,以致于detail比较大的时候,展现出来的几何体会像个球体。
2.3.2 示例代码
const radius = 2;
const detail = 0;
const dodecahedronGeometry = new THREE.DodecahedronGeometry(radius, detail);
const material = new THREE.MeshPhongMaterial({ color: 0x00ff00 });
const myGeometry = new THREE.Mesh(dodecahedronGeometry, material);
scene.add(myGeometry);
运行效果:
修改detail值为5:
4. 创建几何体的边缘(EdgesGeometry )
2.4.1 边缘几何体说明
EdgesGeometry 通常基于其它几何体,用来生成边缘几何体图形。
其构造函数:
THREE.EdgesGeometry(geometry, thresholdAngle)
参数说明:
- geometry: 原始几何体,可以是任何支持边缘显示的几何体;
- thresholdAngle: 一个可选的角度阈值,用于控制哪些边被显示。在视角小于 thresholdAngle 的情况下会显示边。默认值为 1.5。
2.4.2 代码示例
const originalGeometry = new THREE.BoxGeometry(3, 3, 3);
const edgesGeometry = new THREE.EdgesGeometry(originalGeometry);
const material = new THREE.LineBasicMaterial({ color: 0xFFFF00 });
const myGeometry = new THREE.LineSegments(edgesGeometry, material);
scene.add(myGeometry);
这里创建了一个立方体,边缘几何体基于立方体来创建,运行效果:
5. 挤出几何体(ExtrudeGeometry )
2.5.1 挤出几何体说明
挤出几何体是通过沿着轮廓路径将一个平面形状挤压而成的三维形状。这个类的构造函数接受两个主要参数:轮廓路径和挤出选项。
构造函数:
THREE.ExtrudeGeometry(shapes, options)
参数说明:
- shapes: 一个或多个描述轮廓形状的 Shape 对象或路径。可以是单个 Shape 对象或由多个 Shape 组成的数组;
- options: 挤出选项,是一个包含挤出相关参数的对象。常见的选项包括 amount(挤出的距离)和 bevelEnabled(是否启用斜角),还可以设置其他参数。
2.5.2 代码示例
const width = 3;
const height = 1;
const depth = 1;
const extrudeAmount = 3;
// 创建一个矩形轮廓
const rectShape = new THREE.Shape();
rectShape.moveTo(0, 0);
rectShape.lineTo(0, height);
rectShape.lineTo(width, height);
rectShape.lineTo(width, 0);
rectShape.lineTo(0, 0);
// 设置挤出选项
const extrudeOptions = {
amount: extrudeAmount,
bevelEnabled: true,
bevelSegments: 2,
steps: 1,
bevelSize: 0.5,
bevelThickness: 0.5,
};
// 创建 ExtrudeGeometry
const geometry = new THREE.ExtrudeGeometry(rectShape, extrudeOptions);
// 创建材质和网格
const material = new THREE.MeshBasicMaterial({ color: 0x00ffFF, wireframe: true });
const myGeometry = new THREE.Mesh(geometry, material);
scene.add(myGeometry);
运行效果:
6. 二十面体(IcosahedronGeometry)
2.6.1 构造函数
THREE.IcosahedronGeometry(radius, detail)
参数说明:
- radius: 二十面体的外接球的半径;
- detail: 可选参数,控制几何体的细分层级。可以是整数值,表示将每个三角面细分为更小的三角形的次数。默认值为 0。
2.6.2 代码示例
const radius = 1;
const detail = 1;
const icosahedronGeometry = new THREE.IcosahedronGeometry(radius, detail);
const material = new THREE.MeshPhongMaterial({ color: 0x00ff00, wireframe: true });
const myGeometry = new THREE.Mesh(icosahedronGeometry, material);
scene.add(myGeometry);
运行效果:
7. 榫卯体(LatheGeometry)
2.7.1 榫卯体
榫卯体又称为旋转体,是通过旋转二维轮廓形状而成的三维几何体。LatheGeometry 的构造函数接受两个主要参数:路径(轮廓)和细分层级。
构造函数:
THREE.LatheGeometry(points, segments, phiStart, phiLength)
参数说明:
- points: 描述轮廓形状的点的数组。每个点是一个 Vector2 对象,表示二维平面上的坐标;
- segments: 可选参数,表示榫卯体的细分层级,即绕轴旋转的次数。默认值为 12;
- phiStart: 可选参数,表示旋转的起始角度,以弧度为单位。默认值为 0;
- phiLength: 可选参数,表示旋转的角度范围,以弧度为单位。默认值为 Math.PI * 2,表示完整的 360 度。
2.7.2 代码示例
// 定义轮廓的点
const points = [];
for (let i = 0; i < 10; i++) {
const x = Math.sin(i) * 2;
const y = (i - 10)*0.5 ;
points.push(new THREE.Vector2(x, y));
}
// 创建线条几何体,这个几体体只是为了方便查看轮廓点的位置
const geometry = new THREE.BufferGeometry().setFromPoints(points);
// 创建线条材质
const material1 = new THREE.LineBasicMaterial({ color: 0x00ff00 });
// 创建线条对象
const line = new THREE.Line(geometry, material1);
scene.add(line);
line.rotation.x = 1;
line.rotation.y = 0;
line.rotation.z = 0;
// 完成线条几何体的创建
// 基于上面的线段创建 LatheGeometry
const latheGeometry = new THREE.LatheGeometry(points, 50);
const material = new THREE.MeshBasicMaterial({ color: 0xFF2222, wireframe: true });
const myGeometry = new THREE.Mesh(latheGeometry, material);
scene.add(myGeometry);
8. 八面体(OctahedronGeometry)
2.8.1 构造函数
THREE.OctahedronGeometry(radius, detail)
2.8.2 代码
const radius =1;
const detail = 0;
const octahedronGeometry = new THREE.OctahedronGeometry(radius, detail);
const material = new THREE.MeshBasicMaterial({ color: 0x00ffff, wireframe: true });
const myGeometry = new THREE.Mesh(octahedronGeometry, material);
scene.add(myGeometry);
9. 环几何体(RingGeometry)
2.9.1 构造函数
THREE.RingGeometry(innerRadius, outerRadius, thetaSegments, phiSegments)
参数说明:
- innerRadius: 内半径,即环的内圆的半径;
- outerRadius: 外半径,即环的外圆的半径;
- thetaSegments: 可选参数,表示环的分段数,即环被切割成多少段。默认值为 8;
- phiSegments: 可选参数,表示环的纵向分段数,即环的高度被切割成多少段。默认值为 8;
- thetaStart: 可选参数,表示环的起始角度,以弧度为单位。默认值为 0;
- thetaLength: 可选参数,表示环的中央角度,以弧度为单位。默认值为 Math.PI * 2,即完整的 360 度。
2.9.2 示例
const innerRadius = 1;
const outerRadius = 2;
const thetaSegments = 8;
const phiSegments = 8;
const ringGeometry = new THREE.RingGeometry(innerRadius, outerRadius, thetaSegments, phiSegments);
const material = new THREE.MeshBasicMaterial({ color: 0x00ff00, wireframe: true });
const myGeometry = new THREE.Mesh(ringGeometry, material);
scene.add(myGeometry);
10. 四面体(TetrahedronGeometry)
2.10.1 构造函数
THREE.TetrahedronGeometry(radius, detail, type)
- radius: 四面体的外接球的半径;
- detail: 可选参数,控制几何体的细分层级。可以是整数值,表示将每个三角面细分为更小的三角形的次数。默认值为 0;
- type: 可选参数,表示四面体的类型。可以是 ‘regular’(正四面体)或 ‘geodesic’(几何四面体)。默认值为 ‘regular’。
2.10.2 示例
const radius = 2;
const detail = 0;
const type = 'regular';
const tetrahedronGeometry = new THREE.TetrahedronGeometry(radius, detail, type);
const material = new THREE.MeshBasicMaterial({ color: 0x00ff00, wireframe: true });
const myGeometry = new THREE.Mesh(tetrahedronGeometry, material);
scene.add(myGeometry);
11. 圆环几何体(TorusGeometry)
2.11.1 构造函数
THREE.TorusGeometry(radius, tube, radialSegments, tubularSegments)
- radius: 圆环的整体半径;
- tube: 管道半径,即环的管道的半径;
- radialSegments: 可选参数,表示环的管道的分段数,即管道被切割成多少段。默认值为 8;
- tubularSegments: 可选参数,表示环的整体的分段数,即整个圆环被切割成多少段。默认值为 32。
2.11.2 示例
const radius = 2;
const tube = 1;
const radialSegments = 8;
const tubularSegments = 32;
const torusGeometry = new THREE.TorusGeometry(radius, tube, radialSegments, tubularSegments);
const material = new THREE.MeshBasicMaterial({ color: 0x00ffff, wireframe: true });
const myGeometry = new THREE.Mesh(torusGeometry, material);
scene.add(myGeometry);
12. 环面结扣几何体(TorusKnotGeometry)
2.12.1 构造函数
THREE.TorusKnotGeometry(radius, tube, tubularSegments, radialSegments, p, q)
- radius: 环面结扣的整体半径;
- tube: 管道半径,即环面结扣的管道的半径;
- tubularSegments: 管道的分段数,即管道被切割成多少段;
- radialSegments: 环面的分段数,即整个环面被切割成多少段;
- p 和 q: 可选参数,控制环面结扣的形状。它们是整数值,用于确定结扣的形状。默认值为 p = 2 和 q = 3。
2.12.2 示例
const radius = 5;
const tube = 1;
const tubularSegments = 64;
const radialSegments = 8;
const p = 2;
const q = 3;
const torusKnotGeometry = new THREE.TorusKnotGeometry(radius, tube, tubularSegments, radialSegments, p, q);
const material = new THREE.MeshBasicMaterial({ color: 0x00ff00, wireframe: true });
const torusKnot = new THREE.Mesh(torusKnotGeometry, material);
scene.add(torusKnot);
13. 沿路径管道几何体(创建沿着一系列路径的管道几何体。)
2.13.1 构造函数
TubeGeometry(path,tubularSegments ,radius,radialSegments, closed )
- path — Curve - 一条继承自 Curve 基类的 3D 路径。默认为二次贝塞尔曲线;
- tubularSegments — Integer - 构成管道的段数。默认为 64;
- radius — Float - 管道的半径。默认为 1;
- radialSegments — Integer - 构成横截面的段数。默认为 8;
- closed — Boolean - 管道是否是开放或封闭的。默认为 false。
2.13.2 示例
class CustomSinCurve extends THREE.Curve {
constructor( scale = 1 ) {
super();
this.scale = scale;
}
getPoint( t, optionalTarget = new THREE.Vector3() ) {
const tx = t * 3 - 1.5;
const ty = Math.sin( 2 * Math.PI * t );
const tz = 0;
return optionalTarget.set( tx, ty, tz ).multiplyScalar( this.scale );
}
}
const path = new CustomSinCurve( 10 );
const geometry = new THREE.TubeGeometry( path, 20, 2, 8, false );
const material = new THREE.MeshPhongMaterial( { color: 0x00ffff } );
const myGeometry = new THREE.Mesh( geometry, material );
scene.add( myGeometry );
14. 创建几何体的边框几何体
2.14.1 构造函数
THREE.WireframeGeometry(geometry)
参数 geometry是原始的几何体。
2.14.2 示例
const geometry = new THREE.SphereGeometry( 10, 10, 10 );
const wireframe = new THREE.WireframeGeometry( geometry );
const myGeometry = new THREE.LineSegments( wireframe );
myGeometry.material.depthTest = false;
myGeometry.material.opacity = 0.5;
myGeometry.material.transparent = true;
scene.add( myGeometry );