寫文章不容易,點個讚唄兄弟
專一 Vue 源碼分享,文章分爲白話版和 源碼版,白話版助於理解工做原理,源碼版助於瞭解內部詳情,讓咱們一塊兒學習吧
研究基於 Vue版本 【2.5.17】
若是你以爲排版難看,請點擊 下面連接 或者 拉到 下面關注公衆號也能夠吧ide
嗨,又到週末啦,又能夠睡懶覺了,冬天睡懶覺真蘇胡,可是我明天要無名加班學習
好吧,今天咱們 解讀 filter 的工做原理(話題轉得真是生硬),filter 其實實現也是很是簡單的,因此這裏直接出源碼版了
十分鐘就能大概瞭解這個 filter 了吧
好吧,今天的研究,咱們仍然要帶着問題去學習this
一、頁面的 filter 解析成什麼
二、設置的 filter 如何被調用spa
下面的講解會如下面例子 做爲講解模板prototype
這裏有一個過濾器 all,用來過濾 parentNamecode
<div>{{parentName|all }}</div>
new Vue({ el:document.getElementsByTagName("div")[0], data(){ return { parentName:111 } }, filters:{ all(){ return "我是過濾器" } } })
首先,上面的例子會被解析成下面的渲染函數token
(function() { with(this) { return _c('div',[ _v(_s(_f("all")(parentName))) ]) } }
這段代碼繼續解釋下作用域
一、_c 是渲染組件的函數,這裏會渲染出根組件rem
二、這是匿名自執行函數,後面渲染的時候調用,會 綁定當前實例爲做用域
三、with 的做用是,綁定大括號內代碼的 變量訪問做用域,因此裏面的全部變量都會從 實例上獲取
而後,你能夠看到 ' parentName | all ' 被解析成 _f('all')( parentName )
怎麼解析的?
簡單說就是,當匹配到 | 這個符號,就知道你用過濾器,而後就解析成 _f 去獲取對應過濾器 並調用,這個過程不贅述
_f 是什麼?
_f 是獲取具體過濾器的函數
一、_f 會在Vue 初始化的時候,註冊到 Vue 的原型上
// 已簡化 function installRenderHelpers(target) { target._s = toString; target._f = resolveFilter; } installRenderHelpers(Vue.prototype);
所在在 上面的 渲染函數 with 綁定當前實例vm爲做用域 以後,_f 從vm 獲取,成了這樣 vm._f
二、_f 是 resolveFilter,一個能夠獲取 具體filter 的函數
使用 _f("all") 就能獲取到 all 這個過濾器,resolveFilter 下面會說
怎麼獲取下面繼續.......
由上面能夠看到,_f 是 resolveFilter 賦值的,下面是 resolveFilter 源碼
// 已簡化 function resolveFilter(id) { return resolveAsset( this.$options, 'filters', id, true ) || identity }
this.options 會拿到當前組件的全部選項
你問我爲何?
根據上一個問題知道
一、_f 會使用 實例去調用 ,vm._f 類等 vm.resolveFilter
二、因此,resolveFilter 的 執行上下文 this 是 vm
三、因此,this.$options 就是 實例的 options 啦
接着,調用 resolveAsset ,目的就是拿到 組件選項中的 具體 filter
傳入 當前組件的選項 ,指定要其選項 filters ,指定具體 filter 名
function resolveAsset( options, type, id, warnMissing ) { // g:拿到 filters 選項 var assets = options[type]; // g:返回 調用的 filter return assets[id] }
_f("all") 流程 就成了下面這樣
一、拿到 組件選項 中的 filters
二、而後再從 filters 中,拿到 all 這個filter
三、執行返回的 all 過濾函數時,傳入須要過濾的值 parentName
四、獲得 返回了 過濾後的值
因此,當渲染函數解析的時候,碰到使用過濾器的地方,按流程拿到過濾值後,就能夠渲染到頁面上了
_f("all")(parentName)) 就會變成 "我是過濾器" 放到 渲染函數中,最後,就是渲染到頁面了
fitler 其實就是從組件選項 filters 獲取你設置的某個filter,並調用,而後使用你函數執行的返回值渲染
太簡單了,總結跟沒總結同樣.......