mirror of
https://github.com/vim/vim.git
synced 2025-07-26 11:04:33 -04:00
patch 7.4.1124
Problem: MS-Windows: dead key behavior is not ideal. Solution: Handle dead keys differently when not in Insert or Select mode. (John Wellesz, closes #399)
This commit is contained in:
parent
a24f0a550f
commit
25b2b94ea7
@ -312,7 +312,7 @@ static int s_y_pending;
|
|||||||
static UINT s_kFlags_pending;
|
static UINT s_kFlags_pending;
|
||||||
static UINT s_wait_timer = 0; /* Timer for get char from user */
|
static UINT s_wait_timer = 0; /* Timer for get char from user */
|
||||||
static int s_timed_out = FALSE;
|
static int s_timed_out = FALSE;
|
||||||
static int dead_key = 0; /* 0 - no dead key, 1 - dead key pressed */
|
static int dead_key = 0; /* 0: no dead key, 1: dead key pressed */
|
||||||
|
|
||||||
#ifdef WIN3264
|
#ifdef WIN3264
|
||||||
static OSVERSIONINFO os_version; /* like it says. Init in gui_mch_init() */
|
static OSVERSIONINFO os_version; /* like it says. Init in gui_mch_init() */
|
||||||
@ -641,6 +641,8 @@ _OnSysChar(
|
|||||||
int modifiers;
|
int modifiers;
|
||||||
int ch = cch; /* special keys are negative */
|
int ch = cch; /* special keys are negative */
|
||||||
|
|
||||||
|
dead_key = 0;
|
||||||
|
|
||||||
/* TRACE("OnSysChar(%d, %c)\n", ch, ch); */
|
/* TRACE("OnSysChar(%d, %c)\n", ch, ch); */
|
||||||
|
|
||||||
/* OK, we have a character key (given by ch) which was entered with the
|
/* OK, we have a character key (given by ch) which was entered with the
|
||||||
@ -1710,6 +1712,34 @@ gui_mch_draw_part_cursor(
|
|||||||
DeleteBrush(hbr);
|
DeleteBrush(hbr);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Generates a VK_SPACE when the internal dead_key flag is set to output the
|
||||||
|
* dead key's nominal character and re-post the original message.
|
||||||
|
*/
|
||||||
|
static void
|
||||||
|
outputDeadKey_rePost(MSG originalMsg)
|
||||||
|
{
|
||||||
|
static MSG deadCharExpel;
|
||||||
|
|
||||||
|
if (!dead_key)
|
||||||
|
return;
|
||||||
|
|
||||||
|
dead_key = 0;
|
||||||
|
|
||||||
|
/* Make Windows generate the dead key's character */
|
||||||
|
deadCharExpel.message = originalMsg.message;
|
||||||
|
deadCharExpel.hwnd = originalMsg.hwnd;
|
||||||
|
deadCharExpel.wParam = VK_SPACE;
|
||||||
|
|
||||||
|
MyTranslateMessage(&deadCharExpel);
|
||||||
|
|
||||||
|
/* re-generate the current character free of the dead char influence */
|
||||||
|
PostMessage(originalMsg.hwnd, originalMsg.message, originalMsg.wParam,
|
||||||
|
originalMsg.lParam);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Process a single Windows message.
|
* Process a single Windows message.
|
||||||
* If one is not available we hang until one is.
|
* If one is not available we hang until one is.
|
||||||
@ -1790,22 +1820,49 @@ process_message(void)
|
|||||||
if (msg.message == WM_KEYDOWN || msg.message == WM_SYSKEYDOWN)
|
if (msg.message == WM_KEYDOWN || msg.message == WM_SYSKEYDOWN)
|
||||||
{
|
{
|
||||||
vk = (int) msg.wParam;
|
vk = (int) msg.wParam;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* If a dead key was pressed and the user presses VK_SPACE, VK_BACK, or
|
* Handle dead keys in special conditions in other cases we let Windows
|
||||||
* VK_ESCAPE it means that he actually wants to deal with the dead char
|
* handle them and do not interfere.
|
||||||
* now, so do nothing special and let Windows handle it.
|
|
||||||
*
|
*
|
||||||
* Note that VK_SPACE combines with the dead_key's character and only
|
* The dead_key flag must be reset on several occasions:
|
||||||
* one WM_CHAR will be generated by TranslateMessage(), in the two
|
* - in _OnChar() (or _OnSysChar()) as any dead key was necessarily
|
||||||
* other cases two WM_CHAR will be generated: the dead char and VK_BACK
|
* consumed at that point (This is when we let Windows combine the
|
||||||
* or VK_ESCAPE. That is most likely what the user expects.
|
* dead character on its own)
|
||||||
|
*
|
||||||
|
* - Before doing something special such as regenerating keypresses to
|
||||||
|
* expel the dead character as this could trigger an infinite loop if
|
||||||
|
* for some reason MyTranslateMessage() do not trigger a call
|
||||||
|
* immediately to _OnChar() (or _OnSysChar()).
|
||||||
*/
|
*/
|
||||||
if (dead_key && (vk == VK_SPACE || vk == VK_BACK || vk == VK_ESCAPE))
|
if (dead_key)
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* If a dead key was pressed and the user presses VK_SPACE,
|
||||||
|
* VK_BACK, or VK_ESCAPE it means that he actually wants to deal
|
||||||
|
* with the dead char now, so do nothing special and let Windows
|
||||||
|
* handle it.
|
||||||
|
*
|
||||||
|
* Note that VK_SPACE combines with the dead_key's character and
|
||||||
|
* only one WM_CHAR will be generated by TranslateMessage(), in
|
||||||
|
* the two other cases two WM_CHAR will be generated: the dead
|
||||||
|
* char and VK_BACK or VK_ESCAPE. That is most likely what the
|
||||||
|
* user expects.
|
||||||
|
*/
|
||||||
|
if ((vk == VK_SPACE || vk == VK_BACK || vk == VK_ESCAPE))
|
||||||
{
|
{
|
||||||
dead_key = 0;
|
dead_key = 0;
|
||||||
MyTranslateMessage(&msg);
|
MyTranslateMessage(&msg);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
/* In modes where we are not typing, dead keys should behave
|
||||||
|
* normally */
|
||||||
|
else if (!(get_real_state() & (INSERT | CMDLINE | SELECTMODE)))
|
||||||
|
{
|
||||||
|
outputDeadKey_rePost(msg);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/* Check for CTRL-BREAK */
|
/* Check for CTRL-BREAK */
|
||||||
if (vk == VK_CANCEL)
|
if (vk == VK_CANCEL)
|
||||||
@ -1822,6 +1879,19 @@ process_message(void)
|
|||||||
if (special_keys[i].key_sym == vk
|
if (special_keys[i].key_sym == vk
|
||||||
&& (vk != VK_SPACE || !(GetKeyState(VK_MENU) & 0x8000)))
|
&& (vk != VK_SPACE || !(GetKeyState(VK_MENU) & 0x8000)))
|
||||||
{
|
{
|
||||||
|
/*
|
||||||
|
* Behave as exected if we have a dead key and the special key
|
||||||
|
* is a key that would normally trigger the dead key nominal
|
||||||
|
* character output (such as a NUMPAD printable character or
|
||||||
|
* the TAB key, etc...).
|
||||||
|
*/
|
||||||
|
if (dead_key && (special_keys[i].vim_code0 == 'K'
|
||||||
|
|| vk == VK_TAB || vk == CAR))
|
||||||
|
{
|
||||||
|
outputDeadKey_rePost(msg);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
#ifdef FEAT_MENU
|
#ifdef FEAT_MENU
|
||||||
/* Check for <F10>: Windows selects the menu. When <F10> is
|
/* Check for <F10>: Windows selects the menu. When <F10> is
|
||||||
* mapped we want to use the mapping instead. */
|
* mapped we want to use the mapping instead. */
|
||||||
|
@ -741,6 +741,8 @@ static char *(features[]) =
|
|||||||
|
|
||||||
static int included_patches[] =
|
static int included_patches[] =
|
||||||
{ /* Add new patch number below this line */
|
{ /* Add new patch number below this line */
|
||||||
|
/**/
|
||||||
|
1124,
|
||||||
/**/
|
/**/
|
||||||
1123,
|
1123,
|
||||||
/**/
|
/**/
|
||||||
|
Loading…
x
Reference in New Issue
Block a user