工作需求要求threeJS渲染一个模型以供可视化大屏展示,抛出模型精度不谈,只说业务实现
1.Three.JS的引入
ThreeJS官网地址:Three.js – JavaScript 3D Library
查看文档
中文切换及安装创建步骤
如果是自己研究学习用的,在官网安装完后,直接在-创建一个场景-里面直接copy代码玩就行了
如果是业务需求相关,希望快速构建一个简单的模型模块看下一页
2.封装模型模块
第一步先引入模块相关的threeJS模块
import * as THREE from 'three';// gltf文件装载器import { GLTFLoader } from 'three/addons/loaders/GLTFLoader.js';// 视图旋转控件import { OrbitControls } from 'three/examples/jsm/controls/OrbitControls';
第二步构建一个class类并初始化constructor内的参数
class ThreeModel {constructor(GLTF, Dom) {this.glft = GLTF; // 模型文件this.Dom = Dom; // dom容器this.scene = new THREE.Scene(); // 实例化场景this.camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 20000); // 实例化相机this.renderer = new THREE.WebGLRenderer(); // 实例化渲染器this.loader = new GLTFLoader(); // 实例化gltf装载器this.CameraPosition = {x: 0,y: 2600,z: 0}}
}
constructor内的参数分别为GLTF(引用的gltf格式模型文件)、Dom(挂载的dom元素)
我使用的vue2框架,调用该模块时须传入以下
import { ThreeModel } from "../three.js"...mounted() {const model_one = new ThreeModel('Texture/scene.gltf', this.$refs.box);model_one.init()}
接下来是类里面的初始化函数
init() {this.renderer.setSize(window.innerWidth, window.innerHeight);this.Dom.appendChild(this.renderer.domElement);this.loader.load(this.glft,(gltf) => {const model = gltf.scene;// 创建一个Object3D对象const modelContainer = new THREE.Object3D();// 将模型的网格添加到Object3D对象中modelContainer.add(model);// 添加Object3D对象到场景中this.scene.add(modelContainer);},undefined,(err) => {console.log('报错', err)})this.initControls();this.initLight();this.initCamera();const animate = () => {requestAnimationFrame(animate);// 在此处更新场景的其他内容this.renderer.render(this.scene, this.camera);}animate();}
初始化控制三维场景缩放和旋转的函数
initControls() { //使用OrbitControls控制三维场景缩放和旋转等功能this.controls = new OrbitControls(this.camera, this.renderer.domElement);//动态阻尼系数 即鼠标拖拽旋转的灵敏度this.controls.dampingFactor = 0.25;// this.controls.target.set(0, 900, 0)// //上下旋转范围this.controls.minPolarAngle = 0;this.controls.maxPolarAngle = 1.5;this.controls.autoRotate = true;//惯性滑动,滑动大小默认0.25this.controls.dampingFactor = 0.25;//滚轮是否可控制zoom,zoom速度默认1//缩放倍数this.controls.zoomSpeed = 1.0;//最大最小相机移动距离(景深相机)this.controls.minDistance = 1;this.controls.maxDistance = Infinity;//水平方向视角限制this.minAzimuthAngle = -Math.PI * 2;this.maxAzimuthAngle = Math.PI * 2;this.controls.enabledPan = true;this.keyPanSpeed = 7.0;}
初始化光照函数
initLight() { // 初始化光照let ambientLight = new THREE.AmbientLight(0x404040);this.scene.add(ambientLight);//定义灯,并设置位置this.light = new THREE.DirectionalLight(0x333333);this.light.position.set(60, 30, 40);this.light2 = new THREE.DirectionalLight(0xdddddd);this.light2.position.set(-20, 20, -20);this.scene.add(this.light);this.scene.add(this.light2);}
初始化相机函数
initCamera() {//初始化相机this.scene.scale.set(0.1, 0.1, 0.1)this.camera.position.set(0, this.CameraPosition.y, 0); // 设置相机位置,根据需求调整坐标this.camera.lookAt(1, 1, 5); // 设置相机观察的目标位置}
以下是完整代码
import * as THREE from 'three';
import { GLTFLoader } from 'three/addons/loaders/GLTFLoader.js';
// 视图旋转控件
import { OrbitControls } from 'three/examples/jsm/controls/OrbitControls';
// 拖拽控件
// import { DragControls } from 'three/examples/jsm/controls/DragControls';
class ThreeModel {constructor(GLTF, Dom) {this.glft = GLTF; // 模型文件this.Dom = Dom; // dom容器this.scene = new THREE.Scene(); // 实例化场景this.camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 20000); // 实例化相机this.renderer = new THREE.WebGLRenderer(); // 实例化渲染器this.loader = new GLTFLoader(); // 实例化gltf装载器this.CameraPosition = {x: 0,y: 2600,z: 0}}init() {this.renderer.setSize(window.innerWidth, window.innerHeight);this.Dom.appendChild(this.renderer.domElement);this.loader.load(this.glft,(gltf) => {const model = gltf.scene;// 创建一个Object3D对象const modelContainer = new THREE.Object3D();// 将模型的网格添加到Object3D对象中modelContainer.add(model);// 添加Object3D对象到场景中this.scene.add(modelContainer);},undefined,(err) => {console.log('报错', err)})this.initControls();this.initLight();this.initCamera();const animate = () => {requestAnimationFrame(animate);// 在此处更新场景的其他内容this.renderer.render(this.scene, this.camera);}animate();}initControls() { //使用OrbitControls控制三维场景缩放和旋转等功能this.controls = new OrbitControls(this.camera, this.renderer.domElement);//动态阻尼系数 即鼠标拖拽旋转的灵敏度this.controls.dampingFactor = 0.25;// this.controls.target.set(0, 900, 0)// //上下旋转范围this.controls.minPolarAngle = 0;this.controls.maxPolarAngle = 1.5;this.controls.autoRotate = true;//惯性滑动,滑动大小默认0.25this.controls.dampingFactor = 0.25;//滚轮是否可控制zoom,zoom速度默认1//缩放倍数this.controls.zoomSpeed = 1.0;//最大最小相机移动距离(景深相机)this.controls.minDistance = 1;this.controls.maxDistance = Infinity;//水平方向视角限制this.minAzimuthAngle = -Math.PI * 2;this.maxAzimuthAngle = Math.PI * 2;this.controls.enabledPan = true;this.keyPanSpeed = 7.0;}initLight() { // 初始化光照let ambientLight = new THREE.AmbientLight(0x404040);this.scene.add(ambientLight);//定义灯,并设置位置this.light = new THREE.DirectionalLight(0x333333);this.light.position.set(60, 30, 40);this.light2 = new THREE.DirectionalLight(0xdddddd);this.light2.position.set(-20, 20, -20);this.scene.add(this.light);this.scene.add(this.light2);}initCamera() {//初始化相机this.scene.scale.set(0.1, 0.1, 0.1)this.camera.position.set(0, this.CameraPosition.y, 0); // 设置相机位置,根据需求调整坐标this.camera.lookAt(1, 1, 5); // 设置相机观察的目标位置}
}
export { ThreeModel }
3.注意事项和说明
说明:
1.第三方模型文件要按照threeJS支持的格式要求
如图:
2.模型市场
推荐Explore 3D Models - Sketchfab
注意事项:
我使用的是vue项目,一定要将模型文件存放在public文件夹下,否则找不到或报引用错误
本人接触threeJS不多,该模块仅限于基础功能的使用,适用性较低,如果有懂的大佬希望评论或私信交流,如有错误请指出