🎄2022年圣诞节到来啦,很高兴这次我们能一起度过~🎄
文章目录
- 🎉前言
- 🔎预览
- 🎁项目&资源
- 项目源码地址
- 打包
- 运行
- ✒️编码实现
🎉前言
2022圣诞节来了,让我们一起使用Three.js实现导入圣诞树模型吧。
🔎预览
🎁项目&资源
项目源码地址
GitHub: https://github.com/OrbitGW/Chirstmas-Tree.git
GitCode: https://gitcode.net/weixin_43130747/christmas-tree.git
打包
你可以去以上Git仓库下载Release,或者在Three.js圣诞树模型加载 - CSDN下载里获取已打包好的文件。
你也可以阅读项目源码中的README.md自己打包
运行
你可以在源码文件夹里使用一下命令进行预览:
npm install
npm run dev
还可以将打包好的文件部署到你的服务器上。如果你有Python3,可以启动http.server运行:
python -m http.server
✒️编码实现
引入依赖,这里我们用到了Three.js以及Three.js的GLTF加载器和控制器扩展。这些依赖直接用npm安装three就行了。然后就是导入我们要用到的背景图片:
import * as THREE from 'three';
import { GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader';
import { OrbitControls } from 'three/examples/jsm/controls/OrbitControls';
import BG from './model/bg.jpg'
创建Three场景,并将背景贴图设置为刚才导入的背景图片:
Scene:function(){
this.Scene = new THREE.Scene();
this.Scene.background = new THREE.TextureLoader().load(BG);
},
设置WebGL渲染器:
Renderer:function(){
this.Renderer = new THREE.WebGLRenderer();
this.Renderer.setSize(window.innerWidth, window.innerHeight);
this.Renderer.setClearColor(0xffffff);
this.Renderer.shadowMap.enabled = true;
this.Renderer.physicallyCorrectLights = true;
this.Renderer.outputEncoding = THREE.sRGBEncoding;
ThreeApp.appendChild(this.Renderer.domElement);
},
设置一个透视照相机,及位置。摄像机的几个参数分别是:视野,渲染窗口的宽高比,近截面还有远截面:
Camera:function(){
this.Camera = new THREE.PerspectiveCamera(45, window.innerWidth / window.innerHeight,1, 10000);
this.Camera.position.set(0, 0, 20);
this.Camera.lookAt(this.Scene.position);
}
加载GLTF模型并居中,Three加载不同模型细节上会有一点差别,这里以GLTF为例。我们一会会将模型文件操作一下并传入,不能直接写路径,因为Webpack打包后可能会找不到资源:
modelLoader:function(MODEL){
this.Controls.autoRotate = true;
let Loader = new GLTFLoader();
Loader.load(MODEL.path, (geometry)=> {
this.Camera.position.set(0,0,20);
this.Model = geometry.scene;
var box3 = new THREE.Box3();
box3.expandByObject(this.Model);
var center = new THREE.Vector3();
box3.getCenter(center);
this.Model.position.x = this.Model.position.x - center.x;
this.Model.position.y = this.Model.position.y - center.y;
this.Model.position.z = this.Model.position.z - center.z;
this.Scene.add(this.Model);
});
},
添加环境光源,这里添加了一个环境光和四个点光源:
addLight:function(){
var ambient_light = new THREE.AmbientLight(0xFFFFFF,1);
this.Scene.add(ambient_light);
var l1,l2,l3,l4;
l1 = new THREE.DirectionalLight(0xFFFFFF,3);
l2 = new THREE.DirectionalLight(0x1B1B1B,3);
l3 = new THREE.DirectionalLight(0xFFFFFF,1.5);
l4 = new THREE.DirectionalLight(0xFFFFFF,1.5);
l1.position.set(0, 15, 0);
l2.position.set(0, -200, 0);
l3.position.set(0, -5, 20);
l4.position.set(0, -5, -20);
this.Scene.add(l1);
this.Scene.add(l2);
this.Scene.add(l3);
this.Scene.add(l4);
},
鼠标控制器,可以实现鼠标左键旋转,右键拖动,滚轮缩放:
addControls:function() {
this.Controls = new OrbitControls(this.Camera, this.Renderer.domElement);
},
渲染动画
animation:function(){
this.Renderer.render(this.Scene, this.Camera);
this.Controls.update();
requestAnimationFrame(()=>this.animation());
},
改变窗口缓冲区操作,也就是改变窗口大小以后,我们需要重新设置相机和渲染选项,不然渲染比例会出问题:
onWindowResize:function() {
this.Camera.aspect = window.innerWidth / window.innerHeight;
this.Camera.updateProjectionMatrix();
this.Renderer.setSize(window.innerWidth, window.innerHeight);
this.Renderer.render(this.Scene, this.Camera);
},
运行方法,最后调用这个即可
run:function(){
this.init.Renderer.call(this)
this.init.Scene.call(this)
this.init.Camera.call(this)
this.addControls();
this.addLight()
this.modelLoader({path:require('./model/christmas-tree.glb').default});
this.animation();
window.onresize = ()=>this.onWindowResize();
}
最后调用方法:
CTScene.run();
最后运行npm run dev
然后在http://localhost:3000
看一看效果:
Threejs实现圣诞树模型加载效果