单向数据流:父组件值的更新,会影响到子组件,反之则不行;
修改子组件的值:
局部数据:在子组件中定义新的数据,将父组件传过来的值赋值给新定义的数据,之后操作这个新数据;
如果对数据进行简单的操作,可以使用计算属性;
由效果图可知,父组件值的更新,会影响到子组件,而子组件值的更新时,控制台会报错
此时代码:

1 <!DOCTYPE html> 2 <html> 3 <head> 4 <meta charset="UTF-8"> 5 <title> 单向数据流</title> 6 <script type="text/javascript" src="../js/vue.js" ></script> 7 </head> 8 <body> 9 <div> 10 <father-component ></father-component> 11 </div> 12 </body> 13 <template id="father-template"> 14 <div> 15 <h2> 父组件</h2> 16 myData:<span>{{name}}</span><br /> 17 18 <input type="text" v-model="name"/> 19 <hr /> 20 <child-component :name="name" ></child-component> 21 </div> 22 </template> 23 <template id="child-template"> 24 <div> 25 <p> 子组件</p> 26 fatherData:<span >{{name}}</span> 27 <input type="text" v-model="name"/> 28 29 </div> 30 </template> 31 <script> 32 33 34 new Vue({ 35 36 data:{ 37 38 }, 39 components:{ 40 "father-component":{ 41 data(){ 42 return{ 43 44 name:'perfect', 45 46 } 47 }, 48 props:['msg'], 49 template:'#father-template', 50 51 components:{ 52 "child-component":{ 53 54 template:'#child-template', 55 props:['name'] 56 } 57 }, 58 59 60 61 } 62 } 63 64 65 66 }).$mount('div'); 67 </script> 68 </html>
每次父级组件发生更新时,子组件中所有的 prop 都将会刷新为最新的值。这意味着你不应该在一个子组件内部改变 prop。如果你这样做了,Vue 会在浏览器的控制台中发出警告。
解决方法:
首先由于这个 prop 用来传递一个初始值;这个子组件接下来希望将其作为一个本地的 prop 数据来使用。在这种情况下,最好定义一个本地的 data 属性并将这个 prop 用作其初始值:
相当于定义一个局部变量:
这样就可以不影响了;
在子组件中定义如下:
components:{ "child-component":{ template:'#child-template', props:['name'], data(){ return{ childName:this.name } } }
进行调用的demo如下:
<template id="child-template"> <div> <p> 子组件</p> fatherData:<span >{{childName}}</span> <input type="text" v-model="childName"/> </div> </template>
2、这个 prop 以一种原始的值传入且需要进行转换。在这种情况下,最好使用这个 prop 的值来定义一个计算属性:
比如说小写转大写:
components:{ "child-component":{ template:'#child-template', props:['name'], data(){ return{ childName:this.name } }, computed:{//计算属性的值 childUpperName(){ return this.name.toString().toUpperCase(); } } } }
<template id="child-template"> <div> <p> 子组件</p> fatherData:<span >{{childUpperName}}</span> <input type="text" v-model="childUpperName"/> </div> </template>
由图知计算属性仍然不能直接修改父组件中name的值
上述实例的总的代码:

1 <!DOCTYPE html> 2 <html> 3 <head> 4 <meta charset="UTF-8"> 5 <title> 单向数据流</title> 6 <script type="text/javascript" src="../js/vue.js" ></script> 7 </head> 8 <body> 9 <div> 10 <father-component ></father-component> 11 </div> 12 </body> 13 <template id="father-template"> 14 <div> 15 <h2> 父组件</h2> 16 myData:<span>{{name}}</span><br /> 17 18 <input type="text" v-model="name"/> 19 <hr /> 20 <child-component :name="name" ></child-component> 21 </div> 22 </template> 23 <template id="child-template"> 24 <div> 25 <p> 子组件</p> 26 fatherData:<span >{{childUpperName}}</span> 27 <input type="text" v-model="childUpperName"/> 28 29 </div> 30 </template> 31 <script> 32 33 34 new Vue({ 35 36 data:{ 37 38 }, 39 components:{ 40 "father-component":{ 41 data(){ 42 return{ 43 44 name:'perfect', 45 46 } 47 }, 48 props:['msg'], 49 template:'#father-template', 50 51 components:{ 52 "child-component":{ 53 54 template:'#child-template', 55 props:['name'], 56 data(){ 57 58 return{ 59 childName:this.name 60 } 61 }, 62 computed:{//计算属性的值 63 64 childUpperName(){ 65 return this.name.toString().toUpperCase(); 66 } 67 } 68 } 69 } 70 71 72 73 } 74 } 75 76 77 78 }).$mount('div'); 79 </script> 80 </html>
下面介绍如何修改子组件的值同步到父组件中
单向数据流子组件数据同步到父组件
修改子组件的prop,同步到父组件:
1、使用.sync修饰符;
在子组件中写入这个函数:
//数据发生改变就会进行调用 updated(){ console.log(this.childName); this.$emit("update:name", this.childName); },
使用修饰符代码:
<template id="father-template"> <div> <h2> 父组件</h2> myData:<span>{{name}}</span><br /> <input type="text" v-model="name"/> <hr /> <child-component :name.sync="name" ></child-component> </div> </template> <template id="child-template"> <div> <p> 子组件</p> fatherData:<span >{{childName}}</span> <input type="text" v-model="childName"/> </div> </template>
2、将要操作的数据封装成一个对象再操作,进行数据的双向绑定:
使用的vue代码:进行在父组件中定义一个对象user,
components:{ "father-component":{ data(){ return{ name:'perfect', user:{ id:1 } } },
进行调用使用:
<template id="father-template"> <div> <h2> 父组件</h2> name:<span>{{name}}</span><br /> <input type="text" v-model="name"/> <hr /> userID:<span>{{user.id}}</span><br /> <input type="text" v-model="user.id"/> <hr /> <child-component :name.sync="name" :user="user"></child-component> </div> </template> <template id="child-template"> <div> <p> 子组件</p> fatherData:<span >{{childName}}</span><br /> <input type="text" v-model="childName"/><br /> <hr /> userID:<span>{{user.id}}</span><br /> <input type="text" v-model="user.id"/> </div> </template>
总的代码:

1 <!DOCTYPE html> 2 <html> 3 <head> 4 <meta charset="UTF-8"> 5 <title> 单向数据流子组件数据同步到父组件</title> 6 <script type="text/javascript" src="../js/vue.js" ></script> 7 </head> 8 <body> 9 <div> 10 <father-component ></father-component> 11 </div> 12 </body> 13 <template id="father-template"> 14 <div> 15 <h2> 父组件</h2> 16 name:<span>{{name}}</span><br /> 17 18 <input type="text" v-model="name"/> 19 <hr /> 20 21 userID:<span>{{user.id}}</span><br /> 22 23 <input type="text" v-model="user.id"/> 24 <hr /> 25 <child-component :name.sync="name" :user="user"></child-component> 26 </div> 27 </template> 28 <template id="child-template"> 29 <div> 30 <p> 子组件</p> 31 fatherData:<span >{{childName}}</span><br /> 32 <input type="text" v-model="childName"/><br /> 33 <hr /> 34 userID:<span>{{user.id}}</span><br /> 35 36 <input type="text" v-model="user.id"/> 37 38 39 </div> 40 </template> 41 <script> 42 43 44 new Vue({ 45 46 data:{ 47 48 }, 49 components:{ 50 "father-component":{ 51 data(){ 52 return{ 53 54 name:'perfect', 55 user:{ 56 57 id:1 58 } 59 60 } 61 }, 62 63 template:'#father-template', 64 65 components:{ 66 "child-component":{ 67 68 template:'#child-template', 69 props:['name','user'], 70 data(){ 71 72 return{ 73 childName:this.name 74 } 75 }, 76 77 //数据发生改变就会进行调用 78 updated(){ 79 console.log(this.childName); 80 this.$emit("update:name", this.childName); 81 }, 82 computed:{//计算属性的值 83 84 childUpperName(){ 85 return this.name.toString().toUpperCase(); 86 } 87 88 89 } 90 } 91 } 92 93 94 95 } 96 } 97 98 99 100 }).$mount('div'); 101 </script> 102 </html>