From 54e64b2407a377f5bc9331bce0e0ee7bc7bf3886 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=BC=A0=E5=B0=8F=E7=99=BD?= <364772080@qq.com> Date: Fri, 6 Jun 2025 15:31:45 +0800 Subject: [PATCH] windows: Refactor the current ime implementation (#32224) Release Notes: - N/A --- crates/gpui/src/platform/windows/events.rs | 84 +++++++--------------- 1 file changed, 27 insertions(+), 57 deletions(-) diff --git a/crates/gpui/src/platform/windows/events.rs b/crates/gpui/src/platform/windows/events.rs index b5a0653fe9..2db2da6561 100644 --- a/crates/gpui/src/platform/windows/events.rs +++ b/crates/gpui/src/platform/windows/events.rs @@ -691,43 +691,36 @@ fn handle_ime_composition_inner( lparam: LPARAM, state_ptr: Rc, ) -> Option { - let mut ime_input = None; - if lparam.0 as u32 & GCS_COMPSTR.0 > 0 { - let comp_string = parse_ime_composition_string(ctx)?; - with_input_handler(&state_ptr, |input_handler| { - input_handler.replace_and_mark_text_in_range(None, &comp_string, None); - })?; - ime_input = Some(comp_string); - } - if lparam.0 as u32 & GCS_CURSORPOS.0 > 0 { - let comp_string = &ime_input?; - let caret_pos = retrieve_composition_cursor_position(ctx); - with_input_handler(&state_ptr, |input_handler| { - input_handler.replace_and_mark_text_in_range( - None, - comp_string, - Some(caret_pos..caret_pos), - ); - })?; - } - if lparam.0 as u32 & GCS_RESULTSTR.0 > 0 { - let comp_result = parse_ime_composition_result(ctx)?; - with_input_handler(&state_ptr, |input_handler| { - input_handler.replace_text_in_range(None, &comp_result); - })?; - return Some(0); - } - if lparam.0 == 0 { + let lparam = lparam.0 as u32; + if lparam == 0 { // Japanese IME may send this message with lparam = 0, which indicates that // there is no composition string. with_input_handler(&state_ptr, |input_handler| { input_handler.replace_text_in_range(None, ""); })?; - return Some(0); - } + Some(0) + } else { + if lparam & GCS_COMPSTR.0 > 0 { + let comp_string = parse_ime_composition_string(ctx, GCS_COMPSTR)?; + let caret_pos = (lparam & GCS_CURSORPOS.0 > 0).then(|| { + let pos = retrieve_composition_cursor_position(ctx); + pos..pos + }); + with_input_handler(&state_ptr, |input_handler| { + input_handler.replace_and_mark_text_in_range(None, &comp_string, caret_pos); + })?; + } + if lparam & GCS_RESULTSTR.0 > 0 { + let comp_result = parse_ime_composition_string(ctx, GCS_RESULTSTR)?; + with_input_handler(&state_ptr, |input_handler| { + input_handler.replace_text_in_range(None, &comp_result); + })?; + return Some(0); + } - // currently, we don't care other stuff - None + // currently, we don't care other stuff + None + } } /// SEE: https://learn.microsoft.com/en-us/windows/win32/winmsg/wm-nccalcsize @@ -1354,14 +1347,14 @@ fn parse_normal_key( }) } -fn parse_ime_composition_string(ctx: HIMC) -> Option { +fn parse_ime_composition_string(ctx: HIMC, comp_type: IME_COMPOSITION_STRING) -> Option { unsafe { - let string_len = ImmGetCompositionStringW(ctx, GCS_COMPSTR, None, 0); + let string_len = ImmGetCompositionStringW(ctx, comp_type, None, 0); if string_len >= 0 { let mut buffer = vec![0u8; string_len as usize + 2]; ImmGetCompositionStringW( ctx, - GCS_COMPSTR, + comp_type, Some(buffer.as_mut_ptr() as _), string_len as _, ); @@ -1381,29 +1374,6 @@ fn retrieve_composition_cursor_position(ctx: HIMC) -> usize { unsafe { ImmGetCompositionStringW(ctx, GCS_CURSORPOS, None, 0) as usize } } -fn parse_ime_composition_result(ctx: HIMC) -> Option { - unsafe { - let string_len = ImmGetCompositionStringW(ctx, GCS_RESULTSTR, None, 0); - if string_len >= 0 { - let mut buffer = vec![0u8; string_len as usize + 2]; - ImmGetCompositionStringW( - ctx, - GCS_RESULTSTR, - Some(buffer.as_mut_ptr() as _), - string_len as _, - ); - let wstring = std::slice::from_raw_parts::( - buffer.as_mut_ptr().cast::(), - string_len as usize / 2, - ); - let string = String::from_utf16_lossy(wstring); - Some(string) - } else { - None - } - } -} - #[inline] fn is_virtual_key_pressed(vkey: VIRTUAL_KEY) -> bool { unsafe { GetKeyState(vkey.0 as i32) < 0 }