Flutter平台视图集成插件simple_platform_view的使用
Flutter平台视图集成插件simple_platform_view的使用
A Flutter插件,用于直接将平台视图集成到Flutter视图层次结构中,旨在提供最佳性能。
设计
为了实现良好的性能,该插件遵循特定的设计方法:
渲染
- Flutter UI被渲染为单个视图。
- 保持栅格化任务在栅格线程上。
- 这种方法比混合合成模式(将Flutter UI渲染为多个视图并将栅格化任务移动到平台线程)提供了更好的性能。
- 基本上,该插件继续像没有平台视图一样渲染Flutter UI。
平台视图
- 平台视图将按原生应用程序的方式进行渲染。
- 创建平台视图后,它将位于Flutter视图之后。
- 启用平台视图的可见性包括以下步骤:
- 将FlutterSurfaceView转换为FlutterImageView以支持位置同步。
- 清除平台视图下方的内容。
- 需要一种机制将触摸事件从前端视图转发到平台视图。
结果
使用此插件的一些考虑和结果:
-
自定义引擎是必需的:
- 该插件需要对引擎本身进行修改。因此,在Android上运行时,您需要使用修改后的版本的Flutter(参见[入门指南])。
- 虽然最好使用官方Flutter版本,但目前还不可能这样做。
- 自定义框架仓库:[自定义框架仓库链接]
- 自定义引擎仓库:[自定义引擎仓库链接]
- 构建脚本:[构建脚本链接]
-
内容限制:只有绘制在平台视图顶部的内容才会可见,其下方的内容将被清除。
- 如果平台视图是透明的,则底层小部件的缺失会变得明显。
- 但是,如果平台视图是不透明的,则无需渲染背景内容。
- 因此,此模式仅支持不透明的平台视图。
-
FlutterImageView限制:
- 该插件使用FlutterImageView来渲染Flutter UI。在Android 10之前,FlutterImageView每帧都会将每个Flutter帧从图形内存复制到主内存,然后再复制回GPU纹理。由于这种复制每帧发生一次,整个Flutter UI的性能可能会受到影响。
- 从Android 10开始,FlutterImageView使用HardwareBuffer,性能更好。
-
混合合成组合:将此模式与混合合成模式结合使用可能导致意外行为,因此在同时集成多种合成模式时应谨慎。
-
视图层次结构:该插件直接修改视图层次结构,这可能会导致与Flutter本身的冲突。
- 如果您正在使用虚拟显示模式或混合合成纹理层模式且没有问题,则不需要此插件。
- 如果您正在使用混合合成模式并且遇到性能问题,可以尝试使用此插件。
入门
平台 | 状态 |
---|---|
Android | ✅ |
iOS | ❌ |
主机操作系统支持 | 状态 |
---|---|
MacOS | ✅ |
Windows | ✅ |
Linux | ❌ |
下载自定义引擎
下载自定义Flutter版本 这里。
解压下载的 flutter.zip
文件。
首次运行以下命令以下载自定义引擎工件:
$ path_to_custom_version/flutter/bin/flutter doctor
然后使用它就像正常安装Flutter一样:
$ path_to_custom_version/flutter/bin/flutter build apk
对于其他平台上的应用构建,您应该使用 官方Flutter版本。
安装
在您的 pubspec.yaml
文件中添加以下依赖项:
dependencies:
simple_platform_view:
使用
Android:
要使用此插件,只需将 AndroidView
小部件替换为 SimpleAndroidView
:
import 'package:simple_platform_view/simple_platform_view.dart';
[@override](/user/override)
Widget build(BuildContext context) {
return SimpleAndroidView(
viewType: "your_view_type",
onPlatformViewCreated: (id) {
// 您的回调
},
creationParams: {},
creationParamsCodec: const StandardMessageCodec(),
);
}
如果您在ScrollView中使用 SimpleAndroidView
,请向您的 MaterialApp
添加以下内容以防止 StretchingOverscrollIndicator
问题:
import 'package:simple_platform_view/simple_platform_view.dart';
[@override](/user/override)
Widget build(BuildContext context) {
return MaterialApp(
// 解决StretchingOverscrollIndicator问题
scrollBehavior: SimplePlatformViewScrollBehavior(),
);
}
如果您尝试与其他插件一起使用,请克隆它们并替换实现为 SimpleAndroidView
。有关更多详细信息,请参阅示例。
iOS:
iOS不受支持
由其他插件使用:
插件 |
---|
simple_google_maps_flutter |
simple_webview_flutter |
示例代码
以下是 main.dart
的示例代码:
// import 'package:firebase_core/firebase_core.dart';
// import 'package:firebase_crashlytics/firebase_crashlytics.dart';
import 'package:flutter/material.dart';
import 'package:simple_platform_view/simple_platform_view.dart';
import 'package:simple_platform_view_example/screen/select_screen.dart';
void main() async {
WidgetsFlutterBinding.ensureInitialized();
// await Firebase.initializeApp();
// FlutterError.onError = FirebaseCrashlytics.instance.recordFlutterFatalError;
runApp(const MyApp());
}
class MyApp extends StatefulWidget {
const MyApp({super.key});
[@override](/user/override)
State<MyApp> createState() => _MyAppState();
}
class _MyAppState extends State<MyApp> {
[@override](/user/override)
void initState() {
super.initState();
}
[@override](/user/override)
Widget build(BuildContext context) {
return MaterialApp(
// theme: ThemeData(platform: TargetPlatform.iOS),
home: const SelectScreen(),
scrollBehavior: SimplePlatformViewScrollBehavior(),
);
}
}
更多关于Flutter平台视图集成插件simple_platform_view的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html
更多关于Flutter平台视图集成插件simple_platform_view的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html
在Flutter中,平台视图(Platform Views)允许你嵌入原生的Android和iOS视图到你的Flutter应用中。simple_platform_view
是一个示例插件,用于展示如何在Flutter中集成平台视图。虽然 simple_platform_view
本身可能不是一个真实存在的官方插件,但我们可以基于这个概念编写一个类似的插件来演示其使用。
以下是如何创建一个简单的Flutter插件来集成平台视图的基本步骤,以及相应的代码案例。
1. 创建Flutter插件
首先,你需要创建一个Flutter插件项目。你可以使用以下命令:
flutter create --org com.example --template=plugin simple_platform_view
2. 配置Android平台视图
在 android/src/main/java/com/example/simple_platform_view/SimplePlatformViewFactory.java
中实现一个 PlatformViewFactory
:
package com.example.simple_platform_view;
import android.content.Context;
import android.view.View;
import android.widget.TextView;
import io.flutter.embedding.engine.plugins.FlutterPlugin;
import io.flutter.embedding.engine.plugins.activity.ActivityAware;
import io.flutter.embedding.engine.plugins.activity.ActivityPluginBinding;
import io.flutter.plugin.common.BinaryMessenger;
import io.flutter.plugin.platform.PlatformView;
import io.flutter.plugin.platform.PlatformViewFactory;
public class SimplePlatformViewFactory extends PlatformViewFactory implements FlutterPlugin, ActivityAware {
private ActivityPluginBinding activityBinding;
@Override
public PlatformView create(Context context, int id, Object args) {
return new SimplePlatformView(context, activityBinding.getActivity());
}
@Override
public void onAttachedToEngine(FlutterPluginBinding flutterPluginBinding) {
// No-op
}
@Override
public void onDetachedFromEngine(FlutterPluginBinding flutterPluginBinding) {
// No-op
}
@Override
public void onAttachedToActivity(ActivityPluginBinding binding) {
activityBinding = binding;
}
@Override
public void onDetachedFromActivityForConfigChanges() {
activityBinding = null;
}
@Override
public void onReattachedToActivityForConfigChanges(ActivityPluginBinding binding) {
activityBinding = binding;
}
@Override
public void onDetachedFromActivity() {
activityBinding = null;
}
private static class SimplePlatformView implements PlatformView {
private final View nativeView;
SimplePlatformView(Context context, android.app.Activity activity) {
nativeView = new TextView(context);
((TextView) nativeView).setText("Hello from Android Native View!");
}
@Override
public View getView() {
return nativeView;
}
@Override
public void dispose() {
// Clean up resources here if needed
}
}
}
3. 配置iOS平台视图
在 ios/Classes/SimplePlatformViewFactory.swift
中实现一个 FlutterPlatformViewFactory
:
import UIKit
import Flutter
public class SimplePlatformViewFactory: NSObject, FlutterPlatformViewFactory {
public func create(withFrame frame: CGRect,
viewIdentifier viewId: Int64,
arguments args: Any?) -> FlutterPlatformView {
return SimplePlatformView(frame: frame, viewId: viewId, arguments: args)
}
}
class SimplePlatformView: NSObject, FlutterPlatformView {
private let nativeView: UIView
init(frame: CGRect, viewId: Int64, arguments: Any?) {
self.nativeView = UIView(frame: frame)
let label = UILabel(frame: frame)
label.text = "Hello from iOS Native View!"
label.textAlignment = .center
self.nativeView.addSubview(label)
super.init()
}
public func view() -> UIView {
return nativeView
}
}
4. 注册插件
在 android/src/main/kotlin/com/example/simple_platform_view/SimplePlatformViewPlugin.kt
中注册工厂:
package com.example.simple_platform_view
import io.flutter.embedding.engine.plugins.FlutterPlugin
import io.flutter.embedding.engine.plugins.activity.ActivityAware
import io.flutter.embedding.engine.plugins.activity.ActivityPluginBinding
import io.flutter.plugin.platform.PlatformViewRegistry
class SimplePlatformViewPlugin: FlutterPlugin, ActivityAware {
override fun onAttachedToEngine(binding: FlutterPluginBinding) {
val registry = binding.platformViewRegistry
with(registry) {
registerViewFactory("simple_platform_view", SimplePlatformViewFactory())
}
}
override fun onDetachedFromEngine(binding: FlutterPluginBinding) {
// No-op
}
override fun onAttachedToActivity(binding: ActivityPluginBinding) {
// No-op
}
override fun onDetachedFromActivityForConfigChanges() {
// No-op
}
override fun onReattachedToActivityForConfigChanges(binding: ActivityPluginBinding) {
// No-op
}
override fun onDetachedFromActivity() {
// No-op
}
}
在 ios/Classes/SimplePlatformViewPlugin.swift
中注册工厂:
import Flutter
public class SimplePlatformViewPlugin: NSObject, FlutterPlugin {
public static func register(with registrar: FlutterPluginRegistrar) {
let channel = FlutterMethodChannel(name: "simple_platform_view", binaryMessenger: registrar.messenger())
let factory = SimplePlatformViewFactory()
registrar.register(factory, withId: "simple_platform_view")
}
public func handle(_ call: FlutterMethodCall, result: @escaping FlutterResult) {
// No-op
}
}
5. 在Flutter中使用平台视图
在你的Flutter项目中,你可以使用 ui.platformViewRegistry.registerViewFactory
来注册平台视图,并在布局中使用它:
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:simple_platform_view/simple_platform_view.dart'; // 假设你已经将插件添加到pubspec.yaml中
void main() {
runApp(MyApp());
}
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: Text('Platform View Example'),
),
body: Center(
child: PlatformView(
viewType: 'simple_platform_view',
),
),
),
);
}
}
请注意,上述代码是示例性质的,并且假设你已经在 pubspec.yaml
中添加了你的插件依赖。实际使用中,你需要根据具体需求调整代码。