0
点赞
收藏
分享

微信扫一扫

GLB 3d文件在前端页面的展示

                      GLB 3d文件在前端页面的展示

1. 选择方案

前端实现3D效果的选项有以下四点:

A. CSS 3D技术;

B. SVG;

C. WebGL技术;

D. Canvas或者图片模拟3D

其中最后一种是用其他技术或方法去模拟3D效果,前3种才是浏览器真正意义上支持的3D技术。而three.js直接支持前3种渲染方式。three.js是JavaScript编写的WebGL第三方库。提供了非常多的3D显示功能。使用此组件可以自己绘制3D图像或展示在线及本地的3D模型。

2. 引入

three.js可以使用模块化引入,也可以直接用script来引入。在本项目中使用npm引入。

注意事项:

A. 此组件在几年前由three.js更名为three.所以安装时的命令应为npm install three --save。

B. 引入后在应用中需要加载本地或在线的3d文件,需要用户能够在屏幕上交互,所以还需引入构建器。注意引入的路径,其中第一项为对应文件的构建器。

import { GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader.js'

import { OrbitControls } from 'three/examples/jsm/controls/OrbitControls.js'

3. 引入后的必要配置

A. 基本配置

//指定区域

        let container = document.getElementById('scene')

        this.scene = new THREE.Scene()

        //新建相机(参数意义:摄像机视锥体垂直视野角度, 摄像机视锥体长宽比,摄像机视锥体近端面, 摄像机视锥体远端面)

        this.camera = new THREE.PerspectiveCamera(70, container.clientWidth / container.clientHeight, 0.01, 10)

        this.camera.position.set(0,1,1)


        // 添加灯光

        this.ambientLight = new THREE.AmbientLight(0xffffff) // 环境光

        this.scene.add(this.ambientLight)


        // 加载模型

        const loader = new GLTFLoader();

        loader.load("../../static/3dtest.glb", (result) => {

            console.log(result)

            result.scene.position.set(0,0,0)

            result.scene.scale.set(0.3,0.3,0.3)

            result.scene.traverse( function ( child ) {

            if ( child.isMesh ) {

                // child.frustumCulled = false;

                // //模型阴影

                // child.castShadow = false;

                // //模型自发光

                child.material.emissive =  child.material.color;

                child.material.emissiveMap = child.material.map ;

            }})

            this.scene.add(result.scene);

        });

        // 设置渲染器

        this.renderer = new THREE.WebGLRenderer({antialias: true})

        this.renderer.setSize(container.clientWidth, container.clientHeight)

        container.appendChild(this.renderer.domElement)

B. 挂载场景和相机

animate() {

       this.renderer.render(this.scene, this.camera)

        requestAnimationFrame(this.animate)

    },

C. 设置控制项

initControls() {

      //controls = new THREE.OrbitControls( camera, renderer.domElement );

      this.controls = new OrbitControls(

        this.camera,

        this.renderer.domElement

      );

      // 如果使用animate方法时,将此函数删除

      //controls.addEventListener( 'change', render );

      // 使动画循环使用时阻尼或自转 意思是否有惯性

      this.controls.enableDamping = false;

      //动态阻尼系数 就是鼠标拖拽旋转灵敏度

      //controls.dampingFactor = 0.25;

      //是否可以缩放

      this.controls.enableZoom = true;

      //是否自动旋转

      this.controls.autoRotate = true;

      //设置相机距离原点的最远距离

      this.controls.minDistance = 1;

      //设置相机距离原点的最远距离

      this.controls.maxDistance = 10;

      //是否开启右键拖拽

      this.controls.enablePan = false;

    },

D. 设置视角重置

onWindowResize() {

      this.camera.aspect = window.innerWidth / window.innerHeight;

      this.camera.updateProjectionMatrix();

      this.renderer.render(this.scene, this.camera)

    },


E. 在vue的mounted周期中集合上述方法

this.init()

    this.initControls()

    this.animate()

    window.onresize = this.onWindowResize;

4. 销毁实例

在项目中发现频繁的在3D场景的页面和其他页面切换会导致页面卡顿,是由于在切换路由时没有清除相关模型导致大量占用了内存;所以需要在离开3D场景销毁模型,并且释放相关的变量,例如renderer、scene、camera、controls。

beforeDestroy() {

    this.scene.remove()

    this.scene = null

    this.camera = null

    this.scene = null

    this.renderer = null

    this.ambientLight = null

    this.controls = null

  }



5. 实现效果

GLB 3d文件在前端页面的展示_vue


举报

相关推荐

0 条评论