File tree Expand file tree Collapse file tree
Expand file tree Collapse file tree Original file line number Diff line number Diff line change 1+ # [ 200_54] 修复 Fedora/GNOME 输入法候选窗口不跟随光标问题
2+
3+ ## 如何测试
4+
5+ 此 PR 在 Fedora 43 + GNOME (Wayland) 平台下测试,使用 ibus 或 fcitx 输入法框架
6+
7+ 测试项一:ibus 候选窗口应跟随光标
8+ 1 . 启动 Mogan
9+ 2 . 切换到 ibus 输入法(如 ibus-libpinyin)
10+ 3 . 在文档中输入中文,观察候选窗口位置
11+ 4 . 候选窗口应始终跟随光标,不应偏移到屏幕固定位置
12+
13+ 测试项二:fcitx 候选窗口应跟随光标
14+ 1 . 切换到 fcitx5 输入法
15+ 2 . 在文档中输入中文
16+ 3 . 候选窗口应跟随光标移动
17+
18+ 测试项三:跨行/滚动时光标跟踪
19+ 1 . 输入多行中文内容
20+ 2 . 在行尾、行首、段落中间等不同位置输入
21+ 3 . 滚动文档后继续输入
22+ 4 . 候选窗口应始终出现在当前输入位置附近
23+
24+ 测试项四:其他平台不应出现回归
25+ 1 . 在 Windows/macOS/其他 Linux 桌面环境下测试中文输入
26+ 2 . 候选窗口定位行为应与修复前一致或更好
27+
28+ ## 2026/04/23 修复 Fedora/GNOME 输入法悬浮框定位问题
29+
30+ ### What
31+ 修复了在 Fedora/GNOME (Wayland) 环境下,ibus/fcitx 输入法候选窗口不跟随光标、偏移到屏幕固定位置的问题。
32+
33+ ### Why
34+ 在 Qt6 + Wayland 环境下,ibus/fcitx 通过 ` text-input-v3 ` 协议与 compositor 通信。输入法框架在候选窗口弹出后,不会持续主动重新查询光标位置(` Qt::ImCursorRectangle ` ),只在窗口显示前查询一次。这导致光标移动后,候选窗口仍停留在第一次查询时的旧位置,表现为"固定在右侧居中不动"。
35+
36+ ` QTMWidget::inputMethodQuery() ` 本身已正确实现了光标矩形计算,但缺少触发输入法重新查询的机制。
37+
38+ ### How
39+ ` src/Plugins/Qt/qt_simple_widget.cpp ` :26-29, 276-279
40+ - 在 Linux 平台下添加 ` #include <QGuiApplication> ` 和 ` #include <QInputMethod> `
41+ - 在 ` SLOT_CURSOR ` 处理中,仅限 Linux 平台显式调用 ` QInputMethod::update(Qt::ImCursorRectangle) `
42+ - 这会通知输入法框架光标矩形已改变,触发其重新调用 ` QTMWidget::inputMethodQuery() ` 获取最新坐标
43+
44+ ``` cpp
45+ case SLOT_CURSOR: {
46+ check_type<coord2> (val, s);
47+ coord2 p= open_box<coord2> (val);
48+ canvas ()->setCursorPos (to_qpoint (p));
49+ #ifdef Q_OS_LINUX
50+ QInputMethod* im= QGuiApplication::inputMethod ();
51+ if (im) im->update (Qt::ImCursorRectangle);
52+ #endif
53+ } break ;
54+ ```
55+
56+ ### 影响范围
57+ - ** 修复平台** :Linux(Fedora/GNOME Wayland 下的 ibus/fcitx)
58+ - ** 其他平台** :通过 ` #ifdef Q_OS_LINUX ` 条件编译隔离,macOS 和 Windows 完全不受影响
Original file line number Diff line number Diff line change 2323#include " QTMStyle.hpp"
2424#include " QTMTextPopup.hpp"
2525#include " QTMWidget.hpp"
26+ #ifdef Q_OS_LINUX
27+ #include < QGuiApplication>
28+ #include < QInputMethod>
29+ #endif
2630#include < QLayout>
2731#include < QPixmap>
2832#if QT_VERSION >= 0x060000
@@ -269,6 +273,10 @@ qt_simple_widget_rep::send (slot s, blackbox val) {
269273 check_type<coord2> (val, s);
270274 coord2 p= open_box<coord2> (val);
271275 canvas ()->setCursorPos (to_qpoint (p));
276+ #ifdef Q_OS_LINUX
277+ QInputMethod* im= QGuiApplication::inputMethod ();
278+ if (im) im->update (Qt::ImCursorRectangle);
279+ #endif
272280 } break ;
273281
274282 default :
You can’t perform that action at this time.
0 commit comments