1.父子组件间的数据传递

1.1从父组件获取子组件的数据

1.1.1通过绑定 props 将父组件的数据关联到子组件,并修饰 .sync 或者用 v-model 同步来自子组件的数据变化

//使用.sync ://父组件<template>  <div class="home">   <my-dialog :show.sync="valueChild"/>   <button @click="changeValue">toggle</button>  </div></template><script>import myDialog from '@/components/myDialog.vue'export default {  name: 'home',  components: {    myDialog  },  data(){    return{       valueChild:true,    }  },   methods:{      changeValue(){          this.valueChild = !this.valueChild      }    }}</script>//子组件<template>  <div>    <div>myDialog</div>    <div v-if="show">      <p>默认初始值是{{show}},所以是显示的</p>      <button @click.stop="closeDiv">关闭</button>    </div>  </div></template><script>export default {  props:['show'],  methods:{    closeDiv(){      this.$emit('update:show',false)    }  }}</script>
// v-model ://父组件:<template>  <div class="home">    <myDialog v-model="show"></myDialog>    <button @click="toggle">Toggle</button>  </div></template><script>  import myDialog from '@/components/myDialog.vue'  export default {    name: 'home',    components: {      myDialog    },    data() {      return {        show: false      }    },    methods: {      toggle() {        this.show = !this.show      }    }  }</script>//子组件:<template>  <div>    <div v-if="value" class="modal">      {{value}}      <button @click="close">x</button>    </div>  </div></template><script>  export default {    props: ['value'],    methods: {      close() {        this.$emit('input', false)      }    }  }</script>

1.1.2绑定 listener 事件监听器,当子组件状态或者数据发生变化时,触发事件并将数据传递到父组件

$listeners 和 $attrs 两者表面层都是一个意思,$attrs 是向下传递数据,$listeners 是向下传递方法,通过手动去调用 $listeners 对象里的方法,原理就是 $emit 监听事件,$listeners 也可以看成一个包裹监听事件的一个对象。
// 父组件:<template>  <div class="home">    {{firstMsg}}    <myDialog v-on:changeData="changeData" v-on:another='another'></myDialog>  </div></template><script>  import myDialog from '@/components/myDialog.vue'  export default {    name: 'home',    components: {      myDialog    },    data() {      return {        firstMsg: '父组件'      }    },    methods: {      changeData(params) {        this.firstMsg = params      },      another() {        alert(2)      }    }  }</script>//子组件:<template>  <div>    <p @click="$emit('another')">子组件</p>    <other v-on="$listeners"/>  </div></template><script>  import other from '@/components/other.vue'  export default {    props: ['value'],    components:{      other    },    created () {     // eslint-disable-next-line no-console     console.log(this.$listeners)   }  }</script>//孙子组件:<template>  <div>    <p @click='$listeners.changeData("change")'>孙子组件</p>  </div></template><script>export default {  name: 'demo',  created () {      // eslint-disable-next-line no-console      console.log(this.$listeners)  },}</script>

1.2从子组件获取父组件的数据

1.2.1 获取 props 或者 $attrs 传下来的数据

//父组件:<template>  <div class="home">    <myDialog :foo="foo" :boo="boo" :coo="coo" :doo="doo" title="前端工匠"></myDialog>  </div></template><script>  import myDialog from '@/components/myDialog.vue'  export default {    name: 'home',    components: {      myDialog    },    data() {      return {        foo: "Javascript",        boo: "Html",        coo: "CSS",        doo: "Vue"      }    },    methods: {      changeData(params) {        this.firstMsg = params      },      another() {        alert(2)      }    }  }</script>//子组件:<template>  <div>    <p>foo:{{foo}}</p>    <p>子组件的$attrs: {{ $attrs }}</p>    <other v-bind="$attrs" />  </div></template><script>  import other from '@/components/other.vue'  export default {    components: {      other    },    inheritAttrs: false, // 可以关闭自动挂载到组件根元素上的没有在props声明的属性    props: {      foo: String // foo作为props属性绑定    },    created() {      // eslint-disable-next-line no-console      console.log(this.$attrs);    }  }</script>//孙子组件:<template>  <div>    <p>boo: {{ boo }}</p>    <p>孙子:{{$attrs}}</p>  </div></template><script>  export default {    name: 'demo',    inheritAttrs: false,    props: {      boo: String    },    created() {      // eslint-disable-next-line no-console      console.log(this.$attrs);    },  }</script>

2.兄弟组件间的数据传递

处于兄弟关系的组件

2.1通过 EventBus 或者 $root 去注册事件,由兄弟组件去监听事件传递过来的数据变化

2.2 在 Vuex 存放状态,并在两个组件中都监听状态变化
2.3 在父组件上绑定状态,并通过 v-model 或者 .sync 绑定到两个兄弟组件中去,以同步数据变化

3.祖孙组件间的数据传递

3.1孙组件被直接写在了祖先组件的 template 内

在 Vue 中,处于祖孙关系的组件,而且孙组件被直接写在了祖先组件的 template 内,要从祖先组件获取孙组件的数据,有以下几种方式:

3.1.1可以在模板上给孙组件绑定 ref 并通过 $refs 调用孙组件的方法获取数据

//父组件<template>  <div class="home">    {{title}}    {{text}}    <myDialog ref="comA"></myDialog>  </div></template><script>  import myDialog from '@/components/myDialog.vue'  export default {    name: 'home',    components: {      myDialog    },    data() {      return {        title:'',        text:''      }    },    computed: {    },    mounted() {      const comA = this.$refs.comA;      // console.log(comA.title); // Vue.js      this.title = comA.title      this.text = comA.text      comA.sayHello(); // 弹窗    },    methods: {}  }</script>//子组件:<template>  <div>    <div v-if="show">sayHello</div>    <other ref="comB" />  </div></template><script>  import other from '@/components/other.vue'  export default {    components: {      other    },    data() {      return {        title: 'Vue.js',        show: false,        text:''      }    },    created() {    },    mounted() {      const comB = this.$refs.comB;      this.text = comB.text    },    methods: {      sayHello() {        this.show = true        // window.alert('Hello');      }    }  }</script>//孙子组件:<template>  <div>  </div></template><script>  export default {    name: 'demo',    data(){      return{        text:'c'      }    },    created() {    },  }</script>

3.1.2 可以在模板上给孙组件绑定 listener 获取孙组件传过来的数据
3.1.3 可以在模板上给孙组件绑定 v-model 或者 .sync 同步孙组件的数据

3.2孙组件不在祖先组件的 template 内,要从祖先组件获取孙组件的数据

3.2.1先在子组件上绑定 v-model 或者 .sync,接着再在子组件的模板上通过 v-model 或者 .sync 绑定孙组件,以同步孙组件的数据
3.2.2现在孙组件上绑定 listener,再给子组件绑定 listener,数据由事件层层上传给祖先组件

3.3孙组件在祖先组件的 template 内,要从孙组件获取祖先组件的数据

3.3.1直接在祖先组件的 template 中通过 v-bind 将数据传递到孙组件中,孙组件通过 props 或者 $attrs 进行接收

3.4孙组件不在祖先组件的 template 内,要从孙组件获取祖先组件的数据

3.4.1先在子组件上 v-bind 绑定数据,接着再在子组件上通过 v-bind 绑定孙组件,数据层层向下传递
3.4.2孙组件在 EventBus 中注册事件,监听来自祖先组件触发的事件数据
3.4.3祖先组件将数据挂到 Vuex 中,再由孙组件从 Vuex 中去获取数据