vue组件通信方式(多种方案)

一、Props传递数据

 components

  |-Grandson1.vue //孙子1
  |-Grandson2.vue //孙子2
  |-Parent.vue //父亲
  |-Grandson1.vue //儿子1
  |-Grandson1.vue //儿子2

在父组件中使用儿子组件

<template>

  <div>
    父组件:{{money}}
    <Son1 :money="money"><Son1>
  </div>

</template>

<script>
  import Son1 from ''./Son1";
  export default{
    components:{

      Son1
    },

    data(){
      return { money: 100};
    }
  };
</script>
子组件接受数据

props:{
  value:{
    type:Number,

    default:1
  }
}

如果是数组

props:{
  value:{
    type:Array,

    default: ()=>[]
  }
}

二、$emit使用
子组件触发父组件方法,通过回调的方式将修改的内容传递给父组件

父组件

<template>

  <div>
    父组件:{{money}}
    <Son1 :money="money" @input="change"><Son1>
  </div>

</template>

<script>
  import Son1 from ''./Son1";
  export default{
    methods:{
     change(data){
       this.money = data
      } 
    },
    components:{
      Son1
    },

    data(){
      return { money: 100};
    }
  };
</script>

子组件触发绑定自己身上的方法

<template>

  <div>
    子组件1:{{money}}
    <button @click="$emit('input',200)">修改父组件的值<Son1>
  </div>

</template>

<script>
  export default{
    props:{
     money:{
       type:Number
     }
    }

  };
</script>

同步父子组件的数据=>语法糖的写法

.sync
<Son1 :money:sync="money"></Son1>
<--触发的事件名 update:(绑定.sync属性的名字)-->
<button @click="$emit('update:money',200)">更改</button>

v-model
<Son1 v-model="money"></Son1>

<template>

  <div>
    子组件1:{{value}}//触发的时间只能是input
    <button @click="$emit('input',200)">修改父组件的值<Son1>
  </div>

</template>

<script>
  export default{
    props:{
     value:{ //接收到的属性名只能叫value
       type:Number
     }
    }

  };
</script>

三、$parent、$children
多层级传递

<Grandson1 :value="value"></Grandson1>

<template>

  <div>
    孙子1:{{value}}
    <---调用父组件的input事件-->
    <button @click="$parent.$emit('input',200)">更改<Son1>
  </div>

</template>

<script>
  export default{
    props:{
     value:{ 
       type:Number
     }
    }

  };
</script>

如果层级很深就会出现$parent.$parent...这里封装一个$dispach方法进行向上派发
$dispatch
Vue.prototype.$dispatch = function $dispatch(eventName, data){
  let parent  = this.$parent;
  while (parent){
    parent.$emit(eventName,data){
      parent.$emit(eventName,data);
      parent = parent.$parent;
    }
  }
}
$broadcast 向下派发
Vue.prototype.$broadcast = function $broadcast(eventName, data){
  const broadcast  = function () {
    this.$children.forEach((child)=>{
      child.$emit(eventName, data);

      if(child.$children){
        $broadcast.call(child,eventName,data);
      }
    })
  }
  broadcast.call(this,eventName,data);
}

四、$attrs、 $listeners
$attrs批量向下传入属性
<Son2 name="小明" age="18"></Son2>
<--可以在son2组件中使用$attrs,可以将属性继续向下传递-->
<div>
  儿子2:{{  $attrs.name }}
  <Grandson2  v-bind="$attrs"></Grandson2>
</div>
<tempalte>
  <div>孙子:{{$attrs}}</div>
</template>

$listeners批量向下传入方法
<Son2 name="小明" age="18" @click=“()=>{this.money  =500}”></Son2>

<--可以在son2组件中使用$attrs,可以将属性继续向下传递-->

<Grandson2  v-bind="$attrs" v-on="$listeners"></Grandson2>

<button @click="$listeners.click()">更改<Son1>

五、Provide&Inject

Provide 在父级中注入数据
provide(){

  return {parentMsg:'父亲'};

}
Inject
在任意子组件中可以注入父级数据
inject:['parentMsg']//会将数据挂载在当前实例上

六 ref使用
获取组件实例
<Grandson2  name="花花" ref="grand2"></Grandson2>

mounted(){
  console.log(this.$refs.grand2.name);
}

七 EventBus

用于跨组件通知(简单项目)

Vue.prototype.$bus = new Vue();
Son2组件和Grandson1互相通信
mounted() {
  //父亲组件注册
  this.$bus.$on('my',data=>{

    console.log(data)
  })
}

mounted(){
  //侄子组件调用

  this.$nextTick(()=>{

    this.$bus.$emit('my',"我是小红”);
  })

}

八 vuex状态管理

posted @ 2019-08-14 13:17  徐念念  阅读(483)  评论(0编辑  收藏  举报