Vue 实现双向绑定的四种方法


Posted in Javascript onMarch 16, 2018

1. v-model 指令

<input v-model="text" />

上例不过是一个语法糖,展开来是:

<input
 :value="text"
 @input="e => text = e.target.value"
/>

2. .sync 修饰符

<my-dialog :visible.sync="dialogVisible" />

这也是一个语法糖,剥开来是:

<my-dialog
 :visible="dialogVisible"
 @update:visible="newVisible => dialogVisible = newVisible"
/>

my-dialog 组件在 visible 变化时 this.$emit('update:visible', newVisible) 即可。

3. model 属性 (JSX/渲染函数中)

Vue 在 2.2.0 版本以后,允许自定义组件的 v-model ,这就导致在 JSX / 渲染函数中实现 v-model 时得考虑组件的不同配置,不能一律如此(假使 my-dialog 组件的 model 为 { prop: 'visible', event: 'change' } ):

{
 render(h) {
  return h('my-dialog', {
   props: { value: this.dialogVisible },
   on: { input: newVisible => this.dialogVisible = newVisible }
  })
 }
}

而应如此:

{
 render(h) {
  return h('my-dialog', {
   props: { visible: this.dialogVisible },
   on: { change: newVisible => this.dialogVisible = newVisible }
  })
 }
}

然而,利用 model 属性,完全可以做到不用管它 prop 、 event 的目的:

{
 render(h) {
  return h('my-dialog', {
   model: {
    value: this.dialogVisible,
    callback: newVisible => this.dialogVisible = newVisible
   }
  })
 }
}

JSX 中这样使用:

{
 render() {
  return (
   <my-dialog
    {...{
     model: {
      value: this.dialogVisible,
      callback: newVisible => this.dialogVisible = newVisible
     }
    }}
   />
  )
 }
}

4. vue-better-sync 插件

有需求如此:开发一个 Prompt 组件,要求同步用户的输入,点击按钮可关闭弹窗。

Vue 实现双向绑定的四种方法

一般我们会这样做:

<template>
 <div v-show="_visible">
  <div>完善个人信息</div>
  <div>
   <div>尊姓大名?</div>
   <input v-model="_answer" />
  </div>
  <div>
   <button @click="_visible = !_visible">确认</button>
   <button @click="_visible = !_visible">取消</button>
  </div>
 </div>
</template>
<script>
export default {
 name: 'prompt',
 props: {
  answer: String,
  visible: Boolean
 },
 computed: {
  _answer: {
   get() {
    return this.answer
   },
   set(value) {
    this.$emit('input', value)
   }
  },
  _visible: {
   get() {
    return this.visible
   },
   set(value) {
    this.$emit('update:visible', value)
   }
  }
 }
}
</script>

写一两个组件还好,组件规模一旦扩大,写双向绑定真能写出毛病来。于是,为了解放生产力,有了 vue-better-sync 这个轮子,且看用它如何改造我们的 Prompt 组件:

<template>
 <div v-show="actualVisible">
  <div>完善个人信息</div>
  <div>
   <div>尊姓大名?</div>
   <input v-model="actualAnswer" />
  </div>
  <div>
   <button @click="syncVisible(!actualVisible)">确认</button>
   <button @click="syncVisible(!actualVisible)">取消</button>
  </div>
 </div>
</template>
<script>
import VueBetterSync from 'vue-better-sync'
export default {
 name: 'prompt',
 mixins: [
  VueBetterSync({
   prop: 'answer', // 设置 v-model 的 prop
   event: 'input' // 设置 v-model 的 event
  })
 ],
 props: {
  answer: String,
  visible: {
   type: Boolean,
   sync: true // visible 属性可用 .sync 双向绑定
  }
 }
}
</script>

vue-better-sync 统一了 v-model 和 .sync 传递数据的方式,你只需 this.actual${PropName} = newValue 或者 this.sync${PropName}(newValue) 即可将新数据传递给父组件。

GitHub: fjc0k/vue-better-sync

总结

以上所述是小编给大家介绍的Vue 实现双向绑定的四种方法,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对三水点靠木网站的支持!

Javascript 相关文章推荐
IE php关于强制下载文件的代码
Aug 23 Javascript
!DOCTYPE声明对JavaScript的影响分析
Apr 12 Javascript
jquery checkbox实现单选小例
Nov 27 Javascript
给ListBox添加双击事件示例代码
Dec 02 Javascript
JavaScript中的document.referrer在各种浏览器测试结果
Jul 18 Javascript
浅谈JavaScript数据类型
Mar 03 Javascript
JS获取图片lowsrc属性的方法
Apr 01 Javascript
结合代码图文讲解JavaScript中的作用域与作用域链
Jul 05 Javascript
AngularJS ng-change 指令的详解及简单实例
Jul 30 Javascript
js/jq仿window文件夹框选操作插件
Mar 08 Javascript
jQuery、layer实现弹出层的打开、关闭功能
Jun 28 jQuery
Web安全之XSS攻击与防御小结
Dec 13 Javascript
p5.js入门教程之鼠标交互的示例
Mar 16 #Javascript
JS匿名函数和匿名自执行函数概念与用法分析
Mar 16 #Javascript
解决npm管理员身份install时出现权限的问题
Mar 16 #Javascript
vue-router相关基础知识及工作原理
Mar 16 #Javascript
axios post提交formdata的实例
Mar 16 #Javascript
在vue组件中使用axios的方法
Mar 16 #Javascript
axios发送post请求,提交图片类型表单数据方法
Mar 16 #Javascript
You might like
PHP实现定时生成HTML网站首页实例代码
2008/11/20 PHP
如何用phpmyadmin设置mysql数据库用户的权限
2012/01/09 PHP
php文件夹与文件目录操作函数介绍
2013/09/09 PHP
php生成图片缩略图的方法
2015/04/07 PHP
PHPUnit测试私有属性和方法功能示例
2018/06/12 PHP
document.documentElement和document.body区别介绍
2013/09/16 Javascript
浅析基于WEB前端页面的页面内容搜索的实现思路
2014/06/10 Javascript
JQuery radio(单选按钮)操作方法汇总
2015/04/15 Javascript
基于Arcgis for javascript实现百度地图ABCD marker的效果
2015/09/12 Javascript
js获取腾讯视频ID的方法
2016/10/03 Javascript
jQuery编写网页版2048小游戏
2017/01/06 Javascript
教你用十行node.js代码读取docx的文本
2017/03/08 Javascript
jQuery实现动态给table赋值的方法示例
2017/07/04 jQuery
vue-router的HTML5 History 模式设置
2018/09/08 Javascript
jQuery选择器之基本选择器用法实例分析
2019/02/19 jQuery
JS算法题之查找数字在数组中的索引位置
2019/05/15 Javascript
vue通过video.js解决m3u8视频播放格式的方法
2019/07/30 Javascript
微信jssdk踩坑之签名错误invalid signature
2020/05/19 Javascript
在vant 中使用cell组件 定义图标该图片和位置操作
2020/11/02 Javascript
Python语言描述连续子数组的最大和
2018/01/04 Python
python实现定时提取实时日志程序
2018/06/22 Python
django小技巧之html模板中调用对象属性或对象的方法
2018/11/30 Python
django基于cors解决跨域请求问题详解
2019/08/06 Python
python使用梯度下降和牛顿法寻找Rosenbrock函数最小值实例
2020/04/02 Python
Python使用requests模块爬取百度翻译
2020/08/25 Python
让ie浏览器成为支持html5的浏览器的解决方法(使用html5shiv)
2014/04/08 HTML / CSS
购买澳大利亚最好的服装和内衣在线:BONDS
2016/10/14 全球购物
美国知名的家庭连锁百货商店:Boscov’s
2017/07/27 全球购物
洲际酒店集团美国官网:IHG美国
2017/11/16 全球购物
历史专业毕业生的自我鉴定
2013/11/15 职场文书
英语自荐信范文
2013/12/11 职场文书
公开承诺书格式
2014/05/21 职场文书
六一儿童节园长致辞
2015/07/31 职场文书
中国梦党课学习心得体会
2016/01/05 职场文书
Vue h函数的使用详解
2022/02/18 Vue.js
阿里云服务器(windows)手动部署FTP站点详细教程
2022/08/05 Servers