Vue中使用Cytoscape.js

JavaScript019

Vue中使用Cytoscape.js,第1张

在Vue中使用一些第三方库时,很容易犯的错误是直接把第三方库的对象放在Vue的data属性中。

例如在使用 Cytoscape.js 时,用下面这种声明方式。

这样做的确是方便后面的操作,但问题是,这种对象特别大,嵌套层级很深,如下图所示,如果直接放在data里,vue的响应式机制,会监听cy的每个属性,开销巨大,CPU占用瞬间到100%。

所以在使用 Cytoscape.js 、 Echarts.js 与vue结合时,要避免直接放在data属性中。一种方法是,在 mounted() 里引入该对象。

另一种方法是用 Object.freeze()

这两个方法,都能避免vue的响应式开销,后面也能够正常操作 this.cy 对象。

首先在html页面中引入<script src="http://www.yanhuangxueyuan.com/versions/threejsR92/build/three.js"></script>

页面中

<template>

  <div>

    <div id="demo"></div>

  </div>

</template>

<script>

export default {

  data() {

    return {

      mesh: null,

      renderer: null,

      scene: null,

      camera: null,

    }

  },

  mounted() {

    this.init()

  },

  methods: {

    init() {

      // 创建场景

      this.scene = new THREE.Scene()

      // 创建相机(第一个参数视野夹角0~180°,第二参数相机大小,第三,四参数可看像素)

      this.camera = new THREE.PerspectiveCamera(

        75,

        window.innerWidth / window.innerHeight,

        1,

        1000

      )

      // 创建渲染器

      this.renderer = new THREE.WebGLRenderer()

      // 设置渲染器大小

      this.renderer.setSize(window.innerWidth, window.innerHeight)

      // 拿到dom

      let demo = document.getElementById("demo")

      // 把渲染器放到dom中

      demo.appendChild(this.renderer.domElement)

      // 创建一个立方体(长,宽,高)

      let geometry = new THREE.BoxGeometry(10, 10, 10)

      // 创建材料(定义立方体由这个材料组成)

      let material = new THREE.MeshBasicMaterial({

        color: 0xcccccc,

      })

      // 创建网格(合并立方体和材料)

      this.mesh = new THREE.Mesh(geometry, material)

      // 将网格放入场景中

      this.scene.add(this.mesh)

      // 因默认情况相机与场景重合,需要先设定相机位置

      this.camera.position.z = 50

      this.camera.position.y = 0

      // 用渲染器渲染场景,相机

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

      this.animate()

    },

    // 定义3D效果

    animate() {

      // 执行动画函数,执行完上一帧在执行下一帧

      requestAnimationFrame(this.animate)

      this.mesh.rotation.x += 0.05

      // this.mesh.rotation.y += 0.05

      this.mesh.rotateY(0.01)

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

    },

  },

}

</script>

<style>

body {

  margin: 0

  overflow: hidden

  /* 隐藏body窗口区域滚动条 */

}

</style>