Vue组件之间的传参方式小总结

news/2024/7/11 0:43:48 标签: vue.js, es6

学习vue的组件,可能很多人已经了解了组件的创建注册使用,但是随之而来的就是组件之间的通信,父子组件怎么传? 兄弟组件怎么传? 不是父子组件又怎么传?

接下来介绍几种组件之间的传参方式,也是很容易面试被问到的.

1.父传子用props

父组件传递参数给子组件的时候,可以使用props这个属性

 <div id="app">
    <cpn :cmsg="msg"></cpn>
  </div>
  <template id="cpn">
    <div>
      {{cmsg}}
    </div>
  </template>
  <script src="../vue.js"></script>
  <script>
    var cpn = {
      template:'#cpn',

      // props:['cmsg']  props的格式有数组形式和对象形式
      props:{
        cmsg:{
          type:String,
          default:'1000'
        }
      },
      // 如果是类型是Array/Object deafult必须是一个函数dafault(){} 例如 ↓
      // props:{
      //   list:{
      //     type:Array,
      //     default() {
      //       return []
      //     }
      //   }
      // }
    }
    var app = new Vue({
      el:'#app',
      data: {
        msg:'我是父组件的消息'
      },
      components:{
        cpn
      }
    })
  </script>

在这里插入图片描述
运行结果在这里插入图片描述

2.子传父用$emit

emit是发射的意思,也就是,子组件需要向父组件传递数据使用emit来发射一个自定义事件,在子组件上绑定该自定义事件,同时在父组件上有个对应的事件进行双向绑定事件,直接上代码.

 <div id="app">
    {{aaa}}
    <cpn @itemfun='parentEvent'></cpn>
  </div>

  <template id="cpn">
    <div>
      <!-- 这里就需要绑定一个事件 -->
      <button @click="btnClick">点击按钮发送自己的消息给俺爸爸</button>
    </div>
  </template>
  <script src="../vue.js"></script>
  <script>
    var cpn = {
      template:'#cpn',
      data() {
        return{
          aa:'我是子组件上的信息'
        }
      },
      methods: {
        btnClick(){          
          this.$emit('itemfun',this.aa)
        }
      },
    }
    var app = new Vue({//根组件,也相当于是父组件
      el:'#app',
      data: {
        aaa:'我将要被替换'
      },
      methods: {
        parentEvent(val) {
          console.log(val);
          this.aaa = val
        }
      },
      components:{
        cpn
      }
    })
  </script>

在这里插入图片描述
运行结果:
在这里插入图片描述

3.子访问父相互传使用 $refs

这是一重灰常人性化的 传参方式,其实也就是拿参数的一种简便方式 ,ref属性被用来给元素或者组件注册引用信息,引用信息会注册在父组件的$ref对象上(如果ref放在对象上,拿到的是原生节点,ref放在组件上,拿到的就是组件实例),我们先来看一下代码
我已经注册了两个组件,并且在vue根组件上使用,绑定了ref
在这里插入图片描述

我们可以去vue实例里面的生命周期函数mounted里面打印一下这个 this.$fefs ,看看能打印出什么信息.

	mounted() {
        console.log(this.$refs)
    },

可以看大在控制台打印出了两个子组件实例,而且是一数组的方式存储,相当于ref='键名’
取出来的话使用this.$refs.aaa 这样就可以拿到这个组件实例
在这里插入图片描述
通过对象引用的方式就可以拿到不同组件实例上的不同参数和方法
在这里插入图片描述
这里子不能访问父.↓
在这里插入图片描述
在这里插入图片描述

4.父子相互访问 $parent / $root / $children

顾明思议,this.$parent 拿到的就是当前实例组件的父组件,记住是父组件,不是父组件之上的组件,他爸爸的爸爸已经是爷爷了,不是父亲了.而 this. $root 拿到的是根组件,也就是var app = new Vue({})这个根组件实例.

查看$parent的内容
在这里插入图片描述
一起打印看看
在这里插入图片描述

5. 非父子组件(兄弟)组件之间的通信,EventBus,事件总线.

在vue中 是通过单独的事件中心来管理非父子组件,也就是兄弟组件之间的通信
在这里插入图片描述

1.建立事件中心

var EventBus = new Vue()

2.使用事件中心发射自定义事件

eventBus.$emit('自定义事件名',传递的数据)

3.使用事件中心接受数据

eventBus.$on('自定义事件名',[,callback])

下面看示例图
在这里插入图片描述

5. provide 和 inject 跨级传参

这两个参数是一起起作用的,允许一个祖先组件向起所有子孙后代注入一个依赖,不管组件层次有多深,都能建立起关系
provide:是一个对象,返回对象的一个函数,里面包含要给子孙属性的东西,也就是属性和属性值
inject: 一个字符串数组,或者是一个对象,属性值可以是一个对象,包含from和default默认值
from表示在可用的注入内容中收缩用的key,default当然也是默认值

6. 作用域插槽

我們先來想一个需求,假如子组件中有一组数据,但是想以不同的形式展示在父组件中,处理使用$emit等传参方式,也可以使用作用域插槽.

在这里插入图片描述
代码附上:

<div id="app"> 
  <!-- 假如第一个组件里我们想以列表的形式展示 -->
    <cpn v-slot='aa'>
      <slot><ul v-for='item in aa.data'><li>{{item}}</li></ul></slot>
    </cpn>
     <!-- 假如第二个组件里我们想以' - ' 的方式来连接book数组里面的内容 -->
    <cpn v-slot='bb'>
      <span>{{bb.data.join('-')}}</span>
    </cpn>

  </div>
  <template id="cpn">
    <div>
    <span>
    <!-- 这里相当于给book起个别名叫做data -->
      <slot :data='book'></slot>
    </span>
    </div>
  </template>
  <script src="../vue.js"></script>
  <script>

    var cpn = {
      template:'#cpn',
      data() {
        return {
          book:['飞鸽传书','天山雪莲','鲨鱼','翻身']
        }
      }
    }   

    var app = new Vue({
      el:'#app',
      data: {
        
      },
      components:{
        cpn
      }
    })
  </script>

7.非父子组件又不同层次之间的 组件间的传值.

provide/inject:简单的来说就是在父组件中通过provider来提供变量,然后在子组件中通过inject来注入变量。
需要注意的是这里不论子组件有多深,只要调用了inject那么就可以注入provider中的数据。而不是局限于只能从当前父组件的prop属性来获取数据

//父组件
<template>
  <div>
<childOne></childOne>
  </div>
</template>

<script>
  import childOne from '../components/test/ChildOne'
  export default {
    name: "Parent",
    provide: {
      for: "demo"
    },
    components:{
      childOne
    }
  }

子组件一

<template>
  <div>
    {{demo}}
    <childtwo></childtwo>
  </div>
</template>

<script>
  import childtwo from './ChildTwo'
  export default {
    name: "childOne",
    inject: ['for'],
    data() {
      return {
        demo: this.for
      }
    },
    components: {
      childtwo
    }
  }
</script>

子组件二

<template>
  <div>
    {{demo}}
  </div>
</template>

<script>
  export default {
    name: "",
    inject: ['for'],
    data() {
      return {
        demo: this.for
      }
    }
  }
</script>

运行结果:
在这里插入图片描述
最后一个传参的代码是搬运的,也是很清晰明了.

这是一篇拖更了好久的文章,两三个星期前就差点写好了,忙活忙活就忘记补全发出去了,害…

各自努力,顶峰相见.加油


http://www.niftyadmin.cn/n/1496794.html

相关文章

如何评估网页的链接流行度

< DOCTYPE html PUBLIC -WCDTD XHTML TransitionalEN httpwwwworgTRxhtmlDTDxhtml-transitionaldtd> 可以说搜索引擎算法离不开链接&#xff0c;那么链接在搜索引擎中也是必不可少的因素之一&#xff0c;至今到未来链接算法会越来越复杂。搜索引擎对网页的链接的评估有四…

python xml练习:从database.xml文件取databaselist的ip、name、passwd,写入列表

xml&#xff1a; <?xml version1.1 encodingutf-8?><!--this is a test about xml--><databaselist typeoracle> <database userAreasuzhou> <ip>10.192.128.88</ip> <name>xiasam</name> <pass…

用Javascript实现菜单折叠效果

在网上看了好多用Javascript实现菜单折叠的例子都特别的麻烦&#xff0c;于是自己写了一个虽然效果不如网上的强但是也可以实现了相应的功能&#xff1a; functiondisplay(num) { if(menu_left[num].style.display"none") { for(a0;a<menu_left.length;a…

最新面试题整理

js原生 map和foreach的区别 ** 2.2.1、forEach()返回值是undefined&#xff0c;不可以链式调用。   2.2.2、map()返回一个新数组&#xff0c;原数组不会改变。   2.2.3、没有办法终止或者跳出forEach()循环&#xff0c;除非抛出异常&#xff0c;所以想执行一个数组是否满…

data (phantonjs onclick)exploring cleaning

elem driver.find_element_by_id(kw)elem.send_keys(uphp) 相当于在模拟浏览器在百度的首页搜索框中填入了php driver.find_element_by_id(su).click() 相当于点击了百度页面上的‘百度一下’按钮 获取的源码即输入php再点击百度一下后的源码。 此刻在浏览器中输入&#xff…

Database Buffer Cache(2)

The process of retrieve database buffer cache。 referer the book of advanced owi the vsdx file in https://pan.baidu.com/s/1pbUWESPL0FyqFDJhDkf2Lg password:jnqp转载于:https://www.cnblogs.com/dayu-liu/p/8850179.html

React-redux中一些插件/工具件的使用方法

本文主要做个记录,我们在使用redux中需要用的一些插件/工具/中间间,是怎么导入以及使其生效的。 先 看我的演示的目录结构&#xff0c;不记得就回头看 1.多个reducer的合并 reducers的index.js文件 import cartreducer from "./cartreducer"; import homereduc…