<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head><meta http-equiv="content-type" content="text/html; charset=utf-8" />
<title>[192020] trunk</title>
</head>
<body>

<style type="text/css"><!--
#msg dl.meta { border: 1px #006 solid; background: #369; padding: 6px; color: #fff; }
#msg dl.meta dt { float: left; width: 6em; font-weight: bold; }
#msg dt:after { content:':';}
#msg dl, #msg dt, #msg ul, #msg li, #header, #footer, #logmsg { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt;  }
#msg dl a { font-weight: bold}
#msg dl a:link    { color:#fc3; }
#msg dl a:active  { color:#ff0; }
#msg dl a:visited { color:#cc6; }
h3 { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt; font-weight: bold; }
#msg pre { overflow: auto; background: #ffc; border: 1px #fa0 solid; padding: 6px; }
#logmsg { background: #ffc; border: 1px #fa0 solid; padding: 1em 1em 0 1em; }
#logmsg p, #logmsg pre, #logmsg blockquote { margin: 0 0 1em 0; }
#logmsg p, #logmsg li, #logmsg dt, #logmsg dd { line-height: 14pt; }
#logmsg h1, #logmsg h2, #logmsg h3, #logmsg h4, #logmsg h5, #logmsg h6 { margin: .5em 0; }
#logmsg h1:first-child, #logmsg h2:first-child, #logmsg h3:first-child, #logmsg h4:first-child, #logmsg h5:first-child, #logmsg h6:first-child { margin-top: 0; }
#logmsg ul, #logmsg ol { padding: 0; list-style-position: inside; margin: 0 0 0 1em; }
#logmsg ul { text-indent: -1em; padding-left: 1em; }#logmsg ol { text-indent: -1.5em; padding-left: 1.5em; }
#logmsg > ul, #logmsg > ol { margin: 0 0 1em 0; }
#logmsg pre { background: #eee; padding: 1em; }
#logmsg blockquote { border: 1px solid #fa0; border-left-width: 10px; padding: 1em 1em 0 1em; background: white;}
#logmsg dl { margin: 0; }
#logmsg dt { font-weight: bold; }
#logmsg dd { margin: 0; padding: 0 0 0.5em 0; }
#logmsg dd:before { content:'\00bb';}
#logmsg table { border-spacing: 0px; border-collapse: collapse; border-top: 4px solid #fa0; border-bottom: 1px solid #fa0; background: #fff; }
#logmsg table th { text-align: left; font-weight: normal; padding: 0.2em 0.5em; border-top: 1px dotted #fa0; }
#logmsg table td { text-align: right; border-top: 1px dotted #fa0; padding: 0.2em 0.5em; }
#logmsg table thead th { text-align: center; border-bottom: 1px solid #fa0; }
#logmsg table th.Corner { text-align: left; }
#logmsg hr { border: none 0; border-top: 2px dashed #fa0; height: 1px; }
#header, #footer { color: #fff; background: #636; border: 1px #300 solid; padding: 6px; }
#patch { width: 100%; }
#patch h4 {font-family: verdana,arial,helvetica,sans-serif;font-size:10pt;padding:8px;background:#369;color:#fff;margin:0;}
#patch .propset h4, #patch .binary h4 {margin:0;}
#patch pre {padding:0;line-height:1.2em;margin:0;}
#patch .diff {width:100%;background:#eee;padding: 0 0 10px 0;overflow:auto;}
#patch .propset .diff, #patch .binary .diff  {padding:10px 0;}
#patch span {display:block;padding:0 10px;}
#patch .modfile, #patch .addfile, #patch .delfile, #patch .propset, #patch .binary, #patch .copfile {border:1px solid #ccc;margin:10px 0;}
#patch ins {background:#dfd;text-decoration:none;display:block;padding:0 10px;}
#patch del {background:#fdd;text-decoration:none;display:block;padding:0 10px;}
#patch .lines, .info {color:#888;background:#fff;}
--></style>
<div id="msg">
<dl class="meta">
<dt>Revision</dt> <dd><a href="http://trac.webkit.org/projects/webkit/changeset/192020">192020</a></dd>
<dt>Author</dt> <dd>commit-queue@webkit.org</dd>
<dt>Date</dt> <dd>2015-11-04 02:40:17 -0800 (Wed, 04 Nov 2015)</dd>
</dl>

<h3>Log Message</h3>
<pre>SVG: hit testing region for &lt;text&gt; elements is incorrect
https://bugs.webkit.org/show_bug.cgi?id=150838

Patch by Antoine Quint &lt;graouts@apple.com&gt; on 2015-11-04
Reviewed by Dean Jackson.

Source/WebCore:

Hit testing for SVG &lt;text&gt; elements was using the same code as hit testing
for CSS-rendered elements. However, in SVG, text elements should only hit
test based on their character cells, not the rectangular bounds of the
element, see section 16.6 of the SVG 1.1 specification:

http://www.w3.org/TR/SVG11/interact.html#PointerEventsProperty

So we now hit test each SVGTextFragment of each SVGInlineTextBox
that is a child of an SVGRootInlineBox to correctly find whether the
provided HitTestLocation is contained within a character cell.

Tests: svg/hittest/text-dominant-baseline-hanging.svg
       svg/hittest/text-multiple-dx-values.svg
       svg/hittest/text-with-multiple-tspans.svg
       svg/hittest/text-with-text-node-and-content-elements.svg
       svg/hittest/text-with-text-node-only.svg
       svg/hittest/text-with-text-path.svg

* rendering/RootInlineBox.h:
Remove the final keyword since nodeAtPoint() may now be subclassed as
implemented in SVGRootInlineBox.

* rendering/svg/SVGInlineTextBox.cpp:
(WebCore::SVGInlineTextBox::nodeAtPoint):
Iterate over the SVGTextFragments to look for a fragment containing the
provided HitTestLocation.

* rendering/svg/SVGRootInlineBox.cpp:
(WebCore::SVGRootInlineBox::nodeAtPoint):
* rendering/svg/SVGRootInlineBox.h:
Override RootInlineBox::nodeAtPoint() to delegate hit testing to the
children inline boxes.

LayoutTests:

* svg/hittest/text-dominant-baseline-hanging-expected.svg: Added.
* svg/hittest/text-dominant-baseline-hanging.svg: Added.
* svg/hittest/text-multiple-dx-values-expected.svg: Added.
* svg/hittest/text-multiple-dx-values.svg: Added.
* svg/hittest/text-with-multiple-tspans-expected.svg: Added.
* svg/hittest/text-with-multiple-tspans.svg: Added.
* svg/hittest/text-with-text-node-and-content-elements-expected.svg: Added.
* svg/hittest/text-with-text-node-and-content-elements.svg: Added.
* svg/hittest/text-with-text-node-only-expected.svg: Added.
* svg/hittest/text-with-text-node-only.svg: Added.
* svg/hittest/text-with-text-path-expected.svg: Added.
* svg/hittest/text-with-text-path.svg: Added.</pre>

<h3>Modified Paths</h3>
<ul>
<li><a href="#trunkLayoutTestsChangeLog">trunk/LayoutTests/ChangeLog</a></li>
<li><a href="#trunkSourceWebCoreChangeLog">trunk/Source/WebCore/ChangeLog</a></li>
<li><a href="#trunkSourceWebCorerenderingRootInlineBoxh">trunk/Source/WebCore/rendering/RootInlineBox.h</a></li>
<li><a href="#trunkSourceWebCorerenderingsvgSVGInlineTextBoxcpp">trunk/Source/WebCore/rendering/svg/SVGInlineTextBox.cpp</a></li>
<li><a href="#trunkSourceWebCorerenderingsvgSVGRootInlineBoxcpp">trunk/Source/WebCore/rendering/svg/SVGRootInlineBox.cpp</a></li>
<li><a href="#trunkSourceWebCorerenderingsvgSVGRootInlineBoxh">trunk/Source/WebCore/rendering/svg/SVGRootInlineBox.h</a></li>
</ul>

<h3>Added Paths</h3>
<ul>
<li><a href="#trunkLayoutTestssvghittesttextdominantbaselinehangingexpectedsvg">trunk/LayoutTests/svg/hittest/text-dominant-baseline-hanging-expected.svg</a></li>
<li><a href="#trunkLayoutTestssvghittesttextdominantbaselinehangingsvg">trunk/LayoutTests/svg/hittest/text-dominant-baseline-hanging.svg</a></li>
<li><a href="#trunkLayoutTestssvghittesttextmultipledxvaluesexpectedsvg">trunk/LayoutTests/svg/hittest/text-multiple-dx-values-expected.svg</a></li>
<li><a href="#trunkLayoutTestssvghittesttextmultipledxvaluessvg">trunk/LayoutTests/svg/hittest/text-multiple-dx-values.svg</a></li>
<li><a href="#trunkLayoutTestssvghittesttextwithmultipletspansexpectedsvg">trunk/LayoutTests/svg/hittest/text-with-multiple-tspans-expected.svg</a></li>
<li><a href="#trunkLayoutTestssvghittesttextwithmultipletspanssvg">trunk/LayoutTests/svg/hittest/text-with-multiple-tspans.svg</a></li>
<li><a href="#trunkLayoutTestssvghittesttextwithtextnodeandcontentelementsexpectedsvg">trunk/LayoutTests/svg/hittest/text-with-text-node-and-content-elements-expected.svg</a></li>
<li><a href="#trunkLayoutTestssvghittesttextwithtextnodeandcontentelementssvg">trunk/LayoutTests/svg/hittest/text-with-text-node-and-content-elements.svg</a></li>
<li><a href="#trunkLayoutTestssvghittesttextwithtextnodeonlyexpectedsvg">trunk/LayoutTests/svg/hittest/text-with-text-node-only-expected.svg</a></li>
<li><a href="#trunkLayoutTestssvghittesttextwithtextnodeonlysvg">trunk/LayoutTests/svg/hittest/text-with-text-node-only.svg</a></li>
<li><a href="#trunkLayoutTestssvghittesttextwithtextpathexpectedsvg">trunk/LayoutTests/svg/hittest/text-with-text-path-expected.svg</a></li>
<li><a href="#trunkLayoutTestssvghittesttextwithtextpathsvg">trunk/LayoutTests/svg/hittest/text-with-text-path.svg</a></li>
</ul>

</div>
<div id="patch">
<h3>Diff</h3>
<a id="trunkLayoutTestsChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/ChangeLog (192019 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/ChangeLog        2015-11-04 10:13:27 UTC (rev 192019)
+++ trunk/LayoutTests/ChangeLog        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -1,3 +1,23 @@
</span><ins>+2015-11-04  Antoine Quint  &lt;graouts@apple.com&gt;
+
+        SVG: hit testing region for &lt;text&gt; elements is incorrect
+        https://bugs.webkit.org/show_bug.cgi?id=150838
+
+        Reviewed by Dean Jackson.
+
+        * svg/hittest/text-dominant-baseline-hanging-expected.svg: Added.
+        * svg/hittest/text-dominant-baseline-hanging.svg: Added.
+        * svg/hittest/text-multiple-dx-values-expected.svg: Added.
+        * svg/hittest/text-multiple-dx-values.svg: Added.
+        * svg/hittest/text-with-multiple-tspans-expected.svg: Added.
+        * svg/hittest/text-with-multiple-tspans.svg: Added.
+        * svg/hittest/text-with-text-node-and-content-elements-expected.svg: Added.
+        * svg/hittest/text-with-text-node-and-content-elements.svg: Added.
+        * svg/hittest/text-with-text-node-only-expected.svg: Added.
+        * svg/hittest/text-with-text-node-only.svg: Added.
+        * svg/hittest/text-with-text-path-expected.svg: Added.
+        * svg/hittest/text-with-text-path.svg: Added.
+
</ins><span class="cx"> 2015-11-04  Xabier Rodriguez Calvar  &lt;calvaris@igalia.com&gt;
</span><span class="cx"> 
</span><span class="cx">         Unreviewed.
</span></span></pre></div>
<a id="trunkLayoutTestssvghittesttextdominantbaselinehangingexpectedsvg"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/svg/hittest/text-dominant-baseline-hanging-expected.svg (0 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/svg/hittest/text-dominant-baseline-hanging-expected.svg                                (rev 0)
+++ trunk/LayoutTests/svg/hittest/text-dominant-baseline-hanging-expected.svg        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -0,0 +1,3 @@
</span><ins>+&lt;svg width=&quot;500&quot; height=&quot;150&quot; viewBox=&quot;0 0 1000 300&quot; xmlns=&quot;http://www.w3.org/2000/svg&quot;&gt;
+    &lt;rect width=&quot;100%&quot; height=&quot;100%&quot; fill=&quot;green&quot; /&gt;
+&lt;/svg&gt;
</ins></span></pre></div>
<a id="trunkLayoutTestssvghittesttextdominantbaselinehangingsvg"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/svg/hittest/text-dominant-baseline-hanging.svg (0 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/svg/hittest/text-dominant-baseline-hanging.svg                                (rev 0)
+++ trunk/LayoutTests/svg/hittest/text-dominant-baseline-hanging.svg        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -0,0 +1,28 @@
</span><ins>+&lt;svg width=&quot;500&quot; height=&quot;150&quot; viewBox=&quot;0 0 1000 300&quot; xmlns=&quot;http://www.w3.org/2000/svg&quot;&gt;
+    &lt;rect id=&quot;background&quot; width=&quot;100%&quot; height=&quot;100%&quot; fill=&quot;red&quot; /&gt;
+    &lt;text id=&quot;text&quot; dominant-baseline=&quot;hanging&quot; x=&quot;10&quot; y=&quot;10&quot;&gt;Foo&lt;/text&gt;
+    &lt;defs&gt;
+        &lt;style type=&quot;text/css&quot;&gt;
+        &lt;![CDATA[
+            @font-face {
+                font-family: Ahem;
+                src: url(../../resources/Ahem.ttf);
+            }
+            text {
+                font-family: Ahem;
+                font-size: 40px;
+            }
+            ]]&gt;
+        &lt;/style&gt;
+        &lt;script type=&quot;text/javascript&quot;&gt;
+        &lt;![CDATA[
+            // The point at 15,15 is contained within the text's bounding box.
+            var text = document.getElementById(&quot;text&quot;);
+            if (document.elementFromPoint(15, 15) === text) {
+                document.getElementById(&quot;background&quot;).setAttribute(&quot;fill&quot;, &quot;green&quot;);
+                text.remove();
+            }
+        ]]&gt;
+        &lt;/script&gt;
+    &lt;/defs&gt;
+&lt;/svg&gt;
</ins></span></pre></div>
<a id="trunkLayoutTestssvghittesttextmultipledxvaluesexpectedsvg"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/svg/hittest/text-multiple-dx-values-expected.svg (0 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/svg/hittest/text-multiple-dx-values-expected.svg                                (rev 0)
+++ trunk/LayoutTests/svg/hittest/text-multiple-dx-values-expected.svg        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -0,0 +1,3 @@
</span><ins>+&lt;svg width=&quot;500&quot; height=&quot;150&quot; viewBox=&quot;0 0 1000 300&quot; xmlns=&quot;http://www.w3.org/2000/svg&quot;&gt;
+    &lt;rect width=&quot;100%&quot; height=&quot;100%&quot; fill=&quot;green&quot; /&gt;
+&lt;/svg&gt;
</ins></span></pre></div>
<a id="trunkLayoutTestssvghittesttextmultipledxvaluessvg"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/svg/hittest/text-multiple-dx-values.svg (0 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/svg/hittest/text-multiple-dx-values.svg                                (rev 0)
+++ trunk/LayoutTests/svg/hittest/text-multiple-dx-values.svg        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -0,0 +1,31 @@
</span><ins>+&lt;svg width=&quot;500&quot; height=&quot;150&quot; viewBox=&quot;0 0 1000 300&quot; xmlns=&quot;http://www.w3.org/2000/svg&quot;&gt;
+    &lt;rect id=&quot;background&quot; width=&quot;100%&quot; height=&quot;100%&quot; fill=&quot;red&quot; /&gt;
+    &lt;text id=&quot;text&quot; x=&quot;10&quot; y=&quot;1em&quot; dx=&quot;0 50 100&quot;&gt;Foo&lt;/text&gt;
+    &lt;defs&gt;
+        &lt;style type=&quot;text/css&quot;&gt;
+        &lt;![CDATA[
+            @font-face {
+                font-family: Ahem;
+                src: url(../../resources/Ahem.ttf);
+            }
+            text {
+                font-family: Ahem;
+                font-size: 40px;
+            }
+            ]]&gt;
+        &lt;/style&gt;
+        &lt;script type=&quot;text/javascript&quot;&gt;
+        &lt;![CDATA[
+            // The point at 15,15 is contained within the text's bounding box.
+            // The point at 30,15 is contained in between the text's character cells
+            // and thus should return the background.
+            var text = document.getElementById(&quot;text&quot;);
+            var background = document.getElementById(&quot;background&quot;);
+            if (document.elementFromPoint(15, 15) === text &amp;&amp; document.elementFromPoint(35, 15) === background) {
+                background.setAttribute(&quot;fill&quot;, &quot;green&quot;);
+                text.remove();
+            }
+        ]]&gt;
+        &lt;/script&gt;
+    &lt;/defs&gt;
+&lt;/svg&gt;
</ins></span></pre></div>
<a id="trunkLayoutTestssvghittesttextwithmultipletspansexpectedsvg"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/svg/hittest/text-with-multiple-tspans-expected.svg (0 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/svg/hittest/text-with-multiple-tspans-expected.svg                                (rev 0)
+++ trunk/LayoutTests/svg/hittest/text-with-multiple-tspans-expected.svg        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -0,0 +1,3 @@
</span><ins>+&lt;svg xmlns=&quot;http://www.w3.org/2000/svg&quot; width=&quot;300&quot; height=&quot;150&quot; viewBox=&quot;0 0 300 150&quot;&gt;
+    &lt;rect width=&quot;100%&quot; height=&quot;100%&quot; fill=&quot;green&quot; /&gt;
+&lt;/svg&gt;
</ins><span class="cx">\ No newline at end of file
</span></span></pre></div>
<a id="trunkLayoutTestssvghittesttextwithmultipletspanssvg"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/svg/hittest/text-with-multiple-tspans.svg (0 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/svg/hittest/text-with-multiple-tspans.svg                                (rev 0)
+++ trunk/LayoutTests/svg/hittest/text-with-multiple-tspans.svg        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -0,0 +1,36 @@
</span><ins>+&lt;svg xmlns=&quot;http://www.w3.org/2000/svg&quot; width=&quot;300&quot; height=&quot;150&quot; viewBox=&quot;0 0 300 150&quot;&gt;
+    &lt;rect width=&quot;100%&quot; height=&quot;100%&quot; fill=&quot;red&quot; /&gt;
+    &lt;text id=&quot;text&quot;&gt;
+        &lt;tspan x=&quot;10&quot; dy=&quot;1em&quot;&gt;Foo&lt;/tspan&gt;
+        &lt;tspan x=&quot;10&quot; dy=&quot;1.2em&quot;&gt;Foo bar baz&lt;/tspan&gt;
+    &lt;/text&gt;
+    &lt;defs&gt;
+        &lt;style type=&quot;text/css&quot;&gt;
+        &lt;![CDATA[
+            @font-face {
+                font-family: Ahem;
+                src: url(../../resources/Ahem.ttf);
+            }
+            text {
+                font-family: Ahem;
+                font-size: 40px;
+            }
+            ]]&gt;
+        &lt;/style&gt;
+        &lt;script type=&quot;text/javascript&quot;&gt;
+        &lt;![CDATA[
+            if (window.testRunner)
+                testRunner.waitUntilDone();
+
+            setTimeout(function() {
+                // The point at 170,30 is contained within the text's bounding box
+                // but not in a painted part so the element should be the background.
+                document.elementFromPoint(170, 30).setAttribute(&quot;fill&quot;, &quot;green&quot;);
+                document.getElementById(&quot;text&quot;).remove();
+                if (window.testRunner)
+                    testRunner.notifyDone();
+            }, 50);
+        ]]&gt;
+        &lt;/script&gt;
+    &lt;/defs&gt;
+&lt;/svg&gt;
</ins><span class="cx">\ No newline at end of file
</span></span></pre></div>
<a id="trunkLayoutTestssvghittesttextwithtextnodeandcontentelementsexpectedsvg"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/svg/hittest/text-with-text-node-and-content-elements-expected.svg (0 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/svg/hittest/text-with-text-node-and-content-elements-expected.svg                                (rev 0)
+++ trunk/LayoutTests/svg/hittest/text-with-text-node-and-content-elements-expected.svg        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -0,0 +1,3 @@
</span><ins>+&lt;svg width=&quot;500&quot; height=&quot;150&quot; viewBox=&quot;0 0 1000 300&quot; xmlns=&quot;http://www.w3.org/2000/svg&quot;&gt;
+    &lt;rect width=&quot;100%&quot; height=&quot;100%&quot; fill=&quot;green&quot; /&gt;
+&lt;/svg&gt;
</ins></span></pre></div>
<a id="trunkLayoutTestssvghittesttextwithtextnodeandcontentelementssvg"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/svg/hittest/text-with-text-node-and-content-elements.svg (0 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/svg/hittest/text-with-text-node-and-content-elements.svg                                (rev 0)
+++ trunk/LayoutTests/svg/hittest/text-with-text-node-and-content-elements.svg        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -0,0 +1,36 @@
</span><ins>+&lt;svg width=&quot;500&quot; height=&quot;150&quot; viewBox=&quot;0 0 1000 300&quot; xmlns=&quot;http://www.w3.org/2000/svg&quot; onclick=&quot;click(evt)&quot;&gt;
+    &lt;rect id=&quot;background&quot; width=&quot;100%&quot; height=&quot;100%&quot; fill=&quot;red&quot; /&gt;
+    &lt;text id=&quot;text&quot; x=&quot;10&quot; y=&quot;1em&quot;&gt;Foo &lt;tspan id=&quot;tspan&quot;&gt;Bar&lt;/tspan&gt; Baz&lt;/text&gt;
+    &lt;defs&gt;
+        &lt;style type=&quot;text/css&quot;&gt;
+        &lt;![CDATA[
+            @font-face {
+                font-family: Ahem;
+                src: url(../../resources/Ahem.ttf);
+            }
+            text {
+                font-family: Ahem;
+                font-size: 40px;
+            }
+            ]]&gt;
+        &lt;/style&gt;
+        &lt;script type=&quot;text/javascript&quot;&gt;
+        &lt;![CDATA[
+            if (window.testRunner)
+                testRunner.waitUntilDone();
+
+            var text = document.getElementById(&quot;text&quot;);
+            setTimeout(function() {
+                // The point at 15,15 is contained within the word &quot;Foo&quot;, a text node.
+                // The point at 120,15 is contained within the word &quot;Bar&quot;, a &lt;tspan&gt;.
+                if (document.elementFromPoint(15, 15) === text &amp;&amp; document.elementFromPoint(110, 15) === document.getElementById(&quot;tspan&quot;)) {
+                    document.getElementById(&quot;background&quot;).setAttribute(&quot;fill&quot;, &quot;green&quot;);
+                    text.remove();
+                    if (window.testRunner)
+                        testRunner.notifyDone();
+                }
+            }, 50);
+        ]]&gt;
+        &lt;/script&gt;
+    &lt;/defs&gt;
+&lt;/svg&gt;
</ins></span></pre></div>
<a id="trunkLayoutTestssvghittesttextwithtextnodeonlyexpectedsvg"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/svg/hittest/text-with-text-node-only-expected.svg (0 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/svg/hittest/text-with-text-node-only-expected.svg                                (rev 0)
+++ trunk/LayoutTests/svg/hittest/text-with-text-node-only-expected.svg        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -0,0 +1,3 @@
</span><ins>+&lt;svg width=&quot;500&quot; height=&quot;150&quot; viewBox=&quot;0 0 1000 300&quot; xmlns=&quot;http://www.w3.org/2000/svg&quot;&gt;
+    &lt;rect width=&quot;100%&quot; height=&quot;100%&quot; fill=&quot;green&quot; /&gt;
+&lt;/svg&gt;
</ins></span></pre></div>
<a id="trunkLayoutTestssvghittesttextwithtextnodeonlysvg"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/svg/hittest/text-with-text-node-only.svg (0 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/svg/hittest/text-with-text-node-only.svg                                (rev 0)
+++ trunk/LayoutTests/svg/hittest/text-with-text-node-only.svg        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -0,0 +1,28 @@
</span><ins>+&lt;svg width=&quot;500&quot; height=&quot;150&quot; viewBox=&quot;0 0 1000 300&quot; xmlns=&quot;http://www.w3.org/2000/svg&quot;&gt;
+    &lt;rect id=&quot;background&quot; width=&quot;100%&quot; height=&quot;100%&quot; fill=&quot;red&quot; /&gt;
+    &lt;text id=&quot;text&quot; x=&quot;10&quot; y=&quot;1em&quot;&gt;Foo&lt;/text&gt;
+    &lt;defs&gt;
+        &lt;style type=&quot;text/css&quot;&gt;
+        &lt;![CDATA[
+            @font-face {
+                font-family: Ahem;
+                src: url(../../resources/Ahem.ttf);
+            }
+            text {
+                font-family: Ahem;
+                font-size: 40px;
+            }
+            ]]&gt;
+        &lt;/style&gt;
+        &lt;script type=&quot;text/javascript&quot;&gt;
+        &lt;![CDATA[
+            // The point at 15,15 is contained within the text's bounding box.
+            var text = document.getElementById(&quot;text&quot;);
+            if (document.elementFromPoint(15, 15) === text) {
+                document.getElementById(&quot;background&quot;).setAttribute(&quot;fill&quot;, &quot;green&quot;);
+                text.remove();
+            }
+        ]]&gt;
+        &lt;/script&gt;
+    &lt;/defs&gt;
+&lt;/svg&gt;
</ins></span></pre></div>
<a id="trunkLayoutTestssvghittesttextwithtextpathexpectedsvg"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/svg/hittest/text-with-text-path-expected.svg (0 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/svg/hittest/text-with-text-path-expected.svg                                (rev 0)
+++ trunk/LayoutTests/svg/hittest/text-with-text-path-expected.svg        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -0,0 +1,3 @@
</span><ins>+&lt;svg width=&quot;500&quot; height=&quot;150&quot; viewBox=&quot;0 0 1000 300&quot; xmlns=&quot;http://www.w3.org/2000/svg&quot;&gt;
+    &lt;rect id=&quot;background&quot; width=&quot;100%&quot; height=&quot;100%&quot; fill=&quot;green&quot; /&gt;
+&lt;/svg&gt;
</ins></span></pre></div>
<a id="trunkLayoutTestssvghittesttextwithtextpathsvg"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/svg/hittest/text-with-text-path.svg (0 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/svg/hittest/text-with-text-path.svg                                (rev 0)
+++ trunk/LayoutTests/svg/hittest/text-with-text-path.svg        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -0,0 +1,33 @@
</span><ins>+&lt;svg width=&quot;500&quot; height=&quot;150&quot; viewBox=&quot;0 0 1000 300&quot; xmlns=&quot;http://www.w3.org/2000/svg&quot; xmlns:xlink=&quot;http://www.w3.org/1999/xlink&quot;&gt;
+    &lt;rect id=&quot;background&quot; width=&quot;100%&quot; height=&quot;100%&quot; fill=&quot;red&quot; /&gt;
+    &lt;text id=&quot;text&quot;&gt;
+        &lt;textPath xlink:href=&quot;#path&quot;&gt;This is text on a path&lt;/textPath&gt;
+    &lt;/text&gt;
+    &lt;defs&gt;
+        &lt;path id=&quot;path&quot;
+              d=&quot;M 100 200 
+              C 200 100 300   0 400 100
+              C 500 200 600 300 700 200
+              C 800 100 900 100 900 100&quot; /&gt;
+        &lt;style type=&quot;text/css&quot;&gt;
+        &lt;![CDATA[
+            @font-face {
+               font-family: Ahem;
+               src: url(../../resources/Ahem.ttf);
+            }
+            text {
+               font-family: Ahem;
+               font-size: 40px;
+            }
+        ]]&gt;
+        &lt;/style&gt;
+        &lt;script type=&quot;text/javascript&quot;&gt;
+        &lt;![CDATA[
+            // The point at 150,75 is contained within the text's bounding box
+            // but not in a painted part so the element should be the background.
+            document.elementFromPoint(150, 75).setAttribute(&quot;fill&quot;, &quot;green&quot;);
+            document.getElementById(&quot;text&quot;).remove();
+        ]]&gt;
+        &lt;/script&gt;
+    &lt;/defs&gt;
+&lt;/svg&gt;
</ins></span></pre></div>
<a id="trunkSourceWebCoreChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/ChangeLog (192019 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/ChangeLog        2015-11-04 10:13:27 UTC (rev 192019)
+++ trunk/Source/WebCore/ChangeLog        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -1,3 +1,43 @@
</span><ins>+2015-11-04  Antoine Quint  &lt;graouts@apple.com&gt;
+
+        SVG: hit testing region for &lt;text&gt; elements is incorrect
+        https://bugs.webkit.org/show_bug.cgi?id=150838
+
+        Reviewed by Dean Jackson.
+
+        Hit testing for SVG &lt;text&gt; elements was using the same code as hit testing
+        for CSS-rendered elements. However, in SVG, text elements should only hit
+        test based on their character cells, not the rectangular bounds of the
+        element, see section 16.6 of the SVG 1.1 specification:
+        
+        http://www.w3.org/TR/SVG11/interact.html#PointerEventsProperty
+        
+        So we now hit test each SVGTextFragment of each SVGInlineTextBox
+        that is a child of an SVGRootInlineBox to correctly find whether the
+        provided HitTestLocation is contained within a character cell. 
+
+        Tests: svg/hittest/text-dominant-baseline-hanging.svg
+               svg/hittest/text-multiple-dx-values.svg
+               svg/hittest/text-with-multiple-tspans.svg
+               svg/hittest/text-with-text-node-and-content-elements.svg
+               svg/hittest/text-with-text-node-only.svg
+               svg/hittest/text-with-text-path.svg
+
+        * rendering/RootInlineBox.h:
+        Remove the final keyword since nodeAtPoint() may now be subclassed as
+        implemented in SVGRootInlineBox.

+        * rendering/svg/SVGInlineTextBox.cpp:
+        (WebCore::SVGInlineTextBox::nodeAtPoint):
+        Iterate over the SVGTextFragments to look for a fragment containing the
+        provided HitTestLocation.

+        * rendering/svg/SVGRootInlineBox.cpp:
+        (WebCore::SVGRootInlineBox::nodeAtPoint):
+        * rendering/svg/SVGRootInlineBox.h:
+        Override RootInlineBox::nodeAtPoint() to delegate hit testing to the
+        children inline boxes.
+
</ins><span class="cx"> 2015-11-04  Carlos Garcia Campos  &lt;cgarcia@igalia.com&gt;
</span><span class="cx"> 
</span><span class="cx">         [GStreamer] Use RunLoop::Timer for ready state timer in MediaPlayerPrivateGStreamer
</span></span></pre></div>
<a id="trunkSourceWebCorerenderingRootInlineBoxh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/rendering/RootInlineBox.h (192019 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/rendering/RootInlineBox.h        2015-11-04 10:13:27 UTC (rev 192019)
+++ trunk/Source/WebCore/rendering/RootInlineBox.h        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -119,7 +119,7 @@
</span><span class="cx">     virtual LayoutUnit lineHeight() const override final;
</span><span class="cx"> 
</span><span class="cx">     virtual void paint(PaintInfo&amp;, const LayoutPoint&amp;, LayoutUnit lineTop, LayoutUnit lineBottom) override;
</span><del>-    virtual bool nodeAtPoint(const HitTestRequest&amp;, HitTestResult&amp;, const HitTestLocation&amp; locationInContainer, const LayoutPoint&amp; accumulatedOffset, LayoutUnit lineTop, LayoutUnit lineBottom, HitTestAction) override final;
</del><ins>+    virtual bool nodeAtPoint(const HitTestRequest&amp;, HitTestResult&amp;, const HitTestLocation&amp; locationInContainer, const LayoutPoint&amp; accumulatedOffset, LayoutUnit lineTop, LayoutUnit lineBottom, HitTestAction) override;
</ins><span class="cx"> 
</span><span class="cx">     using InlineBox::hasSelectedChildren;
</span><span class="cx">     using InlineBox::setHasSelectedChildren;
</span></span></pre></div>
<a id="trunkSourceWebCorerenderingsvgSVGInlineTextBoxcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/rendering/svg/SVGInlineTextBox.cpp (192019 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/rendering/svg/SVGInlineTextBox.cpp        2015-11-04 10:13:27 UTC (rev 192019)
+++ trunk/Source/WebCore/rendering/svg/SVGInlineTextBox.cpp        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -685,9 +685,25 @@
</span><span class="cx">             boxOrigin.moveBy(accumulatedOffset);
</span><span class="cx">             FloatRect rect(boxOrigin, size());
</span><span class="cx">             if (locationInContainer.intersects(rect)) {
</span><del>-                renderer().updateHitTestResult(result, locationInContainer.point() - toLayoutSize(accumulatedOffset));
-                if (!result.addNodeToRectBasedTestResult(&amp;renderer().textNode(), request, locationInContainer, rect))
-                    return true;
</del><ins>+
+                float scalingFactor = renderer().scalingFactor();
+                ASSERT(scalingFactor);
+                
+                float baseline = renderer().scaledFont().fontMetrics().floatAscent() / scalingFactor;
+
+                AffineTransform fragmentTransform;
+                for (auto&amp; fragment : m_textFragments) {
+                    FloatQuad fragmentQuad(FloatRect(fragment.x, fragment.y - baseline, fragment.width, fragment.height));
+                    fragment.buildFragmentTransform(fragmentTransform);
+                    if (!fragmentTransform.isIdentity())
+                        fragmentQuad = fragmentTransform.mapQuad(fragmentQuad);
+                    
+                    if (fragmentQuad.containsPoint(locationInContainer.point())) {
+                        renderer().updateHitTestResult(result, locationInContainer.point() - toLayoutSize(accumulatedOffset));
+                        if (!result.addNodeToRectBasedTestResult(&amp;renderer().textNode(), request, locationInContainer, rect))
+                            return true;
+                    }
+                }
</ins><span class="cx">              }
</span><span class="cx">         }
</span><span class="cx">     }
</span></span></pre></div>
<a id="trunkSourceWebCorerenderingsvgSVGRootInlineBoxcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/rendering/svg/SVGRootInlineBox.cpp (192019 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/rendering/svg/SVGRootInlineBox.cpp        2015-11-04 10:13:27 UTC (rev 192019)
+++ trunk/Source/WebCore/rendering/svg/SVGRootInlineBox.cpp        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -209,6 +209,18 @@
</span><span class="cx">     return closestLeaf ? closestLeaf : lastLeaf;
</span><span class="cx"> }
</span><span class="cx"> 
</span><ins>+bool SVGRootInlineBox::nodeAtPoint(const HitTestRequest&amp; request, HitTestResult&amp; result, const HitTestLocation&amp; locationInContainer, const LayoutPoint&amp; accumulatedOffset, LayoutUnit lineTop, LayoutUnit lineBottom, HitTestAction hitTestAction)
+{
+    for (InlineBox* leaf = firstLeafChild(); leaf; leaf = leaf-&gt;nextLeafChild()) {
+        if (!leaf-&gt;isSVGInlineTextBox())
+            continue;
+        if (leaf-&gt;nodeAtPoint(request, result, locationInContainer, accumulatedOffset, lineTop, lineBottom, hitTestAction))
+            return true;
+    }
+
+    return false;
+}
+
</ins><span class="cx"> static inline void swapItemsInLayoutAttributes(SVGTextLayoutAttributes* firstAttributes, SVGTextLayoutAttributes* lastAttributes, unsigned firstPosition, unsigned lastPosition)
</span><span class="cx"> {
</span><span class="cx">     SVGCharacterDataMap::iterator itFirst = firstAttributes-&gt;characterDataMap().find(firstPosition + 1);
</span></span></pre></div>
<a id="trunkSourceWebCorerenderingsvgSVGRootInlineBoxh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/rendering/svg/SVGRootInlineBox.h (192019 => 192020)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/rendering/svg/SVGRootInlineBox.h        2015-11-04 10:13:27 UTC (rev 192019)
+++ trunk/Source/WebCore/rendering/svg/SVGRootInlineBox.h        2015-11-04 10:40:17 UTC (rev 192020)
</span><span class="lines">@@ -47,6 +47,8 @@
</span><span class="cx"> 
</span><span class="cx">     InlineBox* closestLeafChildForPosition(const LayoutPoint&amp;);
</span><span class="cx"> 
</span><ins>+    virtual bool nodeAtPoint(const HitTestRequest&amp;, HitTestResult&amp;, const HitTestLocation&amp; locationInContainer, const LayoutPoint&amp; accumulatedOffset, LayoutUnit lineTop, LayoutUnit lineBottom, HitTestAction) override final;
+
</ins><span class="cx"> private:
</span><span class="cx">     virtual bool isSVGRootInlineBox() const override { return true; }
</span><span class="cx">     void reorderValueLists(Vector&lt;SVGTextLayoutAttributes*&gt;&amp;);
</span></span></pre>
</div>
</div>

</body>
</html>