知識
不管是網(wǎng)站,軟件還是小程序,都要直接或間接能為您產(chǎn)生價值,我們在追求其視覺表現(xiàn)的同時,更側(cè)重于功能的便捷,營銷的便利,運營的高效,讓網(wǎng)站成為營銷工具,讓軟件能切實提升企業(yè)內(nèi)部管理水平和效率。優(yōu)秀的程序為后期升級提供便捷的支持!
您當前位置>首頁 » 新聞資訊 » 小程序相關(guān) >
在小程序中實現(xiàn) watch
發(fā)表時間:2021-1-11
發(fā)布人:葵宇科技
瀏覽次數(shù):49
微信小程序官方?jīng)]有提供 watch,用來監(jiān)聽 data 中的屬性的變化
日常開發(fā)中如果少了 watch,會顯得束手束腳
ES5 提供了 Object.defineProperty() 的方法,通過 getter/setter 劫持對象,實現(xiàn)在賦值時調(diào)用 setter 方法,執(zhí)行 watch 中對應的方法,從而實現(xiàn)監(jiān)聽。
設置監(jiān)聽者
setWatcher 函數(shù)遍歷會遍歷 data 中的所有屬性,給沒有一個屬性添加一個監(jiān)聽器 observe
const setWatcher = (page) => {
const data = http://www.wxapp-union.com/page.data
const watch = page.watch
Object.keys(watch).forEach(key => {
let targetData = http://www.wxapp-union.com/data
const targetKey = key
const watchFun = watch[key].handler || watch[key]
const deep = watch[key].deep
observe(targetData, targetKey, watchFun, deep, page)
})
}
復制代碼
實現(xiàn)監(jiān)聽器
observe 函數(shù)接收 5 個參數(shù)
- paga 中的 data
- data 中的屬性 key
- watch 中的函數(shù)
- 是否要對 data 中的屬性進行深度監(jiān)聽
- page,會被傳遞到監(jiān)聽函數(shù)中
如果 deep 為 true 需要深度監(jiān)聽,遞歸調(diào)用 observe,實現(xiàn)深度監(jiān)聽
使用 Object.defineProperty 的 setter 方法攔截外部對 data 數(shù)據(jù)的處理,同時調(diào)用 watchFn 實現(xiàn)監(jiān)聽。
watchFn 接收兩個參數(shù),value 和 oldValue,使用 call 將 page 傳遞進去。使 watch 中可以正常使用 page(this)
/**
*
* @param {Object} obj // data
* @param {String} key // data 屬性
* @param {Fucntion} watchFun // 監(jiān)聽函數(shù)
* @param {Boolean} deep // 是否深度監(jiān)聽
* @param {Object} page // page
*/
const observe = (obj, key, watchFn, deep, page) => {
let oldVal = obj[key]
if (oldVal !== null && typeof oldVal === 'object' && deep) {
Object.keys(oldVal).forEach(item => {
observe(oldVal, item, watchFun, deep, page)
})
}
Object.defineProperty(obj, key, {
configurable: true,
enumerable: true,
set(value) {
if (value =http://www.wxapp-union.com/== oldVal) return
watchFn.call(page, value, oldVal)
oldVal = value
},
get() {
return oldVal
}
})
}
復制代碼
注意事項:
- watch 只能監(jiān)聽已存在的屬性,數(shù)組的 pop() 和 push() 等方法不會觸發(fā)
- 一開始不在 data 中的屬性,后續(xù)動態(tài)添加的屬性也不會觸發(fā)
完整代碼
const observe = (obj, key, watchFun, deep, page) => {
let oldVal = obj[key]
if (oldVal !== null && typeof oldVal === 'object' && deep) {
Object.keys(oldVal).forEach(item => {
observe(oldVal, item, watchFun, deep, page)
})
}
Object.defineProperty(obj, key, {
configurable: true,
enumerable: true,
set(value: any) {
if (value =http://www.wxapp-union.com/== oldVal) return
watchFun.call(page, value, oldVal)
oldVal = value
},
get() {
return oldVal
}
})
}
export const setWatcher = (page) => {
const data = http://www.wxapp-union.com/page.data
const watch = page.watch
Object.keys(watch).forEach(key => {
let targetData = http://www.wxapp-union.com/data
const targetKey = key
const watchFun = watch[key].handler || watch[key]
const deep = watch[key].deep
observe(targetData, targetKey, watchFun, deep, page)
})
}
復制代碼
使用
import { setWatcher} from "/utils/watch.js"
Page({
data: {
age: 12,
person: {
name: 'uccs'
}
},
onLoad() {
setWatcher(this)
},
watch: {
age(val) {
console.log(val)
},
person: {
deep: true,
handler(val) {
console.log(val)
}
}
},
onClick() {
this.data.age = 18
this.data.person.name = 'tiantian'
}
})
復制代碼
相關(guān)案例查看更多
相關(guān)閱讀
- 麗江小程序開發(fā)
- 網(wǎng)站建設哪家強
- 網(wǎng)站建設需要多少錢
- vue開發(fā)小程序
- 云南網(wǎng)站建設案例
- 網(wǎng)絡公司報價
- 微分銷
- 云南省建設廳網(wǎng)站官網(wǎng)
- 做網(wǎng)站
- 網(wǎng)站建設報價
- 小程序開發(fā)公司
- 表單
- 人人商城
- 報廢車拆解系統(tǒng)
- 云南網(wǎng)站建設制作
- 前端技術(shù)
- 制作一個小程序
- 微信小程序
- 云南網(wǎng)站建設哪家好
- 云南小程序開發(fā)
- 云南企業(yè)網(wǎng)站
- 云南電商網(wǎng)站建設
- 云南軟件設計
- 云南衛(wèi)視小程序
- 云南網(wǎng)站制作哪家好
- SEO
- 汽車報廢拆解管理系統(tǒng)
- 云南網(wǎng)站建設列表網(wǎng)
- 云南網(wǎng)絡營銷顧問
- 網(wǎng)站優(yōu)化哪家好