Flutter中PlatformView在鸿蒙中的使用
Flutter中PlatformView在鸿蒙中的使用
- 概述
- 在Flutter中的处理
- 鸿蒙端
- 创建内嵌的鸿蒙视图
- 创建PlatformView
- 创建PlatformViewFactory
- 创建plugin,注册platformview
- 注册插件
概述
集成平台视图(后称为平台视图)允许将原生视图嵌入到 Flutter 应用中,所以你可以通过 Dart 将变换、裁剪和不透明度等效果应用到原生视图。
例如,这使你可以通过使用平台视图直接在 Flutter 应用内部使用鸿蒙中的原生地图。
在Flutter中的处理
首先我们需要再Flutter中创建一个视图,用来加载Ohos平台的view。
import 'dart:async';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
typedef OnViewCreated = Function(CustomViewController);
class CustomOhosView extends StatefulWidget {
final OnViewCreated onViewCreated;
const CustomOhosView(this.onViewCreated, {super.key});
State<CustomOhosView> createState() => _CustomOhosViewState();
}
class _CustomOhosViewState extends State<CustomOhosView> {
late MethodChannel _channel;
Widget build(BuildContext context) {
return _getPlatformFaceView();
}
Widget _getPlatformFaceView() {
// 加载platformview
/**
* viewType:传递给Native侧,告知插件需要创建那个PlatformView,这个PlatformView需要在插件初始化时注册。
onPlatformViewCreated:PlatformView创建成功时的回调。
creationParams:传递给PlatformView的初始化参数。
*/
return OhosView(
viewType: 'com.rex.custom.ohos/customView',
onPlatformViewCreated: _onPlatformViewCreated,
creationParams: const <String, dynamic>{'initParams': 'hello world'},
creationParamsCodec: const StandardMessageCodec(),
);
}
void _onPlatformViewCreated(int id) {
print("platformview==================创建成功");
_channel = MethodChannel('com.rex.custom.ohos/customView$id');
final controller = CustomViewController._(
_channel,
);
widget.onViewCreated(controller);
}
}
// 用于实现Dart侧与Native侧的交互
class CustomViewController {
final MethodChannel _channel;
final StreamController<String> _controller = StreamController<String>();
CustomViewController._(
this._channel,
) {
_channel.setMethodCallHandler(
(call) async {
switch (call.method) {
case 'getMessageFromOhosView':
// 从native端获取数据
final result = call.arguments as String;
_controller.sink.add(result);
break;
}
},
);
}
Stream<String> get customDataStream => _controller.stream;
// 发送数据给native
Future<void> sendMessageToOhosView(String message) async {
await _channel.invokeMethod(
'getMessageFromFlutterView',
message,
);
}
}
鸿蒙端
创建内嵌的鸿蒙视图
该视图就是我们ohos平台中的组件, 示例代码如下:
@Component
export struct PlatformView_Custom {
@Prop params: Params
// customView: video_Customview = this.params.platformView as video_Customview
build() {
Column() {
Column() {
Button("测试按钮")
.onClick(() => {
console.log("点击按钮时间")
})
}
.backgroundColor(Color.Orange)
.height('230vp')
.width('100%')
.justifyContent(FlexAlign.End)
}
.backgroundColor(Color.Pink)
.width('100%')
.height('100%')
}
}
注意:PlatformView_Custom 嵌入到Flutter页面中时, 系统实际上是在我们的这个组件又包裹了一层空间, 并且默认是充满Flutter父空间的全部空间。
创建PlatformView
我们需要创建一个PlatformView的子类,并实现并且实现MethodCallHandler
接口。
该类有两个作用:
- 通过类中的
getView(): WrappedBuilder<[Params]>{}
方法把上面创建的鸿蒙组件加载到这个PlatformView上 - 实现
MethodCallHandler
接口, 负责和Flutter的相关通信
示例代码如下:
/**
* @ProjectName : ohos
* @FileName : PlatformView_plugin
* @Author : issuser
* @Time : 2024/10/11 9:33
* @Description : 文件描述
*/
import {
BinaryMessenger,
MethodCall, MethodCallHandler, MethodChannel, MethodResult, PlatformView,
StandardMethodCodec } from '@ohos/flutter_ohos';
import { Params } from '@ohos/flutter_ohos/src/main/ets/plugin/platform/PlatformView';
import { PlatformView_Custom } from './PlatformView_Custom';
import { common } from '@kit.AbilityKit';
export class PlatformView_plugin extends PlatformView implements MethodCallHandler {
numValue: string = "test";
methodChannel: MethodChannel;
index: number = 1;
// 构造方法
constructor(context: common.Context, viewId: number, args: ESObject, message: BinaryMessenger) {
super();
// 注册消息通道,消息通道根据具体需求添加,代码仅作为示例
this.methodChannel = new MethodChannel(message, `com.rex.custom.ohos/video_CustomView${viewId}`, StandardMethodCodec.INSTANCE);
// 给通道添加监听
this.methodChannel.setMethodCallHandler(this);
}
// 实现onMethodCall接口
onMethodCall(call: MethodCall, result: MethodResult): void {
// 接受Dart侧发来的消息
let method: string = call.method;
let link1: SubscribedAbstractProperty<number> = AppStorage.link('numValue');
switch (method) {
case 'video_getMessageFromFlutterView':
let value: ESObject = call.args;
this.numValue = value;
link1.set(value)
console.log("nodeController receive message from dart: " + this.numValue);
result.success(true);
break;
}
}
// 返回鸿蒙要展示的视图
getView(): WrappedBuilder<[Params]> {
return new WrappedBuilder(platformBuilder)
}
// 生命周期方法 销毁时
dispose(): void {
throw new Error('Method not implemented.');
}
}
// 全局的build函数,通过这个bbuilder函数返回我们的组件view
@Builder
function platformBuilder(param: Params) {
PlatformView_Custom({params: param})
.backgroundColor(Color.Green)
}
创建PlatformViewFactory
PlatformView类的创建是通过PlatformViewFactory
来创建, 所以我们需要创建一个工厂类继承自PlatformViewFactory
。
示例代码:
// 通过工厂方法创建一个plaugin示例
export class CustomFactory extends PlatformViewFactory {
message: BinaryMessenger;
constructor(message: BinaryMessenger, createArgsCodes: MessageCodec<Object>) {
super(createArgsCodes);
this.message = message;
}
public create(context: Context, viewId: number, args: Object): PlatformView {
return new PlatformView_plugin(context, viewId, args, this.message);
}
}
创建plugin,注册platformview
新建一个继承于FlutterPlugin
的CustomPlugin
插件,在onAttachedToEngine
中,注册自定义的PlatformViewFactory
示例代码:
import { StandardMessageCodec } from '@ohos/flutter_ohos';
import {
FlutterPlugin,
FlutterPluginBinding
} from '@ohos/flutter_ohos/src/main/ets/embedding/engine/plugins/FlutterPlugin';
import { CustomFactory } from './CustomFactory';
export class CustomPlugin implements FlutterPlugin {
getUniqueClassName(): string {
return 'CustomPlugin'
}
// 当插件挂载到引擎上时
onAttachedToEngine(binding: FlutterPluginBinding): void {
// 在插件挂在在引擎的时候, 我们需要注册我们的view
binding.getPlatformViewRegistry()?.
registerViewFactory('com.rex.custom.ohos/customView',
new CustomFactory(binding.getBinaryMessenger(), StandardMessageCodec.INSTANCE));
}
onDetachedFromEngine(binding: FlutterPluginBinding): void {
throw new Error('Method not implemented.');
}
}
注册插件
在EntryAblitity中注册我们创建的自定义插件:
export default class EntryAbility extends FlutterAbility {
configureFlutterEngine(flutterEngine: FlutterEngine) {
super.configureFlutterEngine(flutterEngine)
GeneratedPluginRegistrant.registerWith(flutterEngine)
// 注册platformview的自定义插件
this.addPlugin(new CustomPlugin());
}
}
然后执行flutter build hap
命令进行编译, 配置相关证书, 运行。