Комментарии (1)
Ответ сгенерирован нейросетью и может содержать ошибки
Как запускать FlutterActivity
FlutterActivity — это основной компонент Android для интеграции Flutter кода в Android приложение. Это Activity, которая загружает и отображает Flutter UI. Это особенно полезно при встраивании Flutter в существующее Android приложение, написанное на Kotlin/Java.
Основной способ — запуск через Intent
Самый простой способ запустить FlutterActivity:
// На стороне Dart/Flutter — если нужно передать данные
import 'package:flutter/services.dart';
class MainActivity extends FlutterActivity {
// По умолчанию ничего не нужно делать
// FlutterActivity автоматически загружает main.dart
}
// На стороне Kotlin (Android)
import io.flutter.embedding.android.FlutterActivity
import android.content.Intent
import android.os.Bundle
class MyAndroidActivity : AppCompatActivity() {
fun launchFlutterActivity() {
// Способ 1: простой запуск
startActivity(
Intent(this, FlutterActivity::class.java)
)
// Способ 2: запуск с route
startActivity(
FlutterActivity
.withNewEngine()
.initialRoute("/home")
.build(this)
)
}
}
Запуск с передачей данных (Arguments)
Частый случай — передать данные из Android в Flutter:
// Android (Kotlin)
fun launchFlutterWithData() {
val intent = FlutterActivity
.withNewEngine()
.initialRoute("/profile")
.build(this)
// Передаём данные через Bundle
intent.putExtra("userId", "12345")
intent.putExtra("userName", "John Doe")
startActivity(intent)
}
// Flutter (Dart)
import 'dart:async';
import 'package:flutter/services.dart';
future<void> main() async {
WidgetsFlutterBinding.ensureInitialized();
// Получить данные из Intent
final args = await MethodChannel('com.example.app/data')
.invokeMethod('getIntentData');
runApp(MyApp(args: args));
}
Способ с использованием Engine
Для более сложных сценариев можно использовать явное управление FlutterEngine:
// Android (Kotlin)
import io.flutter.embedding.android.FlutterActivity
import io.flutter.embedding.engine.FlutterEngine
class MainActivity : FlutterActivity() {
companion object {
// Постоянный Engine, чтобы переиспользовать между Activities
private var flutterEngine: FlutterEngine? = null
}
override fun configureFlutterEngine(flutterEngine: FlutterEngine) {
super.configureFlutterEngine(flutterEngine)
// Сохраняем Engine
MainActivity.flutterEngine = flutterEngine
// Настраиваем каналы коммуникации
MethodChannel(flutterEngine.dartExecutor.binaryMessenger, "com.example/channel")
.setMethodCallHandler { call, result ->
when (call.method) {
"getData" -> {
val data = mapOf("status" to "success", "value" to 42)
result.success(data)
}
else -> result.notImplemented()
}
}
}
}
// Flutter (Dart) — использование MethodChannel
import 'package:flutter/services.dart';
const platform = MethodChannel('com.example/channel');
class MyWidget extends StatefulWidget {
@override
_MyWidgetState createState() => _MyWidgetState();
}
class _MyWidgetState extends State<MyWidget> {
String _data = 'Unknown';
Future<void> _getData() async {
try {
final result = await platform.invokeMethod<Map>('getData');
setState(() {
_data = result?['value']?.toString() ?? 'Unknown';
});
} catch (e) {
setState(() {
_data = 'Error: $e';
});
}
}
@override
Widget build(BuildContext context) {
return Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Text('Data from Android: $_data'),
ElevatedButton(
onPressed: _getData,
child: Text('Get Data'),
),
],
),
);
}
}
Запуск FlutterActivity из Java
// Java (старый стиль)
import io.flutter.embedding.android.FlutterActivity;
import android.content.Intent;
public class MainActivity extends AppCompatActivity {
public void launchFlutterScreen() {
Intent intent = new Intent(this, FlutterActivity.class);
// Можно добавить extra параметры
intent.putExtra("route", "/details");
startActivity(intent);
}
}
Жизненный цикл и AndroidManifest
В AndroidManifest.xml нужно заявить FlutterActivity:
<!-- AndroidManifest.xml -->
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
<application>
<!-- Основная Activity -->
<activity
android:name=".MainActivity"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<!-- FlutterActivity для встраивания Flutter -->
<activity
android:name="io.flutter.embedding.android.FlutterActivity"
android:exported="true"
android:theme="@style/LaunchTheme" />
</application>
</manifest>
Лучшие практики
1. Переиспользование Engine
Для улучшения производительности лучше переиспользовать один Engine:
// Глобальный Engine (singleton)
object FlutterEngineManager {
private var engine: FlutterEngine? = null
fun getEngine(context: Context): FlutterEngine {
if (engine == null) {
engine = FlutterEngine(context)
engine?.navigationChannel?.setInitialRoute("/")
}
return engine!!
}
fun destroy() {
engine?.destroy()
engine = null
}
}
2. Обработка результатов
Если нужно получить результат из FlutterActivity:
// Запуск с ожиданием результата
startActivityForResult(
Intent(this, FlutterActivity::class.java),
REQUEST_CODE_FLUTTER
)
// Обработка результата
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
if (requestCode == REQUEST_CODE_FLUTTER && resultCode == RESULT_OK) {
val result = data?.getStringExtra("result")
// Обработать результат
}
}
// Flutter — отправка результата
SystemChannels.platform.invokeMethod('SystemNavigator.pop', result);
3. Управление памятью
// Правильно очищать Engine при завершении
override fun onDestroy() {
// FlutterActivity автоматически очищает Engine
super.onDestroy()
}
Сравнение подходов
FlutterActivity с новым Engine:
- Простой запуск
- Каждый раз создаётся новый Engine (медленнее)
- Хорошо для одноразовых переходов
FlutterActivity с кэшированным Engine:
- Лучшая производительность
- Требует управления lifecycle
- Рекомендуется для частых переходов
Типичный сценарий: встраивание Flutter в существующее приложение
// MainActivity на Kotlin
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
// Android UI
findViewById<Button>(R.id.button).setOnClickListener {
// Запускаем Flutter когда нужно
launchFlutter()
}
}
private fun launchFlutter() {
startActivity(
FlutterActivity
.withNewEngine()
.initialRoute("/flutter_screen")
.build(this)
)
}
}
Функция FlutterActivity решает проблему интеграции Flutter в существующие приложения, позволяя плавный переход между Android и Flutter частями приложения.