5package io.flutter.plugin.common;
7import androidx.annotation.Nullable;
8import androidx.annotation.UiThread;
9import io.flutter.BuildConfig;
11import io.flutter.plugin.common.BinaryMessenger.BinaryMessageHandler;
12import io.flutter.plugin.common.BinaryMessenger.BinaryReply;
13import java.nio.ByteBuffer;
14import java.util.concurrent.atomic.AtomicBoolean;
15import java.util.concurrent.atomic.AtomicReference;
33 private static final String TAG =
"EventChannel#";
36 private final String name;
38 @Nullable
private final BinaryMessenger.TaskQueue taskQueue;
60 this(messenger, name, codec,
null);
80 if (messenger ==
null) {
81 Log.
e(
TAG,
"Parameter messenger must not be null.");
84 Log.
e(
TAG,
"Parameter name must not be null.");
87 Log.
e(
TAG,
"Parameter codec must not be null.");
90 this.messenger = messenger;
93 this.taskQueue = taskQueue;
111 if (taskQueue !=
null) {
113 name, handler ==
null ?
null :
new IncomingStreamRequestHandler(handler), taskQueue);
116 name, handler ==
null ?
null :
new IncomingStreamRequestHandler(handler));
176 void error(String errorCode, String errorMessage, Object errorDetails);
187 private final AtomicReference<EventSink> activeSink =
new AtomicReference<>(
null);
190 this.handler = handler;
196 if (
call.method.equals(
"listen")) {
197 onListen(
call.arguments, reply);
198 }
else if (
call.method.equals(
"cancel")) {
199 onCancel(
call.arguments, reply);
206 final EventSink eventSink =
new EventSinkImplementation();
207 final EventSink oldSink = activeSink.getAndSet(eventSink);
208 if (oldSink !=
null) {
213 }
catch (RuntimeException
e) {
214 Log.e(TAG + name,
"Failed to close existing event stream",
e);
218 handler.
onListen(arguments, eventSink);
220 }
catch (RuntimeException
e) {
221 activeSink.set(
null);
222 Log.e(TAG + name,
"Failed to open event stream",
e);
228 final EventSink oldSink = activeSink.getAndSet(
null);
229 if (oldSink !=
null) {
233 }
catch (RuntimeException
e) {
234 Log.e(TAG + name,
"Failed to close event stream",
e);
242 private final class EventSinkImplementation
implements EventSink {
243 final AtomicBoolean hasEnded =
new AtomicBoolean(
false);
247 public void success(Object
event) {
248 if (hasEnded.get() || activeSink.get() !=
this) {
256 public void error(String errorCode, String errorMessage, Object errorDetails) {
257 if (hasEnded.get() || activeSink.get() !=
this) {
266 public void endOfStream() {
267 if (hasEnded.getAndSet(
true) || activeSink.get() !=
this) {
static final boolean DEBUG
static void e(@NonNull String tag, @NonNull String message)
void setStreamHandler(final StreamHandler handler)
EventChannel(BinaryMessenger messenger, String name, MethodCodec codec, BinaryMessenger.TaskQueue taskQueue)
EventChannel(BinaryMessenger messenger, String name)
EventChannel(BinaryMessenger messenger, String name, MethodCodec codec)
static final StandardMethodCodec INSTANCE
FlKeyEvent uint64_t FlKeyResponderAsyncCallback callback
const uint8_t uint32_t uint32_t GError ** error
void reply(@Nullable ByteBuffer reply)
void setMessageHandler(@NonNull String channel, @Nullable BinaryMessageHandler handler)
void error(String errorCode, String errorMessage, Object errorDetails)
void success(Object event)
void onListen(Object arguments, EventSink events)
void onCancel(Object arguments)
ByteBuffer encodeSuccessEnvelope(@Nullable Object result)
ByteBuffer encodeErrorEnvelope( @NonNull String errorCode, @Nullable String errorMessage, @Nullable Object errorDetails)
MethodCall decodeMethodCall(@NonNull ByteBuffer methodCall)
void Log(const char *format,...) SK_PRINTF_LIKE(1
std::function< void(const uint8_t *reply, size_t reply_size)> BinaryReply