vue自定义组件实现双向绑定


Posted in Vue.js onJanuary 13, 2021

场景:

我们比较常用的父子组件之间的交互方式:
父组件通过props将数据流入到子组件;
子组件通过$emit将更新后的数组发送的父组件;

今天,我们通过另一种方式实现交互,参考input框的v-model,实现自定义组件的双向数据绑定。
即:父组件值改变,子组件的值跟着改变;反之,子组件值发生变化,父组件值随之变化

子组件定义:

由于不能直接修改props属性值,我们这里定义valueData,通过监听实时接收value值,通过click方法修改valueData。
这里注意model语法糖prop 是接收的props属性value,保持一致。event是先上传递的事件名。

代码如下:

<template>
  <div>
    <div>{{ `子组件值: ${value}` }}</div>
    <div @click="click">点击此处修改值</div>
  </div>
</template>

<script>
export default {
  name: "",
  model: {
    prop: "value",
    event: "change"
  },
  props: {
    value: Number
  },
  components: {},
  data() {
    return {
      valueData: ""
    };
  },
  watch: {
    value(newValue, oldValue) {
      this.valueData = newValue;
      console.log(`子组件值:${newValue}`);
    }
  },
  created() {
  },
  mounted() {
  },
  methods: {
    click() {
      this.valueData++;
      this.$emit("change", this.valueData);
    }
  }
};
</script>
<style lang='less' scoped>
</style>

父组件定义:

父组件通过v-model绑定text值,名称不一定是value,可以是其他任意符合命名规范的字符串,这里是text。
子组件通过change事件更新数据后,v-mode绑定值随之变化。
或者父组件修改text值后,子组件value值随之变化。

代码如下:

<template>
  <div>
    <div>{{ `父组件值:${text}` }}</div>
    <div @click="click">点击此处修改值</div>


    <span>-----------------------------------------------------------</span>

    <test-children v-model="text"></test-children>

  </div>
</template>

<script>
import TestChildren from "@/views/TestChildren";

export default {
  name: "",
  components: { TestChildren },
  data() {
    return {
      text: 1
    };
  },
  created() {
  },
  mounted() {
  },
  watch: {
    text(newValue, oldValue) {
      console.log(`父组件值:${newValue}`);
    }
  },
  methods: {
    click() {
      this.text--;

    }
  }
};
</script>
<style lang='less' scoped>
</style>

结果:

直接copy代码到自己项目测试。无论是通过父组件改变值,还是子组件改变值。两个组件通过v-mode绑定的值始终保持一致。

答疑:

有同学就问了 ,这不是和通过props向下流入数据,再通过$emit方式向上传递数据一样么也能实现我这种双向绑定的效果。 其实不然,如果不通过v-model,那么我们势必会在父组件写这样的代码:

<test-children @change="changeText"></test-children>

然后在通过定义changeText方法修改text值。

试想,当我们的页面比较复杂,引用组件量比较庞大,页面中就需要多定义这样十几、二十几个方法。可阅读行大大降低,增加了维护成本。

扩展:

vue2.3之后提供了sync方式,也能实现双向绑定

父组件中的写法:

<test-children :value.sync="text"></test-children>

子组件中不需要使用下面model定义,直接删除即可。

model: {
prop: “value”,
event: “change”
},

向父组件传递数据使用如下方式:

this.$emit("update:value", this.valueData);

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Vue.js 相关文章推荐
vue打开其他项目页面并传入数据详解
Nov 25 Vue.js
vue实现表格合并功能
Dec 01 Vue.js
Vue.js桌面端自定义滚动条组件之美化滚动条VScroll
Dec 01 Vue.js
vue使用require.context实现动态注册路由
Dec 25 Vue.js
Vue 简单实现前端权限控制的示例
Dec 25 Vue.js
详解实现vue的数据响应式原理
Jan 20 Vue.js
Vue使用Ref跨层级获取组件的步骤
Jan 25 Vue.js
Vue 数据响应式相关总结
Jan 28 Vue.js
Vue基本指令实例图文讲解
Feb 25 Vue.js
vue+django实现下载文件的示例
Mar 24 Vue.js
vue特效之翻牌动画
Apr 20 Vue.js
Vue页面渲染中key的应用实例教程
Jan 12 #Vue.js
Vue项目中使用mock.js的完整步骤
Jan 12 #Vue.js
vue 页面跳转的实现方式
Jan 12 #Vue.js
Vue过滤器,生命周期函数和vue-resource简单介绍
Jan 12 #Vue.js
详解template标签用法(含vue中的用法总结)
Jan 12 #Vue.js
Vue中ref和$refs的介绍以及使用方法示例
Jan 11 #Vue.js
vue实现防抖的实例代码
Jan 11 #Vue.js
You might like
PHPCMS手机站伪静态设置详细教程
2017/02/06 PHP
PHPExcel实现表格导出功能示例【带有多个工作sheet】
2018/06/13 PHP
ThinkPHP中图片按比例切割的代码实例
2019/03/08 PHP
innerHTML 和 getElementsByName 在IE下面的bug 的解决
2010/04/09 Javascript
jquery操作select大全
2014/04/25 Javascript
js判断是否按下了Shift键的方法
2015/01/27 Javascript
JavaScript获取网页表单提交方式的方法
2015/04/02 Javascript
深入浅出分析javaScript中this用法
2015/05/09 Javascript
JS+CSS实现大气清新的滑动菜单效果代码
2015/10/22 Javascript
如何实现JavaScript动态加载CSS和JS文件
2020/12/28 Javascript
jQuery语法小结(超实用)
2015/12/31 Javascript
angularjs使用directive实现分页组件的示例
2017/02/07 Javascript
详解webpack+es6+angular1.x项目构建
2017/05/02 Javascript
Vue组件选项props实例详解
2017/08/18 Javascript
新手快速上手webpack4打包工具的使用详解
2019/01/28 Javascript
详解关于Vuex的action传入多个参数的问题
2019/02/22 Javascript
浅谈Vue.js组件(二)
2019/04/09 Javascript
vue elementUI 表单校验功能之数组多层嵌套
2019/06/04 Javascript
原生js实现轮播图特效
2020/05/04 Javascript
python中sys.argv函数精简概括
2018/07/08 Python
python 将有序数组转换为二叉树的方法
2019/03/26 Python
Python 实现将大图切片成小图,将小图组合成大图的例子
2020/03/14 Python
Python性能分析工具py-spy原理用法解析
2020/07/27 Python
Python实现七个基本算法的实例代码
2020/10/08 Python
用Python 执行cmd命令
2020/12/18 Python
利用python为PostgreSQL的表自动添加分区
2021/01/18 Python
澳大利亚电子产品购物网站:Dick Smith
2017/02/02 全球购物
what is the difference between ext2 and ext3
2013/11/03 面试题
写好自荐信的要点
2013/11/06 职场文书
《童年》教学反思
2014/02/18 职场文书
成立公司计划书
2014/05/07 职场文书
食品安全处置方案
2014/06/14 职场文书
2019优秀干部竞聘演讲稿范文!
2019/07/02 职场文书
学会掌握自己命运的十条黄金法则:
2019/08/08 职场文书
手把手教你实现PyTorch的MNIST数据集
2021/06/28 Python
nginx刷新页面出现404解决方案(亲测有效)
2022/03/18 Servers