本文同步自wing的地方酒館php
很久沒寫博客了。此次玩一點不同的。java
相信熟悉Xposed的小夥伴們都知道,每次寫完Xposed都要重啓啊!有木有!反射錯了,寫錯了名字,改一個log,都要重啓啊有木有!重啓浪費時間啊有木有!一個字母致使一次重啓!要命啊有木有!android
因此就花時間想了想有木有不重啓就當即生效的辦法呢。git
Xposed每次都須要重啓才能生效,這裏我並不知道具體緣由,可是大題能夠猜想爲燒入系統的代碼,因此若是代碼有變更,必須通過重啓。那麼有沒有隻燒一次,就能夠動態變更的方法呢?github
參考android裏classloader實現,發現findClass()最後都是調用了DexFile來loadClass,那咱們也能夠偷懶,不包裹classloader,直接拿DexFile來動態加載咱們的代碼呀。app
首先,準備hook一下個人zoomheader,在主界面onCreate()的時候,讓他彈出一個Toast. (其實作什麼均可以
,這裏只是方便演示)gradle
此時,打開個人app,就能夠彈出「哈哈」這個Toast
.net
但是,這時候我發現「哈哈」其實寫錯了,我想寫成"呵呵",這時候我不得不修改「哈哈」爲「呵呵」,而後重啓,爲了這一個字等上個三五六分鐘。。插件
因此,這個時候,咱們把須要寫的邏輯代碼單獨放到一個dex裏,而後使用DexFile加載,這時候雖然只燒了一次代碼,可是這個燒了之後的代碼能夠根據動態的dex的代碼來進行邏輯變化。3d
原理很簡單,代碼也很簡單,只須要幾句話。
這裏爲了展現原理,寫了最簡單的,這裏去讀取/sdcard/classes.dex文件,直接導入Hotfix類,調用他的invoke方法,因爲彈出toast須要用到activity參數,因此把這個Activity傳入便可。
HotFix代碼如圖:把Toast邏輯寫在了裏面。
這個時候,只要把hotfix的apk打包,而後提取dex,經過adb push到sdcard, 就能夠實現熱更新了!
不過這樣未免仍是有些麻煩。因此固然要用gradle幫咱們了。
觀察application插件,有個叫作transformClassesWithDex的任務,他就是把class文件轉化爲dex的任務,這個時候,咱們去hook這個任務,在他執行完畢之後,自動把dex push到/sdcard/中。
寫一個任務,叫作pushDex ,而且依賴於transformClassesWithDex。
此時,只要修改完HotFix.java的代碼,而後執行Task pushDex,代碼就自動熱更新完畢!
判斷adb路徑代碼 使用了AppMethodOrder的代碼,感謝原做者 @三斤-虹貓
項目示例代碼已經上傳至github.com/githubwing/…
以爲有用,能節省時間的話,歡迎star哈。
歡迎加入Android地方酒館:425983695