众所周知,v-model 是Vue.js 中实现的一个语法糖,和Vue.js 中推崇的单向数据流表现不一致,用于实现所谓的双向绑定。
但看似简单的 v-model 具体是怎么做到双向绑定的,为了满足下好奇心,不得不深入到源码中看一看。
v-model 的使用情景分为两种:直接用到 input 或textarea 等输入控件中;用于自定义组件中。之所以分为这两类是因为它们在 Vue 源码中的实现的有差异的。
在输入控件中使用 v-model
export default { data() { return { aa: 'hello' } } }
写一个如上的单页面组件,首先会发生什么?
如果我们用的是不带编译器版本的 Vue , 那么 vue-loader 会将其这个文件编译为 一个 render 函数,结果如下:
(function anonymous( ) { with(this){return _c('div',{attrs:{"id":"app"}},[_c('input',{directives:[{name:"model",rawName:"v-model",value:(aa),expression:"aa"}],attrs:{"type":"text"},domProps:{"value":(aa)},on:{"input":function($event){if($event.target.composing)return;aa=$event.target.value}}})])} })
着重看 input 被编译出来的结果:
[_c('input', {directives:[{name:"model",rawName:"v-model",value:(aa),expression:"aa"}], attrs:{"type":"text"},domProps:{"value":(aa)}, on:{"input":function($event){if($event.target.composing)return;aa=$event.target.value}}})]