Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions flutter/shell/platform/tizen/BUILD.gn
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,7 @@ template("embedder") {
"channels/app_control_channel.cc",
"channels/feedback_manager.cc",
"channels/input_device_channel.cc",
"channels/input_panel_channel.cc",
"channels/key_mapping.cc",
"channels/keyboard_channel.cc",
"channels/lifecycle_channel.cc",
Expand Down
62 changes: 62 additions & 0 deletions flutter/shell/platform/tizen/channels/input_panel_channel.cc
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
// Copyright 2026 Samsung Electronics Co., Ltd. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "input_panel_channel.h"

#include "flutter/shell/platform/common/client_wrapper/include/flutter/event_stream_handler_functions.h"
#include "flutter/shell/platform/common/client_wrapper/include/flutter/standard_method_codec.h"
#include "flutter/shell/platform/tizen/logger.h"
#include "flutter/shell/platform/tizen/tizen_input_method_context.h"

namespace {

constexpr char kChannelName[] = "tizen/internal/inputpanel";

} // namespace

namespace flutter {

InputPanelChannel::InputPanelChannel(BinaryMessenger* messenger,
TizenInputMethodContext* imf_context)
: imf_context_(imf_context) {
event_channel_ = std::make_unique<EventChannel<EncodableValue>>(
messenger, kChannelName, &StandardMethodCodec::GetInstance());
auto event_channel_handler = std::make_unique<StreamHandlerFunctions<>>(
[this](const EncodableValue* arguments,
std::unique_ptr<EventSink<>>&& events)
-> std::unique_ptr<StreamHandlerError<>> {
event_sink_ = std::move(events);
imf_context_->SetOnInputPanelStateChanged(
[this](const std::string& state) {
SendInputPanelStateEvent(state);
});
return nullptr;
},
[this](const EncodableValue* arguments)
-> std::unique_ptr<StreamHandlerError<>> {
imf_context_->SetOnInputPanelStateChanged(nullptr);
event_sink_.reset();
return nullptr;
});

event_channel_->SetStreamHandler(std::move(event_channel_handler));
}

InputPanelChannel::~InputPanelChannel() {
event_channel_->SetStreamHandler(nullptr);

imf_context_->SetOnInputPanelStateChanged(nullptr);
}

void InputPanelChannel::SendInputPanelStateEvent(const std::string& state) {
if (!event_sink_) {
return;
}

EncodableMap event;
event[EncodableValue("state")] = EncodableValue(state);
event_sink_->Success(EncodableValue(event));
}

} // namespace flutter
35 changes: 35 additions & 0 deletions flutter/shell/platform/tizen/channels/input_panel_channel.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
// Copyright 2026 Samsung Electronics Co., Ltd. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#ifndef EMBEDDER_INPUT_PANEL_CHANNEL_H_
#define EMBEDDER_INPUT_PANEL_CHANNEL_H_

#include <memory>
#include <string>

#include "flutter/shell/platform/common/client_wrapper/include/flutter/binary_messenger.h"
#include "flutter/shell/platform/common/client_wrapper/include/flutter/encodable_value.h"
#include "flutter/shell/platform/common/client_wrapper/include/flutter/event_channel.h"

namespace flutter {

class TizenInputMethodContext;

class InputPanelChannel {
public:
explicit InputPanelChannel(BinaryMessenger* messenger,
TizenInputMethodContext* imf_context);
virtual ~InputPanelChannel();

private:
void SendInputPanelStateEvent(const std::string& state);

std::unique_ptr<EventChannel<EncodableValue>> event_channel_;
std::unique_ptr<EventSink<EncodableValue>> event_sink_;
TizenInputMethodContext* imf_context_;
};

} // namespace flutter

#endif // EMBEDDER_INPUT_PANEL_CHANNEL_H_
2 changes: 2 additions & 0 deletions flutter/shell/platform/tizen/flutter_tizen_view.cc
Original file line number Diff line number Diff line change
Expand Up @@ -96,6 +96,8 @@ void FlutterTizenView::SetupChannels() {
tizen_view_->input_method_context());

input_device_channel_ = std::make_unique<InputDeviceChannel>(messenger);
input_panel_channel_ = std::make_unique<InputPanelChannel>(
messenger, tizen_view_->input_method_context());
}

void FlutterTizenView::Resize(int32_t width, int32_t height) {
Expand Down
4 changes: 4 additions & 0 deletions flutter/shell/platform/tizen/flutter_tizen_view.h
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
#include "flutter/shell/platform/common/client_wrapper/include/flutter/plugin_registrar.h"
#include "flutter/shell/platform/embedder/embedder.h"
#include "flutter/shell/platform/tizen/channels/input_device_channel.h"
#include "flutter/shell/platform/tizen/channels/input_panel_channel.h"
#include "flutter/shell/platform/tizen/channels/mouse_cursor_channel.h"
#include "flutter/shell/platform/tizen/channels/platform_channel.h"
#include "flutter/shell/platform/tizen/channels/text_input_channel.h"
Expand Down Expand Up @@ -188,6 +189,9 @@ class FlutterTizenView : public TizenViewEventHandlerDelegate {
// A plugin to report input device information.
std::unique_ptr<InputDeviceChannel> input_device_channel_;

// A plugin to report input panel information.
std::unique_ptr<InputPanelChannel> input_panel_channel_;

// The current view rotation degree.
int32_t rotation_degree_ = 0;

Expand Down
47 changes: 47 additions & 0 deletions flutter/shell/platform/tizen/tizen_input_method_context.cc
Original file line number Diff line number Diff line change
Expand Up @@ -143,9 +143,11 @@ TizenInputMethodContext::TizenInputMethodContext(uintptr_t window_id) {
SetContextOptions();
SetInputPanelOptions();
RegisterEventCallbacks();
RegisterInputPanelEventCallback();
}

TizenInputMethodContext::~TizenInputMethodContext() {
UnregisterInputPanelEventCallback();
UnregisterEventCallbacks();

#ifdef NUI_SUPPORT
Expand Down Expand Up @@ -386,4 +388,49 @@ void TizenInputMethodContext::SetInputPanelOptions() {
imf_context_, ECORE_IMF_INPUT_PANEL_LANG_AUTOMATIC);
}

void TizenInputMethodContext::InputPanelStateChangedCallback(
void* data,
Ecore_IMF_Context* ctx,
int value) {
auto* self = static_cast<TizenInputMethodContext*>(data);
Ecore_IMF_Input_Panel_State state =
static_cast<Ecore_IMF_Input_Panel_State>(value);

std::string state_str;
switch (state) {
case ECORE_IMF_INPUT_PANEL_STATE_SHOW:
state_str = "show";
break;
case ECORE_IMF_INPUT_PANEL_STATE_HIDE:
state_str = "hide";
break;
case ECORE_IMF_INPUT_PANEL_STATE_WILL_SHOW:
state_str = "will_show";
break;
default:
state_str = "unknown";
break;
}

if (self->on_input_panel_state_changed_) {
self->on_input_panel_state_changed_(state_str);
}
}

void TizenInputMethodContext::RegisterInputPanelEventCallback() {
FT_ASSERT(imf_context_);

ecore_imf_context_input_panel_event_callback_add(
imf_context_, ECORE_IMF_INPUT_PANEL_STATE_EVENT,
InputPanelStateChangedCallback, this);
}

void TizenInputMethodContext::UnregisterInputPanelEventCallback() {
FT_ASSERT(imf_context_);

ecore_imf_context_input_panel_event_callback_del(
imf_context_, ECORE_IMF_INPUT_PANEL_STATE_EVENT,
InputPanelStateChangedCallback);
}

} // namespace flutter
13 changes: 13 additions & 0 deletions flutter/shell/platform/tizen/tizen_input_method_context.h
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ using OnCommit = std::function<void(std::string str)>;
using OnPreeditChanged = std::function<void(std::string str, int cursor_pos)>;
using OnPreeditStart = std::function<void()>;
using OnPreeditEnd = std::function<void()>;
using OnInputPanelStateChanged = std::function<void(const std::string& state)>;

struct InputPanelGeometry {
int32_t x = 0, y = 0, w = 0, h = 0;
Expand Down Expand Up @@ -70,7 +71,18 @@ class TizenInputMethodContext {

void SetOnPreeditEnd(OnPreeditEnd callback) { on_preedit_end_ = callback; }

void SetOnInputPanelStateChanged(OnInputPanelStateChanged callback) {
on_input_panel_state_changed_ = callback;
}

void RegisterInputPanelEventCallback();
void UnregisterInputPanelEventCallback();

private:
static void InputPanelStateChangedCallback(void* data,
Ecore_IMF_Context* ctx,
int value);

void RegisterEventCallbacks();
void UnregisterEventCallbacks();

Expand All @@ -85,6 +97,7 @@ class TizenInputMethodContext {
OnPreeditChanged on_preedit_changed_;
OnPreeditStart on_preedit_start_;
OnPreeditEnd on_preedit_end_;
OnInputPanelStateChanged on_input_panel_state_changed_;
std::unordered_map<Ecore_IMF_Callback_Type, Ecore_IMF_Event_Cb>
event_callbacks_;
};
Expand Down