1

1.什么是异步组件:

image.png

2.异步组件的使用:

子组件:

<template>
  <div class="asyncCmp">
    一个不需要在首屏中加载的组件。
  </div>
</template>

父组件:

<template>
  <div id="app">
    <AsyncCmp />
  </div>
</template>

<script>
import AsyncCmp from './components/async-cmp'

export default {
  components: {
    AsyncCmp,
  }
}
</script>

看看效果:
image.png
现在使用一个按钮来控制组件的加载:

<template>
  <div id="app">
    <button @click="show = !show">click</button>
    <AsyncCmp v-if="show" />
  </div>
</template>

<script>
import AsyncCmp from './components/async-cmp'

export default {
  components: {
    AsyncCmp,
  },
  data () {
    return {
      show: false,
    }
  }
}
</script>

看效果:
image
虽然初始状态没有展示这个组件,但其实webpack已经将该组件打包并且在父组件中加载进来了。
image.png
在app.js中能够找到它:
image.png
由于我们在点击按钮前并不需要加载这个组件,所以继续改造:

<template>
  <div id="app">
    <button @click="show = !show">click</button>
    <AsyncCmp v-if="show" />
  </div>
</template>

<script>
// import AsyncCmp from './components/async-cmp'

export default {
  components: {
    // AsyncCmp,
    AsyncCmp: () => import('./components/async-cmp'),
  },
  data () {
    return {
      show: false,
    }
  }
}
</script>

可以看到,组件并没有被加载到app.js中:
image.png
效果:
image
而在加载后会生成一个新的js文件:
image.png
如果使用这样的方式加载多个组件会发生什么呢:

子组件:

<template>
  <div class="asyncCmp">
    又一个不需要在首屏中加载的组件。
  </div>
</template>

父组件:

<template>
  <div id="app">
    <button @click="show = !show">click</button>
    <AsyncCmp v-if="show" />
    <AsyncCmp1 v-if="show" />
  </div>
</template>

<script>
export default {
  components: {
    AsyncCmp: () => import('./components/async-cmp'),
    AsyncCmp1: () => import('./components/async-cmp1'),
  },
  data () {
    return {
      show: false,
    }
  }
}
</script>

效果:
image
可以看到,加载后会生成两个新的js文件,如果需要加载的文件有很多个,那么就会生成对应个数的js文件:
image.png
为了减少生成的js文件个数,我们可以将这些同时出现的异步组件合并到一个js文件当中:

<template>
  <div id="app">
    <button @click="show = !show">click</button>
    <AsyncCmp v-if="show" />
    <AsyncCmp1 v-if="show" />
  </div>
</template>

<script>
export default {
  components: {
    AsyncCmp: () => import(/* webpackChunkName: "asyncCmp" */ './components/async-cmp'),
    AsyncCmp1: () => import(/* webpackChunkName: "asyncCmp" */ './components/async-cmp1'),
  },
  data () {
    return {
      show: false,
    }
  }
}
</script>

在加载异步组件的时候注释打包到同一个文件中,效果如下:
image

总结:

异步组件其实可以理解为按需加载的组件,什么时候需要展示了再去加载,而不是首次进入页面之后就全部都加载,这样操作能够很大程度的减少性能的消耗,提高用户体验。


野望
18 声望4 粉丝

一个为了写出漂亮代码而努力的前端人