Flutter aspectd (四) 全埋點(diǎn)實(shí)現(xiàn)

簡(jiǎn)述

aspectd的簡(jiǎn)單原理清楚了,下面嘗試實(shí)現(xiàn)一下全埋點(diǎn),參考大佬文章:
Flutter之全埋點(diǎn)思考與實(shí)現(xiàn)

獲取到點(diǎn)擊的按鈕

 @Execute("package:flutter/src/gestures/binding.dart", "GestureBinding",
      "-dispatchEvent")
  @pragma("vm:entry-point")
  dynamic hookHitTest(PointCut pointCut) {
    PointerEvent pointEvent = pointCut.positionalParams[0];
    HitTestResult hitTestResult = pointCut.positionalParams[1];
    if (pointEvent is PointerUpEvent) {
      HookImpl.getInstance().hookHitTest(hitTestResult.path.first, pointEvent);
    }
    return pointCut.proceed();
  }

上面是通過(guò)攔截,GestureBinding的dispatchEvent方法,獲取到傳給該方法的PointerEvent和HitTestResult參數(shù)。

攔截點(diǎn)擊事件

  @Execute("package:flutter/src/gestures/recognizer.dart", "GestureRecognizer",
      "-invokeCallback")
  @pragma("vm:entry-point")
  dynamic hookInvokeCallback(PointCut pointCut) {
    dynamic result = pointCut.proceed();
    dynamic eventName = pointCut.positionalParams[0];
    print("GestureRecognizer:::::invokeCallback");
    HookImpl.getInstance().hookClick(eventName);
    return result;
  }

攔截GestureRecognizer中的invokeCallback方法,可以通過(guò)傳遞的參數(shù),得到是不是點(diǎn)擊狀態(tài),判斷eventName == "onTap"

 void hookClick(String eventName) {
    if (eventName == "onTap") {
      initValues();
      _getElementPath();
      _getElementType();
      _getElementContent();
      _printClick(elementInfoMap);
      _resetValues();
    }
  }

定位一個(gè)Widget是否是自己寫(xiě)的

可以參照Flutter的track_widget_constructor_locations類(lèi)進(jìn)行更改,所在位置:

kernel/transformations/track_widget_constructor_locations.dart

對(duì)該類(lèi)的更改:

// 判斷當(dāng)導(dǎo)入類(lèi)中有我們定義的類(lèi)的時(shí)候
if (importUri.path.contains('hook_impl.dart')) {
    for (Class class_ in library.classes) {
        // 獲取到所有的類(lèi),如果有_CustomHasCreationLocation,那么把_hasCreationLocationClass賦值為_(kāi)CustomHasCreationLocation,下面同理
      if (class_.name == '_CustomHasCreationLocation') {
        _hasCreationLocationClass = class_;
      } else if (class_.name == '_CustomLocation') {
        _locationClass = class_;
      }
    }
  }

再看看_hasCreationLocationClass做了什么

 void _transformClassImplementingWidget(Class clazz) {
    // 這里是給我們寫(xiě)的組件加了一個(gè)SuperType _CustomHasCreationLocation
    clazz.implementedTypes
        .add(new Supertype(_hasCreationLocationClass, <DartType>[]));
}

這樣我們就可以通過(guò)判斷Widget是不是_CustomHasCreationLocation類(lèi)型,就能知道這個(gè)Widget是不是我們自己寫(xiě)的。

效果

由于大部分都是照著大佬文章實(shí)現(xiàn)的,所以不做過(guò)多的解析。

image

githbu地址

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書(shū)系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容