Bug 1436508 part 5. Switch xbl from nsIDOMKeyEvent to KeyboardEvent. r=masayuki
authorBoris Zbarsky <bzbarsky@mit.edu>
Fri, 09 Feb 2018 11:17:09 -0500
changeset 403177 4e2f9290346a
parent 403176 51d688aa1c80
child 403178 f1f2b10c62e7
push id33416
push userarchaeopteryx@coole-files.de
push date2018-02-09 22:32 +0000
treeherdermozilla-central@c2cddb0cbb20 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersmasayuki
bugs1436508
milestone60.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 1436508 part 5. Switch xbl from nsIDOMKeyEvent to KeyboardEvent. r=masayuki MozReview-Commit-ID: COqUWh5xjfH
dom/events/Event.h
dom/events/KeyboardEvent.h
dom/events/UIEvent.h
dom/xbl/nsXBLEventHandler.cpp
dom/xbl/nsXBLEventHandler.h
dom/xbl/nsXBLPrototypeHandler.cpp
dom/xbl/nsXBLPrototypeHandler.h
dom/xbl/nsXBLWindowKeyHandler.cpp
dom/xbl/nsXBLWindowKeyHandler.h
--- a/dom/events/Event.h
+++ b/dom/events/Event.h
@@ -30,16 +30,17 @@ namespace mozilla {
 namespace dom {
 
 class BeforeUnloadEvent;
 class EventTarget;
 class EventMessageAutoOverride;
 // ExtendableEvent is a ServiceWorker event that is not
 // autogenerated since it has some extra methods.
 class ExtendableEvent;
+class KeyboardEvent;
 class TimeEvent;
 class WantsPopupControlCheck;
 #define GENERATED_EVENT(EventClass_) class EventClass_;
 #include "mozilla/dom/GeneratedEventList.h"
 #undef GENERATED_EVENT
 
 // Dummy class so we can cast through it to get from nsISupports to
 // Event subclasses with only two non-ambiguous static casts.
@@ -114,16 +115,22 @@ public:
   virtual TimeEvent* AsTimeEvent() { return nullptr; }
 
   // BeforeUnloadEvent is not autogenerated because it has a setter.
   virtual BeforeUnloadEvent* AsBeforeUnloadEvent()
   {
     return nullptr;
   }
 
+  // KeyboardEvent has all sorts of non-autogeneratable bits so far.
+  virtual KeyboardEvent* AsKeyboardEvent()
+  {
+    return nullptr;
+  }
+
   // nsIDOMEvent Interface
   NS_DECL_NSIDOMEVENT
 
   void InitPresContextData(nsPresContext* aPresContext);
 
   // Returns true if the event should be trusted.
   bool Init(EventTarget* aGlobal);
 
--- a/dom/events/KeyboardEvent.h
+++ b/dom/events/KeyboardEvent.h
@@ -27,16 +27,21 @@ public:
   NS_DECL_ISUPPORTS_INHERITED
 
   // nsIDOMKeyEvent Interface
   NS_DECL_NSIDOMKEYEVENT
 
   // Forward to base class
   NS_FORWARD_TO_UIEVENT
 
+  virtual KeyboardEvent* AsKeyboardEvent() override
+  {
+    return this;
+  }
+
   static already_AddRefed<KeyboardEvent> Constructor(
                                            const GlobalObject& aGlobal,
                                            const nsAString& aType,
                                            const KeyboardEventInit& aParam,
                                            ErrorResult& aRv);
 
   virtual JSObject* WrapObjectInternal(JSContext* aCx, JS::Handle<JSObject*> aGivenProto) override
   {
--- a/dom/events/UIEvent.h
+++ b/dom/events/UIEvent.h
@@ -31,16 +31,17 @@ public:
   NS_DECL_ISUPPORTS_INHERITED
   NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(UIEvent, Event)
 
   // nsIDOMUIEvent Interface
   NS_DECL_NSIDOMUIEVENT
 
   // Forward to Event
   NS_FORWARD_TO_EVENT_NO_SERIALIZATION_NO_DUPLICATION
+  using Event::GetCurrentTarget;  // Because the forwarding thing shadows it.
   NS_IMETHOD DuplicatePrivateData() override;
   NS_IMETHOD_(void) Serialize(IPC::Message* aMsg, bool aSerializeInterfaceType) override;
   NS_IMETHOD_(bool) Deserialize(const IPC::Message* aMsg, PickleIterator* aIter) override;
 
 
   static already_AddRefed<UIEvent> Constructor(const GlobalObject& aGlobal,
                                                const nsAString& aType,
                                                const UIEventInit& aParam,
@@ -116,16 +117,17 @@ protected:
 };
 
 } // namespace dom
 } // namespace mozilla
 
 #define NS_FORWARD_TO_UIEVENT                               \
   NS_FORWARD_NSIDOMUIEVENT(UIEvent::)                       \
   NS_FORWARD_TO_EVENT_NO_SERIALIZATION_NO_DUPLICATION       \
+  using Event::GetCurrentTarget;  /* Forwarding shadows */  \
   NS_IMETHOD DuplicatePrivateData() override                \
   {                                                         \
     return UIEvent::DuplicatePrivateData();                 \
   }                                                         \
   NS_IMETHOD_(void) Serialize(IPC::Message* aMsg,           \
                               bool aSerializeInterfaceType) \
     override                                                \
   {                                                         \
--- a/dom/xbl/nsXBLEventHandler.cpp
+++ b/dom/xbl/nsXBLEventHandler.cpp
@@ -2,22 +2,22 @@
 /* vim: set ts=8 sts=2 et sw=2 tw=80: */
 /* This Source Code Form is subject to the terms of the Mozilla Public
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 #include "nsCOMPtr.h"
 #include "nsAtom.h"
 #include "nsIDOMEventListener.h"
-#include "nsIDOMKeyEvent.h"
 #include "nsIDOMMouseEvent.h"
 #include "nsXBLPrototypeHandler.h"
 #include "nsContentUtils.h"
 #include "mozilla/dom/Event.h" // for nsIDOMEvent::InternalDOMEvent()
 #include "mozilla/dom/EventTarget.h"
+#include "mozilla/dom/KeyboardEvent.h"
 #include "mozilla/TextEvents.h"
 
 using namespace mozilla;
 using namespace mozilla::dom;
 
 nsXBLEventHandler::nsXBLEventHandler(nsXBLPrototypeHandler* aHandler)
   : mProtoHandler(aHandler)
 {
@@ -81,32 +81,32 @@ nsXBLKeyEventHandler::nsXBLKeyEventHandl
 nsXBLKeyEventHandler::~nsXBLKeyEventHandler()
 {
 }
 
 NS_IMPL_ISUPPORTS(nsXBLKeyEventHandler, nsIDOMEventListener)
 
 bool
 nsXBLKeyEventHandler::ExecuteMatchedHandlers(
-                        nsIDOMKeyEvent* aKeyEvent,
+                        KeyboardEvent* aKeyEvent,
                         uint32_t aCharCode,
                         const IgnoreModifierState& aIgnoreModifierState)
 {
-  WidgetEvent* event = aKeyEvent->AsEvent()->WidgetEventPtr();
-  nsCOMPtr<EventTarget> target = aKeyEvent->AsEvent()->InternalDOMEvent()->GetCurrentTarget();
+  WidgetEvent* event = aKeyEvent->WidgetEventPtr();
+  nsCOMPtr<EventTarget> target = aKeyEvent->GetCurrentTarget();
 
   bool executed = false;
   for (uint32_t i = 0; i < mProtoHandlers.Length(); ++i) {
     nsXBLPrototypeHandler* handler = mProtoHandlers[i];
     bool hasAllowUntrustedAttr = handler->HasAllowUntrustedAttr();
     if ((event->IsTrusted() ||
         (hasAllowUntrustedAttr && handler->AllowUntrustedEvents()) ||
         (!hasAllowUntrustedAttr && !mIsBoundToChrome && !mUsingContentXBLScope)) &&
         handler->KeyEventMatched(aKeyEvent, aCharCode, aIgnoreModifierState)) {
-      handler->ExecuteHandler(target, aKeyEvent->AsEvent());
+      handler->ExecuteHandler(target, aKeyEvent);
       executed = true;
     }
   }
 #ifdef XP_WIN
   // Windows native applications ignore Windows-Logo key state when checking
   // shortcut keys even if the key is pressed.  Therefore, if there is no
   // shortcut key which exactly matches current modifier state, we should
   // retry to look for a shortcut key without the Windows-Logo key press.
@@ -131,19 +131,20 @@ nsXBLKeyEventHandler::HandleEvent(nsIDOM
 
   if (mPhase == NS_PHASE_TARGET) {
     uint16_t eventPhase;
     aEvent->GetEventPhase(&eventPhase);
     if (eventPhase != nsIDOMEvent::AT_TARGET)
       return NS_OK;
   }
 
-  nsCOMPtr<nsIDOMKeyEvent> key(do_QueryInterface(aEvent));
-  if (!key)
+  RefPtr<KeyboardEvent> key = aEvent->InternalDOMEvent()->AsKeyboardEvent();
+  if (!key) {
     return NS_OK;
+  }
 
   WidgetKeyboardEvent* nativeKeyboardEvent =
     aEvent->WidgetEventPtr()->AsKeyboardEvent();
   MOZ_ASSERT(nativeKeyboardEvent);
   AutoShortcutKeyCandidateArray shortcutKeys;
   nativeKeyboardEvent->GetShortcutKeyCandidates(shortcutKeys);
 
   if (shortcutKeys.IsEmpty()) {
--- a/dom/xbl/nsXBLEventHandler.h
+++ b/dom/xbl/nsXBLEventHandler.h
@@ -8,21 +8,23 @@
 #define nsXBLEventHandler_h__
 
 #include "mozilla/Attributes.h"
 #include "nsCOMPtr.h"
 #include "nsIDOMEventListener.h"
 #include "nsTArray.h"
 
 class nsAtom;
-class nsIDOMKeyEvent;
 class nsXBLPrototypeHandler;
 
 namespace mozilla {
 struct IgnoreModifierState;
+namespace dom {
+class KeyboardEvent;
+} // namespace dom
 } // namespace mozilla
 
 class nsXBLEventHandler : public nsIDOMEventListener
 {
 public:
   explicit nsXBLEventHandler(nsXBLPrototypeHandler* aHandler);
 
   NS_DECL_ISUPPORTS
@@ -96,17 +98,17 @@ public:
   {
     mUsingContentXBLScope = aUsingContentXBLScope;
   }
 
 private:
   nsXBLKeyEventHandler();
   virtual ~nsXBLKeyEventHandler();
 
-  bool ExecuteMatchedHandlers(nsIDOMKeyEvent* aEvent, uint32_t aCharCode,
+  bool ExecuteMatchedHandlers(mozilla::dom::KeyboardEvent* aEvent, uint32_t aCharCode,
                               const IgnoreModifierState& aIgnoreModifierState);
 
   nsTArray<nsXBLPrototypeHandler*> mProtoHandlers;
   RefPtr<nsAtom> mEventType;
   uint8_t mPhase;
   uint8_t mType;
   bool mIsBoundToChrome;
   bool mUsingContentXBLScope;
--- a/dom/xbl/nsXBLPrototypeHandler.cpp
+++ b/dom/xbl/nsXBLPrototypeHandler.cpp
@@ -10,17 +10,16 @@
 #include "nsQueryObject.h"
 #include "nsXBLPrototypeHandler.h"
 #include "nsXBLPrototypeBinding.h"
 #include "nsContentUtils.h"
 #include "nsGlobalWindow.h"
 #include "nsGlobalWindowCommands.h"
 #include "nsIContent.h"
 #include "nsAtom.h"
-#include "nsIDOMKeyEvent.h"
 #include "nsIDOMMouseEvent.h"
 #include "nsNameSpaceManager.h"
 #include "nsIDocument.h"
 #include "nsIController.h"
 #include "nsIControllers.h"
 #include "nsXULElement.h"
 #include "nsIURI.h"
 #include "nsIDOMHTMLInputElement.h"
@@ -45,16 +44,17 @@
 #include "nsJSUtils.h"
 #include "mozilla/BasicEvents.h"
 #include "mozilla/JSEventHandler.h"
 #include "mozilla/Preferences.h"
 #include "mozilla/TextEvents.h"
 #include "mozilla/dom/Element.h"
 #include "mozilla/dom/EventHandlerBinding.h"
 #include "mozilla/dom/HTMLTextAreaElement.h"
+#include "mozilla/dom/KeyboardEvent.h"
 #include "mozilla/dom/ScriptSettings.h"
 #include "mozilla/layers/KeyboardMap.h"
 #include "xpcpublic.h"
 
 using namespace mozilla;
 using namespace mozilla::dom;
 using namespace mozilla::layers;
 
@@ -581,32 +581,28 @@ nsXBLPrototypeHandler::DispatchXULKeyCom
                                   eCaseMatters)) {
     // Don't dispatch command events for disabled keys.
     return NS_OK;
   }
 
   aEvent->PreventDefault();
 
   // Copy the modifiers from the key event.
-  nsCOMPtr<nsIDOMKeyEvent> keyEvent = do_QueryInterface(aEvent);
+  RefPtr<KeyboardEvent> keyEvent = aEvent->InternalDOMEvent()->AsKeyboardEvent();
   if (!keyEvent) {
     NS_ERROR("Trying to execute a key handler for a non-key event!");
     return NS_ERROR_FAILURE;
   }
 
   // XXX We should use mozilla::Modifiers for supporting all modifiers.
 
-  bool isAlt = false;
-  bool isControl = false;
-  bool isShift = false;
-  bool isMeta = false;
-  keyEvent->GetAltKey(&isAlt);
-  keyEvent->GetCtrlKey(&isControl);
-  keyEvent->GetShiftKey(&isShift);
-  keyEvent->GetMetaKey(&isMeta);
+  bool isAlt = keyEvent->AltKey();
+  bool isControl = keyEvent->CtrlKey();
+  bool isShift = keyEvent->ShiftKey();
+  bool isMeta = keyEvent->MetaKey();
 
   nsContentUtils::DispatchXULCommand(handlerElement, true,
                                      nullptr, nullptr,
                                      isControl, isAlt, isShift, isMeta);
   return NS_OK;
 }
 
 Modifiers
@@ -705,40 +701,41 @@ nsXBLPrototypeHandler::GetController(Eve
     controllers->GetControllerAt(0, getter_AddRefs(controller));
   }
 
   return controller.forget();
 }
 
 bool
 nsXBLPrototypeHandler::KeyEventMatched(
-                         nsIDOMKeyEvent* aKeyEvent,
+                         KeyboardEvent* aKeyEvent,
                          uint32_t aCharCode,
                          const IgnoreModifierState& aIgnoreModifierState)
 {
   if (mDetail != -1) {
     // Get the keycode or charcode of the key event.
     uint32_t code;
 
     if (mMisc) {
       if (aCharCode)
         code = aCharCode;
       else
-        aKeyEvent->GetCharCode(&code);
+        code = aKeyEvent->CharCode();
       if (IS_IN_BMP(code))
         code = ToLowerCase(char16_t(code));
     }
     else
-      aKeyEvent->GetKeyCode(&code);
+      code = aKeyEvent->KeyCode();
 
     if (code != uint32_t(mDetail))
       return false;
   }
 
-  return ModifiersMatchMask(aKeyEvent, aIgnoreModifierState);
+  return ModifiersMatchMask(static_cast<nsIDOMKeyEvent*>(aKeyEvent),
+                            aIgnoreModifierState);
 }
 
 bool
 nsXBLPrototypeHandler::MouseEventMatched(nsIDOMMouseEvent* aMouseEvent)
 {
   if (mDetail == -1 && mMisc == 0 && (mKeyMask & cAllModifiers) == 0)
     return true; // No filters set up. It's generic.
 
--- a/dom/xbl/nsXBLPrototypeHandler.h
+++ b/dom/xbl/nsXBLPrototypeHandler.h
@@ -16,29 +16,29 @@
 #include "nsXBLEventHandler.h"
 #include "nsIWeakReference.h"
 #include "nsCycleCollectionParticipant.h"
 #include "js/TypeDecls.h"
 
 class nsIDOMEvent;
 class nsIContent;
 class nsIDOMUIEvent;
-class nsIDOMKeyEvent;
 class nsIDOMMouseEvent;
 class nsIObjectInputStream;
 class nsIObjectOutputStream;
 class nsXBLPrototypeBinding;
 
 namespace mozilla {
 
 struct IgnoreModifierState;
 
 namespace dom {
 class AutoJSAPI;
 class EventTarget;
+class KeyboardEvent;
 } // namespace dom
 
 namespace layers {
 class KeyboardShortcut;
 } // namespace layers
 
 } // namespace mozilla
 
@@ -108,17 +108,17 @@ public:
           KeyboardShortcut* aOut) const;
 
   bool EventTypeEquals(nsAtom* aEventType) const
   {
     return mEventName == aEventType;
   }
 
   // if aCharCode is not zero, it is used instead of the charCode of aKeyEvent.
-  bool KeyEventMatched(nsIDOMKeyEvent* aKeyEvent,
+  bool KeyEventMatched(mozilla::dom::KeyboardEvent* aKeyEvent,
                        uint32_t aCharCode,
                        const IgnoreModifierState& aIgnoreModifierState);
 
   bool MouseEventMatched(nsIDOMMouseEvent* aMouseEvent);
   inline bool MouseEventMatched(nsAtom* aEventType,
                                   nsIDOMMouseEvent* aEvent)
   {
     if (!EventTypeEquals(aEventType)) {
--- a/dom/xbl/nsXBLWindowKeyHandler.cpp
+++ b/dom/xbl/nsXBLWindowKeyHandler.cpp
@@ -4,17 +4,16 @@
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 #include "nsCOMPtr.h"
 #include "nsXBLPrototypeHandler.h"
 #include "nsXBLWindowKeyHandler.h"
 #include "nsIContent.h"
 #include "nsAtom.h"
-#include "nsIDOMKeyEvent.h"
 #include "nsXBLService.h"
 #include "nsIServiceManager.h"
 #include "nsGkAtoms.h"
 #include "nsXBLDocumentInfo.h"
 #include "nsIDOMElement.h"
 #include "nsFocusManager.h"
 #include "nsIURI.h"
 #include "nsNetUtil.h"
@@ -29,16 +28,17 @@
 #include "mozilla/EventStateManager.h"
 #include "mozilla/HTMLEditor.h"
 #include "mozilla/Move.h"
 #include "mozilla/Preferences.h"
 #include "mozilla/StaticPtr.h"
 #include "mozilla/TextEvents.h"
 #include "mozilla/dom/Element.h"
 #include "mozilla/dom/Event.h"
+#include "mozilla/dom/KeyboardEvent.h"
 #include "mozilla/layers/KeyboardMap.h"
 
 using namespace mozilla;
 using namespace mozilla::dom;
 using namespace mozilla::layers;
 
 class nsXBLSpecialDocInfo : public nsIObserver
 {
@@ -262,41 +262,38 @@ nsXBLWindowKeyHandler::EnsureHandlers()
       sXBLSpecialDocInfo->GetAllHandlers("browser", &mHandler, &mUserHandler);
     }
   }
 
   return NS_OK;
 }
 
 nsresult
-nsXBLWindowKeyHandler::WalkHandlers(nsIDOMKeyEvent* aKeyEvent, nsAtom* aEventType)
+nsXBLWindowKeyHandler::WalkHandlers(KeyboardEvent* aKeyEvent, nsAtom* aEventType)
 {
-  bool prevent;
-  aKeyEvent->AsEvent()->GetDefaultPrevented(&prevent);
-  if (prevent)
+  if (aKeyEvent->DefaultPrevented()) {
     return NS_OK;
+  }
 
-  bool trustedEvent = false;
   // Don't process the event if it was not dispatched from a trusted source
-  aKeyEvent->AsEvent()->GetIsTrusted(&trustedEvent);
-
-  if (!trustedEvent)
+  if (!aKeyEvent->IsTrusted()) {
     return NS_OK;
+  }
 
   nsresult rv = EnsureHandlers();
   NS_ENSURE_SUCCESS(rv, rv);
 
   bool isDisabled;
   nsCOMPtr<Element> el = GetElement(&isDisabled);
   if (!el) {
     if (mUserHandler) {
       WalkHandlersInternal(aKeyEvent, aEventType, mUserHandler, true);
-      aKeyEvent->AsEvent()->GetDefaultPrevented(&prevent);
-      if (prevent)
+      if (aKeyEvent->DefaultPrevented()) {
         return NS_OK; // Handled by the user bindings. Our work here is done.
+      }
     }
   }
 
   // skip keysets that are disabled
   if (el && isDisabled) {
     return NS_OK;
   }
 
@@ -486,17 +483,18 @@ nsXBLWindowKeyHandler::ConvertEventToDOM
   MOZ_ASSERT_UNREACHABLE(
     "All event messages which this instance listens to should be handled");
   return nullptr;
 }
 
 NS_IMETHODIMP
 nsXBLWindowKeyHandler::HandleEvent(nsIDOMEvent* aEvent)
 {
-  nsCOMPtr<nsIDOMKeyEvent> keyEvent(do_QueryInterface(aEvent));
+  RefPtr<KeyboardEvent> keyEvent =
+    aEvent->InternalDOMEvent()->AsKeyboardEvent();
   NS_ENSURE_TRUE(keyEvent, NS_ERROR_INVALID_ARG);
 
   uint16_t eventPhase;
   aEvent->GetEventPhase(&eventPhase);
   if (eventPhase == nsIDOMEvent::CAPTURING_PHASE) {
     if (aEvent->WidgetEventPtr()->mFlags.mInSystemGroup) {
       HandleEventOnCaptureInSystemEventGroup(keyEvent);
     } else {
@@ -539,37 +537,37 @@ nsXBLWindowKeyHandler::HandleEvent(nsIDO
 
   RefPtr<nsAtom> eventTypeAtom =
     ConvertEventToDOMEventType(*widgetKeyboardEvent);
   return WalkHandlers(keyEvent, eventTypeAtom);
 }
 
 void
 nsXBLWindowKeyHandler::HandleEventOnCaptureInDefaultEventGroup(
-                         nsIDOMKeyEvent* aEvent)
+                         KeyboardEvent* aEvent)
 {
   WidgetKeyboardEvent* widgetKeyboardEvent =
-    aEvent->AsEvent()->WidgetEventPtr()->AsKeyboardEvent();
+    aEvent->WidgetEventPtr()->AsKeyboardEvent();
 
   if (widgetKeyboardEvent->IsReservedByChrome()) {
     return;
   }
 
   bool isReserved = false;
   if (HasHandlerForEvent(aEvent, &isReserved) && isReserved) {
     widgetKeyboardEvent->MarkAsReservedByChrome();
   }
 }
 
 void
 nsXBLWindowKeyHandler::HandleEventOnCaptureInSystemEventGroup(
-                         nsIDOMKeyEvent* aEvent)
+                         KeyboardEvent* aEvent)
 {
   WidgetKeyboardEvent* widgetEvent =
-    aEvent->AsEvent()->WidgetEventPtr()->AsKeyboardEvent();
+    aEvent->WidgetEventPtr()->AsKeyboardEvent();
 
   // If the event won't be sent to remote process, this listener needs to do
   // nothing.
   if (widgetEvent->mFlags.mOnlySystemGroupDispatchInContent ||
       !widgetEvent->WillBeSentToRemoteProcess()) {
     return;
   }
 
@@ -640,24 +638,24 @@ nsXBLWindowKeyHandler::IsHTMLEditableFie
 // WalkHandlersInternal and WalkHandlersAndExecute
 //
 // Given a particular DOM event and a pointer to the first handler in the list,
 // scan through the list to find something to handle the event. If aExecute = true,
 // the handler will be executed; otherwise just return an answer telling if a handler
 // for that event was found.
 //
 bool
-nsXBLWindowKeyHandler::WalkHandlersInternal(nsIDOMKeyEvent* aKeyEvent,
+nsXBLWindowKeyHandler::WalkHandlersInternal(KeyboardEvent* aKeyEvent,
                                             nsAtom* aEventType,
                                             nsXBLPrototypeHandler* aHandler,
                                             bool aExecute,
                                             bool* aOutReservedForChrome)
 {
   WidgetKeyboardEvent* nativeKeyboardEvent =
-    aKeyEvent->AsEvent()->WidgetEventPtr()->AsKeyboardEvent();
+    aKeyEvent->WidgetEventPtr()->AsKeyboardEvent();
   MOZ_ASSERT(nativeKeyboardEvent);
 
   AutoShortcutKeyCandidateArray shortcutKeys;
   nativeKeyboardEvent->GetShortcutKeyCandidates(shortcutKeys);
 
   if (shortcutKeys.IsEmpty()) {
     return WalkHandlersAndExecute(aKeyEvent, aEventType, aHandler,
                                   0, IgnoreModifierState(),
@@ -674,39 +672,39 @@ nsXBLWindowKeyHandler::WalkHandlersInter
       return true;
     }
   }
   return false;
 }
 
 bool
 nsXBLWindowKeyHandler::WalkHandlersAndExecute(
-                         nsIDOMKeyEvent* aKeyEvent,
+                         KeyboardEvent* aKeyEvent,
                          nsAtom* aEventType,
                          nsXBLPrototypeHandler* aFirstHandler,
                          uint32_t aCharCode,
                          const IgnoreModifierState& aIgnoreModifierState,
                          bool aExecute,
                          bool* aOutReservedForChrome)
 {
   if (aOutReservedForChrome) {
     *aOutReservedForChrome = false;
   }
 
   WidgetKeyboardEvent* widgetKeyboardEvent =
-    aKeyEvent->AsEvent()->WidgetEventPtr()->AsKeyboardEvent();
+    aKeyEvent->WidgetEventPtr()->AsKeyboardEvent();
   if (NS_WARN_IF(!widgetKeyboardEvent)) {
     return false;
   }
 
   // Try all of the handlers until we find one that matches the event.
   for (nsXBLPrototypeHandler* handler = aFirstHandler;
        handler;
        handler = handler->GetNextHandler()) {
-    bool stopped = aKeyEvent->AsEvent()->IsDispatchStopped();
+    bool stopped = aKeyEvent->IsDispatchStopped();
     if (stopped) {
       // The event is finished, don't execute any more handlers
       return false;
     }
 
     if (aExecute) {
       // If the event is eKeyDownOnPlugin, it should execute either keydown
       // handler or keypress handler because eKeyDownOnPlugin events are
@@ -800,17 +798,17 @@ nsXBLWindowKeyHandler::WalkHandlersAndEx
       // XXX commandElement may be nullptr...
       target = commandElement;
     } else {
       target = mTarget;
     }
 
     // XXX Do we execute only one handler even if the handler neither stops
     //     propagation nor prevents default of the event?
-    nsresult rv = handler->ExecuteHandler(target, aKeyEvent->AsEvent());
+    nsresult rv = handler->ExecuteHandler(target, aKeyEvent);
     if (NS_SUCCEEDED(rv)) {
       return true;
     }
   }
 
 #ifdef XP_WIN
   // Windows native applications ignore Windows-Logo key state when checking
   // shortcut keys even if the key is pressed.  Therefore, if there is no
@@ -842,21 +840,21 @@ nsXBLWindowKeyHandler::IsReservedKey(Wid
   if (reserved == XBLReservedKey_True) {
     return true;
   }
 
   return nsContentUtils::ShouldBlockReservedKeys(aKeyEvent);
 }
 
 bool
-nsXBLWindowKeyHandler::HasHandlerForEvent(nsIDOMKeyEvent* aEvent,
+nsXBLWindowKeyHandler::HasHandlerForEvent(KeyboardEvent* aEvent,
                                           bool* aOutReservedForChrome)
 {
   WidgetKeyboardEvent* widgetKeyboardEvent =
-    aEvent->AsEvent()->WidgetEventPtr()->AsKeyboardEvent();
+    aEvent->WidgetEventPtr()->AsKeyboardEvent();
   if (NS_WARN_IF(!widgetKeyboardEvent) || !widgetKeyboardEvent->IsTrusted()) {
     return false;
   }
 
   nsresult rv = EnsureHandlers();
   NS_ENSURE_SUCCESS(rv, false);
 
   bool isDisabled;
--- a/dom/xbl/nsXBLWindowKeyHandler.h
+++ b/dom/xbl/nsXBLWindowKeyHandler.h
@@ -9,34 +9,35 @@
 
 #include "mozilla/EventForwards.h"
 #include "mozilla/layers/KeyboardMap.h"
 #include "nsWeakPtr.h"
 #include "nsIDOMEventListener.h"
 
 class nsAtom;
 class nsIDOMElement;
-class nsIDOMKeyEvent;
 class nsXBLPrototypeHandler;
 
 namespace mozilla {
 class EventListenerManager;
 class WidgetKeyboardEvent;
 struct IgnoreModifierState;
 namespace dom {
 class Element;
 class EventTarget;
+class KeyboardEvent;
 } // namespace dom
 } // namespace mozilla
 
 class nsXBLWindowKeyHandler : public nsIDOMEventListener
 {
   typedef mozilla::EventListenerManager EventListenerManager;
   typedef mozilla::IgnoreModifierState IgnoreModifierState;
   typedef mozilla::layers::KeyboardMap KeyboardMap;
+  typedef mozilla::dom::KeyboardEvent KeyboardEvent;
 
 public:
   nsXBLWindowKeyHandler(nsIDOMElement* aElement, mozilla::dom::EventTarget* aTarget);
 
   void InstallKeyboardEventListenersTo(
          EventListenerManager* aEventListenerManager);
   void RemoveKeyboardEventListenersFrom(
          EventListenerManager* aEventListenerManager);
@@ -44,43 +45,43 @@ public:
   static KeyboardMap CollectKeyboardShortcuts();
 
   NS_DECL_ISUPPORTS
   NS_DECL_NSIDOMEVENTLISTENER
 
 protected:
   virtual ~nsXBLWindowKeyHandler();
 
-  nsresult WalkHandlers(nsIDOMKeyEvent* aKeyEvent, nsAtom* aEventType);
+  nsresult WalkHandlers(KeyboardEvent* aKeyEvent, nsAtom* aEventType);
 
   // walk the handlers, looking for one to handle the event
-  bool WalkHandlersInternal(nsIDOMKeyEvent* aKeyEvent,
+  bool WalkHandlersInternal(KeyboardEvent* aKeyEvent,
                             nsAtom* aEventType,
                             nsXBLPrototypeHandler* aHandler,
                             bool aExecute,
                             bool* aOutReservedForChrome = nullptr);
 
   // walk the handlers for aEvent, aCharCode and aIgnoreModifierState. Execute
   // it if aExecute = true.
-  bool WalkHandlersAndExecute(nsIDOMKeyEvent* aKeyEvent, nsAtom* aEventType,
+  bool WalkHandlersAndExecute(KeyboardEvent* aKeyEvent, nsAtom* aEventType,
                               nsXBLPrototypeHandler* aHandler,
                               uint32_t aCharCode,
                               const IgnoreModifierState& aIgnoreModifierState,
                               bool aExecute,
                               bool* aOutReservedForChrome = nullptr);
 
   // HandleEvent function for the capturing phase in the default event group.
-  void HandleEventOnCaptureInDefaultEventGroup(nsIDOMKeyEvent* aEvent);
+  void HandleEventOnCaptureInDefaultEventGroup(KeyboardEvent* aEvent);
   // HandleEvent function for the capturing phase in the system event group.
-  void HandleEventOnCaptureInSystemEventGroup(nsIDOMKeyEvent* aEvent);
+  void HandleEventOnCaptureInSystemEventGroup(KeyboardEvent* aEvent);
 
   // Check if any handler would handle the given event. Optionally returns
   // whether the command handler for the event is marked with the "reserved"
   // attribute.
-  bool HasHandlerForEvent(nsIDOMKeyEvent* aEvent,
+  bool HasHandlerForEvent(KeyboardEvent* aEvent,
                           bool* aOutReservedForChrome = nullptr);
 
   // Returns true if the key would be reserved for the given handler. A reserved
   // key is not sent to a content process or single-process equivalent.
   bool IsReservedKey(mozilla::WidgetKeyboardEvent* aKeyEvent,
                      nsXBLPrototypeHandler* aHandler);
 
   // Returns event type for matching between aWidgetKeyboardEvent and