添加Flutter到現有應用

原文連接:flutter.dev/docs/develo…java

概述

使用Flutter對咱們現有的應用進行重構並非一件容易的事,針對這種狀況,Flutter能夠分次以庫或模塊的形式集成到現有應用,在應用中能夠對部分UI使用Flutter進行渲染。僅僅經過簡單的幾部,就能夠在咱們現有應用中引入Flutter強大的功能。android

在FlutterV1.12版本中,支持將全屏Flutter實例添加到現有應用中,目前有如下限制:緩存

  • 運行多個Flutter實例或局部Flutter UI可能會有不穩定的表現
  • 在後臺模式下使用Flutter依舊不成熟
  • 暫不支持打包Flutter庫到另外一個庫,以及集成多個Flutter庫到一個應用中

已支持的功能

添加Flutter到Android應用中

  • 在gradle腳本文件中添加相關配置便可自動引入和構建Flutter模塊

添加Flutter到iOS應用中

架構

添加Flutter到現有應用

基礎配置

Flutter能夠藉助gradle腳本以源碼形式集成到現有應用中,也可使用aar形式集成到現有應用。可使用Android Studio提供的插件來集成,也能夠用命令行來手動集成。app

注意:現有應用可能會支持mips和x86/x86_64架構,但Flutter目前使用AOT模式編譯庫僅支持armeabi-v7a和arm64-v8a架構,所以建議在gradle文件中使用abiFilters來限制支持的架構平臺,來避免出現丟失libflutter.so運行時異常。相關配置示例以下:ide

android {
  //...
  defaultConfig {
    ndk {
      // Filter for architectures supported by Flutter.
      abiFilters 'armeabi-v7a', 'arm64-v8a'
    }
  }
}
複製代碼

Flutter引擎有x86和x86_64版本,因此在使用模擬器調試時,Flutter會以JIT模式進行編譯運行。gradle

使用Android Studio集成Flutter

使用Android Studio能夠很方便的集成Flutter,藉助Android Studio,能夠將Android代碼和Flutter代碼放到一個文件目錄下,能夠繼續正常使用IntelliJ的系列插件如Dart代碼補全、熱重載、Widget分析器等等。‘優化

使用Android Studio集成Flutter須要Android Studio版本在3.6以上,Flutter IntelliJ插件版本在42以上。目前僅支持使用gradle腳本和源碼的方式集成,暫不支持使用aar的形式。ui

打開現有應用項目,在Android Studio的菜單File > New > New Module...中,能夠選擇建立一個新的Flutter Module或選擇已存在的Flutter Module。this

若是選擇建立新的Flutter Module,能夠在嚮導中配置該Module的名字、路徑等信息。

Android Studio插件會自動配置現有應用項目來依賴Flutter Module,如今項目已經能夠進行構建了。

tip:在項目Project視圖下能夠看到Flutter文件目錄,若是看不到多是以Android視圖查看的,調整視圖便可。

使用命令行手動集成Flutter

添加一個簡單Flutter Screen

下面介紹如何添加一個Flutter Screen到現有應用中,Flutter Screen能夠有普通的、不透明的、可透視的以及透明的幾種形式。

添加一個普通的Screen

一、添加FlutterActivity到清單文件中

在Android應用中,Flutter提供FlutterActivity來顯示相關UI,和其餘普通Activity同樣,FlutterActivity必須在清單文件中進行註冊,示例以下:

<activity android:name="io.flutter.embedding.android.FlutterActivity" android:theme="@style/LaunchTheme" android:configChanges="orientation|keyboardHidden|keyboard|screenSize|locale|layoutDirection|fontScale|screenLayout|density|uiMode" android:hardwareAccelerated="true" android:windowSoftInputMode="adjustResize" />
複製代碼

其中theme屬性的@style/LaunchTheme能夠替換成其餘任何普通的theme,theme的設定和Android系統的Chrome有關?如導航欄。

二、導航到FlutterActivity

在添加完清單文件後,能夠在任什麼時候候導航到FlutterActivity了,示例以下:

myButton.setOnClickListener(new OnClickListener() {
  @Override
  public void onClick(View v) {
    startActivity(
      FlutterActivity.createDefaultIntent(currentActivity)
    );
  }
});
複製代碼

上面的示例假設了Dart代碼的入口點在main()方法,Flutter路由路徑是/。Dart代碼的入口點並不能經過Intent來更改,可是初始化路由是能夠經過Intent來更改的,下面的示例演示瞭如何更改初始化路由:

myButton.addOnClickListener(new OnClickListener() {
  @Override
  public void onClick(View v) {
    startActivity(
      FlutterActivity
        .withNewEngine()
        .initialRoute("/my_route")
        .build(currentActivity)
      );
  }
});
複製代碼

能夠經過替換/my_route來更改指望的初始化路由。

使用withNewEngine() 方法,建立了擁有本身的FlutterEngine實例的FlutterActivity對象,這帶來一個FlutterEngine初始化耗時問題,優化的方法是預加載並緩存FlutterEngine,建立FlutterActivity對象時就無需再初始化FlutterEngine,來最小化FlutterActivity的耗時問題,關於此問題下文將會詳述。

三、(可選)緩存FlutterEngine

默認狀況下,每個FlutterActivity都會建立本身的FlutterEngine對象,每個FlutterEngine都須要加載耗時,也就是說打開每個標準的FlutterActivity時都會有一個延遲。爲了減小這個延遲,能夠在打開FlutterActivity前預加載FlutterEngine,須要使用的時候直接使用預加載好的FlutterEngine。

須要找一個合適的地方來預加載FlutterEngine,下面的示例在Application代碼中進行預加載:

public class MyApplication extends Application {
  @Override
  public void onCreate() {
    super.onCreate();
    // Instantiate a FlutterEngine.
    flutterEngine = new FlutterEngine(this);

    // Start executing Dart code to pre-warm the FlutterEngine.
    flutterEngine.getDartExecutor().executeDartEntrypoint(
      DartEntrypoint.createDefault()
    );

    // Cache the FlutterEngine to be used by FlutterActivity.
    FlutterEngineCache
      .getInstance()
      .put("my_engine_id", flutterEngine);
  }
}
複製代碼

傳遞給FlutterEngineCache的id能夠是任意值,只要確保和在FlutterActivity和FlutterFragment中取出FlutterEngine時使用的一致便可。下面來看看如何使用緩存的FlutterEngine。

myButton.addOnClickListener(new OnClickListener() {
  @Override
  public void onClick(View v) {
    startActivity(
      FlutterActivity
        .withCachedEngine("my_engine_id")
        .build(currentActivity)
      );
  }
});
複製代碼

當使用withCachedEngine方法時,注意id要和預加載FlutterEngine時保持一致。如今再打開FlutterActivity時,延遲問題就好不少了。

添加一個透明的Flutter Screen

大部分的Flutter UI是不透明的,可是有時候須要顯示成部分UI,好比Dialog、底部sheet等,Flutter支持透明的FlutterActivity。接下來看看如何實現透明的FlutterActivity。

一、使用透明主題

Android中須要使用特殊的屬性來渲染透明背景,以下:

<style name="MyTheme" parent="@style/MyParentTheme"> <item name="android:windowIsTranslucent">true</item> </style>
複製代碼
<activity android:name="io.flutter.embedding.android.FlutterActivity" android:theme="@style/MyTheme" android:configChanges="orientation|keyboardHidden|keyboard|screenSize|locale|layoutDirection|fontScale|screenLayout|density|uiMode" android:hardwareAccelerated="true" android:windowSoftInputMode="adjustResize" />
複製代碼

如今FlutterActivity支持了透明顯示了,接下來在打開時須要明確設置透明模式。

二、打開透明的FlutterActivity

打開透明背景的FlutterActivity,須要傳遞適當的BackgroundMode值給IntentBuilder,示例以下:

// Using a new FlutterEngine.
startActivity(
  FlutterActivity
    .withNewEngine()
    .backgroundMode(FlutterActivity.BackgroundMode.transparent)
    .build(context)
);

// Using a cached FlutterEngine.
startActivity(
  FlutterActivity
    .withCachedEngine("my_engine_id")
    .backgroundMode(FlutterActivity.BackgroundMode.transparent)
    .build(context)
);
複製代碼

如今就擁有了一個背景透明的FlutterActivity了。

添加一個Flutter Fragment

添加一個閃屏

相關文章
相關標籤/搜索