Adapter 的使用

1. 初步认识 Adapter

先看个例子,对 Adapter 有个直观印象和基本概念。Chameleon SDK 里打印日志使用的是默认的 android.util.Log, 如果想替换它可以按照如下步骤实行:

1.1 替换和注册

如果用户想替换 SDK 默认提供的日志打印,可以实现 CmlLoggerAdapter 接口,并按如下方式注册进 SDK:

  1. // 接口实现
  2. public class MyLoggerDefault implements CmlLoggerAdapter {
  3. @Override
  4. public void d(String tag, String msg) {
  5. // 这里实现自己的日志打印
  6. }
  7. ...
  8. }
  9. // 接口注册
  10. public class MyApplication extends Application implements ICmlConfig {
  11. @Override
  12. public void onCreate() {
  13. super.onCreate();
  14. CmlEngine.getInstance().init(this, this);
  15. }
  16. @Override
  17. public void configAdapter() {
  18. CmlEnvironment.setLoggerAdapter(new MyLoggerDefault()); // 注册自己的Adapter
  19. ...
  20. }
  21. ...
  22. }

以上就完成了日志打印能力的替换。

1.2 原理说明

SDK Adapter 定义和默认实现如下:

  1. // 日志接口定义
  2. public interface CmlLoggerAdapter {
  3. void d(String tag, String msg);
  4. ...
  5. }
  6. // 日志接口默认实现
  7. public class CmlLoggerDefault implements CmlLoggerAdapter {
  8. @Override
  9. public void d(String tag, String msg) {
  10. Log.d(tag, msg);
  11. }
  12. ...
  13. }

如果用户注册了自己的 Log Adapter 实现则优先使用,否则使用 SDK 默认提供的实现。

1.3 日志打印的使用

日志打印通过 CmlLogUtil 类调用,注册自己的 Logger Adapter 后,打印日志的相关方法就会回调到自定义的方法实现里,使用示例:

  1. // 日志打印
  2. public void launchPage(@NonNull Activity activity, String url, HashMap<String, Object> options) {
  3. if (TextUtils.isEmpty(url)) {
  4. CmlLogUtil.e(TAG, "CmlEngine launchPage, url is empty.");
  5. return;
  6. }
  7. ...
  8. }

2. Adapter 基本概念

  Adapter 的目的是定义一系列能力接口来隔离具体的实现,方便 SDK 使用者在需要时灵活替换成自己的实现。Chameleon SDK 框架层在使用 Adapter 相关能力时都是面向接口的,使用者只需要实现相关能力的 Adapter 接口并通过 SDK 注册接口进行注册,即可轻松替换成自己的实现并进行能力扩展。

  Chameleon SDK 并没有完整的实现所有 Adapter 接口,也就是说一部分有默认实现的 Adapter 可以直接使用,未提供默认实现的需要使用者自己实现,否则框架将无法使用对应的接口能力。

Chameleon SDK 定义了如下的 Adapter 接口

接口功能默认实现
ICmlDegradeAdapter降级
ICmlImgLoaderAdapter图片加载
CmlLoggerAdapter日志
ICmlNavigatorAdapterurl 跳转
ICmlStatisticsAdapter统计信息输出
ICmlWebSocketAdapterWebSocket
CmlHttpAdapterHttp 请求
CmlJsonAdapterjson 解析
CmlDialogAdapter对话框
CmlToastAdapter提示浮层
CmlStorageAdapterkey->value 存储
CmlThreadAdapter线程

2.1 重点 Adapter 说明

降级、对话框、提示浮层 Adapter 在 SDK 实际使用时替换可能性较大,分别说明。

2.1.1 降级

  ICmlDegradeAdapter 降级接口没有提供默认实现,《变色龙SDK使用范例》 示例里示范了如何实现一个降级处理类 CmlDegradeDefault。 CmlDegradeDefault 默认会关闭 native 渲染容器,并打开 Web 容器加载降级url。

  1. public class CmlDegradeDefault implements ICmlDegradeAdapter {
  2. @Override
  3. public DegradeViewWrapper getDegradeView(int degradeCode) {
  4. return new DegradeViewWrapper() {
  5. CmlWebView webView;
  6. @Override
  7. public View getView(@NonNull Context context) {
  8. webView = new CmlWebView(context);
  9. webView.onCreate();
  10. return webView;
  11. }
  12. @Override
  13. public void onDestroy() {
  14. if (null != webView) {
  15. webView.onDestroy();
  16. }
  17. }
  18. @Override
  19. public void loadURL(@NonNull Context context, @NonNull String url, @Nullable HashMap<String, Object> options) {
  20. if (null != webView) {
  21. webView.render(url, null);
  22. }
  23. }
  24. };
  25. }
  26. @Override
  27. public void degradeActivity(@NonNull Activity activity, @NonNull String url, @Nullable HashMap<String, Object> options, int degradeCode) {
  28. if (url.contains("?")) {
  29. url = url.substring(0, url.indexOf("?"));
  30. }
  31. CmlEngine.getInstance().launchPage(activity, url, null);
  32. }
  33. }

degradeActivity 会在如下降级场景发生时回调

  • 下载 JSBundle 失败
  • 解析 JSBundle 发生异常
  • 降级调试开关打开(在CmlEnvironment里设置)
  • 前端代码手动降级

2.1.2 对话框

此接口定义以下两种对话框能力

  • showAlert
  • showConfirm
    CmlModalTip 实现了此接口,通过 CmlModalModule 类暴露给 JS 侧调用,前端用法参考 Chameleon DOC API一章的 《交互反馈》

2.1.3 提示浮层

此接口定义以下浮层提示能力

  • showToast
    CmlModalTip 实现了此接口,通过 CmlModalModule 类暴露给 JS 侧调用,前端用法参考 Chameleon DOC API一章的 《交互反馈》

2.2 其他 Adapter 说明

2.2.1 图片加载

CmlDefaultImgLoaderAdapter ,默认使用 Glide,需要用户手动集成 Glide

2.2.2 日志打印

CmlLoggerDefault,默认使用系统 log 输出

2.2.3 跳转

默认使用 Intent.ACTION_VIEW 处理

2.2.4 统计信息输出

没有默认实现,不关心可以不用实现

2.2.5 WebSocket

CmlDefaultWebSocketAdapter,默认使用 OkHttp3,需要用户手动集成 OkHttp3

2.2.6 Http 请求

执行 http 请求,并监听 http 响应

2.2.7 json 解析

转换成 json 字符串和反解成 json 对象

2.2.8 key->value 存储

前端用法参考 Chameleon DOC API一章的 《数据存储》

2.2.9 线程

定义工作线程和 ui 线程