threejs学习笔记
- 1. 官网
- 2. 本地搭建官网
- 3. 新的打包工具(parcel)
- 4. 使用threejs去渲染第一个场景和物体
- 5. 添加轨道控制器
- 6. 坐标辅助器
- 7. 控制物体移动
- 8. 物体的缩放与旋转
- 9. requestAnimationFrame
- 10. gsap
- 11. 根据尺寸实现自适应画面
- 12. 通过js来控制是否全屏
- 13. dat.gui
- 14. 常见网格集合体
- 15. 材质与纹理
- 16. 纹理的偏移、旋转和重复
- 17. 透明材质和纹理
- 18. 环境遮挡贴图和强度
- 19. PBR
- 20. 粗糙度和粗糙度贴图
- 21. 金属度和金属贴图
- 22. 法线贴图
- 23. 如何获取各种类型的纹理贴图
- 24. 纹理加载进度情况
- 25. 环境贴图
- 26. 灯光和阴影的关系与设置
- 27. 平行光阴影
- 28. 聚光灯
- 29. 点光源
- 30. 杂记
1. 官网
https://threejs.org/(外网,访问较慢)
2. 本地搭建官网
https://github.com/mrdoob/three.js/
下载压缩包进行本地启动
3. 新的打包工具(parcel)
官网
使用
npm install -g parcel-bundler
parcel index.html
4. 使用threejs去渲染第一个场景和物体
<template>
<div class="container" ref="container"></div>
</template>
<script setup>
import { ref, onMounted } from 'vue';
import * as THREE from "three";
// 导入轨道控制器
import { OrbitControls } from "three/examples/jsm/controls/OrbitControls";
// 1. 创建场景
const scene = new THREE.Scene();
// 2. 创建相机
// 2. 创建相机
const camere = new THREE.PerspectiveCamera(
75,
window.innerWidth / window.innerHeight,
0.1,
1000
);
// 3. 改变相机的位置
camere.position.set(0, 0, 10);
// 4. 添加相机到场景中
scene.add(camere);
// 5. 添加物体(点、线、面),材质
const geometry = new THREE.BoxGeometry(1, 1, 1);
const material = new THREE.MeshBasicMaterial({ color: "red" }); // 不透光材质
// 6. 创建物体
const cube = new THREE.Mesh(geometry, material);
// 7. 添加物体到场景中
scene.add(cube);
// 8. 初始化渲染器
const renderer = new THREE.WebGLRenderer();
// 9. 设置渲染器的大小
renderer.setSize(window.innerWidth, window.innerHeight);
const render = () => {
// 11. 使用渲染器将相机场景渲染出来
renderer.render(scene, camere);
requestAnimationFrame(render);
}
const container = ref(null);
onMounted(() => {
// 初始化轨道控制器
const controlls = new OrbitControls(camere, renderer.domElement);
controlls.enableDamping = true;
// 10. 将webgl渲染的canvas内容添加到dom节点中
container.value.append(renderer.domElement);
render();
})
</script>
<style>
* {
margin: 0;
padding: 0;
}
.container {
width: 100vw;
height: 100vh;
background-color: skyblue;
}
</style>
5. 添加轨道控制器
// 导入轨道控制器
import { OrbitControls } from "three/examples/jsm/controls/OrbitControls";
// 初始化轨道控制器
const controlls = new OrbitControls(camere, renderer.domElement);
controlls.enableDamping = true;
6. 坐标辅助器
// 添加坐标辅助器
const axesHelper = new THREE.AxesHelper(5);
scene.add(axesHelper);
7. 控制物体移动
cube.position.set(10, 10, 10)
cube.position.x += 0.1;
8. 物体的缩放与旋转
cube.scale.set(3, 1, 1);
cube.scale.x += 0.1;
cube.rotation.set(Math.PI / 3, 20, 10);
9. requestAnimationFrame
一般一帧在16毫秒左右
10. gsap
官网
使用
import { gsap } from "gsap";
// gsap
// gsap
const animation = gsap.to(cube.position, {
x: 2,
duration: 5,
ease: "elastic",
});
多种使用方式,详细查看官网
11. 根据尺寸实现自适应画面
// 监听画面的变化,更新渲染
window.addEventListener("resize", () => {
// 首先更新摄像头
camere.aspect = window.innerWidth / window.innerHeight;
camere.updateProjectionMatrix();
// 更新渲染器
renderer.setSize(window.innerWidth, window.innerHeight);
renderer.setPixelRatio(window.devicePixelRatio);
})
12. 通过js来控制是否全屏
// 双击进入全屏
window.addEventListener("dblclick", () => {
const fullScreenElement = document.fullscreenElement;
if (!fullScreenElement) {
renderer.domElement.requestFullscreen();
} else {
document.exitFullscreen();
}
})
13. dat.gui
安装
npm i dat.gui
使用
import datGui from "dat.gui";
// dat.gui
const gui = new datGui.GUI();
// 修改位置
gui
.add(cube.position, "x")
.min(0)
.max(10)
.step(0.01)
.name("位置")
.onChange((val) => {
console.log("值被修改", val);
}).onFinishChange((val) => {
console.log("完全被修改", val);
})
// 旋转
gui
.add(cube.rotation, "x")
.min(0)
.max(89)
.step(0.01)
.name("旋转")
.onChange((val) => {
console.log("值被修改", val);
})
// 缩放
gui
.add(cube.scale, "x")
.min(0)
.max(89)
.step(0.01)
.name("缩放")
.onChange((val) => {
console.log("值被修改", val);
})
14. 常见网格集合体
- BoxGeometry
- CircleGeometry
- SphereGeometry
- BufferGeometry
- TorusGeometry
- …
15. 材质与纹理
// 纹理
const textureLoader = new THREE.TextureLoader();
// vue写法
// eslint-disable-next-line @typescript-eslint/no-var-requires
const logoTextureLoader = textureLoader.load(require("./assets/logo.png"));
const material = new THREE.MeshBasicMaterial({
map: logoTextureLoader,
}); // 不透光材质
16. 纹理的偏移、旋转和重复
logoTextureLoader.offset.x = 0.2;
logoTextureLoader.offset.y = 0.2;
logoTextureLoader.rotation = Math.PI / 4;
logoTextureLoader.repeat.set(2, 3);
17. 透明材质和纹理
需要贴图,alpha是一张灰度纹理,用于控制整个表面的不透明度。(黑色:完全透明;白色完全不透明)。默认值为null。
const material = new THREE.MeshBasicMaterial({
map: logoTextureLoader,
alphaMap: alphaTextureLoader,
transparent: true,
}); // 不透光材质
18. 环境遮挡贴图和强度
此纹理的红色通道用作环境光遮挡贴图。默认值为空。aoMap需要第二组UV。
19. PBR
什么是PBR
物理属性的引擎渲染
PBR的组成部分
灯光属性:直接照明、间接照明、直接高光、间接高光、阴影、环境光
表面属性:基础色、法线、高光、粗糙度、金属度
20. 粗糙度和粗糙度贴图
rougness:材质的粗糙程度,0.0表示光滑的镜面反射,1.0表示完全漫反射。默认值为1.0。如果还提供rougnessMap,则两个值相乘。
rougnessMap:该纹理的绿色通道用于改变材质的粗糙度。
21. 金属度和金属贴图
metalness:材质和金属的相似度,非金属材质,如木材或石材,使用0.0,金属使用1.0,通常没有中间值。默认值为0.0。0.0到1.0之间的值可用于生锈金属的外观。如果还提供metalnessMap,则两个值相乘。
metalnessMap:该纹理的蓝色通道用于改变材质的金属度。
22. 法线贴图
normalMap: 纹理创建法线贴图。RGB值影响每个像素片段的表面法线,并改变颜色的照明方式。法线贴图不改变表面的实际形状,只改变照明。如果材料有一个使用左手习惯的法线映射,normalScale的y分量应该被否定,以补偿不同的手性。
23. 如何获取各种类型的纹理贴图
网站:
24. 纹理加载进度情况
LoadingManager
const manager = new THREE.LoadingManager();
manager.onStart = function ( url, itemsLoaded, itemsTotal ) {
console.log( 'Started loading file: ' + url + '.\nLoaded ' + itemsLoaded + ' of ' + itemsTotal + ' files.' );
};
manager.onLoad = function ( ) {
console.log( 'Loading complete!');
};
manager.onProgress = function ( url, itemsLoaded, itemsTotal ) {
console.log( 'Loading file: ' + url + '.\nLoaded ' + itemsLoaded + ' of ' + itemsTotal + ' files.' );
};
manager.onError = function ( url ) {
console.log( 'There was an error loading ' + url );
};
const loader = new THREE.OBJLoader( manager );
loader.load( 'file.obj', function ( object ) {
//
} );
25. 环境贴图
envMap
26. 灯光和阴影的关系与设置
- 材质要满足能够对光照有但应
- 设置渲染器开启阴影的计算
renderer.shadowMap.enabled = true
- 设置光照投影阴影
directionalLight.catsShadow = true
- 设置物体投影阴影
sphere.catsShadow = true
- 设置物体接收阴影
plane.catsShadow = true
27. 平行光阴影
设置阴影模糊度
directionalLight.shadow.radius = 20
设置阴影贴图模糊度
directionalLight.shadow.mapSize.set(2048, 2048)
28. 聚光灯
SpotLight
const spotLight = new THREE.SpotLight( 0xffffff );
spotLight.position.set( 100, 1000, 100 );
spotLight.map = new THREE.TextureLoader().load( url );
spotLight.castShadow = true;
spotLight.shadow.mapSize.width = 1024;
spotLight.shadow.mapSize.height = 1024;
spotLight.shadow.camera.near = 500;
spotLight.shadow.camera.far = 4000;
spotLight.shadow.camera.fov = 30;
scene.add( spotLight );
29. 点光源
PointLight
const light = new THREE.PointLight( 0xff0000, 1, 100 );
light.position.set( 50, 50, 50 );
scene.add( light );
30. 杂记
renderer.setClearColor
设置透明颜色和不透明度。
球环境贴图
texture.mapping = THREE.EquirectangularReflectionMapping