vue2组件之间双向数据绑定问题
最近在使用element-ui的dialog组件二次封装成独立组件使用时,子组件需要将关闭dialog状态返回给父组件,简单的说就是要实现父子组件之间的数据双向绑定问题。
大致代码如下:
1,父组件
<template>
  <button @click="openDialog">打开弹窗</button>
  <dialogCompenent :show="result" :result="result" @dialogData="closeDialog"></dialogCompenent>
</template>
<script type="text/babel">
import dialogCompenent from '/dialogCompenent'
export default {
  data () {
    return {
      result: false
    }
  },
  components: {
    dialogCompenent
  },
  methods: {
    openDialog () {
      this.result = true
    },
    closeDialog (data) {
      this.result = data
    }
  }
}
</script>
2,子组件 childCompenent
<template>
<el-dialog
  title="弹框组件"
  :visible.sync="result"
  @open="doOpen"
  @close="doClose"
  :show="result"
  size="tiny">
  <div class="content-wrapper">
    具体业务代码...
  </div>
</el-dialog>
  </div>
</template>
<script type="text/babel">
  import videoApi from '../../api/videoApi/videoApi'
  export default {
    name: 'dialogCompenent',
    props: {
      result: Boolean
    },
    methods: {
      doOpen () {
        ...
      },
      doClose () {
        this.$emit('dialogData', false)
        ...
      }
    }
  }
</script>
程序在浏览器上虽然能够正常运行,但是在vue2.0却会报错:
[Vue warn]: Avoid mutating a prop directly since the value will be overwritten whenever the parent component re-renders. Instead, use a data or computed property based on the prop's value. Prop being mutated: "result" (found in component )
组件内不能修改props的值,同时修改的值也不会同步到组件外层,即调用组件方不知道组件内部当前的状态是什么
这是什么原因造成的呢?
在vue1.x版本中利用props的twoWay和.sync绑定修饰符就可以实现props的双向数据绑定。
在vue2.0中移除了组件的props的双向数据绑定功能,如果需要双向绑定需要自己来实现。
在vue2.0中组件的props的数据流动改为了只能单向流动,即只能由(父组件)通过组件的v-bind:attributes传递给(子组件),子组件只能被动接收父组件传递过来的数据,并在子组件内不能修改由父组件传递过来的props数据。
官方文档解释:
prop 是单向绑定的:当父组件的属性变化时,将传导给子组件,但是不会反过来。这是为了防止子组件无意修改了父组件的状态——这会让应用的数据流难以理解。
虽然废弃了props的双向绑定对于整个项目整体而言是有利且正确的,但是在某些时候我们确实需要从组件内部修改props的需求
在Vue2.0中,实现组件属性的双向绑定方式
子组件修改:
<template>
    <el-dialog
      title="弹框组件"
      :visible.sync="openStatus"
      @open="doOpen"
      @close="doClose"
      :show="openStatus"
      size="tiny">
      <div class="content-wrapper">
        具体业务代码...
      </div>
    </el-dialog>
  </div>
</template>
<script type="text/babel">
  import videoApi from '../../api/videoApi/videoApi'
  export default {
    name: 'dialogCompenent',
    props: {
      result: Boolean
    },
	/*创建一个openStatus变量缓存result数据
	*在子组件需要调用result的地方调用data对象openStatus
	*/
    data () {
      return {
        openStatus: this.result
      }
    },
	//新增result的watch,监听变更同步到openStatus
	//监听父组件对props属性result的修改,并同步到组件内的data属性
    watch: {
      result (val) {
        this.openStatus = val
      }
    },
    methods: {
      doOpen () {
        ...
      },
      doClose () {
        this.$emit('dialogData', false)//子组件对openStatus修改后向父组件发送事件通知
        ...
      }
    }
  }
</script>
父组件修改:
<template>
  <button @click="openDialog">打开弹窗</button>
  <dialogCompenent :show="result" :result="result" @dialogData="closeDialog"></dialogCompenent>
</template>
<script type="text/babel">
import dialogCompenent from '/dialogCompenent'
export default {
  data () {
    return {
      result: false
    }
  },
  components: {
    dialogCompenent
  },
  methods: {
    openDialog () {
      this.result = true
    },
    closeDialog (data) {
      this.result = data//子组件触发父组件事件,进行数据变更,同步result数据
    }
  }
}
</script>
至此,实现了子组件内数据与父组件的数据的双向绑定,组件内外数据的同步。最后归结为一句话就是:组件内部自己变了告诉外部,外部决定要不要变。
结语
那么为什么vue1.0还有的数据双向绑定在vue2.0版本中反而抛弃了呢,通过上述案例我们也可以发现双向绑定的props代码多,不利于组件间的数据状态管理,尤其是在复杂的业务中更是如此,所以尽量不使用这种方式的双向绑定,过于复杂的数据处理使用vuex来进行数据管理。(https://vuex.vuejs.org/zh-cn/intro.html)
vue2组件之间双向数据绑定问题的更多相关文章
- Angular:实现组件间双向数据绑定
		学过Angular的同学都知道,输入框通过[(ngModel)]实现双向数据绑定,那么父子组件间能不能实现双向数据绑定呢?答案是肯定的. Angular中,我们常常需要通过方括号[]和圆括号()实现组 ... 
- Vue: 一个简单的Vue2.0 v-model双向数据绑定的实现,含源代码,小白也能看懂
		首先说一下原理吧 View层(dom元素)的变动如何响应到Model层(Js变量)呢? 通过监听元素的input事件来动态的改变js变量的值,实际上不是改变的js变量的值,而是改变的js变量的gett ... 
- vue2.*     事件结合双向数据绑定、模块化以及封装Storage实现todolist 待办事项 已经完成 和进行中持久化  06
		ceshi.vue <template> <div id="app"> <input type='text' v-model='todo' @keyd ... 
- 组件使用v-model、$listeners、.sync(区别于v-model的双向数据绑定)
		自定义组件 自定义组件的v-model 首先我们先说一下在自定义组件中使用v-model的必要条件 在自定义的组件中要有input(这里我们先不讨论单选复选框) 在自定义组件的模板对象中要有props ... 
- Angular自定义组件实现数据双向数据绑定
		学过Angular的同学都知道,输入框通过[(ngModel)]实现双向数据绑定,那么自定义组件能不能实现双向数据绑定呢?答案是肯定的. Angular中,我们常常需要通过方括号[]和圆括号()实现组 ... 
- 7.vue组件(二)--双向绑定,父子组件访问
		本文主要说两件事 1. 如何实现父子组件之间的双向绑定 2. 父组件如何访问子组件的data,method, 子组件如何访问父组件的data,method等 一. 如何实现父子组件之间的双向绑定 案例 ... 
- Vue2.0父子组件之间的双向数据绑定问题解决方案
		对于vue 1.0项目代码,如果把vue换成vue 2.0,那么之后项目代码就完全奔溃不能运行,vue 2.0在父子组件数据绑定的变化(不再支持双向绑定)颠覆了1.0的约定,很遗憾. 解决方案只有两种 ... 
- vue3.x自定义组件双向数据绑定v-model
		vue2.x 语法 在 2.x 中,在组件上使用 v-model 相当于绑定 value prop 并触发 input 事件: <ChildComponent v-model="pag ... 
- 如何在Vue2中实现组件props双向绑定
		Vue学习笔记-3 前言 Vue 2.x相比较Vue 1.x而言,升级变化除了实现了Virtual-Dom以外,给使用者最大不适就是移除的组件的props的双向绑定功能. 以往在Vue1.x中利用pr ... 
随机推荐
- angular.js和ionic框架搭建一个webApp
			原文地址:http://www.jianshu.com/p/ea0dcf1d31c9 
- 可决系数R^2和MSE,MAE,SMSE
			波士顿房价预测 首先这个问题非常好其实要完整的回答这个问题很有难度,我也没有找到一个完整叙述这个东西的资料,所以下面主要是结合我自己的理解和一些资料谈一下r^2,mean square error 和 ... 
- 内存修改之IOS版ce
			开源工具,算法全部在内存中完成,速度比bmsq,igg快,直接搜索0也是无压力.使用c++编写,有一定的扩展能力,可以自己扩展value type和comparator. 项目地址: https:// ... 
- 用javascript编写猜拳游戏(函数)
			const readline = require('readline-sync')//引用readline-sync console.log('欢迎进入猜拳游戏'); //电脑随机出拳 let fn ... 
- ffmpeg 简单使用总结
			FFMPEG 生成指定长度的空白音频: ffmpeg -f lavfi -i aevalsrc=0 -t seconds -q:a 9 -acodec libmp3lame out.mp3 FFMPE ... 
- mpvue开发美团外卖点餐小程序
			mpvue-meituan mpvue-meituan 是一款使用mpvue开发的实战小程序项目,完全仿制美团官方外卖点餐小程序开发而成,项目的框架结构完全按照企业开发架构搭建而成.结合了原生小程序的 ... 
- HDU Ellipse(simpson积分)
			Time Limit: 1000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submission( ... 
- 在控制台中操作MYSQL数据库步骤以及一些小问题
			一直用Navicat来对MySQL数据库进行操作,今天突然想试试用DOS控制台来操作,特记录自己第一次使用经历,若有错误之处,还望大佬们指点. 首先打开控制台,win+R键,输入cmd,确定 输入my ... 
- Linux性能检查命令总结[转]
			一些常用的网络.IO.内存监控指令,Linux性能检查命令总结 
- WARNING: IPv4 forwarding is disabled. Networking will not work.
			1:Test environment [root@docker-node1 ~]# cat /etc/redhat-release CentOS Linux release 7.5.1804 (Cor ... 
