vue3源碼分析-實(shí)現(xiàn)props,emit,事件處理等
>
本期來實(shí)現(xiàn), setup里面使用props,父子組件通信props和emit等 ,所有的源碼請(qǐng)查看
在render函數(shù)中, 可以通過this,來訪問setup返回的內(nèi)容,還可以訪問this.$el等
由于是測(cè)試dom,jest需要提前注入下面的內(nèi)容,讓document里面有app節(jié)點(diǎn),下面測(cè)試用例類似在html中定義一個(gè)app節(jié)點(diǎn)哦
本功能的測(cè)試用例正式開始
上面的測(cè)試用例
解決這兩個(gè)需求:
針對(duì)上面的分析,需要在setupStatefulComponent中來創(chuàng)建proxy并且綁定到instance當(dāng)中,并且setup的執(zhí)行結(jié)果如果是對(duì)象,也已經(jīng)存在instance中了,可以通過instance.setupState來進(jìn)行獲取
通過上面的操作,從render中this.xxx獲取setup返回對(duì)象的內(nèi)容就ok了,接下來處理el
需要在mountElement中,創(chuàng)建節(jié)點(diǎn)的時(shí)候,在vnode中綁定下,el,并且在setupStatefulComponent 中的代理對(duì)象中判斷當(dāng)前的key
看似沒有問題吧,但是實(shí)際上是有問題的,請(qǐng)仔細(xì)思考一下, mountElement是不是比setupStatefulComponent 后執(zhí)行,setupStatefulComponent執(zhí)行的時(shí)候,vnode.el不存在,后續(xù)mountelement的時(shí)候,vnode就會(huì)有值,那么上面的測(cè)試用例肯定是報(bào)錯(cuò)的,$el為null
解決這個(gè)問題的關(guān)鍵,mountElement的加載順序是 render -> patch -> mountElement,并且render函數(shù)返回的subtree是一個(gè)vnode,改vnode中上面是mount的時(shí)候,已經(jīng)賦值好了el,所以在patch后執(zhí)行下操作
在vue中,可以使用onEvent來寫事件,那么這個(gè)功能是怎么實(shí)現(xiàn)的呢,咋們一起來看看
在本功能的測(cè)試用例中,可以分析以下內(nèi)容:
解決問題:
這個(gè)功能比較簡(jiǎn)單,在處理prop中做個(gè)判斷, 屬性是否滿足 /^on[A-Z]/i這個(gè)格式,如果是這個(gè)格式,則進(jìn)行事件注冊(cè),但是vue3會(huì)做事件緩存,這個(gè)是怎么做到?
緩存也好實(shí)現(xiàn),在傳入當(dāng)前的el中增加一個(gè)屬性 el._vei || (el._vei = {}) 存在這里,則直接使用,不能存在則創(chuàng)建并且存入緩存
事件處理就ok啦
父子組件通信,在vue中是非常常見的,這里主要實(shí)現(xiàn)props與emit
根據(jù)上面的測(cè)試用例,分析props的以下內(nèi)容:
解決問題:
問題1: 想要在子組件的setup函數(shù)中第一個(gè)參數(shù), 使用props,那么在setup函數(shù)調(diào)用的時(shí)候,把當(dāng)前組件的props傳入到setup函數(shù)中即可 問題2: render中this想要問題,則在上面的那個(gè)代理中,在 加入一個(gè)判斷,key是否在當(dāng)前instance的props中 問題3: 修改報(bào)錯(cuò),那就是只能讀,可以使用以前實(shí)現(xiàn)的 api shallowReadonly來包裹一下 既可
做完之后,可以發(fā)現(xiàn)咋們的測(cè)試用例是運(yùn)行沒有毛病的
上面實(shí)現(xiàn)了props,那么emit也是少不了的,那么接下來就來實(shí)現(xiàn)下emit
根據(jù)上面的測(cè)試用例,可以分析出:
解決辦法: 問題1: emit 是setup的第二個(gè)參數(shù), 那么可以在setup函數(shù)調(diào)用的時(shí)候,傳入第二個(gè)參數(shù) 問題2: 關(guān)于emit的第一個(gè)參數(shù), 可以做條件判斷,把xxx-xxx的形式轉(zhuǎn)成xxxXxx的形式,然后加入on,最后在props中取找,存在則調(diào)用,不存在則不調(diào)用 問題3:emit的第二個(gè)參數(shù), 則使用剩余參數(shù)即可
到此就圓滿成功啦!
相關(guān)評(píng)說:
西秀區(qū)移動(dòng): ______ this.props 對(duì)象的屬性與組件的屬性一一對(duì)應(yīng),但是有一個(gè)例外,就是 this.props.children 屬性.它表示組件的所有子節(jié)點(diǎn) var NotesList = React.createClass({render: function() {return (<ol>{React.Children.map(this.props.children, function (child) {...
西秀區(qū)移動(dòng): ______ //整理一下源碼如下 #include <stdio.h> int main() { int a[2][4]={1,2,3,4,5,6,7,8}; int (*pa)[4]=a; printf("%d,%d",*(*(pa+1)+2),pa[1][3]); return 0; }問題的關(guān)鍵是要理解 *pa是什么類型,它是一個(gè) int [4]的類型.*(pa+1) //因?yàn)閜a是 int [4]的類型,所以+...
西秀區(qū)移動(dòng): ______ 1. 父組件 -> 前幾層子組件: props 2. 父組件 -> 非常深入的子組件(比如從最頂層到第5層以后): context 這種情況幾乎很少見,除非寫框架或者工具,最好是只用props,清晰明了 3. 子組件 -> 父組件:callback 4. 子組件時(shí)間:
西秀區(qū)移動(dòng): ______ 瀑布模型、極限編程、敏捷開發(fā)是有代表性的開發(fā)模式,在對(duì)開發(fā)者、客戶、最終的產(chǎn)品的關(guān)注上的變化,體現(xiàn)了軟件開發(fā)管理者在管理模式上的變化. 瀑布模型 是一種理想化的開發(fā)模型,要求有明確的需求分析,無法解決軟件需求不明確或不準(zhǔn)確的問題. 瀑布模型像工廠流水
西秀區(qū)移動(dòng): ______ 簡(jiǎn)單來說,有兩種方式,一種是源碼debug,即分析源碼來找出bug位置,一般使用printf()打印出程序執(zhí)行每一步的信息,一種是可執(zhí)行文件debug
西秀區(qū)移動(dòng): ______ 基于spark1.3.1的源碼進(jìn)行分析 Spark master啟動(dòng)源碼分析1、在start-master.sh調(diào)用master的main方法,main方法調(diào)用 def main(argStrings: Array[String]) { SignalLogger.register(log) val conf = new SparkConf val args = new MasterArguments(...
西秀區(qū)移動(dòng): ______ 可分析源碼所得:varexpress=require('express');varapp=express();app.get('/',function(req,res){res.send('HelloWorld!');});varserver=app.listen(3000,function(){varhost=server.address().address;varport=server.address().port;console.log('...