v-model:雙資料綁定
一、v-model是一個文法糖
<template>
<div id="app">
<input type="text" v-model="name">
<p>{{name}}</p>
</div>
</template>
<script>
export default {
data() {
return {
name: '孫藝珍',
age: 18
}
}
}
</script>
以上代碼在運作時就可以達到雙資料綁定的效果:
v-model其實是 value 屬性和 input 事件的文法糖,什麼意思呢?
如果把 v-model='name' 替換為 :value='name' @input="(e)=>name=e.target.value" 效果是一樣的
<template>
<div id="app">
<!-- <input type="text" v-model="name"> -->
<input type="text" :value='name' @input="(e)=>name=e.target.value">
<p>{{name}}</p>
</div>
</template>
就是說寫了v-model就相當于綁定了value屬性和input事件!
二、v-model可以給元件綁定資料
1、定義MyInput.vue元件:
<template>
<div>
<h1>自定義input</h1>
<input type="text" :value="value" @input="(e)=>$emit('input',e.target.value)">
<p>{{value}}</p>
</div>
</template>
<script>
export default {
props: ['value']
}
</script>
2、App.vue中引入并使用
<template>
<div id="app">
<input type="text" v-model="name">
<p>{{name}}</p>
<MyInput v-model="name" />
</div>
</template>
<script>
import MyInput from './components/MyInput'
export default {
data() {
return {
name: '孫藝珍',
age: 18
}
},
components: { MyInput }
}
</script>
此時,MyInput.vue中修改value會實時綁定到App.vue中的name
為什麼MyInput.vue中props可以接收value,并且通過$emit觸發input事件呢?
因為 <MyInput v-model="name" /> 就相當于 <MyInput :value="name" @input="(val)=>name=val" />
v-model是value屬性和input事件的文法糖~
其中,@input="(val)=>name=val" 也可以寫成 @input="name=$event"
三、sync修飾符
如果需要給自定義元件綁定多個v-model,此時需要用到sync修飾符。
1、App.vue中将age傳遞給MyInput.vue
<MyInput v-model="name" :age.sync='age' />
2、MyInput.vue
<template>
<div>
<h1>自定義input</h1>
<input type="text" :value="value" @input="(e)=>$emit('input',e.target.value)">
<p>{{value}}</p>
<input type="text" :value="age" @input="(e)=>$emit('update:age',e.target.value)">
<p>{{age}}</p>
</div>
</template>
<script>
export default {
props: ['value', 'age']
}
</script>
注意:修改age時觸發的自定義事件為 update:age
既然用到了sync屬性,那麼将v-model也改成sync的寫法,保持統一:
1、App.vue
<MyInput :name.sync='name' :age.sync='age' />
2、MyInput.vue
<template>
<div>
<h1>自定義input</h1>
<input type="text" :value="name" @input="(e)=>$emit('update:name',e.target.value)">
<p>{{name}}</p>
<input type="text" :value="age" @input="(e)=>$emit('update:age',e.target.value)">
<p>{{age}}</p>
</div>
</template>
<script>
export default {
props: ['name', 'age']
}
</script>
四、sync是一個文法糖
<MyInput v-model="name" :age.sync='age' />
為什麼age屬性經過sync修飾後,修改age時觸發的事件名為 update:age ?
因為 :age.sync='age' 就是 :age='age' @update:age='age=$event' 的文法糖~
五、vue3中v-model的使用
1、執行vue add vue-next将vue2更新到vue3
2、App.vue
<MyInput v-model:name="name" v-model:age="age" />
3、MyInput.vue
<template>
<div>
<h1>自定義input</h1>
<input type="text" :value="name" @input="(e)=>$emit('update:name',e.target.value)" />
<p>{{name}}</p>
<input type="text" :value="age" @input="(e)=>$emit('update:age',e.target.value)" />
<p>{{age}}</p>
</div>
</template>
<script>
export default {
props: ['name', 'age']
}
</script>
此時,就将App.vue中的name、age和MyInput.vue元件雙向綁定了