• Vue使用的扩展


    1、Bus(总线)实现非父子组件通信

    Vue2.0提供了Vuex进行非父子组件之间的通信,但在简单的场景下,可以使用一个空的Vue实例作为中央事件总线。

    实现代码示例:

    <div id="app">
        <c1></c1>
        <c2></c2>
    </div>
    var Bus = new Vue();   //为了方便将Bus(空vue)定义在一个组件中,在实际的运用中一般会新建一Bus.js
    Vue.component('c1',{   //这里以全局组件为例,同样,单文件组件和局部组件也同样适用
    template:'<div>{{msg}}</div>',
      data: () => ({
        msg: 'Hello World!'
      }),
      created() {
        Bus.$on('setMsg', content => {     //监听Vue示例 Bus 的某一个事件
          this.msg = content;
        });
      }
    });
    Vue.component('c2',{
      template: '<button @click="sendEvent">Say Hi</button>',
      methods: {
        sendEvent() {
          Bus.$emit('setMsg', 'Hi Vue!');  //触发vue示例 bus 的某一个事件,并且将参数作为数据传过去
        }
      }
    });
    var app= new Vue({
        el:'#app'
    })

    在实际运用中,一般将Bus抽离出来:

    // Bus.js
    import Vue from 'vue'
    const Bus = new Vue()
    export default Bus

    组件调用时先引入

    // 组件1
    import Bus from './Bus'
    export default {
      data() {
          return {
             .........
           }
        },
      methods: {
          ....
          Bus.$emit('log', 120)
      },
    }
    // 组件2
    import Bus from './Bus'
    export default {
        data() {
            return {
                .........
                }
          },
        mounted () {
           Bus.$on('log', content => { 
              console.log(content)
            });    
        }    
    } 

    但这种引入方式,经过webpack打包后可能会出现Bus局部作用域的情况,即引用的是两个不同的Bus,导致不能正常通信

    1.1、推荐使用Bus的方式

    (1)直接将Bus注入到Vue根对象中

    import Vue from 'vue'
    const Bus = new Vue()
    var app= new Vue({
        el:'#app',
       data:{
        Bus
        }  
    })

    在子组件中通过this.$root.Bus.$on()、this.$root.Bus.$emit()来调用

    (2)在一个教程视频中看过,也可以通过将Bus放在vue示例的原型对象中使用

    Vue.prototype.bus = new Vue();

    每个组件都是一个Vue示例,所以每个组件都会有bus属性,在组件中可以通过 this.bus.$emit、this.bus.$on 来调用

    Vue.component('c2',{
      template: '<button @click="sendEvent">Say Hi</button>',
      methods: {
        sendEvent() {
          this.bus.$emit('setMsg', 'Hi Vue!');  
        }
      }
    });

     参考:https://www.cnblogs.com/fanlinqiang/p/7756566.html

    2、异步组件(按需加载)

    官方文档:https://cn.vuejs.org/v2/guide/components-dynamic-async.html

    在单页应用中,如果没有应用懒加载,运用webpack打包后的文件将会异常的大(此时通常只有一个JS文件),造成进入首页时,需要加载的内容过大,延时过长,不利于用户体验,而运用懒加载则可以将页面进行划分,需要的时候加载页面,可以有效的分担首页所承担的加载压力,减少首页加载用时。

    其实 vue 中实现按需加载也非常简单,只要将平常的导入组件的方式改一下就行,vue-router会自动帮我们实现按需加载需要的组件,而 webpack 会自动帮我们实现代码拆分,由此实现了在需要的时候才加载需要的组件文件。

    2.1、使用resolve => require([’./_account’], resolve)实现按需加载

    创建一个项目,组件目录:Helloworld 组件是首页,在 HelloWord 中引入加载 item01 组件,在 item01 组件中引入加载 item02 组件。

         1、使用普通的引入方式:

    //HelloWord.vue 中的代码
    <template>
      <div class="hello">
        <h3>this is HelloWorld</h3>
        <template v-if="showItem">
          <Item01></Item01>
        </template>
        <button @click="toggleItem">切换</button>
      </div>
    </template>
    
    import Item01 from './Item01.vue'
    export default {
      name: 'HelloWorld',
      data () {
        return {
          showItem: false
        }
      },
      components: {
        Item01
      },
      methods: {
        toggleItem () {
          this.showItem = !this.showItem;
        }
      }
    }
    
    //Item01.vue 中的代码
    <template>
      <div>
        <h3>this is item01</h3>
        <Item02></Item02>
      </div>
    </template>
    
    import Item02 from './Item02.vue'

    运行项目:

    点击切换按钮,显示 item01、item02 组件:

     

    可以看到,加载的 JS 文件并没有任何变化,即没有新加载 JS 文件。可以看到 item01和 item02 组件都被打包到了 app.js 文件中,所有的组件 JS 代码都被打包到了一个文件中,这会导致该文件过大,影响加载速度。

         

          2、使用按需加载的方式:

    //HelloWord.vue 中的代码
    <template>
      <div class="hello">
        <h3>this is HelloWorld</h3>
        <template v-if="showItem">
          <Item01></Item01>
        </template>
        <button @click="toggleItem">切换</button>
      </div>
    </template>
    
    const Item01 = resolve => require(['./Item01'],resolve)   //按需加载 item01 组件
    export default {
      name: 'HelloWorld',
      data () {
        return {
          showItem: false
        }
      },
      components: {
        Item01
      },
      methods: {
        toggleItem () {
          this.showItem = !this.showItem;
        }
      }
    }
    
    //Item01.vue 中的代码
    <template>
      <div>
        <h3>this is item01</h3>
        <Item02></Item02>
      </div>
    </template>
    
    const Item02 = resolve => require(['./Item02'],resolve)   //按需加载 item02 组件

    运行项目:

     

    点击切换按钮,显示 item01、item02 组件:

    可以看到,一开始没有显示 item01、item02 组件时,浏览器只加载了 app.js 文件。当点击按钮显示 item01、item02 组件后,开始依次加载 item01、item02打包后的 JS 文件。

    通过按需加载,webpack 会帮我们将需要按需加载的组件跟一开始需要加载的 JS 文件分离开,当需要加载的时候再加载。按需加载只是改变掉加载组件的方式而已,webpack 会自动帮我们实现按需加载。

    利用此特性,我们便能做很多针对前端的优化。比如:将页面核心功能(音、视频播放、文章、商品等等)打包成一个核心模块,通过框架优先加载。其他的一些周边功能打包后,通过服务器异步加载,从而解决业务需求越来越多导致的系统难维护、访问慢问题。

    参考:https://segmentfault.com/a/1190000012138052

    其它实现按需加载的引入方法可以参考:https://blog.csdn.net/scarlett_dream/article/details/83756392https://segmentfault.com/a/1190000011519350

    3、Vue 动态插入组件

    代码示例:

    <div id="app">
      <p>{{ message }}</p >
      <button @click="add('a-component', '我是A')">添加A组件</button>
      <button @click="add('b-component', '我是B')">添加B组件</button>
      <component :is="item.component" :text="item.text" v-for="item in items"></component>
    </div>
    js:
    
    <script>
    const aComponent = Vue.extend({
      props: ['text'],
      template: '<li>A Component: {{ text }}</li>'
    })
    
    const bComponent = Vue.extend({
      props: ['text'],
      template: '<li>B Component: {{ text }}</li>'
    })
    
    new Vue({
      el: '#app',
      data () {
        return {
          message: 'Hello Vue.js!',
          items: []
        }
      },
      methods: {
        add (name, text) {
           this.items.push({
             component: name,
             text: text
           })
        }
      },
      components: {
        aComponent,
        bComponent
      }
    })
    </script>

    Vue.extend 是构造一个组件的语法器。你给它参数它给你一个组件,然后这个组件你可以作用到Vue.component 这个全局注册方法里, 也可以在任意vue模板里使用<apple>组件

    var apple = Vue.extend({
       ....
    })
    Vue.component('apple',apple) 

    也可以作用到vue实例或者某个组件中的components属性中并在内部使用apple组件

    new Vue({ 
      components:{
         apple:apple
      }
    })
  • 相关阅读:
    CC学iOS杂记 001_Device
    低字节序和高字节序相互转换(Little Endian/Big Endian)
    wpf 控件复制 克隆
    压缩图片
    网络流转换为Byte数组
    JS屏蔽右键菜单,复制,粘帖xxxxx........
    记录详细错误信息
    Media Queries详解--转
    解决 asp.net 伪静态 IIS设置后 直正HTML无法显示的问题
    对C#泛型实例化对像--转
  • 原文地址:https://www.cnblogs.com/wenxuehai/p/10509839.html
Copyright © 2020-2023  润新知