Changeset 4051

Show
Ignore:
Timestamp:
2006年03月13日 03時31分50秒 (2 years ago)
Author:
horiguti
Message:

Change of IME control, See ticket:241.

Files:

Legend:

Unmodified
Added
Removed
Modified
Copied
Moved
  • trunk/lisp/ChangeLog.Meadow

    r4049 r4051  
     12006-03-13  Kyotaro HORIGUCHI  <horiguti@meadowy.org> 
     2 
     3        * international/meadow.el (mw32-ime-cont-on): Change default value 
     4        to 'always. 
     5        (mw32-ime-sync-state): Don't sync IME state when 
     6        mw32-ime-composition-window is not nil. Modify to handle (eq 
     7        mw32-ime-cont-on 'always). 
     8        (mw32-ime-initialize): Ditto. 
     9        (mw32-ime-uninitialize): Ditto. 
     10        (mw32-isearch-mode-hook-function): Ditto. 
     11        (mw32-isearch-update): New function. 
     12        (mw32-input-method): Keystroke protection is moved into 
     13        mw32-ime-input-method-function. 
     14 
    1152006-02-28  Shun-ichi GOTO  <gotoh@taiyo.co.jp> 
    216 
  • trunk/lisp/international/meadow.el

    r4044 r4051  
    155155(defvar mw32-ime-mode-line-format-original nil 
    156156  "Original mode line format.") 
    157 (defvar mw32-ime-cont-on t 
    158   "It not nil, IME is always on during current-input-method is MW32-IME.") 
     157(defvar mw32-ime-cont-on 'always 
     158"If not nil, IME is always on during current-input-method is MW32-IME 
     159on the ordinary buffer.") 
    159160(defvar mw32-input-method-noconv-regexp nil 
    160161  "Regexp represents printable-chars that does not activate IME.") 
     
    330331 
    331332(defun mw32-ime-sync-state (window) 
    332   (when mw32-ime-buffer-switch-p 
     333  (when (and mw32-ime-buffer-switch-p 
     334             (not mw32-ime-composition-window)) 
    333335    (with-current-buffer (window-buffer window) 
    334336      (if (window-minibuffer-p) 
     
    340342          (if mw32-ime-cont-on 
    341343              (if (string= current-input-method "MW32-IME") 
    342                   (if (eq input-method-function 'mw32-input-method) 
     344                  (if (or (eq mw32-ime-cont-on 'always) 
     345                          (eq input-method-function 'mw32-input-method)) 
    343346                      (fep-force-on)) 
    344347                (fep-force-off)))))))) 
     
    410413      (defadvice isearch-toggle-input-method (after mw32-fep-off activate) 
    411414        "Deactivate fep when mw32-ime-cont-on is not nil." 
    412         (if mw32-ime-cont-on (fep-force-off))) 
     415        (if (eq mw32-ime-cont-on t) (fep-force-off))) 
    413416      (defadvice isearch-done (after mw32-fep-on activate) 
    414417        "Deactivate fep when mw32-ime-cont-on is not nil." 
    415418        (if (and mw32-ime-cont-on 
    416419                 (string= current-input-method "MW32-IME")) 
    417             (fep-force-on))))))) 
     420            (fep-force-on) 
     421          (fep-force-off)) 
     422        (setq mw32-ime-composition-window nil)))))) 
     423 
     424(defun mw32-isearch-update () 
     425  (interactive) 
     426  (isearch-update)) 
    418427 
    419428(defun mw32-isearch-mode-hook-function () 
    420   (if mw32-ime-cont-on 
    421       (fep-force-off)) 
     429  (cond 
     430   ((eq mw32-ime-cont-on t) 
     431    (fep-force-off)) 
     432   ((eq mw32-ime-cont-on 'always) 
     433    (setq mw32-ime-composition-window (minibuffer-window)))) 
    422434  (define-key isearch-mode-map [kanji] 'isearch-toggle-input-method) 
    423   (define-key isearch-mode-map [compend] 'ignore)) 
     435  (define-key isearch-mode-map [compend] 'mw32-isearch-update)) 
    424436       
    425437     
     
    461473          (add-hook 'minibuffer-exit-hook 'mw32-ime-exit-from-minibuffer)) 
    462474        (make-local-variable 'input-method-function) 
    463         (setq input-method-function 'mw32-input-method
    464         (if (and mw32-ime-cont-on 
    465                 (not (window-minibuffer-p))) 
     475        (if (not (eq mw32-ime-cont-on 'always)
     476            (setq input-method-function 'mw32-input-method)) 
     477        (if mw32-ime-cont-on 
    466478            (fep-force-on))) 
    467479    (setq current-input-method nil) 
     
    529541    (let ((redisplay-dont-pause t)) 
    530542      (sit-for 0)) 
    531     (mw32-protect-fep-input) 
    532     (fep-force-on) 
     543 
    533544    (let* ((pos (point)) 
    534545           (modified-p (buffer-modified-p)) 
    535546           (ov (make-overlay (point) (1+ (point)))) 
    536            (ret (mw32-ime-input-method-function (char-to-string key))) 
    537            (result (append (car ret) nil)) 
    538            (redisplay-dont-pause t)) 
    539       ;; Continue to conversion if composition string cannot be 
    540       ;; convert into single ascii character. 
     547           (redisplay-dont-pause t) 
     548           ret result) 
    541549      (unwind-protect 
    542           (while (or 
    543                   (> (length (cadr ret)) 1) 
    544                   (and 
    545                    (cadr ret) 
    546                    (> (length (cadr ret)) 0) 
    547                    (not (eq (string-to-char (japanese-hankaku (cadr ret))) 
    548                             (car (cddr ret)))))) 
    549             (insert (car ret)) 
    550             (move-overlay ov pos (point)) 
    551             (if input-method-highlight-flag 
    552                 (overlay-put ov 'face 'underline)) 
    553             (sit-for 0) 
    554             (setq ret (mw32-ime-input-method-function)) 
    555             (setq result (append result (append (car ret) nil)))) 
     550          (progn 
     551            (setq ret  (mw32-ime-input-method-function (char-to-string key))) 
     552            (setq result (append (car ret) nil)) 
     553            (while (> (length (cadr ret)) 1) 
     554              (insert (car ret)) 
     555              (move-overlay ov pos (point)) 
     556              (if input-method-highlight-flag 
     557                  (overlay-put ov 'face 'underline)) 
     558              (sit-for 0) 
     559              (setq ret (mw32-ime-input-method-function)) 
     560              (setq result (append result (append (car ret) nil))))) 
    556561        (if (and (cadr ret) 
    557                  (eq (length (cadr ret)) 1) 
    558                  (eq (string-to-char (japanese-hankaku (cadr ret))) 
    559                      (car (cddr ret)))) 
    560             (setq unread-input-method-events 
    561                   (cons (car (cddr ret)) unread-input-method-events))) 
    562         (fep-force-off) 
     562                 (eq (length (cadr ret)) 1)) 
     563            (progn 
     564              (setq unread-input-method-events 
     565                    (cons (car (cddr ret)) unread-input-method-events)))) 
    563566        (delete-region pos (point)) 
    564567        (delete-overlay ov) 
     
    576579 
    577580(provide 'meadow) 
    578  
    579  
  • trunk/src/ChangeLog.Meadow

    r4044 r4051  
     12006-03-13  Kyotaro HORIGUCHI  <horiguti@meadowy.org> 
     2 
     3        * mw32term.h (WM_EMACS_FLUSH_MESSAGE): New message. 
     4        (WM_EMACS_KEYSTROKE): New message. 
     5 
     6        * mw32term.c (mw32_message_loop): Modify related to IME input. 
     7        (mw32_message_loop<WM_EMACS_FLUSH_MESSAGE>): New message handler. 
     8        (mw32_message_loop<WM_EMACS_KEYSTROKE>): New message handler.   (mw32_message_loop<WM_KEYDOWN>): Modify related to IME input. 
     9 
     10        * mw32ime.c (Vmw32_ime_composition_window): New variable. 
     11        (mw32_set_ime_conv_window): Use Vmw32_ime_composition_window if 
     12        possible. 
     13        (mw32_ime_record_keycode): Don't record keycode when choking 
     14        keystrokes. 
     15        (mw32_get_ime_result_string): Start keystroke choking immediately 
     16        if needed. 
     17        (mw32_ime_choke_keystroke): Add parameter for debugging. 
     18        (mw32_ime_stop_choke_keystrokes): New function. 
     19        (mw32_change_shift_state): New function. 
     20        (mw32_ime_inject_keystrokes): Moved out from 
     21        mw32-ime-input-method-function and widen applicable chars. 
     22        (mw32_ime_inject_keymessage): New function. 
     23        (mw32_ime_input_method_function_unwind): Fix coding style. Stop 
     24        choking keystrokes and put them into message queue. 
     25        (mw32-ime-input-method-function): Improve tolerance of key 
     26        fastshot. 
     27        (mw32-protect-fep-input): Removed. 
     28        (fep-force-on): Don't send keyup message. 
     29        (fep-force-on): Ditto. 
     30        (syms_of_mw32ime): Add initialize of Vmw32_ime_composition_window. 
     31 
    1322006-02-24  Kyotaro HORIGUCHI  <horiguti@meadowy.org> 
    233 
  • trunk/src/mw32ime.c

    r4044 r4051  
    160160Lisp_Object VIME_command_off_flag; 
    161161Lisp_Object Qim_info; 
     162Lisp_Object Vmw32_ime_composition_window; 
    162163int mw32_fep_switch_by_key_event; 
    163164 
     
    182183mw32_ime_record_keycode (int keycode, int keymod) 
    183184{ 
     185  if (choke_keystroke) 
     186    return; 
     187 
    184188  last_ime_vkeycode = keycode; 
    185189  last_ime_vkeymod  = keymod; 
     
    193197      HWND IMEhwnd; 
    194198      COMPOSITIONFORM cf; 
     199 
     200      /* If Vmw32_ime_composition_window is set, try it. */ 
     201      if (!NILP (Vmw32_ime_composition_window) 
     202          && WINDOWP (Vmw32_ime_composition_window) 
     203          && WINDOW_FRAME (XWINDOW (Vmw32_ime_composition_window)) 
     204          == WINDOW_FRAME (w)) 
     205        w = XWINDOW (Vmw32_ime_composition_window); 
    195206 
    196207      IMEhwnd = (ImmGetDefaultIMEWndProc) (hwnd); 
     
    289300  struct mw32_display_info *dpyinfo = GET_MW32_DISPLAY_INFO (hwnd); 
    290301 
     302  if (waiting_on_main_thread) 
     303    choke_keystroke = TRUE; 
     304   
    291305  hIMC = (ImmGetContextProc) (hwnd); 
    292306  if (!hIMC) return FALSE; 
     
    799813} 
    800814 
     815 
     816/* Keystroke choking functions. 
     817   Snatch keystrokes on IME switching. This cannot be perfectly done 
     818   by other than filter driver of keyboard. Here is the second best 
     819   way that occasionally fails to protect the order of keystrokes. */ 
    801820int 
    802 mw32_ime_choke_keystroke (int keycode
     821mw32_ime_choke_keystroke (int keycode, int n
    803822{ 
    804823  if (! choke_keystroke 
    805824      || keycode == 0 
    806       || choked_key_index >= CHOKEDKEYBUFLEN) return FALSE; 
     825      || choked_key_index >= CHOKEDKEYBUFLEN) 
     826    return FALSE; 
    807827 
    808828  choked_key_buf[choked_key_index++] = keycode; 
     829  choked_key_buf[choked_key_index] = 0; 
    809830 
    810831  return TRUE; 
     832} 
     833 
     834int 
     835mw32_ime_stop_choke_keystrokes () 
     836{ 
     837  choke_keystroke = 0; 
     838  choked_key_index = 0; 
     839  choked_key_buf[0] = 0; 
     840   
     841  return 0; 
     842} 
     843 
     844/* Key strokes cannot be directly posted into IME process. */ 
     845static void 
     846mw32_change_shift_state (int *ctrlstate, int ctrl, int *shiftstate, int shift) 
     847{ 
     848  if (*ctrlstate && ! ctrl) 
     849    mw32_send_key_input (VK_CONTROL, 0, KEYEVENTF_KEYUP); 
     850  else if (! *ctrlstate && ctrl) 
     851    mw32_send_key_input (VK_CONTROL, 0, 0); 
     852  if (*shiftstate && ! shift) 
     853    mw32_send_key_input (VK_SHIFT, 0, KEYEVENTF_KEYUP); 
     854  else if (! *shiftstate && shift) 
     855    mw32_send_key_input (VK_SHIFT, 0, 0); 
     856 
     857  *ctrlstate = ctrl; 
     858  *shiftstate = shift; 
     859} 
     860 
     861 
     862static void 
     863mw32_ime_inject_keystrokes (char *str) 
     864{ 
     865  char *p; 
     866  int orgctrlstate, ctrlstate; 
     867  int orgshiftstate, shiftstate; 
     868 
     869  /* Cancel control key if pressed */ 
     870  orgctrlstate = ctrlstate = (GetKeyState (VK_CONTROL) & 0x80) != 0; 
     871  orgshiftstate = shiftstate = (GetKeyState (VK_SHIFT) & 0x80) != 0; 
     872   
     873  /* str assumed not to contain non-ascii characters. */ 
     874  for (p = str ; *p ; p++) 
     875    { 
     876      SHORT ret; 
     877      int vk; 
     878      UINT sc; 
     879      int ctrl, shift; 
     880      HKL kl; 
     881 
     882      kl = GetKeyboardLayout (0); 
     883      ret = VkKeyScanEx (*p, kl); 
     884      if (ret == 0xffff) continue; 
     885      ctrl = ((ret & 0x200) != 0); 
     886      shift = ((ret & 0x100) != 0); 
     887      vk = ret & 0xff; 
     888      sc = MapVirtualKeyEx (vk, 0, kl); 
     889 
     890      mw32_change_shift_state (&ctrlstate, ctrl, &shiftstate, shift); 
     891 
     892      if (GetKeyState (vk) & 0x8000) 
     893        mw32_send_key_input (vk, sc, KEYEVENTF_KEYUP); 
     894      mw32_send_key_input (vk, sc, 0); 
     895    } 
     896   
     897  mw32_change_shift_state (&ctrlstate, orgctrlstate, 
     898                           &shiftstate, orgshiftstate); 
     899} 
     900 
     901/* Keystrokes can be posted directly into message thread while IME is 
     902   deactivated. */ 
     903void 
     904mw32_ime_inject_keymessage (char *str) 
     905{ 
     906  char *p; 
     907 
     908  for (p = str ; *p ; p++) 
     909    { 
     910      PostMessage (FRAME_MW32_WINDOW (XFRAME (selected_frame)), 
     911                   WM_EMACS_KEYSTROKE, 
     912                   toupper (*p), 
     913                   1); 
     914    } 
     915 
     916  if (*p) 
     917    PostMessage (FRAME_MW32_WINDOW (XFRAME (selected_frame)), 
     918                 WM_EMACS_FLUSH_MESSAGE, 0, 0); 
    811919} 
    812920 
     
    824932}        
    825933 
    826 Lisp_Object mw32_ime_input_method_function_unwind (arg) 
    827   Lisp_Object arg; 
     934Lisp_Object 
     935mw32_ime_input_method_function_unwind (arg) 
     936     Lisp_Object arg; 
    828937{ 
    829938  mw32_ime_cancel_input_function (); 
     
    832941    Ffep_force_off (Qnil); 
    833942 
     943  if (choked_key_index > 0) 
     944    mw32_ime_inject_keymessage (choked_key_buf); 
     945  mw32_ime_stop_choke_keystrokes (); 
    834946  return Qnil; 
    835947} 
     
    866978  ResetEvent (input_method_function_event); 
    867979 
    868   Fmw32_protect_fep_input ()
     980  choke_keystroke = TRUE
    869981  Ffep_force_on (Qnil); 
    870982 
    871983  result = Qnil; 
     984 
     985  /* Flush received but not emacs-queued message. */ 
     986  PostMessage (FRAME_MW32_WINDOW (XFRAME (selected_frame)), 
     987               WM_EMACS_FLUSH_MESSAGE, 0, 0); 
    872988 
    873989  /* If new ascii (expected..) key event comes after this function 
    874990     invoked, get it and add to composition string. */ 
    875   if (kbd_buffer_events_waiting (0)) 
     991  while (kbd_buffer_events_waiting (0)) 
    876992    { 
    877993      Lisp_Object kseq, args[2]; 
     
    8871003  /* redisplay won't done when waiting keyevents exist. */ 
    8881004  redisplay_preserve_echo_area (30); 
    889  
    890   /* Key strokes after keystroke choking has turned on till here is 
    891      stored into choked_key_buf */ 
     1005  mw32_set_ime_conv_window (hwnd, 
     1006                            cursor_in_echo_area ? 
     1007                            XWINDOW (f->minibuffer_window): 
     1008                            XWINDOW (f->selected_window)); 
     1009 
    8921010  if (choked_key_index > 0) 
    8931011    { 
     
    8971015      str = Fconcat (2, args); 
    8981016    } 
    899   choke_keystroke = FALSE; 
    900   choked_key_index = 0; 
    901  
    902   mw32_set_ime_conv_window (hwnd, 
    903                             cursor_in_echo_area ? 
    904                             XWINDOW (f->minibuffer_window): 
    905                             XWINDOW (f->selected_window)); 
    906  
    907   /* Put the initnal string into IME via message. */ 
     1017  mw32_ime_stop_choke_keystrokes (); 
    9081018  if (STRINGP (str)) 
    909     { 
    910       char *p; 
    911       int ctrlstate; 
    912  
    913       /* Cancel control key if pressed */ 
    914       ctrlstate = GetKeyState (VK_CONTROL) & 0x80; 
    915       if (ctrlstate) 
    916         mw32_send_key_input (VK_CONTROL, 0, KEYEVENTF_KEYUP); 
    917  
    918       /* str assumed not to contain non-ascii characters. */ 
    919       for (p = SDATA (str) ; *p ; p++) 
    920         { 
    921           int c = toupper (*p); 
    922            
    923           mw32_send_key_input (c, 0, 0); 
    924           mw32_send_key_input (c, 0, KEYEVENTF_KEYUP); 
    925         } 
    926  
    927       /* Restore the state of control key */ 
    928       if (ctrlstate) 
    929         mw32_send_key_input (VK_CONTROL, 0, 0); 
    930     } 
     1019    mw32_ime_inject_keystrokes (SDATA (str)); 
    9311020 
    9321021  /* Rescue from dead block. This may not happen. */ 
     
    9351024    QUIT; 
    9361025 
     1026  choke_keystroke = TRUE; 
    9371027  hstr = input_method_function_string; 
    9381028  input_method_function_string = INVALID_HANDLE_VALUE; 
     
    9751065  result = Fcons (resultstr, 
    9761066                  Fcons (compstr, 
    977                          Fcons (make_number (last_ime_vkeymod ? 0 
    978                                              : last_ime_vkeycode), 
     1067                         Fcons (make_number (last_ime_vkeycode), 
    9791068                                Qnil))); 
    980  
    9811069  return unbind_to (count, result); 
    9821070} 
     
    9991087{ 
    10001088  return (make_number (((int)GetKeyboardLayout (0)) & 0xffff)); 
    1001 } 
    1002  
    1003 DEFUN ("mw32-protect-fep-input", Fmw32_protect_fep_input, Smw32_protect_fep_input, 0, 0, 0, 
    1004        doc: /* Start choking of fep-input to protect them from disordering 
    1005 on fep-swithing. 
    1006 This function is internal function for mw32-input-method. */) 
    1007   () 
    1008 { 
    1009   if (NILP (Ffep_get_mode ())) 
    1010     choke_keystroke = TRUE; 
    1011  
    1012   return Qnil; 
    10131089} 
    10141090 
     
    10371113          ResetEvent (fep_switch_event); 
    10381114          mw32_send_key_input (VK_KANJI, 0, 0); 
    1039           mw32_send_key_input (VK_KANJI, 0, KEYEVENTF_KEYUP); 
    10401115          WaitForSingleObject (fep_switch_event, 500L); 
    10411116        } 
     
    10721147          ResetEvent (fep_switch_event); 
    10731148          mw32_send_key_input (VK_KANJI, 0, 0); 
    1074           mw32_send_key_input (VK_KANJI, 0, KEYEVENTF_KEYUP); 
    10751149          WaitForSingleObject (fep_switch_event, 500L); 
    10761150        } 
     
    19272001and `fep-force-off'. */); 
    19282002  mw32_fep_switch_by_key_event = FALSE; 
     2003  DEFVAR_LISP ("mw32-ime-composition-window", &Vmw32_ime_composition_window, 
     2004               doc: /* If this is a window of current frame, IME composition window appears on the 
     2005window instead of current window." */); 
     2006  Vmw32_ime_composition_window = Qnil; 
    19292007 
    19302008  defsubr (&Simm_get_conversion_status); 
     
    19322010  defsubr (&Smw32_ime_available); 
    19332011  defsubr (&Smw32_input_language_code); 
    1934   defsubr (&Smw32_protect_fep_input); 
    19352012  defsubr (&Sfep_force_on); 
    19362013  defsubr (&Sfep_force_off); 
  • trunk/src/mw32term.c

    r4044 r4051  
    36213621  in.ki.wScan = scancode; 
    36223622  in.ki.dwFlags = flags; 
    3623   in.ki.time = GetTickCount ()
     3623  in.ki.time = 0
    36243624  in.ki.dwExtraInfo = 0; 
    36253625  SendInputProc (1, &in, sizeof (in)); 
     
    45804580      int up; 
    45814581      int modifier; 
     4582      int injected_key; 
    45824583 
    45834584      if (lastmsgp) lastmsgp = 0; 
     
    46124613        f = NULL; 
    46134614 
     4615      injected_key = FALSE; 
    46144616      switch (msg.message) 
    46154617        { 
     4618        case WM_EMACS_FLUSH_MESSAGE: 
     4619          return count; 
     4620 
     4621        case WM_EMACS_KEYSTROKE: 
     4622          injected_key = TRUE; 
     4623          msg.message = WM_KEYDOWN; 
     4624          /*  fall through */ 
    46164625        case WM_KEYDOWN: 
    46174626        case WM_SYSKEYDOWN: 
     
    46274636                { 
    46284637                  int vkey = mw32_ime_get_virtual_key (msg.hwnd); 
    4629                   mw32_emacs_translate_message (dpyinfo, 1, vkey, 
    4630                                                 &keycode, &keymod); 
    4631                   mw32_ime_record_keycode (keycode, keymod); 
    4632                   if (mw32_ime_choke_keystroke (keycode)) 
    4633                     break; 
     4638                  if (mw32_emacs_translate_message (dpyinfo, 1, vkey, 
     4639                                                    &keycode, &keymod) == 1) 
     4640                    { 
     4641                      mw32_ime_record_keycode (keycode, keymod); 
     4642                      if (mw32_ime_choke_keystroke (keycode, 0)) 
     4643                        break; 
     4644                    } 
    46344645                } 
    46354646              keyflag = mw32_emacs_translate_message (dpyinfo, 1, msg.wParam, 
    46364647                                                      &keycode, &keymod); 
    46374648 
    4638               if (keyflag ==1 && mw32_ime_choke_keystroke (keycode)) 
     4649              if (keyflag == 1 
     4650                  && ! injected_key 
     4651                  && mw32_ime_choke_keystroke (keycode, 1)) 
    46394652                break; 
    46404653 
  • trunk/src/mw32term.h

    r4042 r4051  
    839839#define WM_EMACS_UPDATE_ALPHA                   (WM_USER+2013) 
    840840#define WM_EMACS_EXPOSE_FRAME                   (WM_USER+2014) 
     841#define WM_EMACS_KEYSTROKE                      (WM_USER+2015) 
     842#define WM_EMACS_FLUSH_MESSAGE                  (WM_USER+2016) 
    841843/* to report "switch-buffer" event by himi */ 
    842844#define WM_IME_REPORT     0x0280