fix(sdk/ime): IME 修复(shift小写基/OK只提交不关/阻塞喂on_tick agent-169) + dialog INPUT回归(dlg_ime_change_cb实时回写+适配新语义 agent-173) + test_sdk_fixes shift断言更新 + 宿主测试test_ime_fix

This commit is contained in:
MeowOS committed 2026-08-31 02:01:56 +08:00
1 parent c515a33ac4
commit 2d7fe81229
7 files changed
+359 -15

No files matched your search

+73 -4
View File
@@ -3,7 +3,8 @@
* bug4 disabled 按钮圆角外无灰方块(角点 = 页面背景而非叠暗);
* bug1 圆形进度环带确实画到 = 半径+thk/2 处(bbox 与真实像素一致,漏刷修复的几何前提);
* bug3 modal(Dialog)open→cancel 后背景还原(scrim 不累积/无残影);
* bug7 IME 回显实时同步(on_change 随键入触发)+ 关闭后键盘区背景还原。
* bug7 IME 回显实时同步(on_change 随键入触发)+ 关闭后键盘区背景还原;
* fix1 dialog INPUT 在 ESC/背景(result=0)关闭后文本不丢(M2.71-IME-fix 新语义:回车只提交不关)。
*
* 编译(宿主 gcc,链真实 gfx/sys/theme/vol/log/widget/input/activity/dialog/ime + 打桩 font/global):
* gcc -Wall -o test_sdk_fixes test_sdk_fixes.c test_host_stub.c \
@@ -39,6 +40,7 @@ static int near(int a, int b) { int d = a - b; if (d < 0) d = -d; return d <= 12
/* ---- 为阻塞模态/IME 在后台注入事件 ---- */
static int g_inj_tap_x = 0, g_inj_tap_y = 0, g_inj_delay = 0;
static int K_DLG_OK_X = 0, K_DLG_OK_Y = 0; /* dialog INPUT 的 OK 按钮中心(运行时算) */
static void *inject_thread(void *arg)
{
(void)arg;
@@ -122,10 +124,14 @@ static void test_ime_echo_and_restore(void)
/* --- 异步:验『回显/输入框实时同步(on_change 随键入触发)』--- */
meow_ui_text_input_async(&c);
assert(meow_ime_active() == 1);
meow_input_inject(MEOW_EV_TAP, 20, 580); /* ASCII 第3行第1键 = 'A'(shift 关 → 缓冲 'A') */
meow_input_inject(MEOW_EV_TAP, 20, 580); /* ASCII 行3第1键 = 'a'(shift 关 → 小写 'a') */
meow_ime_handle_tap(20, 580);
assert(strcmp(g_echo, "A") == 0 && strcmp(meow_ime_text(), "A") == 0);
printf("[bug7] ime echo live-sync after 'A' -> \"%s\" (on_change fired) PASS\n", g_echo); fflush(stdout);
assert(strcmp(g_echo, "a") == 0 && strcmp(meow_ime_text(), "a") == 0);
printf("[bug7] ime echo live-sync after 'a' -> \"%s\" (shift-off lower) PASS\n", g_echo); fflush(stdout);
meow_ime_handle_tap(450, 584); /* SHIFT 开 */
meow_ime_handle_tap(20, 580); /* 'a' → 'A' 大写 */
assert(strcmp(g_echo, "aA") == 0 && strcmp(meow_ime_text(), "aA") == 0);
printf("[bug7] shift-on -> 'A' (echo \"%s\") PASS\n", g_echo); fflush(stdout);
meow_input_inject(MEOW_EV_TAP, 20, 680); /* ESC(X) → 取消 */
meow_ime_handle_tap(20, 680);
assert(meow_ime_active() == 0);
@@ -143,6 +149,68 @@ static void test_ime_echo_and_restore(void)
printf("PASS\n");
}
/* ---- 回归①:dialog INPUT 在 ESC/背景(result=0)关闭后文本不丢(M2.71-IME-fix 新语义)。
* 复现 dialog.c dlg_input_ok_center → 复用 dialog 的 OK 按钮中心几何(与 dlg_calc 同一公式)。 */
static void dialog_input_ok_center(int *ox, int *oy)
{
const meow_theme *th = meow_theme_get();
int W = meow_ui_width(), H = meow_ui_height();
int sb = meow_ui_statusbar_height(); if (sb < 0) sb = 0;
int pad = 24, btn = 44;
int tH = meow_ui_text_height(th->font_title);
int bH = meow_ui_text_height(th->font_body);
int content = bH + 8; /* INPUT(无 items)→ 1 行正文预览 */
int dw = 348; if (dw > W - 40) dw = W - 40;
int dx = (W - dw) / 2;
int dh = pad + tH + 12 + content + pad + (16 + btn);
int avail = H - sb - 20;
if (dh > avail) dh = avail;
int dy = (H - dh) / 2; if (dy < sb) dy = sb;
int row_y = dy + pad + tH + 12;
int btn_y = row_y + content + 16;
int btn_w = (dw - 2 * pad - 12) / 2;
int cx = dx + pad + btn_w + 12; /* OK = 右侧填充按钮左缘 */
*ox = cx + btn_w / 2;
*oy = btn_y + btn / 2;
}
static void *dlg_input_driver(void *arg)
{
(void)arg;
usleep(40000); /* 等 dialog show 起(遮罩+卡片已绘) */
meow_input_inject(MEOW_EV_TAP, K_DLG_OK_X, K_DLG_OK_Y); /* 点 OK → 打开阻塞 IME */
usleep(140000);
meow_input_inject(MEOW_EV_TAP, 20, 584); /* 行3第1键 'a'(shift 关) */
usleep(140000);
meow_input_inject(MEOW_EV_TAP, 20, 680); /* ESC → 关 IME → dialog 随之关 */
return NULL;
}
static void test_dialog_input_preserve(void)
{
const meow_theme *th = meow_theme_get();
meow_ui_clear(th->bg);
meow_ui_flush();
meow_ime_ctx ime; memset(&ime, 0, sizeof ime);
ime.mode = MEOW_IME_ASCII; ime.maxlen = 64;
strcpy(ime.buf, "");
meow_dialog *d = meow_dialog_create(MEOW_DLG_INPUT, "Name");
meow_dialog_set_ime(d, &ime);
dialog_input_ok_center(&K_DLG_OK_X, &K_DLG_OK_Y);
pthread_t thd; pthread_create(&thd, NULL, dlg_input_driver, NULL);
meow_dialog_show(d);
pthread_join(thd, NULL);
/* ESC 关闭(result=0)→ 文本应保留:App 原始 ctx.buf 应含 'a'(不再丢失),且是取消语义 */
printf("[fix1] dialog INPUT after ESC: result=%d App.ime.buf=\"%s\" (expect 0, \"a\")\n",
meow_dialog_result(d), ime.buf);
assert(meow_dialog_result(d) == 0);
assert(strcmp(ime.buf, "a") == 0);
printf("[fix1] dialog INPUT text preserved on ESC PASS\n");
meow_dialog_free(d);
}
int main(void)
{
setenv("MEOW_UI_DUMP", "/tmp/fixes.ppm", 1);
@@ -152,6 +220,7 @@ int main(void)
test_circular_extent();
test_modal_restore();
test_ime_echo_and_restore();
test_dialog_input_preserve();
meow_ui_shutdown();
printf("ALL PASS\n");
return 0;