vue组件传值详解

全局组件VS局部组件

  1. 全局组件

全局可调用,可在一个或多个挂在了Vue实例的DOM节点内使用该组件。

<body>
    <div id="app1">
        <my-component></my-component>
    </div>
    <div id="app2">
        <my-component></my-component>
    </div>
    <!-- js -->
    <script>
        Vue.component("my-component",{
            template:`<div>我是全局组件</div>`
        })
        new Vue({
            el:'#app1',
        })
        new Vue({
            el:'#app2'
        })
    </script>
</body>
  1. 局部组件

在Vue实例内声明的组件,只能在该实例内调用,局部组件和全局组件同时存在(组件名相同)时,局部组件会覆盖全局组件。

<body>
    <div id="app">
        <my-component></my-component>
    </div>
    <!-- js -->
    <script>
        new Vue({
            el:'#app',
            components:{
                'my-component':{
                    template:`<div>我是局部组件</div>`,
                }
            }
        })
    </script>
</body>

组件间通信方案

  1. 通过props传递

  2. $emit触发自定义事件

  3. 使用 ref

  4. 总线,EventBus

  5. parent/root

  6. attrslisteners

  7. ProvideInject

  8. Vuex

父->子

父组件通过属性赋值的方式向子组件传值,子组件通过props接收,使用。

<body>
    <div id="app">
        <my-component :title="title"></my-component>
    </div>
    <!-- js -->
    <script>
        Vue.component("my-component",{
            template:`<div @click='cont++'>{{cont}}</div>`,
            data(){ //子组件的data必须是函数
                return{
                    cont:this.title, //将接收的值暂存
                }
            },
            props:{
                title:{
                    type: Number, //传过来的值必须是Number类型
                    default:0,
                    required:true //传值不能为空
                }
            }
        })
        new Vue({
            el:'#app', 
            data(){
                return{
                    title:0 //父组件绑定传值
                }
            }, 
        })
    </script>
</body>

子->父

子组件通过向外触发方法的方式向父组件传值。

<body>
    <div id="app">
        {{total}}
        <my-component @addtotal="add"></my-component>
        <my-component v-on:addtotal="add"></my-component>
    </div>
    <!-- js -->
    <script>
        Vue.component("my-component",{
            template:`<div @click='addCont'>{{cont}}</div>`,
            data(){
                return{
                    cont:0 
                }
            },
            methods:{
                addCont(){
                    this.cont++;
                    this.$emit("addtotal");//子组件通过$emit向上触发方法
                }
            },
        })
        new Vue({
            el:'#app', 
            data(){
                return{
                    total:0, 
                }
            }, 
            methods:{
                add(){
                    this.total++;
                }
            }
        })
    </script>
</body>

ref

父组件获取子组件实例,调用子组件方法、获取子组件数据

// 子组件
<Children ref='son'></Children>

this.$refs.son  // 子组件实例,可继续 . 拿到对应数据

EventBus

适用于:兄弟组件、无关系组件

// 创建总线(vue 已经实现了Bus)
class Bus {
    constructor(){
        this.callbacks = {};    // 存放事件的名字
    }
    $on(name,fn){
        this.callbacks[name] = this.callbacks[name] || [];
        this.callbacks[name].push(fn);
    }
    $emit(name,args){
        if(this.callbacks[name]){
            this.callbacks[name].forEach(cb => cb(args));
        }
    }
}

// main.js (挂在在vue实例的原形上)
Vue.prototype.$bus = new Bus();

// 未完……

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。