首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >通过EventChannel接收来自Android的字符串

通过EventChannel接收来自Android的字符串
EN

Stack Overflow用户
提问于 2021-10-22 07:05:45
回答 1查看 540关注 0票数 1

我目前正在学习Flutter,特别是如何与设备本身进行通信。

目前我已经设置了一个MethodChannel,我在其中接收一个字符串列表作为结果,但是现在我想将它更改为通过一个EventChannel在流上接收这些字符串。

我知道我仍然需要依赖MethodChannel来触发Android端的方法,然后它通过EventChannel将数据(在我的例子中是String)发送回flutter。但是我真的不知道如何让EventChannel只发送几个流(可能在它们之间有一点延迟),因为我发现的每个关于EventChannel的教程对我来说都是困惑而不是有用的:(

下面是我目前通过EventChannel获取内容的代码:

flutter-plugin:

代码语言:javascript
复制
static const EventChannel messageChannel = EventChannel('eventChannelStream');

  Stream<String> get messageStream async* {
    messageChannel.receiveBroadcastStream().map((message) {
      return message;
    });
  }

android端的Kotlin代码:

代码语言:javascript
复制
class HelperPlugin : FlutterPlugin, MethodCallHandler, EventChannel.StreamHandler {

    private lateinit var channel: MethodChannel
    private var messageChannel: EventChannel? = null
    private var eventSink: EventChannel.EventSink? = null

    override fun onListen(arguments: Any?, eventSink: EventChannel.EventSink?) {
        this.eventSink = eventSink
    }

    override fun onCancel(arguments: Any?) {
        eventSink = null
        messageChannel = null
    }

    override fun onAttachedToEngine(@NonNull flutterPluginBinding: FlutterPlugin.FlutterPluginBinding) {
        channel = MethodChannel(flutterPluginBinding.binaryMessenger, "methodChannel")
        channel.setMethodCallHandler(this)

        messageChannel = EventChannel(flutterPluginBinding.binaryMessenger, "eventChannelStream")
        messageChannel?.setStreamHandler(this)
    }


... 
// Doing other stuff here

以及我希望如何在BLoC中使用这些消息,以便在事件发生后将它们发送到UI:

代码语言:javascript
复制
Stream<String> retrieveMessage(Stream<String> messageStream) async* {
  await for (String message in messageStream) {
    //await Future.delayed(const Duration(milliseconds: 1500));
    yield message;
  }
}
EN

回答 1

Stack Overflow用户

发布于 2021-10-22 13:05:19

好了,开始工作了。这可能不是最好的方法,但至少它是有效的:)

下面是我是如何做到的,也许它可以帮助其他人:):

Android响应的Kotlin代码:

代码语言:javascript
复制
class HelperPlugin : FlutterPlugin, MethodCallHandler, EventChannel.StreamHandler {

    private lateinit var channel: MethodChannel
    private var messageChannel: EventChannel? = null
    private var eventSink: EventChannel.EventSink? = null


    override fun onListen(arguments: Any?, eventSink: EventChannel.EventSink?) {
        this.eventSink = eventSink
    }

    override fun onCancel(arguments: Any?) {
        eventSink = null
        messageChannel = null
    }

    override fun onAttachedToEngine(@NonNull flutterPluginBinding: FlutterPlugin.FlutterPluginBinding) {
        channel = MethodChannel(flutterPluginBinding.binaryMessenger, "methodChannel")
        channel.setMethodCallHandler(this)

        messageChannel = EventChannel(flutterPluginBinding.binaryMessenger, "eventChannelStream")
        messageChannel?.setStreamHandler(this)
    }

    override fun onMethodCall(@NonNull call: MethodCall, @NonNull result: Result) {
        when (call.method) {
            "getPlatformVersion" -> {
                result.success(tellVersionNumber())
            }
            "tellJoke" -> {
                result.success(tellJoke())
            }
            "cantAnswer" -> {
                result.success(cantAnswer())
            }
            "whoAreYou" -> {
                result.success(whoAreYou())
            }
            "currentTime" -> {
                result.success(currentTime())
            }
            "upTime" -> {
                result.success(upTime())
            }
            "greetUser" -> {
                result.success(greetUser())
            }
            "systemInformation" -> {
                result.success(systemInformation())
            }
            else -> {
                result.notImplemented()
            }
        }
    }

    override fun onDetachedFromEngine(@NonNull binding: FlutterPlugin.FlutterPluginBinding) {
        channel.setMethodCallHandler(null)
    }

// Here are Functions, which add Strings to the EventChannel via eventSink?.success("String to Add")

}

Flutter-Plugin:

代码语言:javascript
复制
class ChatbotHelper extends ChatbotInterface {
  static const MethodChannel _channel = MethodChannel('methodChannel');
  static const EventChannel messageChannel = EventChannel('eventChannelStream');

  Stream<String> get messageStream async* {
    await for (String message in messageChannel.receiveBroadcastStream().map((message) => message)){
      yield message;
    }
  }

  @override
  Future<void> platformVersion() async {
    await _channel.invokeMethod('getPlatformVersion');
  }

  @override
  Future<void> tellJoke() async {
        await _channel.invokeMethod('tellJoke');
  }
// other invokeMethods and answerQuestion function, which calls these invokeMethods depending on a String message

...

}

下面是我如何在我的BLoC中使用流:

代码语言:javascript
复制
 Future<void> _initializeAnswerStream(
      InitializeMessageStreamEvent event, Emitter<ChatState> emit) async {
    try{
        await for(String message in retrieveMessageStream(_helper.messageStream)) {

        add(AddResponseMessageEvent(responseMessage: message));
      }
    }catch(e){
      print(e);
    }
  }

在我的窗口小部件树中创建相应的BlocProvider时,将调用此BLoC-Event来初始化流并等待消息。

编辑:修复了一些我重命名的值,将其发布在这里

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/69672645

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档