前期回顾:
接下来, 我们通过三种基础的变换来加深对3D坐标系中坐标和单位的理解, 同时也是动画的基础. 分别是:
- 移动
- 缩放
- 旋转
效果
1. 网络辅助工具
为了更好的理解坐标和单位, 我们引入网格辅助工具
(GridHelper)
// 5. 创建立方体(几何+材质)
const cubeGeometry = new THREE.BoxGeometry(2, 2, 2)
const cubeMaterial = new THREE.MeshNormalMaterial()
const cube = new THREE.Mesh(cubeGeometry, cubeMaterial)
// 创建网格辅助工具
const gridHelper = new THREE.GridHelper( 20, 20, 0xffffff, 0xffffff )
// 为了更方便观察, 设置opacity透明度
gridHelper.material.transparent = true
gridHelper.material.opacity = 0.5
// 添加到场景中
scene.add( gridHelper )
- 为了方便观察, 我们把立方体的大小改成了(2,2,2). 这种x轴的范围为(-1, 1)
- 创建网格辅助工具, 并添加到场景中
- 第一个参数(size): 网格的总宽高, 设置为20, 对应x轴的坐标范围为(-10, 10), 默认值为
10
- 第二个参数(divisions): 网格分成多少份, 设置为20, 每份就是1个单位, 默认值为
10
- 第三个参数(colorCenterLine): 中线的颜色, 默认值为
0x444444
- 第四个参数(colorGrid): 网络线的颜色, 默认值为
0x888888
- 第一个参数(size): 网格的总宽高, 设置为20, 对应x轴的坐标范围为(-10, 10), 默认值为
2. 移动
通过改变物体的position
属性, 控制物体的移动
// 通过设置三维向量的属性控制移动
cube.position.x = 2
cube.position.y = 2
cube.position.z = 2
// 通过调用三维向量的方法控制移动
cube.position.set(3, 3, 3)
// 添加到场景
scene.add(cube)
通过设置cube的position
(三维向量)对象的x, y, z的值来控制立方体分别沿x, y, z轴移动
3. 缩放
通过改变物体的scale
属性, 控制物体的缩放
// 通过设置三维向量的属性控制缩放比例
cube.scale.x = 1
cube.scale.y = 2
cube.scale.z = 3
// 通过调用三维向量的方法控制缩放
cube.scale.set(3, 3, 3)
4. 旋转
通过改变物体的rotation
属性, 控制物体的旋转.
这里需要注意的是: 旋转的单位是弧度, 不是角度
换算公式
π弧度 = 180度
- 弧度=角度×(π ÷ 180)
- 角度=弧度×(180 ÷ π)
常用弧度
π/2弧度 = 90度
π/3弧度 = 60度
π/4弧度 = 45度
π/6弧度 = 30度
按照右手法则, 大拇指指向x轴, 四指方向为正方向, 即从x轴方向观察, 逆时间旋转
// 通过设置三维向量的属性控制旋转
cube.rotation.x = Math.PI / 4
// 通过三维向量的方法控制旋转
cube.rotation.set(Math.PI / 4, 0, 0)
5. 集成Gui工具
我们发现, 如果每次通过修改代码的方式修改属性值效率太低
这里我们可以集成一种Gui工具, 通过UI交互界面来修改方便很多
dat.gui的npm链接
1) 安装
npm i dat.gui
2) 基本使用
// 导入dat
import * as dat from 'dat.gui'
// 初始化
const gui = new dat.GUI()
gui.add(cube.position, 'x').min(-10).max(10).step(1)
这里我们可以做一个分组
// 5. 创建立方体(几何+材质)
const cubeGeometry = new THREE.BoxGeometry(2, 2, 2)
const cubeMaterial = new THREE.MeshNormalMaterial()
const cube = new THREE.Mesh(cubeGeometry, cubeMaterial)
const gui = new dat.GUI()
const guiPosition = gui.addFolder('移动')
guiPosition.add(cube.position, 'x').min(-10).max(10).step(1)
guiPosition.add(cube.position, 'y').min(-10).max(10).step(1)
guiPosition.add(cube.position, 'z').min(-10).max(10).step(1)
const guiScale = gui.addFolder('缩放')
guiScale.add(cube.scale, 'x').min(1).max(10).step(1)
guiScale.add(cube.scale, 'y').min(1).max(10).step(1)
guiScale.add(cube.scale, 'z').min(1).max(10).step(1)
const guiRotate = gui.addFolder('旋转(度)')
const data = {
x: 0,
y: 0,
z: 0,
}
guiRotate.add(data, 'x', -180, 180, 1).onChange((value) => {
// 在onChange的回调中
// 1. 通过形参获取修改的数值
// 2. 使用THREE提供的数学工具, 将 度 转换成 弧度
cube.rotation.x = THREE.MathUtils.degToRad(value)
})
guiRotate.add(data, 'y', -180, 180, 1).onChange((value) => {
cube.rotation.y = THREE.MathUtils.degToRad(value)
})
guiRotate.add(data, 'z', -180, 180, 1).onChange((value) => {
cube.rotation.z = THREE.MathUtils.degToRad(value)
})
完整示例:
// 导入three.js
import * as THREE from 'three'
import { OrbitControls } from 'three/addons/controls/OrbitControls.js'
// 导入dat.gui
import * as dat from 'dat.gui'
// 1. 创建场景
const scene = new THREE.Scene()
// 5. 创建立方体(几何+材质)
const cubeGeometry = new THREE.BoxGeometry(2, 2, 2)
const cubeMaterial = new THREE.MeshNormalMaterial()
const cube = new THREE.Mesh(cubeGeometry, cubeMaterial)
scene.add(cube)
// 集成Gui工具
const gui = new dat.GUI()
/**
* 添加一个配置项
* @param Object
* @param Attr
*/
const guiPosition = gui.addFolder('位置信息')
guiPosition.add(cube.position, 'x', -10, 10, 1)
guiPosition.add(cube.position, 'y', -10, 10, 1)
guiPosition.add(cube.position, 'z', -10, 10, 1)
const guiScale = gui.addFolder('缩放')
guiScale.add(cube.scale, 'x', 1, 10, 1)
guiScale.add(cube.scale, 'y', 1, 10, 1)
guiScale.add(cube.scale, 'z', 1, 10, 1)
const guiRotate = gui.addFolder('旋转(度)')
const data = {
x: 0,
y: 0,
z: 0,
}
guiRotate.add(data, 'x', -180, 180, 1).onChange((value) => {
// 在onChange的回调中
// 1. 通过形参获取修改的数值
// 2. 使用THREE提供的数学工具, 将 度 转换成 弧度
cube.rotation.x = THREE.MathUtils.degToRad(value)
})
guiRotate.add(data, 'y', -180, 180, 1).onChange((value) => {
// 在onChange的回调中
// 1. 通过形参获取修改的数值
// 2. 使用THREE提供的数学工具, 将 度 转换成 弧度
cube.rotation.y = THREE.MathUtils.degToRad(value)
})
guiRotate.add(data, 'z', -180, 180, 1).onChange((value) => {
// 在onChange的回调中
// 1. 通过形参获取修改的数值
// 2. 使用THREE提供的数学工具, 将 度 转换成 弧度
cube.rotation.z = THREE.MathUtils.degToRad(value)
})
// 2. 创建相机
const camera = new THREE.PerspectiveCamera(
45,
window.innerWidth / window.innerHeight,
1,
1000
)
camera.position.set(20, 20, 20)
camera.lookAt(0, 0, 0)
// 6. 创建坐标轴的辅助对象
const axesHelper = new THREE.AxesHelper(10)
scene.add(axesHelper)
// 创建网格辅助对象
const gridHelper = new THREE.GridHelper(20, 20, 0xffffff, 0xffffff)
gridHelper.material.transparent = true
gridHelper.material.opacity = 0.5
scene.add(gridHelper)
// 3. 创建渲染器
const renderer = new THREE.WebGLRenderer({ antialias: true })
renderer.setSize(window.innerWidth, window.innerHeight)
renderer.setPixelRatio(window.devicePixelRatio)
renderer.setAnimationLoop(animation)
document.body.appendChild(renderer.domElement)
// 4. 渲染
function animation() {
renderer.render(scene, camera)
}
// 7. 创建轨道控制器
const controls = new OrbitControls(camera, renderer.domElement)
// 8. 监听window的resize事件
window.addEventListener('resize', () => {
// 重新设置相机的宽高比
camera.aspect = window.innerWidth / window.innerHeight
camera.updateProjectionMatrix()
// 设置渲染器的出图(照片的大小)
renderer.setSize(window.innerWidth, window.innerHeight)
})
需要视频教程的,可以点击下方卡片备注【threejs】
GIS资料免费获取https://www.wjx.cn/vm/wRqdSxO.aspx#
标签:10,cube,const,入门教程,THREE,Three,add,new,JS From: https://blog.csdn.net/2401_84715637/article/details/141215587