To:
[email protected]
Subject: Patch 6.3a.019 (extra)
Fcc: outbox
From: Bram Moolenaar <
[email protected]>
Mime-Version: 1.0
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: 8bit
------------
Patch 6.3a.019 (extra)
Problem: Win32: typing non-latin1 characters doesn't work.
Solution: Invoke _OnChar() directly to avoid that the argument is truncated
to a byte. Convert the UTF-16 character to bytes according to
'encoding' and ignore 'termencoding'. Same for _OnSysChar().
Files: src/gui_w32.c, src/gui_w48.c
*** ../vim-6.3a.018/src/gui_w32.c Wed May 12 17:24:27 2004
--- src/gui_w32.c Thu May 13 14:15:10 2004
***************
*** 611,617 ****
HANDLE_MSG(hwnd, WM_DEADCHAR, _OnDeadChar);
HANDLE_MSG(hwnd, WM_SYSDEADCHAR, _OnDeadChar);
/* HANDLE_MSG(hwnd, WM_ACTIVATE, _OnActivate); */
- HANDLE_MSG(hwnd, WM_CHAR, _OnChar);
HANDLE_MSG(hwnd, WM_CLOSE, _OnClose);
/* HANDLE_MSG(hwnd, WM_COMMAND, _OnCommand); */
HANDLE_MSG(hwnd, WM_DESTROY, _OnDestroy);
--- 611,616 ----
***************
*** 643,648 ****
--- 642,653 ----
_OnEndSession();
break;
+ case WM_CHAR:
+ /* Don't use HANDLE_MSG() for WM_CHAR, it truncates wParam to a single
+ * byte while we want the UTF-16 character value. */
+ _OnChar(hwnd, wParam, (int)(short)LOWORD(lParam));
+ return 0L;
+
case WM_SYSCHAR:
/*
* if 'winaltkeys' is "no", or it's "menu" and it's not a menu
***************
*** 655,661 ****
|| (p_wak[0] == 'm' && !gui_is_menu_shortcut((int)wParam))
)
#endif
! return HANDLE_WM_SYSCHAR((hwnd), (wParam), (lParam), (_OnSysChar));
#ifdef FEAT_MENU
else
return MyWindowProc(hwnd, uMsg, wParam, lParam);
--- 660,669 ----
|| (p_wak[0] == 'm' && !gui_is_menu_shortcut((int)wParam))
)
#endif
! {
! _OnSysChar(hwnd, wParam, (int)(short)LOWORD(lParam));
! return 0L;
! }
#ifdef FEAT_MENU
else
return MyWindowProc(hwnd, uMsg, wParam, lParam);
***************
*** 663,669 ****
case WM_SYSKEYUP:
#ifdef FEAT_MENU
! /* Thus used to be done only when menu is active: ALT key is used for
* that. But that caused problems when menu is disabled and using
* Alt-Tab-Esc: get into a strange state where no mouse-moved events
* are received, mouse pointer remains hidden. */
--- 671,677 ----
case WM_SYSKEYUP:
#ifdef FEAT_MENU
! /* This used to be done only when menu is active: ALT key is used for
* that. But that caused problems when menu is disabled and using
* Alt-Tab-Esc: get into a strange state where no mouse-moved events
* are received, mouse pointer remains hidden. */
*** ../vim-6.3a.018/src/gui_w48.c Wed May 12 17:24:27 2004
--- src/gui_w48.c Thu May 13 14:09:17 2004
***************
*** 476,483 ****
}
/*
* Key hit, add it to the input buffer.
- * Careful: CSI arrives as 0xffffff9b.
*/
static void
_OnChar(
--- 476,539 ----
}
/*
+ * Convert Unicode character "ch" to bytes in "string[slen]".
+ * Return the length.
+ */
+ static int
+ char_to_string(ch, string, slen)
+ int ch;
+ char_u *string;
+ int slen;
+ {
+ int len;
+ int i;
+ #ifdef FEAT_MBYTE
+ WCHAR wstring[2];
+ char_u *ws = NULL;;
+
+ /* "ch" is a UTF-16 character. Convert it to a string of bytes. When
+ * "enc_codepage" is non-zero use the standard Win32 function, otherwise
+ * use our own conversion function (e.g., for UTF-8). */
+ wstring[0] = ch;
+ if (enc_codepage > 0)
+ len = WideCharToMultiByte(enc_codepage, 0, wstring, 1, string, slen,
+ 0, NULL);
+ else
+ {
+ len = 1;
+ ws = ucs2_to_enc(wstring, &len);
+ if (ws == NULL)
+ len = 0;
+ else
+ {
+ if (len > slen) /* just in case */
+ len = slen;
+ mch_memmove(string, ws, len);
+ vim_free(ws);
+ }
+ }
+ if (len == 0)
+ #endif
+ {
+ string[0] = ch;
+ len = 1;
+ }
+
+ for (i = 0; i < len; ++i)
+ if (string[i] == CSI && len <= slen - 2)
+ {
+ /* Insert CSI as K_CSI. */
+ mch_memmove(string + i + 3, string + i + 1, len - i - 1);
+ string[++i] = KS_EXTRA;
+ string[++i] = (int)KE_CSI;
+ len += 2;
+ }
+
+ return len;
+ }
+
+ /*
* Key hit, add it to the input buffer.
*/
static void
_OnChar(
***************
*** 486,516 ****
int cRepeat)
{
char_u string[40];
! string[0] = ch;
! if (string[0] == Ctrl_C && ctrl_c_interrupts)
{
trash_input_buf();
got_int = TRUE;
}
! if (string[0] == CSI)
! {
! /* Insert CSI as K_CSI. */
! string[1] = KS_EXTRA;
! string[2] = (int)KE_CSI;
! add_to_input_buf(string, 3);
! }
! else
! {
! int len = 1;
!
! #ifdef FEAT_MBYTE
! if (input_conv.vc_type != CONV_NONE)
! len = convert_input(string, len, sizeof(string));
! #endif
! add_to_input_buf(string, len);
! }
}
/*
--- 542,557 ----
int cRepeat)
{
char_u string[40];
+ int len = 0;
! len = char_to_string(ch, string, 40);
! if (len == 1 && string[0] == Ctrl_C && ctrl_c_interrupts)
{
trash_input_buf();
got_int = TRUE;
}
! add_to_input_buf(string, len);
}
/*
***************
*** 565,594 ****
string[len++] = K_SECOND((int)ch);
string[len++] = K_THIRD((int)ch);
}
- else if (ch == CSI)
- {
- string[len++] = CSI;
- string[len++] = KS_EXTRA;
- string[len++] = (int)KE_CSI;
- }
else
{
! string[len++] = ch;
! #ifdef FEAT_MBYTE
! if (input_conv.vc_type != CONV_NONE)
! len += convert_input(string + len - 1, 1, sizeof(string) - len) - 1;
! else if (enc_utf8 && string[len - 1] >= 0x80)
! {
! /* convert to utf-8 */
! string[len] = string[len - 1] & 0xbf;
! string[len - 1] = ((unsigned)string[len - 1] >> 6) + 0xc0;
! if (string[len++] == CSI)
! {
! string[len++] = KS_EXTRA;
! string[len++] = (int)KE_CSI;
! }
! }
! #endif
}
add_to_input_buf(string, len);
--- 606,616 ----
string[len++] = K_SECOND((int)ch);
string[len++] = K_THIRD((int)ch);
}
else
{
! /* Although the documentation isn't clear about it, we assume "ch" is
! * a Unicode character. */
! len += char_to_string(ch, string + len, 40 - len);
}
add_to_input_buf(string, len);
***************
*** 1509,1515 ****
{
MSG msg;
UINT vk = 0; /* Virtual key */
! char_u string[3];
int i;
int modifiers = 0;
int key;
--- 1531,1537 ----
{
MSG msg;
UINT vk = 0; /* Virtual key */
! char_u string[40];
int i;
int modifiers = 0;
int key;
***************
*** 1649,1661 ****
}
else
{
! int len = 1;
! string[0] = key;
! #ifdef FEAT_MBYTE
! if (input_conv.vc_type != CONV_NONE)
! len = convert_input(string, len, sizeof(string));
! #endif
add_to_input_buf(string, len);
}
break;
--- 1671,1680 ----
}
else
{
! int len;
! /* Handle "key" as a Unicode character. */
! len = char_to_string(key, string, 40);
add_to_input_buf(string, len);
}
break;
*** ../vim-6.3a.018/src/version.c Wed May 12 21:56:02 2004
--- src/version.c Thu May 13 14:19:09 2004
***************
*** 643,644 ****
--- 643,646 ----
{ /* Add new patch number below this line */
+ /**/
+ 19,
/**/
--
Microsoft's definition of a boolean: TRUE, FALSE, MAYBE
"Embrace and extend"...?
/// Bram Moolenaar --
[email protected] --
http://www.Moolenaar.net \\\
/// Sponsor Vim, vote for features --
http://www.Vim.org/sponsor/ \\\
\\\ Project leader for A-A-P --
http://www.A-A-P.org ///
\\\ Buy at Amazon and help AIDS victims --
http://ICCF.nl/click1.html ///