Vue02-監(jiān)視屬性watch,響應式數(shù)據(jù)添加(set),補充一些零碎..
監(jiān)視屬性
? ?const vm=new Vue(
? ? ? ? el:#root,
? ? ? ? data:{
? ? ? ? ? ? isHot:true,
? ? ? ? ? ? numbers:{
? ? ? ? ? ? ? ? a:1,
? ? ? ? ? ? ? ? b:4
? ? ? ? ? ? }
? ? ? ? },
? ? ? ? methods:{
? ? ? ? ? ? ...
? ? ? ? },
? ? ? ? watch:{
? ? ? ? ? ? isHot:{
? ? ? ? ? ? ? ? handler(newValue,oldValue){
? ? ? ? ? ? ? ? ? ? .....
? ? ? ? ? ? ? ? },
? ? ? ? ? ? ? ? immediate:true,//初始化時就讓Handler調(diào)用一次
? ? ? ? ? ? ? ? deep:true //深度監(jiān)視, 即監(jiān)控的對象的內(nèi)部改變也會觸發(fā)Handler
? ? ? ? ? ? }
? ? ? ? }
? ? );
? ? 另一種監(jiān)視寫法:
? ? vm.$watch('isHot',{
? ? ? ? handler(newValue,oldValue){
? ? ? ? ? ? .....
? ? ? ? },
? ? ? ? immediate:true
? ? });
? ? 此時, 只有handler時簡寫:
? ? vm.$watch('isHot',function(newValue,oldValue){
? ? ? ? .....//此處千萬不要寫箭頭函數(shù), 否則一旦使用this就會指向window..., 原因你知道
? ? });
vue中是默認提供了深度監(jiān)視的, 比如通過瀏覽器控制臺vm.numbers.a=8這樣的命令可以觸發(fā)頁面上使用numbers.a的那部分頁面元素發(fā)生改變 ( 頁面元素改變一定是通過其他方式發(fā)現(xiàn)了數(shù)據(jù)變化 ), 但是watch默認是不進行深度監(jiān)視的, 需要開啟deep, 才能監(jiān)控到numbers的屬性改變, 否則除非發(fā)生整個numbers的替換才會觸發(fā)handler.
Vue中的數(shù)據(jù)監(jiān)測
? let oneObj={
? ? ? ? name:'111',
? ? ? ? age:18
? ? }
? ? let okObj=new Observer(oneObj);
? ? function Obsercer(obj){
? ? ? ? let arr=Object.keys(obj);
? ? ? ? arr.forEach((k)=>{
? ? ? ? ? ? Object.defineProperty(this,k,{
? ? ? ? ? ? ? ? get(){
? ? ? ? ? ? ? ? ? ? return obj[k]
? ? ? ? ? ? ? ? },
? ? ? ? ? ? ? ? set(val){
? ? ? ? ? ? ? ? ? ? obj[k]=val
? ? ? ? ? ? ? ? }
? ? ? ? ? ? })
? ? ? ? })
? ? }
這樣的okObj就擁有了oneObj的屬性字段, 并且有g(shù)et和set. 每一個data中的屬性字段, 在vue系統(tǒng)中都會被進行這樣的處理, 一旦該字段發(fā)生改變就會觸發(fā)set中的頁面重繪.
所以, 為了動態(tài)添加屬性, 并且該屬性要被vue監(jiān)測到變動, 即添加的屬性同樣被要求是響應式的話,
? ? Vue.set(obj,'屬性名',value);
? ? 或者
? ? vm.$set(obj,'屬性名',value);
**注意:** 這里的obj不能是vue實例, 或者vue實例的根對象(vm._data), set方法只能為data中的對象添加屬性, data內(nèi)部的根一層探測不到普通的屬性添加.
? ? Vue.set(vm._data,'name','1111') ? ? ? ?×
? ? Vue.set(vm._data.person,'name','1111') ?
對于數(shù)組數(shù)據(jù), 情況有所不同:

有兩種方法可以在修改數(shù)組數(shù)據(jù)時引發(fā)頁面變化:
1. Vue.set(arr1,1,value)或vm.$set()也同理, 1就是數(shù)組的索引值, 此時就是在進行數(shù)組數(shù)據(jù)的替換, 并且借助set的數(shù)據(jù)檢測影響頁面.
2. 使用數(shù)組的push(),pop(),shift(),unshift(),splice(),sort(),reverse()可以觸發(fā)響應, vue中的數(shù)組的這些方法都已經(jīng)經(jīng)過重寫, 不再是Array的原型的對應方法, 進行過響應式改造了.
**注意:** 上面例子中的arr2是一個對象數(shù)組, 數(shù)組本身元素沒有g(shù)et和set, 但不代表其元素本身的屬性沒有g(shù)et和set, 元素對象的屬性依舊是響應式的.
v-once指令
初次動態(tài)渲染后, 之后視作靜態(tài)內(nèi)容.
? ? <div>
? ? ? ? <h2 v-once>起始值:{{x}}</h2>
? ? ? ? <h2>最新值:{{x}}</h2>
? ? </div>
? ? v-once中的x除了初始顯示一下, 不會再隨著后續(xù)數(shù)據(jù)的變動而改變.