WebKit's focus events are UIEvents (instead of FocusEvent) and thus don't expose...
authorharaken@chromium.org <haraken@chromium.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Thu, 7 Feb 2013 08:30:00 +0000 (08:30 +0000)
committerharaken@chromium.org <haraken@chromium.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Thu, 7 Feb 2013 08:30:00 +0000 (08:30 +0000)
https://bugs.webkit.org/show_bug.cgi?id=76216

Reviewed by Eric Seidel.

Spec: http://www.w3.org/TR/DOM-Level-3-Events/#events-FocusEvent

This patch creates a new FocusEvent class with a relatedTarget attribute.
Now when focusin or focusout events are dispatched, a FocusEvent is created with
the relatedTarget attribute set accordingly.

Source/WebCore:

Test: fast/events/related-target-focusevent.html

* CMakeLists.txt:
* DerivedSources.cpp:
* DerivedSources.make:
* DerivedSources.pri:
* GNUmakefile.list.am:
* Target.pri:
* WebCore.gypi:
* WebCore.xcodeproj/project.pbxproj:
* dom/DOMAllInOne.cpp:
* dom/Event.cpp:
(WebCore::Event::isFocusEvent):
(WebCore):
* dom/Event.h:
(Event):
* dom/EventContext.cpp:
(WebCore::EventContext::handleLocalEvents):
* dom/EventNames.in:
* dom/FocusEvent.h: Added.
(WebCore):
(FocusEvent):
(WebCore::FocusEvent::create):
(WebCore::FocusEvent::relatedTarget):
(WebCore::FocusEvent::setRelatedTarget):
(WebCore::toFocusEvent):
* dom/FocusEvent.idl: Added.
* dom/Node.cpp:
(WebCore::Node::dispatchFocusInEvent):
(WebCore::Node::dispatchFocusOutEvent):

LayoutTests:

* fast/dom/shadow/shadow-boundary-events-expected.txt:
* fast/dom/shadow/shadow-boundary-events.html:
* fast/events/related-target-focusevent-expected.txt: Added.
* fast/events/related-target-focusevent.html: Added.

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@142072 268f45cc-cd09-0410-ab3c-d52691b4dbfc

23 files changed:
LayoutTests/ChangeLog
LayoutTests/fast/dom/shadow/shadow-boundary-events-expected.txt
LayoutTests/fast/dom/shadow/shadow-boundary-events.html
LayoutTests/fast/events/related-target-focusevent-expected.txt [new file with mode: 0644]
LayoutTests/fast/events/related-target-focusevent.html [new file with mode: 0644]
Source/WebCore/CMakeLists.txt
Source/WebCore/ChangeLog
Source/WebCore/DerivedSources.cpp
Source/WebCore/DerivedSources.make
Source/WebCore/DerivedSources.pri
Source/WebCore/GNUmakefile.list.am
Source/WebCore/Target.pri
Source/WebCore/WebCore.gypi
Source/WebCore/WebCore.xcodeproj/project.pbxproj
Source/WebCore/dom/DOMAllInOne.cpp
Source/WebCore/dom/Event.cpp
Source/WebCore/dom/Event.h
Source/WebCore/dom/EventContext.cpp
Source/WebCore/dom/EventNames.in
Source/WebCore/dom/FocusEvent.cpp [new file with mode: 0644]
Source/WebCore/dom/FocusEvent.h [new file with mode: 0644]
Source/WebCore/dom/FocusEvent.idl [new file with mode: 0644]
Source/WebCore/dom/Node.cpp

index 5c28ee6..d36dba4 100644 (file)
@@ -1,3 +1,21 @@
+2013-02-03  Kentaro Hara  <haraken@chromium.org>
+
+        WebKit's focus events are UIEvents (instead of FocusEvent) and thus don't expose .relatedTarget
+        https://bugs.webkit.org/show_bug.cgi?id=76216
+
+        Reviewed by Eric Seidel.
+
+        Spec: http://www.w3.org/TR/DOM-Level-3-Events/#events-FocusEvent
+
+        This patch creates a new FocusEvent class with a relatedTarget attribute.
+        Now when focusin or focusout events are dispatched, a FocusEvent is created with
+        the relatedTarget attribute set accordingly.
+
+        * fast/dom/shadow/shadow-boundary-events-expected.txt:
+        * fast/dom/shadow/shadow-boundary-events.html:
+        * fast/events/related-target-focusevent-expected.txt: Added.
+        * fast/events/related-target-focusevent.html: Added.
+
 2013-02-06  Mike West  <mkwst@chromium.org>
 
         Entity-header extension headers honored on 304 responses.
index 9a5f9db..40cebc2 100644 (file)
@@ -61,13 +61,13 @@ PASS dispatchedEvent("mouseout") is ["divH(<-shadowK)(@divH)", "shadowG(<-shadow
 
 Move focus from a node to its sibling node. All nodes are outside of shadow boundary.
 Moving focus from divB to divC
-PASS dispatchedEvent("focusin") is ["divC(@divC)", "divC(@divA)"]
-PASS dispatchedEvent("focusout") is ["divB(@divB)", "divB(@divA)"]
+PASS dispatchedEvent("focusin") is ["divC(<-divB)(@divC)", "divC(<-divB)(@divA)"]
+PASS dispatchedEvent("focusout") is ["divB(<-divC)(@divB)", "divB(<-divC)(@divA)"]
 
 Old focused node and new focused node exist in separated subtrees, crossing shadow boundaries. Making sure that an event is not dispatched beyond the lowest common boundary.
 Moving focus from shadowD/shadowF/shadowG/divH to shadowD/shadowK/divL
-PASS dispatchedEvent("focusin") is ["divL(@divL)", "shadowK(@shadowK)", "shadowK(@divJ)"]
-PASS dispatchedEvent("focusout") is ["divH(@divH)", "shadowG(@shadowG)", "shadowF(@shadowF)", "shadowF(@divE)"]
+PASS dispatchedEvent("focusin") is ["divL(<-shadowF)(@divL)", "shadowK(<-shadowF)(@shadowK)", "shadowK(<-shadowF)(@divJ)"]
+PASS dispatchedEvent("focusout") is ["divH(<-shadowK)(@divH)", "shadowG(<-shadowK)(@shadowG)", "shadowF(<-shadowK)(@shadowF)", "shadowF(<-shadowK)(@divE)"]
 
 Move focus from a node to its sibling node. All nodes are outside of shadow boundary.
 Moving focus from divB to divC
index 933de74..8dfc0c7 100644 (file)
@@ -180,13 +180,13 @@ function test()
     // Test for focusin/focusout events.
     moveFocus('divB', 'divC',
               'Move focus from a node to its sibling node. All nodes are outside of shadow boundary.');
-    shouldBe('dispatchedEvent("focusin")', '["divC(@divC)", "divC(@divA)"]');
-    shouldBe('dispatchedEvent("focusout")', '["divB(@divB)", "divB(@divA)"]');
+    shouldBe('dispatchedEvent("focusin")', '["divC(<-divB)(@divC)", "divC(<-divB)(@divA)"]');
+    shouldBe('dispatchedEvent("focusout")', '["divB(<-divC)(@divB)", "divB(<-divC)(@divA)"]');
 
     moveFocus('shadowD/shadowF/shadowG/divH', 'shadowD/shadowK/divL',
               'Old focused node and new focused node exist in separated subtrees, crossing shadow boundaries. Making sure that an event is not dispatched beyond the lowest common boundary.');
-    shouldBe('dispatchedEvent("focusin")', '["divL(@divL)", "shadowK(@shadowK)", "shadowK(@divJ)"]');
-    shouldBe('dispatchedEvent("focusout")', '["divH(@divH)", "shadowG(@shadowG)", "shadowF(@shadowF)", "shadowF(@divE)"]');
+    shouldBe('dispatchedEvent("focusin")', '["divL(<-shadowF)(@divL)", "shadowK(<-shadowF)(@shadowK)", "shadowK(<-shadowF)(@divJ)"]');
+    shouldBe('dispatchedEvent("focusout")', '["divH(<-shadowK)(@divH)", "shadowG(<-shadowK)(@shadowG)", "shadowF(<-shadowK)(@shadowF)", "shadowF(<-shadowK)(@divE)"]');
 
     // Omitted test cases where either a oldFocusedNode or newFocusedNode is an ancestor of the other.
     // Due to a focus transfer mechanism on shadow hosts, a focused node should be a leaf node in general.
diff --git a/LayoutTests/fast/events/related-target-focusevent-expected.txt b/LayoutTests/fast/events/related-target-focusevent-expected.txt
new file mode 100644 (file)
index 0000000..38b9b30
--- /dev/null
@@ -0,0 +1,15 @@
+PASS event.relatedTarget is null
+PASS event.relatedTarget is input2
+PASS event.relatedTarget is input1
+PASS event.relatedTarget is input3
+PASS event.relatedTarget is input2
+PASS event.relatedTarget is input4
+PASS successfullyParsed is true
+
+TEST COMPLETE
+Checks that the relatedTarget attribute for FocusEvent objects is being set correctly when focusin/focusout events are dispatched. Press tab four times to dispatch a focusin and focusout event for each of the inputs below.
+
+On success, you will see a series of "PASS" messages, followed by "TEST COMPLETE".
+
+
+   
diff --git a/LayoutTests/fast/events/related-target-focusevent.html b/LayoutTests/fast/events/related-target-focusevent.html
new file mode 100644 (file)
index 0000000..fd76353
--- /dev/null
@@ -0,0 +1,33 @@
+<html>
+<head>
+<script src="../js/resources/js-test-pre.js"></script>
+</head>
+<body>
+<p id="description"></p>
+<input id="input1" type="text"></input>
+<input id="input2" type="text"></input>
+<input id="input3" type="text"></input>
+<input id="input4" type="text"></input>
+<script>
+jsTestIsAsync = true;
+
+description("Checks that the relatedTarget attribute for FocusEvent objects is being set correctly when focusin/focusout events are dispatched.  <b>Press tab four times</b> to dispatch a focusin and focusout event for each of the inputs below.");
+
+var input1 = document.getElementById('input1');
+var input2 = document.getElementById('input2');
+var input3 = document.getElementById('input3');
+
+input1.addEventListener("focusin", function(event) { shouldBe('event.relatedTarget', 'null'); });
+input1.addEventListener("focusout", function(event) { shouldBe('event.relatedTarget', 'input2'); });
+input2.addEventListener("focusin", function(event) { shouldBe('event.relatedTarget', 'input1'); });
+input2.addEventListener("focusout", function(event) { shouldBe('event.relatedTarget', 'input3'); });
+input3.addEventListener("focusin", function(event) { shouldBe('event.relatedTarget', 'input2'); });
+input3.addEventListener("focusout", function(event) { shouldBe('event.relatedTarget', 'input4'); finishJSTest(); });
+
+for (var i = 0; i < 4; i++) {
+    eventSender.keyDown('\t');
+}
+</script>
+<script src="../js/resources/js-test-post.js"></script>
+</body>
+</html>
index c933d2d..bfd51fd 100644 (file)
@@ -371,6 +371,7 @@ set(WebCore_IDL_FILES
     dom/EventException.idl
     dom/Event.idl
     dom/EventTarget.idl
+    dom/FocusEvent.idl
     dom/HashChangeEvent.idl
     dom/KeyboardEvent.idl
     dom/MessageChannel.idl
@@ -1186,6 +1187,7 @@ set(WebCore_SOURCES
     dom/EventTarget.cpp
     dom/ExceptionBase.cpp
     dom/ExceptionCodePlaceholder.cpp
+    dom/FocusEvent.cpp
     dom/GenericEventQueue.cpp
     dom/GestureEvent.cpp
     dom/IconURL.cpp
index 75b507c..ddeb8e5 100644 (file)
@@ -1,3 +1,47 @@
+2013-02-03  Kentaro Hara  <haraken@chromium.org>
+
+        WebKit's focus events are UIEvents (instead of FocusEvent) and thus don't expose .relatedTarget
+        https://bugs.webkit.org/show_bug.cgi?id=76216
+
+        Reviewed by Eric Seidel.
+
+        Spec: http://www.w3.org/TR/DOM-Level-3-Events/#events-FocusEvent
+
+        This patch creates a new FocusEvent class with a relatedTarget attribute.
+        Now when focusin or focusout events are dispatched, a FocusEvent is created with
+        the relatedTarget attribute set accordingly.
+
+        Test: fast/events/related-target-focusevent.html
+
+        * CMakeLists.txt:
+        * DerivedSources.cpp:
+        * DerivedSources.make:
+        * DerivedSources.pri:
+        * GNUmakefile.list.am:
+        * Target.pri:
+        * WebCore.gypi:
+        * WebCore.xcodeproj/project.pbxproj:
+        * dom/DOMAllInOne.cpp:
+        * dom/Event.cpp:
+        (WebCore::Event::isFocusEvent):
+        (WebCore):
+        * dom/Event.h:
+        (Event):
+        * dom/EventContext.cpp:
+        (WebCore::EventContext::handleLocalEvents):
+        * dom/EventNames.in:
+        * dom/FocusEvent.h: Added.
+        (WebCore):
+        (FocusEvent):
+        (WebCore::FocusEvent::create):
+        (WebCore::FocusEvent::relatedTarget):
+        (WebCore::FocusEvent::setRelatedTarget):
+        (WebCore::toFocusEvent):
+        * dom/FocusEvent.idl: Added.
+        * dom/Node.cpp:
+        (WebCore::Node::dispatchFocusInEvent):
+        (WebCore::Node::dispatchFocusOutEvent):
+
 2013-02-06  Kent Tamura  <tkent@chromium.org>
 
         Fix style of RenderTheme.cpp and RenderThemeChromiumWin.h
index 6551c68..7d96bfa 100644 (file)
 #include "JSFileWriterSync.cpp"
 #include "JSFloat32Array.cpp"
 #include "JSFloat64Array.cpp"
+#include "JSFocusEvent.cpp"
 #include "JSGeolocation.cpp"
 #include "JSGeoposition.cpp"
 #include "JSHashChangeEvent.cpp"
index 605a21e..39bde8e 100644 (file)
@@ -235,6 +235,7 @@ BINDING_IDLS = \
     $(WebCore)/dom/EventException.idl \
     $(WebCore)/dom/EventListener.idl \
     $(WebCore)/dom/EventTarget.idl \
+    $(WebCore)/dom/FocusEvent.idl \
     $(WebCore)/dom/HashChangeEvent.idl \
     $(WebCore)/dom/KeyboardEvent.idl \
     $(WebCore)/dom/MessageChannel.idl \
index 1cbcc37..8ac7738 100644 (file)
@@ -248,6 +248,7 @@ IDL_BINDINGS += \
     $$PWD/dom/EventException.idl \
 #    $$PWD/dom/EventListener.idl \
     $$PWD/dom/EventTarget.idl \
+    $$PWD/dom/FocusEvent.idl \
     $$PWD/dom/HashChangeEvent.idl \
     $$PWD/dom/KeyboardEvent.idl \
     $$PWD/dom/MouseEvent.idl \
index b39f6cd..6b953d2 100644 (file)
@@ -286,6 +286,8 @@ webcore_built_sources += \
        DerivedSources/WebCore/JSFloat32Array.h \
        DerivedSources/WebCore/JSFloat64Array.cpp \
        DerivedSources/WebCore/JSFloat64Array.h \
+       DerivedSources/WebCore/JSFocusEvent.cpp \
+       DerivedSources/WebCore/JSFocusEvent.h \
        DerivedSources/WebCore/JSGamepad.cpp \
        DerivedSources/WebCore/JSGamepad.h \
        DerivedSources/WebCore/JSGamepadList.cpp \
@@ -1383,6 +1385,7 @@ dom_binding_idls += \
        $(WebCore)/dom/Event.idl \
        $(WebCore)/dom/EventTarget.idl \
        $(WebCore)/dom/EventException.idl \
+       $(WebCore)/dom/FocusEvent.idl \
        $(WebCore)/dom/HashChangeEvent.idl \
        $(WebCore)/dom/KeyboardEvent.idl \
        $(WebCore)/dom/MessageChannel.idl \
@@ -2865,6 +2868,8 @@ webcore_sources += \
        Source/WebCore/dom/ExceptionCode.h \
        Source/WebCore/dom/ExceptionCodePlaceholder.cpp \
        Source/WebCore/dom/ExceptionCodePlaceholder.h \
+       Source/WebCore/dom/FocusEvent.cpp \
+       Source/WebCore/dom/FocusEvent.h \
        Source/WebCore/dom/FragmentScriptingPermission.h \
        Source/WebCore/dom/GestureEvent.cpp \
        Source/WebCore/dom/GestureEvent.h \
index a4f2488..b6983ba 100644 (file)
@@ -414,6 +414,7 @@ SOURCES += \
     dom/EventTarget.cpp \
     dom/ExceptionBase.cpp \
     dom/ExceptionCodePlaceholder.cpp \
+    dom/FocusEvent.cpp \
     dom/GenericEventQueue.cpp \
     dom/GestureEvent.cpp \
     dom/IconURL.cpp \
@@ -1632,6 +1633,7 @@ HEADERS += \
     dom/EventTarget.h \
     dom/ExceptionBase.h \
     dom/ExceptionCode.h \
+    dom/FocusEvent.h \
     dom/FragmentScriptingPermission.h \
     dom/GestureEvent.h \
     dom/IdTargetObserver.h \
index 1804156..28c8e7d 100644 (file)
             'dom/EventException.idl',
             'dom/EventListener.idl',
             'dom/EventTarget.idl',
+            'dom/FocusEvent.idl',
             'dom/HashChangeEvent.idl',
             'dom/KeyboardEvent.idl',
             'dom/MessageChannel.idl',
             'dom/ExceptionBase.cpp',
             'dom/ExceptionBase.h',
             'dom/ExceptionCodePlaceholder.cpp',
+            'dom/FocusEvent.cpp',
+            'dom/FocusEvent.h',
             'dom/GenericEventQueue.cpp',
             'dom/GenericEventQueue.h',
             'dom/GestureEvent.cpp',
             '<(PRODUCT_DIR)/DerivedSources/WebCore/JSFileWriterSync.h',
             '<(PRODUCT_DIR)/DerivedSources/WebCore/JSFloat32Array.cpp',
             '<(PRODUCT_DIR)/DerivedSources/WebCore/JSFloat32Array.h',
+            '<(PRODUCT_DIR)/DerivedSources/WebCore/JSFocusEvent.cpp',
+            '<(PRODUCT_DIR)/DerivedSources/WebCore/JSFocusEvent.h',
             '<(PRODUCT_DIR)/DerivedSources/WebCore/JSGeolocation.cpp',
             '<(PRODUCT_DIR)/DerivedSources/WebCore/JSGeolocation.h',
             '<(PRODUCT_DIR)/DerivedSources/WebCore/JSGeoposition.cpp',
index c2afefd..b626736 100644 (file)
                B658FFA21522EF3A00DD5595 /* JSRadioNodeList.h in Headers */ = {isa = PBXBuildFile; fileRef = B658FFA01522EF3A00DD5595 /* JSRadioNodeList.h */; };
                B658FFA51522EFAA00DD5595 /* RadioNodeList.cpp in Sources */ = {isa = PBXBuildFile; fileRef = B658FFA31522EFAA00DD5595 /* RadioNodeList.cpp */; };
                B658FFA61522EFAA00DD5595 /* RadioNodeList.h in Headers */ = {isa = PBXBuildFile; fileRef = B658FFA41522EFAA00DD5595 /* RadioNodeList.h */; };
+               B6D9D23514EABD260090D75E /* FocusEvent.h in Headers */ = {isa = PBXBuildFile; fileRef = B6D9D23314EABD260090D75E /* FocusEvent.h */; };
+               B6D9D23614EABD260090D75E /* FocusEvent.cpp in Sources */ = {isa = PBXBuildFile; fileRef = B6D9D23414EABD260090D75E /* FocusEvent.cpp */; };
+               B6D9D27B14EAC0860090D75E /* JSFocusEvent.h in Headers */ = {isa = PBXBuildFile; fileRef = B6D9D27914EAC0860090D75E /* JSFocusEvent.h */; };
+               B6D9D27C14EAC0860090D75E /* JSFocusEvent.cpp in Sources */ = {isa = PBXBuildFile; fileRef = B6D9D27A14EAC0860090D75E /* JSFocusEvent.cpp */; };
                B71FE6DF11091CB300DAEF77 /* PrintContext.h in Headers */ = {isa = PBXBuildFile; fileRef = B776D43A1104525D00BEB0EC /* PrintContext.h */; settings = {ATTRIBUTES = (Private, ); }; };
                B734B181119B9911006587BD /* FontTranscoder.cpp in Sources */ = {isa = PBXBuildFile; fileRef = B734B180119B9911006587BD /* FontTranscoder.cpp */; };
                B734B183119B991D006587BD /* FontTranscoder.h in Headers */ = {isa = PBXBuildFile; fileRef = B734B182119B991D006587BD /* FontTranscoder.h */; };
                B658FFA01522EF3A00DD5595 /* JSRadioNodeList.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = JSRadioNodeList.h; sourceTree = "<group>"; };
                B658FFA31522EFAA00DD5595 /* RadioNodeList.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = RadioNodeList.cpp; sourceTree = "<group>"; };
                B658FFA41522EFAA00DD5595 /* RadioNodeList.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RadioNodeList.h; sourceTree = "<group>"; };
+               B6D9D23314EABD260090D75E /* FocusEvent.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = FocusEvent.h; sourceTree = "<group>"; };
+               B6D9D23414EABD260090D75E /* FocusEvent.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = FocusEvent.cpp; sourceTree = "<group>"; };
+               B6D9D27214EABF030090D75E /* FocusEvent.idl */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text; path = FocusEvent.idl; sourceTree = "<group>"; };
+               B6D9D27914EAC0860090D75E /* JSFocusEvent.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = JSFocusEvent.h; sourceTree = "<group>"; };
+               B6D9D27A14EAC0860090D75E /* JSFocusEvent.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = JSFocusEvent.cpp; sourceTree = "<group>"; };
                B734B180119B9911006587BD /* FontTranscoder.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = FontTranscoder.cpp; path = transcoder/FontTranscoder.cpp; sourceTree = "<group>"; };
                B734B182119B991D006587BD /* FontTranscoder.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = FontTranscoder.h; path = transcoder/FontTranscoder.h; sourceTree = "<group>"; };
                B776D43A1104525D00BEB0EC /* PrintContext.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PrintContext.h; sourceTree = "<group>"; };
                                BC60D9BE0D2A269A00B9918F /* JSEventException.h */,
                                C6A703325C9D0B6CDCBC4D78 /* JSEventTarget.cpp */,
                                5FC7DC26CFE2563200B85AE5 /* JSEventTarget.h */,
+                               B6D9D27A14EAC0860090D75E /* JSFocusEvent.cpp */,
+                               B6D9D27914EAC0860090D75E /* JSFocusEvent.h */,
                                8482B74F1198CB6B00BFB005 /* JSHashChangeEvent.cpp */,
                                8482B7501198CB6B00BFB005 /* JSHashChangeEvent.h */,
                                A86629CE09DA2B47009633A5 /* JSKeyboardEvent.cpp */,
                                935FBCF109BA143B00E230B1 /* ExceptionCode.h */,
                                A7CACDB013CE875B00BBBE3F /* ExceptionCodePlaceholder.cpp */,
                                A74BB76A13BDA86300FF7BF0 /* ExceptionCodePlaceholder.h */,
+                               B6D9D23414EABD260090D75E /* FocusEvent.cpp */,
+                               B6D9D23314EABD260090D75E /* FocusEvent.h */,
+                               B6D9D27214EABF030090D75E /* FocusEvent.idl */,
                                A853123C11D0471B00D4D077 /* FragmentScriptingPermission.h */,
                                0720B09E14D3323500642955 /* GenericEventQueue.cpp */,
                                0720B09F14D3323500642955 /* GenericEventQueue.h */,
                                D72F6D7A153159A3001EE44E /* FlowThreadController.h in Headers */,
                                14993BE60B2F2B1C0050497F /* FocusController.h in Headers */,
                                062287840B4DB322000C34DF /* FocusDirection.h in Headers */,
+                               B6D9D23514EABD260090D75E /* FocusEvent.h in Headers */,
                                B2C3DA610D006CD600EF6F26 /* Font.h in Headers */,
                                BCB92D4F1293550B00C8387F /* FontBaseline.h in Headers */,
                                B2C3DA630D006CD600EF6F26 /* FontCache.h in Headers */,
                                893C47BC1238A0A9002B3D86 /* JSFileWriterCallback.h in Headers */,
                                49EECF03105070C400099FAB /* JSFloat32Array.h in Headers */,
                                6EBC5EB0138B50F200A0CF8A /* JSFloat64Array.h in Headers */,
+                               B6D9D27B14EAC0860090D75E /* JSFocusEvent.h in Headers */,
                                FDA15EAC12B03EE1003A583A /* JSGainNode.h in Headers */,
                                FE80DA640E9C4703000D6F75 /* JSGeolocation.h in Headers */,
                                FE80DA660E9C4703000D6F75 /* JSGeoposition.h in Headers */,
                                B275357A0B053814002CE64F /* FloatSizeMac.mm in Sources */,
                                D72F6D79153159A3001EE44E /* FlowThreadController.cpp in Sources */,
                                14993BE50B2F2B1C0050497F /* FocusController.cpp in Sources */,
+                               B6D9D23614EABD260090D75E /* FocusEvent.cpp in Sources */,
                                B2C3DA600D006CD600EF6F26 /* Font.cpp in Sources */,
                                B2C3DA620D006CD600EF6F26 /* FontCache.cpp in Sources */,
                                B2AFFC7C0D00A5C10030074D /* FontCacheMac.mm in Sources */,
                                893C47BB1238A0A9002B3D86 /* JSFileWriterCallback.cpp in Sources */,
                                49EECF02105070C400099FAB /* JSFloat32Array.cpp in Sources */,
                                6EBC5EAF138B50F200A0CF8A /* JSFloat64Array.cpp in Sources */,
+                               B6D9D27C14EAC0860090D75E /* JSFocusEvent.cpp in Sources */,
                                FDA15EAB12B03EE1003A583A /* JSGainNode.cpp in Sources */,
                                FE80DA630E9C4703000D6F75 /* JSGeolocation.cpp in Sources */,
                                FE80D7AB0E9C1ED2000D6F75 /* JSGeolocationCustom.cpp in Sources */,
index af41d88..bd598a0 100644 (file)
@@ -84,6 +84,7 @@
 #include "EventTarget.cpp"
 #include "ExceptionBase.cpp"
 #include "ExceptionCodePlaceholder.cpp"
+#include "FocusEvent.cpp"
 #include "IconURL.cpp"
 #include "IdTargetObserver.cpp"
 #include "IdTargetObserverRegistry.cpp"
index 939f514..d5d1fbe 100644 (file)
@@ -122,6 +122,11 @@ bool Event::isMouseEvent() const
     return false;
 }
 
+bool Event::isFocusEvent() const
+{
+    return false;
+}
+
 bool Event::isKeyboardEvent() const
 {
     return false;
index 36f0293..0cbf9b8 100644 (file)
@@ -124,6 +124,7 @@ public:
     // These events are general classes of events.
     virtual bool isUIEvent() const;
     virtual bool isMouseEvent() const;
+    virtual bool isFocusEvent() const;
     virtual bool isKeyboardEvent() const;
     virtual bool isTouchEvent() const;
 
index 887f683..163ae58 100644 (file)
@@ -30,6 +30,7 @@
 #include "DOMWindow.h"
 #include "Document.h"
 #include "Event.h"
+#include "FocusEvent.h"
 #include "MouseEvent.h"
 #include "Node.h"
 
@@ -51,6 +52,8 @@ void EventContext::handleLocalEvents(Event* event) const
     event->setCurrentTarget(m_currentTarget.get());
     if (m_relatedTarget.get() && event->isMouseEvent())
         toMouseEvent(event)->setRelatedTarget(m_relatedTarget.get());
+    else if (m_relatedTarget.get() && event->isFocusEvent())
+        toFocusEvent(event)->setRelatedTarget(m_relatedTarget);
     m_node->handleLocalEvents(event);
 }
 
index b4b5a3e..a2c3c9c 100644 (file)
@@ -8,6 +8,7 @@ CloseEvent
 CompositionEvent
 CustomEvent
 ErrorEvent
+FocusEvent
 HashChangeEvent
 KeyboardEvent
 KeyboardEvents interfaceName=KeyboardEvent
diff --git a/Source/WebCore/dom/FocusEvent.cpp b/Source/WebCore/dom/FocusEvent.cpp
new file mode 100644 (file)
index 0000000..622ffd2
--- /dev/null
@@ -0,0 +1,54 @@
+/*
+ * Copyright (C) 2013 Google Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "config.h"
+#include "FocusEvent.h"
+
+#include "Event.h"
+#include "EventNames.h"
+
+namespace WebCore {
+
+const AtomicString& FocusEvent::interfaceName() const
+{
+    return eventNames().interfaceForFocusEvent;
+}
+
+bool FocusEvent::isFocusEvent() const
+{
+    return true;
+}
+
+FocusEvent::FocusEvent()
+{
+}
+
+FocusEvent::FocusEvent(const AtomicString& type, bool canBubble, bool cancelable, PassRefPtr<AbstractView> view, int detail, PassRefPtr<EventTarget> relatedTarget)
+    : UIEvent(type, canBubble, cancelable, view, detail)
+    , m_relatedTarget(relatedTarget)
+{
+}
+
+} // namespace WebCore
diff --git a/Source/WebCore/dom/FocusEvent.h b/Source/WebCore/dom/FocusEvent.h
new file mode 100644 (file)
index 0000000..5a99fd8
--- /dev/null
@@ -0,0 +1,67 @@
+/*
+ * Copyright (C) 2013 Google Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef FocusEvent_h
+#define FocusEvent_h
+
+#include "EventTarget.h"
+#include "UIEvent.h"
+
+namespace WebCore {
+
+class FocusEvent : public UIEvent {
+public:
+    static PassRefPtr<FocusEvent> create()
+    {
+        return adoptRef(new FocusEvent);
+    }
+
+    static PassRefPtr<FocusEvent> create(const AtomicString& type, bool canBubble, bool cancelable, PassRefPtr<AbstractView> view, int detail, PassRefPtr<EventTarget> relatedTarget)
+    {
+        return adoptRef(new FocusEvent(type, canBubble, cancelable, view, detail, relatedTarget));
+    }
+
+    EventTarget* relatedTarget() const { return m_relatedTarget.get(); }
+    void setRelatedTarget(PassRefPtr<EventTarget> relatedTarget) { m_relatedTarget = relatedTarget; }
+
+    virtual const AtomicString& interfaceName() const;
+    virtual bool isFocusEvent() const;
+
+private:
+    FocusEvent();
+    FocusEvent(const AtomicString& type, bool canBubble, bool cancelable, PassRefPtr<AbstractView>, int, PassRefPtr<EventTarget>);
+
+    RefPtr<EventTarget> m_relatedTarget;
+};
+
+inline FocusEvent* toFocusEvent(Event* event)
+{
+    ASSERT(event && event->isFocusEvent());
+    return static_cast<FocusEvent*>(event);
+}
+
+} // namespace WebCore
+
+#endif // FocusEvent_h
diff --git a/Source/WebCore/dom/FocusEvent.idl b/Source/WebCore/dom/FocusEvent.idl
new file mode 100644 (file)
index 0000000..01dac94
--- /dev/null
@@ -0,0 +1,29 @@
+/*
+ * Copyright (C) 2013 Google Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+interface FocusEvent : UIEvent
+{
+    readonly attribute EventTarget relatedTarget;
+};
index d64939b..74a64c2 100644 (file)
@@ -59,6 +59,7 @@
 #include "EventListener.h"
 #include "EventNames.h"
 #include "ExceptionCode.h"
+#include "FocusEvent.h"
 #include "Frame.h"
 #include "FrameView.h"
 #include "HTMLElement.h"
@@ -2356,14 +2357,14 @@ void Node::dispatchFocusInEvent(const AtomicString& eventType, PassRefPtr<Node>
 {
     ASSERT(!NoEventDispatchAssertion::isEventDispatchForbidden());
     ASSERT(eventType == eventNames().focusinEvent || eventType == eventNames().DOMFocusInEvent);
-    dispatchScopedEventDispatchMediator(FocusInEventDispatchMediator::create(UIEvent::create(eventType, true, false, document()->defaultView(), 0), oldFocusedNode));
+    dispatchScopedEventDispatchMediator(FocusInEventDispatchMediator::create(FocusEvent::create(eventType, true, false, document()->defaultView(), 0, 0), oldFocusedNode));
 }
 
 void Node::dispatchFocusOutEvent(const AtomicString& eventType, PassRefPtr<Node> newFocusedNode)
 {
     ASSERT(!NoEventDispatchAssertion::isEventDispatchForbidden());
     ASSERT(eventType == eventNames().focusoutEvent || eventType == eventNames().DOMFocusOutEvent);
-    dispatchScopedEventDispatchMediator(FocusOutEventDispatchMediator::create(UIEvent::create(eventType, true, false, document()->defaultView(), 0), newFocusedNode));
+    dispatchScopedEventDispatchMediator(FocusOutEventDispatchMediator::create(FocusEvent::create(eventType, true, false, document()->defaultView(), 0, 0), newFocusedNode));
 }
 
 bool Node::dispatchDOMActivateEvent(int detail, PassRefPtr<Event> underlyingEvent)