<em>Mac</em>Book项目 2009年学校开始实施<em>Mac</em>Book项目,所有师生配备一本<em>Mac</em>Book,并同步更新了校园无线网络。学校每周进行电脑技术更新,每月发送技术支持资料,极大改变了教学及学习方式。因此2011
2021-06-01 09:32:01
接上章節:parseHTML 函數原始碼解析AST 基本形成
在正式扎進Vue parse原始碼之前,我們先了解下他周邊的工具函數, 這能幫我們快速的去理解閱讀。
還記得我們在上章節講的element元素節點的描述物件嗎?
var element = { type: 1, tag: tag, parent: null, attrsList: attrs, children: [] }
在原始碼中定義了一個createASTElement函數,用來建立一個元素的描述物件。
function createASTElement(tag, attrs, parent) { return { type: 1, tag: tag, attrsList: attrs, attrsMap: makeAttrsMap(attrs), parent: parent, children: [] } }
var onRE = /^@|^v-on:/; var dirRE = /^v-|^@|^:/; var forAliasRE = /([sS]*?)s+(?:in|of)s+([sS]*)/; var forIteratorRE = /,([^,}]]*)(?:,([^,}]]*))?$/; var stripParensRE = /^(|)$/g; var argRE = /:(.*)$/; var bindRE = /^:|^v-bind:/; var modifierRE = /.[^.]+/g;
在解析開始標籤的時候你遇到的不僅有屬性,還有一些Vue 自定義的指令。下面一起來分析下解析指令會有用哪些正則。
onRE
var onRE = /^@|^v-on:/;
匹配以字元 @ 或 v-on: 開頭的字串,主要作用是檢測標籤屬性名是否是監聽事件的指令。
dirRE
var const dirRE = /^v-|^@|^:/
匹配以字元 v- 或 @ 或 : 開頭的字串,主要作用是檢測標籤屬性名是否是指令。在Vue中所有以 v- 開頭的屬性都被認為是指令,另外@字元是 v-on 的縮寫,: 字元是 v-bind 的縮寫。
forAliasRE
var forAliasRE = /([sS]*?)s+(?:in|of)s+([sS]*)/;
匹配 v-for 屬性的值,並捕獲 in 或 of 前後的字串。都是正則大神就不解釋怎麼捕獲的了。
forIteratorRE
var forIteratorRE = /,([^,}]]*)(?:,([^,}]]*))?$/;
這個也是匹配v-for的屬性值,不過比之前要稍微複雜點:列表渲染 v-for(https://cn.vuejs.org/v2/guide/list.html)需要先了解下這個。
//範例:1 <div v-for="(value, name) in object"> {{ name }}: {{ value }} </div> //範例:2 <div v-for="(value, name, index) in object"> {{ index }}. {{ name }}: {{ value }} </div>
沒錯就是用來捕獲,範例1中的:'obj , index' 範例2中的:'value, key, index' 。
stripParensRE
var stripParensRE = /^(|)$/g;
這個捕獲組用來捕獲要麼以字元 ( 開頭,要麼以字元 ) 結尾的字串,或者兩者都滿足。那麼這個正則的作用是什麼呢?我們在講解正則 forIteratorRE 時有個細節不知道大家注意到了沒有,就是 forIteratorRE 正則所匹配的字串是 'obj, index' ,而不是 '(obj, index)' ,這兩個字串的區別就在於第二個字串擁有左右括號,所以在使用 forIteratorRE 正則之前,需要使用 stripParensRE 正則去掉字串 '(obj, index)' 中的左右括號,實現方式很簡單:
"(obj, index)".replace(stripParensRE, "")
argRE
var argRE = /:(.*)$/;
argRE正則用來匹配指令編寫中的引數,並且擁有一個捕獲組,用來捕獲引數的名字。
範例:
<div v-on:click.item="handle"></div>
其中 v-on 為指令,click為傳遞給 v-on 指令的引數,stop 為修飾符。
bindRE
var bindRE = /^:|^v-bind:/;
該正則用來匹配以字元:
或字串 v-bind: 開頭的字串,主要用來檢測一個標籤的屬性是否是繫結(v-bind)。
modifierRE
var modifierRE = /.[^.]+/g;
該正則用來匹配修飾符的,但是並沒有捕獲任何東西,但你可以用match、exec等方法獲取與當前正則匹配成功的資訊。
在講解 parse 函數直接我們還需要先了解下它內部所定義的一些變數以及用途。
function parse(template, options) { warn$2 = options.warn || baseWarn; platformIsPreTag = options.isPreTag || no; platformMustUseProp = options.mustUseProp || no; platformGetTagNamespace = options.getTagNamespace || no; transforms = pluckModuleFunction(options.modules, 'transformNode'); preTransforms = pluckModuleFunction(options.modules, 'preTransformNode'); postTransforms = pluckModuleFunction(options.modules, 'postTransformNode'); delimiters = options.delimiters; var stack = []; var preserveWhitespace = options.preserveWhitespace !== false; var root; var currentParent; var inVPre = false; var inPre = false; var warned = false; function warnOnce(msg) { //... } function closeElement(element) { //... } parseHTML(template, { warn: warn$2, expectHTML: options.expectHTML, isUnaryTag: options.isUnaryTag, canBeLeftOpenTag: options.canBeLeftOpenTag, shouldDecodeNewlines: options.shouldDecodeNewlines, shouldDecodeNewlinesForHref: options.shouldDecodeNewlinesForHref, shouldKeepComment: options.comments, start: function start(tag, attrs, unary) {}, end: function end() {}, chars: function chars(text) {}, comment: function comment(text) {}, }); return root }
我們先來看下針對web平臺初始化的一些變數。
warn$2 = options.warn || baseWarn; platformIsPreTag = options.isPreTag || no; platformMustUseProp = options.mustUseProp || no; platformGetTagNamespace = options.getTagNamespace || no; transforms = pluckModuleFunction(options.modules, 'transformNode'); preTransforms = pluckModuleFunction(options.modules, 'preTransformNode'); postTransforms = pluckModuleFunction(options.modules, 'postTransformNode'); delimiters = options.delimiters;
繼續往下看:
var stack = []; var preserveWhitespace = options.preserveWhitespace !== false; var root; var currentParent; var inVPre = false; var inPre = false; var warned = false;
好了一些邊邊角角的東西就先講到這,接下來我們一起來分析Vue parse原始碼看看一顆完整的AST樹是如何構建出來的。更多關於vue parseHTML函數AST預備的資料請關注it145.com其它相關文章!
相關文章
<em>Mac</em>Book项目 2009年学校开始实施<em>Mac</em>Book项目,所有师生配备一本<em>Mac</em>Book,并同步更新了校园无线网络。学校每周进行电脑技术更新,每月发送技术支持资料,极大改变了教学及学习方式。因此2011
2021-06-01 09:32:01
综合看Anker超能充系列的性价比很高,并且与不仅和iPhone12/苹果<em>Mac</em>Book很配,而且适合多设备充电需求的日常使用或差旅场景,不管是安卓还是Switch同样也能用得上它,希望这次分享能给准备购入充电器的小伙伴们有所
2021-06-01 09:31:42
除了L4WUDU与吴亦凡已经多次共事,成为了明面上的厂牌成员,吴亦凡还曾带领20XXCLUB全队参加2020年的一场音乐节,这也是20XXCLUB首次全员合照,王嗣尧Turbo、陈彦希Regi、<em>Mac</em> Ova Seas、林渝植等人全部出场。然而让
2021-06-01 09:31:34
目前应用IPFS的机构:1 谷歌<em>浏览器</em>支持IPFS分布式协议 2 万维网 (历史档案博物馆)数据库 3 火狐<em>浏览器</em>支持 IPFS分布式协议 4 EOS 等数字货币数据存储 5 美国国会图书馆,历史资料永久保存在 IPFS 6 加
2021-06-01 09:31:24
开拓者的车机是兼容苹果和<em>安卓</em>,虽然我不怎么用,但确实兼顾了我家人的很多需求:副驾的门板还配有解锁开关,有的时候老婆开车,下车的时候偶尔会忘记解锁,我在副驾驶可以自己开门:第二排设计很好,不仅配置了一个很大的
2021-06-01 09:30:48
不仅是<em>安卓</em>手机,苹果手机的降价力度也是前所未有了,iPhone12也“跳水价”了,发布价是6799元,如今已经跌至5308元,降价幅度超过1400元,最新定价确认了。iPhone12是苹果首款5G手机,同时也是全球首款5nm芯片的智能机,它
2021-06-01 09:30:45