# flutter_module_demo **Repository Path**: jiodg45/demo_module ## Basic Information - **Project Name**: flutter_module_demo - **Description**: demo for flutter module - **Primary Language**: Unknown - **License**: Not specified - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2021-08-24 - **Last Updated**: 2021-09-12 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # Android module 创建`my_module`和`demo_app` ``` . ├── README.md ├── demo_app │ ├── android_app //android host app, 编译构建android module | .... │ │ └── settings.gradle │ └── ios_app //ios host app, 编译构建ios module │ ├── ios_app | ..... └── my_module ├── README.md ├── build │ └── host │ └── outputs │ └── repo //flutter android module的构建产物路径,包含vm snapshot, .so,assets ├── lib │ └── main.dart ├── my_module.iml ├── .ios //iOS module 调试和构建 ├── .android //android module 调试和构建 ├── my_module_android.iml ├── pubspec.lock ├── pubspec.yaml //flutter module相关依赖plugin和package配置 └── test └── widget_test.dart ``` ## Git设置 上传git默认会忽略`.ios`和`.android`,在`my_module`下通过以下命令重新生成模版,注意`org`参数保持一致 ``` flutter create --template=module --org com.jiodg45 . ``` Note: org用于指定 java包名字和ios的organization ```text (defaults to "A new Flutter project.") --org The organization responsible for your new Flutter project, in reverse domain name notation. This string is used in Java package names and as prefix in the iOS bundle identifier. ``` ## 构建android module 1. 通过添加AAR(Anrdoid Archive)依赖到host app中, follow those steps ``` 1. Open /app/build.gradle 2. Ensure you have the repositories configured, otherwise add them: String storageUrl = System.env.FLUTTER_STORAGE_BASE_URL ?: "https://storage.googleapis.com" repositories { maven { url '/Users/qxq4633/demo_module/my_module/build/host/outputs/repo' } maven { url "$storageUrl/download.flutter.io" } } 3. Make the host app depend on the Flutter module: dependencies { debugImplementation 'jiodg45.my_module:flutter_debug:1.0' profileImplementation 'jiodg45.my_module:flutter_profile:1.0' releaseImplementation 'jiodg45.my_module:flutter_release:1.0' } 4. Add the `profile` build type: android { buildTypes { profile { initWith debug } } } ``` `cd my_module && flutter build aar` 2. 将flutter_module作为一个子工程添加到host app的`settings.gradle`中 添加`settings.gradle`依赖 ``` // Include the host app project. include ':app' // assumed existing content setBinding(new Binding([gradle: this])) // new evaluate(new File( // new settingsDir.parentFile, // new 'my_flutter/.android/include_flutter.groovy' // new )) // new ``` 添加`flutter`依赖 ``` dependencies { implementation project(':flutter') } ``` 3. 从activity加载flutter module 使用Application提前初始化flutterEngine,减少延迟 ```java public class MainApplication extends Application { private final String engineId = "engine_id"; public FlutterEngine flutterEngine; @Override public void onCreate() { super.onCreate(); // java.lang.AssertionError: DartEntrypoints can only be created once a FlutterEngine is created. // DartExecutor.DartEntrypoint dartEntrypoint = DartExecutor.DartEntrypoint.createDefault(); flutterEngine = new FlutterEngine(this,null, false); //自定义的flutter engine必须要提前设置路由 flutterEngine.getNavigationChannel().setInitialRoute("/"); //指定默认的dartEntryPoint, main函数 // flutterEngine.getDartExecutor().executeDartEntrypoint(dartEntrypoint); FlutterInjector.instance().flutterLoader().startInitialization(this); String flutterAppPath = FlutterInjector.instance().flutterLoader().findAppBundlePath(); DartExecutor.DartEntrypoint customEntryPoint = new DartExecutor.DartEntrypoint(flutterAppPath, "custommain"); flutterEngine.getDartExecutor().executeDartEntrypoint(customEntryPoint); FlutterEngineCache.getInstance().put(engineId, flutterEngine); } } ``` Note: `MainApplication`需设置为`public`添加到`AndroidManifest.xml`,`FlutterActivity`也需提前在`AndroidManifest`申明 初始化`FlutterActivity`并展示 ``` Intent intent = FlutterActivity .withCachedEngine("engine_id") .build(currentActivity); startActivity(intent); ``` ## 构建ios module 1. 使用`ios module`生成的`podhelper.rb`脚本,将生成的`module`产物集成到工程 ```ruby # Uncomment the next line to define a global platform for your project # platform :ios, '9.0' # pod 'Flutter', :podspec => '/Users/qxq4633/demo_module/my_module/Flutter/Debug/Flutter.podspec' flutter_application_path = '../../my_module' load File.join(flutter_application_path, '.ios', 'Flutter', 'podhelper.rb') target 'ios_app' do # Comment the next line if you don't want to use dynamic frameworks use_frameworks! install_all_flutter_pods(flutter_application_path) # Pods for ios_app target 'ios_appTests' do inherit! :search_paths # Pods for testing end target 'ios_appUITests' do # Pods for testing end end ``` 2. 通过`flutter build ios-framework`生成对应的framework,并将其`embed`到工程中 ``` flutter build ios-framework --output=some/path/MyApp/Flutter/ ``` 3. Note,为了方便dark进行多个dns服务解析(devTools和hotReload)需要添加ios的本地网络权限`NSLocalNetworkUsageDescription` 设置iOS的entryPoint ``` import UIKit import Flutter import FlutterPluginRegistrant class ViewController: UIViewController { var engine: FlutterEngine! override func viewDidLoad() { super.viewDidLoad() setupEngine() setupView() } func setupEngine() { let dartProjectPath = Bundle.main.bundlePath + "/App.framework" let dartBundle = Bundle.init(path: dartProjectPath) let dartProject = FlutterDartProject.init(precompiledDartBundle: dartBundle) engine = FlutterEngine.init(name: "engine_id", project: dartProject, allowHeadlessExecution: true, restorationEnabled: false) GeneratedPluginRegistrant.register(with: engine) } func setupView() { let gesture = UITapGestureRecognizer(target: self, action: #selector(ViewController.showCustomEntryPoint(gesture:))) gesture.numberOfTapsRequired = 1 · } @objc func showCustomEntryPoint(gesture: UITapGestureRecognizer){ if (engine.run(withEntrypoint: "custommain", initialRoute: "/")){ let vc = FlutterViewController.init(engine: engine, nibName: nil, bundle: nil) vc.modalPresentationStyle = .fullScreen self.present(vc, animated: true, completion: nil) } else { print("failed run entry pint `custommain and initial route /`") } } } ``` ## 参考 https://flutter.dev/docs/development/add-to-app/ios/project-setup