[React Native] Android 白屏优化

APP是原生嵌入一个React Native界面

背景

按官方实例集成了一个React Native界面,但每次打开都感觉等待时间有点长,会有白屏状态。这对于强迫症来说简直不能忍。于是决定优化。

效果

优化前的效果,白屏时间较长。

优化前

优化后,白屏时间明显变短。

优化后

原因

当Android要运行React Native时,需要先加载JSBundle,这块是比较耗时的。
之前的做法是在打开界面的时候才去加载,所以会慢一拍。
优化之后,在App启动时,就初始化JSBundle,然后在RN界面直接使用。

解决方案

创建一个RN加载器的单利


import android.app.Activity;
import android.app.Application;
import android.content.Context;
import android.os.Bundle;

import com.facebook.react.ReactInstanceManager;
import com.facebook.react.ReactInstanceManagerBuilder;
import com.facebook.react.ReactRootView;
import com.facebook.react.common.LifecycleState;
import com.facebook.react.modules.core.DefaultHardwareBackBtnHandler;
import com.prance.lib.react.pack.MyReactPackage;

/**
 * JSBundle加载唯一实例
 * <p>
 * Created by bingbing on 2017/5/9.
 */

public class MyReactInstanceManager {

    private static MyReactInstanceManager mInstance;

    private ReactInstanceManager mReactInstanceManager;

    public static MyReactInstanceManager getInstance() {
        if (mInstance == null) {
            synchronized (MyReactInstanceManager.class) {
                if (mInstance == null) {
                    mInstance = new MyReactInstanceManager();
                }
            }
        }
        return mInstance;
    }

    /**
     * 初始化
     *
     * @param context
     */
    public void init(Context context) {
        getReactInstanceManager(context);
    }

    /**
     * 初始化 ReactInstanceManager
     * 预加载jsBundle
     * @param context
     * @return
     */
    public ReactInstanceManager getReactInstanceManager(Context context) {

        Application application = (Application) context.getApplicationContext();

        if (mReactInstanceManager == null) {
            ReactInstanceManagerBuilder builder = ReactInstanceManager.builder()
                    .setApplication(application)
                    .setBundleAssetName("index.android.bundle")
                    .setJSMainModuleName("index.android")
                    .setUseDeveloperSupport(false)
                    .addPackage(new MyReactPackage());

            //这里注意!!一定要是LifecycleState.BEFORE_CREATE
            //这样当正式加载的时候,才可以获取到mCurrentActivity的引用
            builder.setInitialLifecycleState(LifecycleState.BEFORE_CREATE);

            mReactInstanceManager = builder.build();

            //预加载!!!
            mReactInstanceManager.createReactContextInBackground();
        }

        return mReactInstanceManager;
    }

    /**
     * 开启开发者菜单
     */
    public void showDevOptionsDialog() {
        mReactInstanceManager.showDevOptionsDialog();
    }

    /**
     * 返回键
     */
    public void onBackPressed() {
        mReactInstanceManager.onBackPressed();
    }

    /**
     * 在Activity的onResume中调用
     * @param activity
     * @param handler
     */
    public void onHostResume(Activity activity, DefaultHardwareBackBtnHandler handler) {
        mReactInstanceManager.onHostResume(activity, handler);
    }

    /**
     * 在Activity的onPause中调用
     * 
     * @param activity
     */
    public void onHostPause(Activity activity) {
        mReactInstanceManager.onHostPause(activity);
    }

    /**
     * 创建ReactRootView实例,并启动React Native
     * @param context
     * @param initialProps
     * @return
     */
    public ReactRootView getRootView(Context context, Bundle initialProps) {

        ReactRootView view = new ReactRootView(context);
        view.startReactApplication(mReactInstanceManager, "App", initialProps);
        return view;
    }

    /**
     * 销毁RootView,在Activity的onDestroy中调用
     * @param view
     */
    public void destroy(ReactRootView view) {
        mReactInstanceManager.detachRootView(view);
    }

    /**
     * 销毁Manager,在程序退出或者最后一个RN界面结束时调用
     */
    public void destroy() {
        mReactInstanceManager.onHostDestroy();
    }

}

初始化

  1. 在Application或者第一个界面调用
MyReactInstanceManager.getInstance().init(this);
  1. 在Activity中调用
ReactRootView rootView = MyReactInstanceManager.getInstance().getRootView(mActivity, initialProps);
setContentView(rootView);

万事大吉

评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值