Vue 组件多级继承、继承全部属性
核心方法在B组件中添加v-bind="$attrs"和 v-on="$listeners"两个属性即可`A 组件中:<B v-bind="$attrs" v-on="$listeners></B>这样在A中就能使用B的属性和绑定的方法了如果想详细理解,请继续阅读一、关于组件之间的通信组件之间相互传递数据、方法,就可以理解为组件之间的通信。比如A组件传一个对象给B组件,这就是
核心方法
在B组件中添加v-bind="$attrs" 和 v-on="$listeners"两个属性即可`
A 组件中:
<B v-bind="$attrs" v-on="$listeners>
</B>
这样在A中就能使用B的属性和绑定的方法了
如果想详细理解,请继续阅读
一、关于组件之间的通信
组件之间相互传递数据、方法,就可以理解为组件之间的通信。比如A组件传一个对象给B组件,这就是通信。
二、组件之间通信的常见方式
使用props或vuex可以实现。具体实现可参考:
但他们各有缺陷:
- 如果仅仅使用vuex,来实现组件通信,则就有点杀鸡用牛刀了。
 - 使用props, 在多级包含关系的组件之间传递又太麻烦。
 
三、如何简单的实现组件多级传递属性和方法
使用v-bind="$attrs" 和 v-on="$listeners"。看下面这个例子
现在有一下三个组件:
grandfather组件:
<template>
  <section>
    <father
      name="name"
      age="18"
      gender="666"
      sdf="asd"
      @isClick="isClick"
      @asd="asd"
    ></father>
  </section>
</template>
<script>
  import father from '~/components/father';
  export default {
    components: {
      father
    },
    methods: {
      asd() {
        console.log('gr', 999);
      },
      isClick() {
        console.log('gr', 666);
      }
    }
  };
</script>
这个组件内部包含了一个father组件,并为father组件传递了四个参数和2个方法。
father组件
<template>
  <section>
    <div class="mt-10">
      <son v-bind="$attrs" v-on="$listeners" />
    </div>
  </section>
</template>
<script>
  import son from '~/components/son';
  export default {
    components: {
      son
    },
    props: {
      name: {
        type: String,
        default: 'default'
      },
      age: {
        type: String,
        default: 'default'
      }
    }
  };
</script>
在father组件中,只递归一了两个入参:name和age。使用了v-bind=“attrs"属性,该属性包含了父作用域中不作为prop被识别(且获取)的特性绑定(class和style除外)。未识别的事件通过‘v−on="attrs" 属性,该属性包含了父作用域中不作为 prop 被识别 (且获取) 的特性绑定 (class 和 style 除外)。未识别的事件通过`v-on="attrs"属性,该属性包含了父作用域中不作为prop被识别(且获取)的特性绑定(class和style除外)。未识别的事件通过‘v−on="listeners”`传入
son组件
<template>
  <section>
    <div>
      {{ $attrs['gender'] }}  在$attrs里面只会有props没有注册的属性
      <br>
      {{ gender }}
    </div>
  </section>
</template>
<script>
  export default {
    props: {
      gender: {
        type: String,
        default: ''
      }
    },
    mounted() {
      console.log('son', this.$attrs);
      console.log('son', this.$listeners);
      this.$listeners.isClick();
      this.$listeners.asd();
    }
  };
</script>
结果
加载爷爷组件grandfather,运行结果如下:
son {sdf: 'asd'}
son {asd: function, isClick: function}
gr 666
gr 999 
页面上显示:
在$attrs里面只会有props没有注册的属性
666 
从结果分析:
1.在儿子组件中,console.log(‘son’, this.$attrs);的结果为什么是 {sdf: ‘asd’}
在爸爸节点中调用儿子组件时,使用了v-bind="attrs"。在儿子节点中的vm.attrs"。在儿子节点中的vm.attrs"。在儿子节点中的vm.attrs只会包含父节点中没有绑定的属性。爷爷那里传过来了name, age, gender, sdf。其中name age在爸爸那里已经定义了,gender在儿子的props里也定义了。所以只有sdf没有定义,结果中就只有sdf属性了
2.在儿子组件中,console.log(‘son’, this.$listeners);的结果为什么是son {asd: function, isClick: function}
通过listeners传递了爷爷中的方法到孙子组件,但是在孙子组件中,不能直接使用该方法,哪怕将同名方法暴露在孙子的props中,在孙子组件里也不能使用爷爷传过来的方法。可以通过vm.listeners传递了爷爷中的方法到孙子组件,但是在孙子组件中,不能直接使用该方法,哪怕将同名方法暴露在孙子的props中,在孙子组件里也不能使用爷爷传过来的方法。可以通过vm.listeners传递了爷爷中的方法到孙子组件,但是在孙子组件中,不能直接使用该方法,哪怕将同名方法暴露在孙子的props中,在孙子组件里也不能使用爷爷传过来的方法。可以通过vm.listeners.方法名() 的方式来使用爷爷传递的方法
4.如何理解页面上显示的666
子组件中的gender属性是props中的属性,在爷爷组件中传入了gender的值是666。所以,通过$atter可以直接在爷爷组件传递数据给孙子组件
更多推荐
 


所有评论(0)