Vue组件通信的方式【面试题】

1,191 阅读1分钟

Vue组件通信的方式【面试题】

1、Props+$emit

父子间通信:父亲提供数据通过属性 props传给儿子;儿子通过 $on 绑父亲的事件,再通过 $emit 触发自己的事件(发布订阅)。

父组件:

    <template>
      <div class="navbar">
        <Child :msg="msg" @changeMsg="msg = $event"></Child>
      </div>
    </template>

    <script>
    import Child from "./Child.vue";

    export default {
      name: "Father",
      components: { Child },
      data() {
        return {
          msg: "hello son",
        };
      },
    };
    </script>

子组件:

    <template>
      <div class="">
       {{msg}}
       <button @click="changeMsg"></button>
      </div>
    </template>

    <script>

    export default {
      props: ["msg"],
      name: "Child",
      data() {
        return {
        };
      },
      methods:{
        changeMsg(){
          this.$$emit('changeMsg','hello father')
        }
      }
    };
    </script>

2、回调函数

回调函数的用法其实和上一种差不多。

父组件:

    <template>
      <div class="">
       <Child :msg="msg" :changeFn="changeMsg"></Child>
      </div>
    </template>

    <script>
    import Child from './Child.vue'
    export default {
      name: "Father",
      components:{Child},
      data() {
        return {
          msg:'hello child'
        };
      },
      methods:{
        changeMsg(){
          this.msg="hello father"
        }
      }
    };
    </script>

子组件:

    <template>
      <div class="">
      {{msg}}
      <button @click="changeFn"></button>
      </div>
    </template>

    <script>
    export default {
      name: "Child",
      props:['msg','changeFN'],
      data() {
        return {
        };
      }
    };
    </script>

3、利用父子关系$parent$children

父组件:

    this.$childfren[0]['子组件的属性或者方法'] // 一个父组件中可能会引入多个子组件,固this.$childfren[0]标识第一个子组件

子组件:

    this.$parent['父组件的属性活方法']

4、使用 provide + inject

父组件提供数据,子组件注入。 ·provide· 、 ·inject· ,插件用得多。

在父组件中提供数据(provide):

    <template>
      <div class=""></div>
    </template>

    <script>
    export default {
      name: "Father",
      provide: { msg: "hello son" },
      data() {
        return {};
      },
    };
    </script>

在子组件中注入消费:

    <template>
      <div class="">
        {{ msg }}
      </div>
    </template>

    <script>
    import Child from './Child.vue'
    export default {
      name: "Child",
      inject: ["msg"],
      data() {
        return {};
      },
    };
    </script>

5、使用 $listeners

$listeners属性:包含了组件的所有监听器。可直接绑定在组件子元素.

场景:父亲->儿子->孙子

父组件:

    <template>
      <div class="">
        <Child :msg="msg"></Child>
      </div>
    </template>

    <script>
    import Child from "./Child.vue";
    export default {
      name: "Father",
      components: { Child },
      data() {
        return {
          msg: "",
        };
      },
    };
    </script>

子组件:

    <template>
      <div class="">
        <!-- 直接使用 listeners 访问父组件的属性 -->
        {{$listeners.msg}}
        <GrandChild v-bind="$attrs"></GrandChild>
      </div>
    </template>

    <script>
    import GrandChild from "./GrandChild.vue";
    export default {
      name: "Child",
      components: { GrandChild },
      data() {
        return {};
      },
    };
    </script>

孙组件:

    <template>
      <div class="">
        {{ $attrs.msg }}
      </div>
    </template>
    <script>
    export default {
      name: "GrandCHild",
      data() {
        return {};
      },
    };
    </script>

6、ref 获取组件实例,调用组件的属性、方法

ref 获取组件实例,调用组件的属性、方法

父组件:

    <template>
      <div class="">
        <Child :ref="childComponent"></Child>
      </div>
    </template>
    <script>
    import Child from "./Child.vue";
    export default {
      name: "Father",
      components: { Child },
      data() {
        return {};
      },
      created() {
        this.$$ref.childComponent.showMeLook();
        this.$ref.childComponent.msgs; // 通过注册的子组件示例访问子组件的方法或者属性
      },
    };
    </script>

子组件:

    <template>
     <div class=""></div>
   </template>
   <script>
   export default {
     name: "Child",
     data() {
       return {
         msgs: "i am son",
       };
     },
     methods: {
       showMeLook() {
        this.msgs = "alert('我是儿')";
       },
     },
   };
   </script>

7、vuex 状态管理实现通信和跨组件通信 Event Bus

  1. vuex 状态管理实现通信
  2. Vue.prototype.bus = new Vue其实基于on与$emit