上一篇文章,講解了路由框架實現的原理,並實現了基本的路由框架 頁面路由的跳轉 Android元件化專題 - 路由框架原理。
本篇文章來對基礎的路由框架進階,來實現模組間的業務通訊功能。
我們來看以下實現的效果圖:
app --> module1 | module1 --> module2 |
---|---|
首先我們先回顧,路由框架的設計思路,如下圖:
- 通過註解 Activity 類,註解處理器處理註解(APT)動態生成路由資訊。
- 收集路由:通過定義的包名,找到所有動態生成的類,將路由資訊儲存到本地倉庫 (rootMap).
- 頁面跳轉:根據註解的路由地址,從本地倉庫中找到相關的路由資訊,獲取到要跳轉的類,然後實現跳轉。
路由框架的實現思路很容易理解,建議手擼一遍,基本掌握這種實現思路。
模組間的業務通訊
如何在路由框架的基礎上擴充套件模組間的業務通訊呢?
看下圖設計思路:
只要弄懂了路由框架的原理,模組間的業務通訊就很容易實現了。
我們繼續在上一遍文章的程式碼擴充套件。
- 修改primrouter-compiler 包中的 RouterProcessor 類 在之前只有Activity類的基礎上,加上一個Service型別
//獲得Activity的型別
TypeElement activity = elementUtils.getTypeElement(Consts.Activity);
//獲取Service的型別
TypeElement service = elementUtils.getTypeElement(Consts.Service);
//只能指定的類上面使用
if (typeUtils.isSubtype(typeMirror, activity.asType())) {
//儲存路由相關的資訊
routerMeta = new RouterMeta(RouterMeta.Type.ACTIVITY, annotation, element);
} else if (typeUtils.isSubtype(typeMirror, service.asType())) {
//儲存路由相關的資訊
routerMeta = new RouterMeta(RouterMeta.Type.SERVICE, annotation, element);
} else {
throw new RuntimeException("Just Support Activity Router!");
}
複製程式碼
Service 類是在primrouter-core 核心庫中的一個介面類
public static final String Service = "com.primrouter_core.interfaces.IService";
複製程式碼
這個空介面,就是為了實現業務間的通訊
public interface IService {
}
複製程式碼
- 修改primrouter-core 庫中的PrimRouter 類
在生成跳卡的方法中擴充套件如下程式碼,實際上就是將IService 的具體實現存到JumpCard 中去。
private void produceJumpCard(JumpCard card){
if{
........
} else {
//設定要跳轉的類
card.setDestination(routerMeta.getDestination());
//設定要跳轉的型別
card.setType(routerMeta.getType());
switch (routerMeta.getType()) {
case SERVICE:
Class<?> destination = routerMeta.getDestination();
IService iService = Depository.serviceMap.get(destination);
if (iService == null) {
iService = (IService) destination.getConstructor().newInstance();
Depository.serviceMap.put(destination, iService);
}
card.setService(iService);
break;
default:
break;
}
}
}
複製程式碼
然後直接返回IService 轉換成 IService 的子類。
public Object navigation(Context context, final JumpCard jumpCard, final int requestCode, Object o1) {
..........
..........
..........
case SERVICE:
Log.e(TAG, "navigation: " + jumpCard.getService());
return jumpCard.getService();
}
複製程式碼
- 修改base庫,base 庫是所有模組都必須引入的基礎庫
extends IService
public interface TestService extends IService {
void test(Context context,String s);
}
複製程式碼
然後哪個模組需要TestService業務邏輯,就實現具體的TestService,並註解@Router(path),
app:
@Router(path = "/app/service")
public class AppService implements TestService {
@Override
public void test(Context context, String s) {
Toast.makeText(context, "我是app,我是被:" + s + "模組呼叫的,模組間通訊測試成功", Toast.LENGTH_SHORT).show();
}
}
複製程式碼
module1:
@Router(path = "/module1/service")
public class Module1Service implements TestService {
private static final String TAG = "Module1Service";
@Override
public void test(Context context, String s) {
Toast.makeText(context, "我是Module1,我是被:" + s + "模組呼叫的,模組測試通訊成功", Toast.LENGTH_SHORT).show();
}
}
複製程式碼
module2:
@Router(path = "/module2/service")
public class Module2Service implements TestService {
@Override
public void test(Context context, String s) {
Toast.makeText(context, "我是Module2,我是被:" + s + "模組呼叫的,模組測試通訊成功", Toast.LENGTH_SHORT).show();
}
}
複製程式碼
呼叫方式: 可以在任意模組呼叫
TestService testService = (TestService) PrimRouter.getInstance().jump("/module1/service").navigation();
testService.test(this, "app");
複製程式碼
執行效果如下圖所示:
Android的元件化專題: 元件化配置
下一篇:Activity跳轉引數自動注入和Fragment的跳轉。