2016-02-14 11 views
5

Ich arbeite an einem großen bestehenden Android- und iOS-Projekt, und mein Team würde gerne nativ reagieren. Zunächst möchten wir ein einzelnes Feature in RN implementieren, da wir nicht in der Lage sind, das gesamte Projekt auf einmal zu migrieren.Was ist der richtige Weg, um einer vorhandenen Android-Anwendung eine einzelne React Native-Ansicht hinzuzufügen?

Es ist mir gelungen, eine RN-Ansicht erfolgreich hinzuzufügen, sowohl von einem lokalen Knotenserver als auch von einer JS-Bundle-Datei im Ordner "Assets", aber es fühlt sich ein bisschen hacky an. Ich weiß, dass dies auf iOs unterstützt wird, aber ich konnte in den Dokumenten nichts über die Integration in ein bestehendes Android-Projekt finden. Hier ist der Kern dessen, was ich kam mit:

public class ReactNativeView extends FrameLayout { 

    private static final String COMPONENT_NAME = "AwesomeProject"; 
    // Path of our RN module relative to project root 
    private static final String MODULE_NAME = "react-sources/index.android" 

    public ReactNativeView(Context Context) { 
     super(context); 
    } 

    @Override 
    protected void onAttachedToWindow() { 
     super.onAttachedToWindow(); 

     ReactInstanceManager.Builder builder = ReactInstanceManager.builder() 
       .setApplication(AppDelegate.sharedApplication()) 
       .addPackage(new MainReactPackage()) 
       .setUseDeveloperSupport(BuildConfig.DEBUG) 
       .setInitialLifecycleState(LifecycleState.BEFORE_RESUME); 

     if (BuildConfig.USE_RN_LOCAL_SERVER) { 
      // Set module name to be loaded from local node server 
      builder.setJSMainModuleName(MODULE_NAME); 
     } else { 
      Uri uri = AssetsManager.getInstance().getJsBundleUri(); 
      // Load bundled jsBundle 
      builder.setJSBundleFile(uri.getPath()); 
     } 

     ReactInstanceManager reactInstanceManager = builder.build(); 
     MainActivity mainActivity = MainActivity.getMainActivity(); 

     setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT)); 
     ReactRootView reactRootView = 
      new ReactRootView(AppDelegate.sharedApplication().getTopActivity()); 
     // Is it really necessary to call 'startReactApplication' each time we want to render a react component? 
     reactRootView.startReactApplication(reactInstanceManager, COMPONENT_NAME, null); 

     addView(reactRootView); 
     // After the view is added to the hierarchy we call the manager's 'onResume' function 
     // to show the react view 
     reactInstanceManager.onResume(mainActivity, mainActivity); // <-- What kind of sorcery is this?! 
    } 
} 

Und ich habe auch eine Variable zur BuildConfig hinzugefügt, die bestimmt, welche JS Bündel zu verwenden:

buildTypes { 
    debug { 
     buildConfigField "boolean", "USE_RN_LOCAL_SERVER", "true" // load from local server 
    } 
    release { 
     minifyEnabled true 
     proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' 
     buildConfigField "boolean", "USE_RN_LOCAL_SERVER", "false" 
    } 
} 

Dies ist eine komplette Hack ist. Rufen Sie startReactApplication auf, wenn das, was ich gerade tue, einfach eine Ansicht zum Bildschirm hinzufügt, fühlt sich unangenehm an. Fehle ich eine API oder ist dies noch kein unterstütztes Szenario?

Antwort

0

Haben Sie die RN official doc zu diesem Thema überprüft?

Es zeigt Ihnen, wie Sie eine RN-Ansicht in einer Java-codierten Android-App sauber ausführen.

+1

Die Dokumentation zeigt, wie eine Reactive View integriert wird, die eine Wurzel einer neuen App ist. Es gibt keine Beispiele dafür, wie mehrere RN-Ansichten hinzugefügt werden, die dieselbe RN-Bridge verwenden (was unter iOS möglich ist). Es gibt ein [offenes Problem] (https://github.com/facebook/react-native/issues/1398) darüber in der RN GitHub Seite. –

0

So scheinbar startReactApplication aufrufen ist in der Tat zu korrigieren Weg zu gehen. Wenn jemand an einer vollständigeren und besser organisierten Lösung interessiert ist, können Sie einen Blick auf werfen.

Verwandte Themen