<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
</head>
<body>
<!-- 配置一个导入的映射 -->
<script type="importmap">
{
"imports" : {
"three" : "./threejs/build/three.module.js",
"three/addons/" : "./threejs/examples/jsm/"
}
}
</script>
<script type="module">
/*
三维坐标系的理解
=> 常见的坐标系有两种
-> 第一种: 左手坐标系 也是传统坐标系 (3d设计软件常用)
+ 在很多的设计软件中是左手坐标系(C4D)X轴指向右侧、Y轴指向上方、Z指向屏幕内。
-> 第二种: 右手坐标系 (three.js默认)
+ 在ThreeJS中是右手坐标系,X轴指向右侧、Y轴指向上方、Z指向屏幕外。
=> 就是如果按照我们上面实现的图形我们是很难分辨出那个是x轴方向 那个是 y 轴方向 那个是 z 轴方向
=> 也就是能转动但是看不到坐标线
添加一个辅助线(辅助器)
=> 语法: const axesHelper = new THREE.AxesHelper(辅助线的长度)
-> 辅助线的长度: 是一个数字 没有单位
添加一个网格辅助线
=> 语法: const gridHelper = new THREE.GridHelper(网格的长度, 网格的宽度)
*/
// 1. 首先就是导入我们的three.js
import * as THREE from "three"
// 1.1 导入我们要使用的控件 相机控件
import { OrbitControls } from 'three/addons/controls/OrbitControls.js'
// 2. 场景: 我们需要创建一个用来展示 3d 内容的场景
// 也就是我们的三维场景, 和我们平时的平面的还是不一样的
// 不能正常的展示到网页中 需要单独创建一个场景
// 创建三维场景的语法: const scene = new THREE.Scene()
// 创建三维场景
const scene = new THREE.Scene()
// 3. 相机: 用来代替我们的眼睛去观察物体,通过相机摆放在不同的位置来实现对于3d物体的不同角度的效果的呈现
// 3d 物体有各个面 我们需要使用相机来对各个面进行观察
// 创建一个相机
const camera = new THREE.PerspectiveCamera( 75, window.innerWidth / window.innerHeight, 0.1, 1000 );
// 4. 渲染器: 我们的场景和相机都是一个虚拟的概念,如果要把内容呈现到网页当中,需要通过渲染器来进行渲染。
// 其实就是把我们要展示的物体在页面中展示出来
// 创建一个渲染器
const renderer = new THREE.WebGLRenderer({
// 注意: 新增3
// 因为我们的底色是黑色的 我们看起来依旧是不直观
// 所以我们来设置辅助透射层
// alpha: 英/ˈælfə/ 阿尔法
alpha: true, // 背景是否可以设置透明色
antialias: true // 表示是否开启反锯齿
// 注意: 这里有问题不能起效果
});
// 设置渲染器的大小, 我们设置的大小就是我们的整个窗口
renderer.setSize( window.innerWidth, window.innerHeight ); // 设置渲染器的大小
// 把渲染器要渲染的内容添加到body中
document.body.appendChild( renderer.domElement ); // 把渲染器的内容加载成为一个body的子元素
// 5. 着色器: 一个基础的几何体,并不是最终要展示的内容而是一个等待被描述的几何体(毛坯) 也是一个什么样的物体
// 这就相当于是我们的毛坯房还没有进行装修
// 创建着色器(这里就是创建了一个立方体) 除了立方体还有其他几何体: 圆柱体 球体 .....
// 注意: 新增4
// 这里的三个值,指的就是正方体三个方向(x, y, z)的大小
const geometry = new THREE.BoxGeometry( 2, 2, 1 );
// 6. 材质: 用于对着色器(几何体)表面材料的说明
// 创建材质
const material = new THREE.MeshBasicMaterial( {
// 这里我们设置了一个颜色 红色
color: 0xff0000, // 0xff0000 等同于 css当中的 #ff0000 这样的是以 0x 开头
// 注意: 新增2
// 开启我们材料的透明度
transparent: true,
// 设置透明度
opacity: 0.5
});
// 7. 物体: Mesh 网格模型 , 网格模型就是最终需要展示的3d物体
// 创建最终要展示的物体
const cube = new THREE.Mesh(geometry, material);// 创建的物体是哪个着色器(几何体) 使用那种材质
// 在场景scene当中添加创建好的物体
// 也就是把物体添加到场景中
scene.add(cube);
// 8. 设置相机的位置
camera.position.z = 5;
// camera.position.x = 2;
// camera.position.y = 5;
// 注意: 新增1
// 创建一个辅助线(辅助器)
const axesHelper = new THREE.AxesHelper(3)
// 在我们的场景中使用辅助线
scene.add(axesHelper)
// 注意: 我们添加的辅助线默认是在物体的中心位置的
// 注意: 但是现在还看不见 我们可以设置一下物体的透明度
// 注意:新增5
// 除了我们的辅助线以外能对我们的立体图形更好的理解的辅助线是网格
// 创建网格辅助线
// 传递的参数表示的是网格的长和宽
// grid: 英/ɡrɪd/ 网格的意思
const gridHelper = new THREE.GridHelper(10, 10)
// 在场景中使用网格辅助线
scene.add(gridHelper)
// 上面导入了我们的控件以后我们就可以得到一个控制器
// 9. 我们创建一个控制器
// Orbit: 英/ˈɔːbɪt/ 轨道的意思
// 需要传递参数
// 第一个: 我们的相机
// 第二个: 我们的渲染器中的节点
// 作用: 其实的对像机器的参数做出调整的
const controls = new OrbitControls(camera, renderer.domElement)
// 证明 : 对像机器的参数做出调整的
// 给控制器添加一个事件
controls.addEventListener('change', () => {
// 我们打印出相机的位置
// console.log('camera.position', camera.position);
// 值发生改变以后执行重新的渲染即可
renderer.render(scene, camera)
})
// 这个时候我们直接使用渲染函数进行渲染就好了
// 也就不需要之前的自动旋转了
renderer.render(scene, camera)
</script>
</body>
</html>