Vue组件开发及数据v-model双向绑定讲解

重点介绍自定义组件的 v-model 实现

如何开发一个Vue组件

当你会开始一个理想的,且合理的vue组件时,你方才可以说,你会玩vue了。

如何开发一个子组件呢,开发vue组件需要考虑的几个关键问题是什么?

这里,我们使用的vue-element-ui 的vue-element-template作为基础框架,进行举例

vue-element-template的源代码git库
.git仓库

1、如何引用子组件

引用局部引用vue组件很简单,如下

<template>
 <div> 
   <h3>当前为父组件</h3>
   <!-- 使用子组件 -->
   <child-comp abc="text comp" :val=1 @ok="show" />
 </div>
</template>
<script>

// 引入组件
import ChildComp from './ChildComp.vue'

export default {
  // 务必记得将ChildComp在 components中添加
  components:{
    ChildComp
  },
  methods: {
    show(e){
      alert(e)
    }
  }
}

</script>

注意: 组件在模块中使用时,需要建议使用小写字组,并将驼峰命,转为如上所示的短横杆式命名

2、如何开发子组件

2.1 定义属性

组件定义的关键,是声明属性,只有声明过的属性,方可在模板中与普通html元素一个使用属性赋值
abcval 这些属性都应在子组件中声明,如下子组件如示

<template>
 <div> 
   <h3>这是子组件</h3>
   <span>属性abc {{abc}} </span>
   <span>属性val: {{val}} </span>
   <input v-model="childValue" v-on:change="isChangeShow"  />
 </div>
</template>

<script>
export default {
  props: {
    abc: String,
    val: Number
  },
  data(){
  	childValue:null,
  },
  methods: {
  	isChangeShow(e){
  	  this.$emit('ok',this.childValue)
  	}
  }
}
</script>

关于属性prop的定义 见官方文档

2.2 如何在子组件中调用事件

如上所示,使用组件中调用父定义的事件回调需要使用this.$emit(eventName, data)

2.3 如何实现v-model双向绑定

我们在使用el-input 时,通常都会使用v-model="var" 进进动态绑定数据,用起来特别爽。但是,当我们自己开发了组件时,有时在子组件中也封装了一个input或,也需要实现子组件与父组件都可双向修改的属性 怎么办呢?

扫描二维码关注公众号,回复: 11113431 查看本文章

首先我们需要了,为什么el-input 中,使用v-model="var" 就能实现对var变量的双向绑定呢?
其实v-model 可以看成是

<el-input v-bind:value="var" v-on:input="var = $event" />

<el-input :value="var" @input="var = $event" />

及一个单向绑定(实现父到子的数据传递)+ 加一个事件方法(实现子到父的数据传递)
v-bind 不用多说,就vue的基本数据单向绑定语法
v-on 也不用多说,就是一个事件绑定的语法

这里我们看到了一个$event变量,实际上var = $event 等于在methods只定义的某个方法,如下所示的modifyVar方法(var = $event只是如下函数的便写)

<!-- 这里是父组件 -->
<template>
	<el-input v-bind:value="var" v-on:input="modifyVar" />
</template>
<script>
export default {
	data(){
		return {
		 var: 220,
		}
	},
	methods: {
	  modifyVar(e) {
		this.var = e
      }
	}
}
</script>

v-model实际上就是 选则了一个特殊的属性value进行单向绑定(假设绑定的变量名叫var),及选择了一个特殊的事件input进行事件绑定,而该特殊的事件input的方法的功能就是改写绑定到value的变量var的值。

el-input组件中,则存在this.emit('input', data) 这样的代码,来实现对父中定义的modifyVar的调用。实际上,el-inputthis.emit()存在于 <el-input>中封装的<input> 的默认input事件的回调中。

显然,如何设计这套vue框架的人要是乐意,可以考虑选择aaa 作为特殊属性而不是value,;选择bbb作为特殊的事件,而不是input事件。这时v-model="var"就相当于如下:

<!-- 父组件 -->
<el-input v-bind:aaa="var" v-on:bbb="var = $event" />

当然上而存属于假设,但是,我们貌似发现了个自己开发组件,实现v-model双向绑定的思路,同时,也可以自定义某些别的属性,进行双向绑定的实现途径,如上aaa属性,bbb事件。当然,vue并不推荐对普通属性进行双向绑定设计(属性都是不可直接修改的),尽管你可以参考上面轻易实现这样的需求

而子组件中,必然存在 this.emit('bbb', data) 来实现,对"var = $ event" 这段代码的调用

2.4 关于动态元素的数据双向绑定

在使用v-for 指令生成的动态元素,有时动态元素需要动态变量动态绑定v-model,这时v-model绑定的变量无法双向关联,需要this.$set(Object, key, value) 来进行添加变量见这里

发布了132 篇原创文章 · 获赞 7 · 访问量 2万+

猜你喜欢

转载自blog.csdn.net/youlinhuanyan/article/details/104022845