data 和props
- props常用于數(shù)據(jù)傳遞剥槐,子組件中不可以直接修改,這也是vue 單向數(shù)據(jù)流的特性
- data在任何情況下改變硕并,都能同步反應(yīng)的view層
怎么在子組件中改動(dòng)props傳遞過(guò)來(lái)的數(shù)據(jù)呢冷守?
- 利用data的動(dòng)態(tài)性,將props數(shù)據(jù)存在data中嗓奢,通過(guò)修改data數(shù)據(jù)更新視圖
props: ['msg'],
data() {
return {
myMsg: this.msg
}
}
- 將props轉(zhuǎn)存到計(jì)算屬性computed中
props:['msg']
computed : {
myMsg () {
return this.msg;
}
}
不過(guò)因?yàn)閷?duì)象和數(shù)組是引用類(lèi)型,指向同一個(gè)內(nèi)存空間,所以不要通過(guò)computed來(lái)對(duì)父組件傳遞來(lái)的引用類(lèi)型數(shù)據(jù)進(jìn)行計(jì)算過(guò)濾含衔,改變數(shù)據(jù)會(huì)影響到父組件的狀態(tài)。
$emit二庵、$on 和 v-on
子組件更新父組件數(shù)據(jù)
- $on(eventName, callback) 監(jiān)聽(tīng)事件, 第二個(gè)參數(shù)是回調(diào)函數(shù)贪染,回調(diào)函數(shù)的參數(shù)為$emit傳遞的數(shù)據(jù)內(nèi)容
- $emit(eventName, [...arg]) 觸發(fā)事件, 第二個(gè)參數(shù)會(huì)傳遞給on監(jiān)聽(tīng)器的回調(diào)函數(shù)
- v-on則是使用在父組件標(biāo)簽中的催享,可以對(duì)其子組件的$emit監(jiān)聽(tīng)
.sync 雙向綁定
v-model也是用于雙向綁定的杭隙,上一節(jié)已經(jīng)講到。
- .sync的功能是:子組件改變了 prop睡陪,會(huì)同步到父組件中所綁定寺渗。
- 使用方式:
<comp :foo.sync="bar"></comp>
; 相當(dāng)于:<comp :foo="bar" @update:foo="val => bar = val"></comp>
- 當(dāng)子組件需要更新 foo 的值時(shí)兰迫,它需要顯式地觸發(fā)一個(gè)更新事件:
this.$emit('update:foo', newValue)
舉個(gè)栗子:
- 父組件代碼
<template>
<div>
<certificate-input :p_model.sync='pname'>
</certificate-input>
</div>
</template>
import CertificateInput from '../common/CertificateInput.vue'
export default {
name: 'fathor',
components: {
CertificateInput
},
data() {
return {
pname:""
}
}
- 子組件代碼
<template>
<div>
<input
title="姓名"
v-model="name"
></input>
<span>{{address}}</span>
</div>
</template>
<script>
export default{
name:'certificateInput',
props:["p_model"],
data(){
return{
name:this.p_model,
address: ""
}
},
watch:{
p_model(val) {
this.address = val;
},
name(val){
//設(shè)置監(jiān)聽(tīng)信殊,如果改變就更新 p_model
this.$emit('update:p_model', val)
}
}
}
</script>
其它栗子:
<!--常見(jiàn)的如餓了么組件中的:current-page.sync-->
<el-pagination
layout="prev, pager, next"
:total="meta.total"
@current-change="load"
:current-page.sync="meta.current_page"
background>
</el-pagination>
<!--js部分:-->
props: {
meta: {
type: Object,
required: true,
},
},
再如,餓了么組件Dialog:
<el-dialog
title="提示"
:visible.sync="dialogVisible"
width="30%"
:before-close="handleClose">
<span>這是一段信息</span>
<span slot="footer" class="dialog-footer">
<el-button @click="dialogVisible = false">取 消</el-button>
<el-button type="primary" @click="dialogVisible = false">確 定</el-button>
</span>
</el-dialog>
與通過(guò)自定義事件(emit)從子組件向父組件中傳遞數(shù)據(jù)的區(qū)別汁果?
- 在我們講解sync的這一小節(jié)里涡拘, 自定義事件發(fā)生時(shí)候運(yùn)行的響應(yīng)表達(dá)式是:
<son :foo="bar" v-on:update="val => bar = val"></son> 中的 "val => bar = val"
- 在二中的“通過(guò)自定義事件從子組件向父組件中傳遞數(shù)據(jù)” 里,自定義事件發(fā)生時(shí)候運(yùn)行的響應(yīng)表達(dá)式是:
<Son v-on: eventYouDefined = "arg => functionYours(arg)" /> 中的 "arg => functionYours(arg)"
對(duì)前者据德,表達(dá)式 val => bar = val意味著強(qiáng)制讓父組件的數(shù)據(jù)等于子組件傳遞過(guò)來(lái)的數(shù)據(jù)鳄乏, 這個(gè)時(shí)候,我們發(fā)現(xiàn)父子組件的地位是平等的棘利。 父可以改變子(數(shù)據(jù))橱野, 子也可以改變父(數(shù)據(jù))
對(duì)后者,你的functionYours是在父組件中定義的善玫, 在這個(gè)函數(shù)里水援, 你可以對(duì)從子組件接受來(lái)的arg數(shù)據(jù)做任意的操作或處理, 決定權(quán)完全落在父組件中茅郎, 也就是: 父可以改變子(數(shù)據(jù))蜗元, 但子不能直接改變父(數(shù)據(jù))!系冗, 父中數(shù)據(jù)的變動(dòng)只能由它自己決定