vue子組件監(jiān)聽父組件數(shù)據(jù)變化并作出改變(親測有效)
1. 問題
1.1 封裝組件時經(jīng)常會遇到子組件需要根據(jù)父組件數(shù)據(jù)變化并執(zhí)行對應的操作邏輯
1.2 監(jiān)聽方法中加了deep、immediate 等參數(shù)監(jiān)聽數(shù)組/對象還是沒有生效
1.3 類型table組件需要根據(jù)父組件數(shù)據(jù)變化對表格數(shù)據(jù)進行更新
1.4 根據(jù)數(shù)據(jù)動態(tài)渲染組件需實時監(jiān)聽父組件變化
1.5 使用$refs 有些時候很難找到嵌套組件的ref
2. 思路
2.1 本文章主要的思路就是 provide / inject
2.2 創(chuàng)建父組件時,無論有多少層級的子組件都可以進行數(shù)據(jù)的相互依賴
2.3 那么在子組件可以利用這些依賴對父組件數(shù)據(jù)進行監(jiān)聽
3. 解決方法
3.1 首先在父組件定義 provide,代碼如下
//父組件提供參數(shù)給子組件(響應式時需設置為對象)
provide(){
return {
superParams:this
}
},
data(){ //定義幾個參數(shù)
return {
test:{
testLevel1:{
testLevel2:''
}
},
testList:[]
}
}
3.2 子組件添加 inject,代碼如下
// 子組件:childrenComponent1
inject: ['superParams'],
watch:{ //監(jiān)聽數(shù)據(jù)變化
'superParams.test':{
immediate:true, // 將立即以表達式的當前值觸發(fā)回調(diào)
handler:function (val,oldVal) {
console.log("監(jiān)聽test對象");
console.log(val,oldVal);
},
deep:true,
},
'superParams.test.testLevel1':{
immediate:true, // 將立即以表達式的當前值觸發(fā)回調(diào)
handler:function (val,oldVal) {
console.log("監(jiān)聽testLevel1屬性");
console.log(val,oldVal);
},
deep:true,
},
'superParams.test.testLevel1.testLevel2':{
immediate:true, // 將立即以表達式的當前值觸發(fā)回調(diào)
handler:function (val,oldVal) {
console.log("監(jiān)聽testLevel1屬性");
console.log(val,oldVal);
},
deep:true,
},
'superParams.testList':{
immediate:true, // 將立即以表達式的當前值觸發(fā)回調(diào)
handler:function (val,oldVal) {
console.log("監(jiān)聽testList數(shù)組");
console.log(val,oldVal);
},
deep:true,
}
}
3.3 另外一個子組件觸發(fā)父組件數(shù)據(jù)變化(同/不同層級都可以觸發(fā))
// 子組件:childrenComponent2
inject: ['superParams'],
mounted(){
this.superParams.test.testLevel1.testLevel2 = 'testLevel22';
this.superParams.testList.push({test:'test'})
}
舉例一(子組件按順序展示):先顯示childrenComponent2 ,再到childrenComponent1,(下圖的數(shù)據(jù)在childrenComponent1展示后輸出)結果如圖所示
舉例二(子組件都展示, 在父組件或其他地方觸發(fā)數(shù)據(jù)更新)
在父組件添加一個按鈕點擊觸發(fā)方法代碼如下
updateText(){
console.log("Text數(shù)據(jù)更新");
this.test.testLevel1.testLevel2 = 'testLevel22';
this.testList.push({test:'test'})
}
結果如下圖所示
注意
- 當前組件監(jiān)聽方法數(shù)據(jù)作出了改變,但組件卻沒有更新,這時需在組件本身找更新原因
- 組件顯示時會對監(jiān)聽方法進行初始化
- 對于對象存在多層的監(jiān)聽問題,可監(jiān)聽整個對象
- 對于數(shù)組會不會存在漏監(jiān)聽的情況,經(jīng)測試調(diào)用數(shù)組的pop、push、shift、unshift、splice、sort、reverse等方法時是可以監(jiān)聽到數(shù)組的變化
- immediate、deep 要了解
補充
針對注意點1,以el-input-number(element ui)組件為例
<el-input-number v-model="item.max" @change="handleChange" :min="0" :key="Math.random()" :max="superParams.max"></el-input-number>
在沒有加上 :key=“Math.random()” 前組件并沒有隨著父組件數(shù)據(jù)(superParams.max)變化
加上后可根據(jù)父組件數(shù)據(jù)動態(tài)改變
父組件改變參數(shù)值代碼如下圖所示文章來源:http://www.zghlxwxcb.cn/news/detail-403423.html
'formData.isTrue':function (val,oldVal) {
if(val){
this.max = 100;
}else {
this.max = 50;
}
},
并不是所有組件都能用 :key=“Math.random()” ,某些組件使用后會出現(xiàn)卡頓或者無法輸入值文章來源地址http://www.zghlxwxcb.cn/news/detail-403423.html
到了這里,關于vue子組件監(jiān)聽父組件數(shù)據(jù)變化并作出改變(親測有效)的文章就介紹完了。如果您還想了解更多內(nèi)容,請在右上角搜索TOY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關文章,希望大家以后多多支持TOY模板網(wǎng)!