关于react-native:React-Native填坑之旅开启TurboModuleAndroid

FB宣传了N多年的新架构预计很多人都熟知了。最次要的改良就是从所有通信都通过异步Bridge的形式转为间接通信的形式。缩小音讯通信提早,进步性能。这其中最要害的就是TurboModule

开启TurboModule

开启TurboModule没有文档。只有就的原生module里夹杂着只言片语。一个例子就把开发同学带到react-native的代码里了。这阐明官网早就反对这个机制了,只是没正式官宣。然而复杂度太高,还须要对react-native的repo代码构造有理解。还有一个更好的例子react-native-animated。

这个我的项目大小适中,构造也不那么简单。很适宜类比钻研,实现。

实现NativeModule

和之前一样,继承ReactContextBaseJavaModule。具体能够参考这里。实现getName办法

增加ReactModule注解

这是和之前的形式不同的一点。

当初代码看起来是这样的:


@ReactModule(name = ReanimatedModule.NAME)
public class ReanimatedModule extends ReactContextBaseJavaModule {

  public static final String NAME = "ReanimatedModule";

  public ReanimatedModule(ReactApplicationContext reactContext) {
    super(reactContext);
  }

  @Override
  public String getName() {
    return NAME;
  }
}

最初增加ReactMethod

  @ReactMethod
  public void animateNextTransition(int tag, ReadableMap config) {
    mTransitionManager.animateNextTransition(tag, config);
  }

原生模块这部分就完事儿了。上面看看如何注册这个原生模块。

注册原生模块

这个局部就是重点了。上一节,和之前开发原生模块惟一不同的点就是多了一个@ReactModule的注解。这一部分不同的中央就有点多,依照官网的说法是比之前略微多了几步。

1. 增加一个继承了TurboReactPackage的类

public class ReanimatedPackage extends TurboReactPackage {}

2. 实现getModule办法

  @Override
  public NativeModule getModule(String name, ReactApplicationContext reactContext) {
    if (name.equals(ReanimatedModule.NAME)) {
      return new ReanimatedModule(reactContext);
    }

    return null;
  }

3. 实现getReactModuleInfoProvider

  @Override
  public ReactModuleInfoProvider getReactModuleInfoProvider() {
    Class<? extends NativeModule>[] moduleList =
        new Class[] {
          ReanimatedModule.class, ReanimatedUIManager.class,
        };

    final Map<String, ReactModuleInfo> reactModuleInfoMap = new HashMap<>();
    for (Class<? extends NativeModule> moduleClass : moduleList) {
      ReactModule reactModule = moduleClass.getAnnotation(ReactModule.class);

      reactModuleInfoMap.put(
          reactModule.name(),
          new ReactModuleInfo(        // *
              reactModule.name(),
              moduleClass.getName(),
              true,
              reactModule.needsEagerInit(),
              reactModule.hasConstants(),
              reactModule.isCxxModule(),
              TurboModule.class.isAssignableFrom(moduleClass)));
    }

    return new ReactModuleInfoProvider() {
      @Override
      public Map<String, ReactModuleInfo> getReactModuleInfos() {
        return reactModuleInfoMap;
      }
    };
  }

在这里Module的名字仍然表演了重要的角色,它是把前(JS)后(原生),在原生里注册的多个原生模块之间如何找到那个模块都须要这模块名称。所以在初始化ReactModuleInfo的时候第一个参数就是模块名称。

第三个参数canOverrideExistingModule,个别在你还有不是TurboModules的时候最好是设置为false

needEgerInit如果你须要这个模块懒加载的话设置为false。除非你要你的app在初始化的时候也一起初始化你的模块。这样会减少开机工夫。

hasConstant如果你的模块有常量导出的话设置为true

isCxxModuletrue如果代码都是C代码。

isTurboModule如果以后模块是turbo module设置为true。不是为false。这个参数在这里是因为ReactModuleInfo不是只服务于turbo module的。

4. 在Application里注册Package

public class MainApplication extends Application implements ReactApplication {

  private final ReactNativeHost mReactNativeHost = new ReactNativeHost(this) {
    @Override
    public boolean getUseDeveloperSupport() {
      return BuildConfig.DEBUG;
    }

    @Override
    protected List<ReactPackage> getPackages() {
      return Arrays.<ReactPackage>asList(
          // ...
          new ReanimatedPackage(), //*
          // ...
      );
    }
}

在办法getPackages()里注册ReanimatedPackage()对象。

总结

FB对React Native架构的优化次要集中在优化性能。在具体的开发流动里,次要就是利用turbo module来应用新架构的优化。放慢开机速度,让动画更晦涩,让长列表滚动更加晦涩。

评论

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

这个站点使用 Akismet 来减少垃圾评论。了解你的评论数据如何被处理