Aidl Lite

由于嘴賤,立了個flag...
And thanks for this flag ...
To be continued...

Aidl

1)快速上手

  1. JavaBean
    首先,先寫一個JavaBean備用
    PS:該文件不要同AIDL文件放置同一個包下,否是運行會提示找不到該類


    Book.java
  2. JavaBean.aidl
    然后在開始我們新建我們的AIDL文檔前,先新建一個與上面JavaBean同名的AIDL文件,既Book.aidl,并在其中聲明我們的Book對象

    Book.aidl

    并且該文件需要同上面的JavaBean文件在AIDL下放至于相同的位置,應該是IDE 解析的時候會自動去相同路徑下查詢,算是一種映射吧,因為待會Sync項目后source下會自動生成java代碼,import引用的是aidl路徑下的Book.aidl,而這則是由實現(xiàn)了Parcelable的Book.java映射過去的,所以這中間路徑需保持一致,不然鎖鏈就斷了 (待研究)
    278511509262463_.pic_hd.jpg

  3. AIDL
    最后我們開始新建真正所要用的AIDL對象:BookManager.aidl,并在其中寫入接口函數(shù)
    在我這小菜鳥現(xiàn)有的理解中,可以暫且將AIDL作為接口來看待,但不同于接口的是
    要注意:

    • 在AIDL文件中使用自定義的JavaBean對象(或非默認數(shù)據(jù)類型),都必須要在文件中顯式地導入進來,正如注釋所寫的:在此用導入語句來聲明任何非默認類型;
    • 并且別忘了對象參數(shù)的類型定義,既in/out/inout

    不然會導致第四步的Sync Project的時候報錯......(慘痛經(jīng)歷)


    Aidl
  4. Sync Project with Gradle Files
    至此,在AS中點擊Sync Project同步下項目,編譯器將自動根據(jù)我們的AIDL文件生成同名的.java文件(若這里忘了同步,則在后續(xù)代碼的調(diào)用將不會有快捷提示了)
    生成的.java路徑(Project模式下):


    image.png
  5. Service
    由于我們的AIDL是跟Service配合使用的,所以我們就接著在Service中創(chuàng)建并調(diào)用,具體如下
    由于AIDL也是Binder的子類(有點忘了,我后續(xù)確認下嘿嘿嘿),所以只要通過binder新建個aidl的對象,然后自然就會重寫我們aidl里的方法(這也是為什么我暫且將其作為接口看待的原因)


    Service

    然后記得在onBind()函數(shù)中將上述myBinder返回即可,至此Service部分就寫完了

  6. Activity
    最后是我們的Activity,Activity部分也挺簡單的
    我們只需要在onServiceConnected()中通過調(diào)用AIDL.Stub.asInterface(),并將該方法中的IBinder型參數(shù)傳入即可,這樣我們就獲取到了我們的AIDL對象,而后續(xù)的事也就是通過該對象來調(diào)用之前寫在里面的方法罷了


    Activity
  1. 結(jié)果


    image.png

2)添加監(jiān)聽

  1. 新建監(jiān)聽aidl文件:BookListener.aidl,并在其中完善監(jiān)聽接口


    BookListener.aidl
  2. 在BookManager.aidl中也添加注冊和解綁監(jiān)聽的方法,記得需要顯式導包


    BookManager.aidl
  3. Service中重寫AIDL中兩個新添加的方法以實現(xiàn)注冊和解綁,并且模擬添加書籍


    重寫方法

(模擬添加書籍可參照開發(fā)藝術(shù)探索P78)


模擬持續(xù)添加book
  1. Activity中獲取BookListener的對象,并重寫方法打印,然后記得調(diào)用bookManager.registerListener()即可


    2017-10-27-09-36-41.jpg

    2017-10-27-09-37-06.jpg
  2. 結(jié)果:
    可以從log里看到,當Activity銷毀調(diào)用unregisterListener()時,無法找到之前注冊的listener


    Log

PS:若Service和Activity在同一個進程的情況下,則不會有上述現(xiàn)象

3)使用RemoteCallbackList

由于我們的Service和Activity是在兩個進程,而對象不能跨進程傳輸,而多進程跨進程的話,無法調(diào)取到同一對象,因為對象不能跨進程傳輸,所以Binder會把客戶端傳遞過來的對象重新轉(zhuǎn)換生成一個新的對象,
故若多進程時解綁,需要使用RemoteCallbackList

  1. 將listenerList類型從List改為RemoteCallbackList


    RemoteCallbackList
  2. 重寫binder中的注冊和解綁函數(shù)


    修改注冊解綁方法

    需要注意的是RemoteCallbackList的size可以通過beginBroadcast()獲取,但需要在調(diào)用后,調(diào)用finishBroadcast()


    RemoteCallbackList.begin
  3. 結(jié)果


    Log

項目地址:

遺留

  • AIDL里的in,out,inout三種類型
  • 由于上面只是知其然,還需要看官方文檔知其所以然下

Refrence

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

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

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