Bug 855975 part.14 Move following WM_*CHAR message handler from nsWindow::OnKeyDown() to widget::NativeKey::DispatchKeyPressEventForFollowingCharMessage() r=jimm
authorMasayuki Nakano <masayuki@d-toybox.com>
Wed, 29 May 2013 15:34:48 +0900
changeset 133251 91ba04b50639072addaaa5882251cf5ae976c650
parent 133250 fef076fed8ab620052e9d4474c93a7162958cdb3
child 133252 0ed82af5475f4de390a9d5c9dad982a296bd36e3
push id24747
push useremorley@mozilla.com
push dateWed, 29 May 2013 14:24:37 +0000
treeherdermozilla-central@8d85de779506 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersjimm
bugs855975
milestone24.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 855975 part.14 Move following WM_*CHAR message handler from nsWindow::OnKeyDown() to widget::NativeKey::DispatchKeyPressEventForFollowingCharMessage() r=jimm
widget/windows/KeyboardLayout.cpp
widget/windows/KeyboardLayout.h
widget/windows/nsWindow.cpp
--- a/widget/windows/KeyboardLayout.cpp
+++ b/widget/windows/KeyboardLayout.cpp
@@ -13,16 +13,17 @@
 #include "nsQuickSort.h"
 #include "nsAlgorithm.h"
 #include "nsGUIEvent.h"
 #include "nsUnicharUtils.h"
 #include "WidgetUtils.h"
 #include "WinUtils.h"
 #include "nsWindowDbg.h"
 #include "nsServiceManagerUtils.h"
+#include "nsPrintfCString.h"
 
 #include "nsIDOMKeyEvent.h"
 #include "nsIIdleServiceInternal.h"
 
 #include "npapi.h"
 
 #include <windows.h>
 #include <winuser.h>
@@ -1195,16 +1196,71 @@ NativeKey::DispatchKeyPressEventsWithKey
     keypressEvent.alternativeCharCodes.AppendElements(altArray);
     InitKeyEvent(keypressEvent, modKeyState);
     defaultPrevented = (DispatchKeyEvent(keypressEvent) || defaultPrevented);
   }
 
   return defaultPrevented;
 }
 
+bool
+NativeKey::DispatchKeyPressEventForFollowingCharMessage(
+                        const UniCharsAndModifiers& aInputtingChars,
+                        const EventFlags& aExtraFlags) const
+{
+  MOZ_ASSERT(mMsg.message == WM_KEYDOWN || mMsg.message == WM_SYSKEYDOWN);
+
+  const MSG& msg = RemoveFollowingCharMessage();
+  if (mIsFakeCharMsg) {
+    if (msg.message == WM_DEADCHAR) {
+      return aExtraFlags.mDefaultPrevented;
+    }
+#ifdef DEBUG
+    if (IsPrintableKey()) {
+      nsPrintfCString log(
+        "mOriginalVirtualKeyCode=0x%02X, aInputtingChars={ mChars=[ 0x%04X, "
+        "0x%04X, 0x%04X, 0x%04X, 0x%04X ], mLength=%d }, wParam=0x%04X",
+        mOriginalVirtualKeyCode, aInputtingChars.mChars[0],
+        aInputtingChars.mChars[1], aInputtingChars.mChars[2],
+        aInputtingChars.mChars[3], aInputtingChars.mChars[4],
+        aInputtingChars.mLength, msg.wParam);
+      if (aInputtingChars.IsEmpty()) {
+        log.Insert("length is zero: ", 0);
+        NS_ERROR(log.get());
+        NS_ABORT();
+      } else if (aInputtingChars.mChars[0] != msg.wParam) {
+        log.Insert("character mismatch: ", 0);
+        NS_ERROR(log.get());
+        NS_ABORT();
+      }
+    }
+#endif // #ifdef DEBUG
+    return HandleCharMessage(msg, nullptr, &aExtraFlags);
+  }
+
+  // If prevent default set for keydown, do same for keypress
+  if (msg.message == WM_DEADCHAR) {
+    bool defaultPrevented = aExtraFlags.mDefaultPrevented;
+    if (mWidget->PluginHasFocus()) {
+      // We need to send the removed message to focused plug-in.
+      defaultPrevented = mWidget->DispatchPluginEvent(msg) || defaultPrevented;
+    }
+    return defaultPrevented;
+  }
+
+  bool defaultPrevented = (HandleCharMessage(msg, nullptr, &aExtraFlags) ||
+                           aExtraFlags.mDefaultPrevented);
+  // If a syschar keypress wasn't processed, Windows may want to
+  // handle it to activate a native menu.
+  if (!defaultPrevented && msg.message == WM_SYSCHAR) {
+    ::DefWindowProcW(msg.hwnd, msg.message, msg.wParam, msg.lParam);
+  }
+  return defaultPrevented;
+}
+
 /*****************************************************************************
  * mozilla::widget::KeyboardLayout
  *****************************************************************************/
 
 KeyboardLayout* KeyboardLayout::sInstance = nullptr;
 nsIIdleServiceInternal* KeyboardLayout::sIdleService = nullptr;
 
 // static
--- a/widget/windows/KeyboardLayout.h
+++ b/widget/windows/KeyboardLayout.h
@@ -362,16 +362,25 @@ public:
    * Returns true if the dispatched keypress event is consumed.  Otherwise,
    * false.
    */
   bool DispatchKeyPressEventsAndDiscardsCharMessages(
                         const UniCharsAndModifiers& aInputtingChars,
                         const EventFlags& aExtraFlags) const;
 
   /**
+   * DispatchKeyPressEventForFollowingCharMessage() dispatches keypress event
+   * for following WM_*CHAR message.
+   * Returns true if the event is consumed.  Otherwise, false.
+   */
+  bool DispatchKeyPressEventForFollowingCharMessage(
+                        const UniCharsAndModifiers& aInputtingChars,
+                        const EventFlags& aExtraFlags) const;
+
+  /**
    * Checkes whether the key event down message is handled without following
    * WM_CHAR messages.  For example, if following WM_CHAR message indicates
    * control character input, the WM_CHAR message is unclear whether it's
    * caused by a printable key with Ctrl or just a function key such as Enter
    * or Backspace.
    */
   bool NeedsToHandleWithoutFollowingCharMessages() const;
 
--- a/widget/windows/nsWindow.cpp
+++ b/widget/windows/nsWindow.cpp
@@ -6452,69 +6452,23 @@ LRESULT nsWindow::OnKeyDown(const MSG &a
   extraFlags.mDefaultPrevented = noDefault;
 
   if (nativeKey.NeedsToHandleWithoutFollowingCharMessages()) {
     return nativeKey.DispatchKeyPressEventsAndDiscardsCharMessages(
                        inputtingChars, extraFlags);
   }
 
   if (nativeKey.IsFollowedByCharMessage()) {
-    const MSG& msg = nativeKey.RemoveFollowingCharMessage();
-    if (aFakeCharMessage) {
-      if (msg.message == WM_DEADCHAR) {
-        return false;
-      }
-#ifdef DEBUG
-      if (nativeKey.IsPrintableKey()) {
-        nsPrintfCString log(
-          "OriginalVirtualKeyCode=0x%02X, inputtingChar={ mChars=[ 0x%04X, "
-          "0x%04X, 0x%04X, 0x%04X, 0x%04X ], mLength=%d }, wParam=0x%04X",
-          nativeKey.GetOriginalVirtualKeyCode(), inputtingChars.mChars[0],
-          inputtingChars.mChars[1], inputtingChars.mChars[2],
-          inputtingChars.mChars[3], inputtingChars.mChars[4],
-          inputtingChars.mLength, msg.wParam);
-        if (!inputtingChars.mLength) {
-          log.Insert("length is zero: ", 0);
-          NS_ERROR(log.get());
-          NS_ABORT();
-        } else if (inputtingChars.mChars[0] != msg.wParam) {
-          log.Insert("character mismatch: ", 0);
-          NS_ERROR(log.get());
-          NS_ABORT();
-        }
-      }
-#endif // #ifdef DEBUG
-      return static_cast<LRESULT>(
-        nativeKey.HandleCharMessage(msg, nullptr, &extraFlags));
-    }
-
-    // If prevent default set for keydown, do same for keypress
-    if (msg.message == WM_DEADCHAR) {
-      if (!PluginHasFocus())
-        return false;
-
-      // We need to send the removed message to focused plug-in.
-      nsWindowBase::DispatchPluginEvent(msg);
-      return noDefault;
-    }
-
-    PR_LOG(gWindowsLog, PR_LOG_ALWAYS,
-           ("%s charCode=%d scanCode=%d\n",
-            msg.message == WM_SYSCHAR ? "WM_SYSCHAR" : "WM_CHAR",
-            msg.wParam, HIWORD(msg.lParam) & 0xFF));
-
-    bool result = nativeKey.HandleCharMessage(msg, nullptr, &extraFlags);
-    // If a syschar keypress wasn't processed, Windows may want to
-    // handle it to activate a native menu.
-    if (!result && msg.message == WM_SYSCHAR)
-      ::DefWindowProcW(mWnd, msg.message, msg.wParam, msg.lParam);
-    return static_cast<LRESULT>(result);
-  }
-  else if (!aModKeyState.IsControl() && !aModKeyState.IsAlt() &&
-            !aModKeyState.IsWin() && nativeKey.IsPrintableKey()) {
+    return static_cast<LRESULT>(
+      nativeKey.DispatchKeyPressEventForFollowingCharMessage(inputtingChars,
+                                                             extraFlags));
+  }
+
+  if (!aModKeyState.IsControl() && !aModKeyState.IsAlt() &&
+      !aModKeyState.IsWin() && nativeKey.IsPrintableKey()) {
     // If this is simple KeyDown event but next message is not WM_CHAR,
     // this event may not input text, so we should ignore this event.
     // See bug 314130.
     return PluginHasFocus() && noDefault;
   }
 
   if (nativeKey.IsDeadKey()) {
     return PluginHasFocus() && noDefault;