<!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>[174446] releases/WebKitGTK/webkit-2.6</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/174446">174446</a></dd>
<dt>Author</dt> <dd>carlosgc@webkit.org</dd>
<dt>Date</dt> <dd>2014-10-08 06:16:35 -0700 (Wed, 08 Oct 2014)</dd>
</dl>
<h3>Log Message</h3>
<pre>Merge <a href="http://trac.webkit.org/projects/webkit/changeset/174074">r174074</a> - AX: in an aria-labelledby computation, do not traverse into elements whose nameFrom value does not include 'contents'
https://bugs.webkit.org/show_bug.cgi?id=136714
Reviewed by Darin Adler.
Source/WebCore:
There are certain ARIA elements that tell us we should not query their children when determining the name of the object.
Those ones have the "nameFrom" property set to "author" instead of "contents." WebKit needs to honor that status.
Test: accessibility/aria-namefrom-author.html
Modified: accessibility/aria-labelledby-with-descendants.html
* accessibility/AccessibilityNodeObject.cpp:
(WebCore::shouldUseAccessiblityObjectInnerText):
(WebCore::shouldAddSpaceBeforeAppendingNextElement):
(WebCore::appendNameToStringBuilder):
(WebCore::AccessibilityNodeObject::textUnderElement):
(WebCore::accessibleNameForNode):
(WebCore::AccessibilityNodeObject::accessibilityDescriptionForElements):
* accessibility/AccessibilityObject.cpp:
(WebCore::AccessibilityObject::accessibleNameDerivesFromContent):
(WebCore::initializeRoleMap):
* accessibility/AccessibilityObject.h:
LayoutTests:
* accessibility/aria-labelledby-with-descendants-expected.txt:
* accessibility/aria-labelledby-with-descendants.html:
* accessibility/aria-namefrom-author-expected.txt: Added.
* accessibility/aria-namefrom-author.html: Added.</pre>
<h3>Modified Paths</h3>
<ul>
<li><a href="#releasesWebKitGTKwebkit26LayoutTestsChangeLog">releases/WebKitGTK/webkit-2.6/LayoutTests/ChangeLog</a></li>
<li><a href="#releasesWebKitGTKwebkit26LayoutTestsaccessibilityarialabelledbywithdescendantsexpectedtxt">releases/WebKitGTK/webkit-2.6/LayoutTests/accessibility/aria-labelledby-with-descendants-expected.txt</a></li>
<li><a href="#releasesWebKitGTKwebkit26LayoutTestsaccessibilityarialabelledbywithdescendantshtml">releases/WebKitGTK/webkit-2.6/LayoutTests/accessibility/aria-labelledby-with-descendants.html</a></li>
<li><a href="#releasesWebKitGTKwebkit26SourceWebCoreChangeLog">releases/WebKitGTK/webkit-2.6/Source/WebCore/ChangeLog</a></li>
<li><a href="#releasesWebKitGTKwebkit26SourceWebCoreaccessibilityAccessibilityNodeObjectcpp">releases/WebKitGTK/webkit-2.6/Source/WebCore/accessibility/AccessibilityNodeObject.cpp</a></li>
<li><a href="#releasesWebKitGTKwebkit26SourceWebCoreaccessibilityAccessibilityObjectcpp">releases/WebKitGTK/webkit-2.6/Source/WebCore/accessibility/AccessibilityObject.cpp</a></li>
<li><a href="#releasesWebKitGTKwebkit26SourceWebCoreaccessibilityAccessibilityObjecth">releases/WebKitGTK/webkit-2.6/Source/WebCore/accessibility/AccessibilityObject.h</a></li>
</ul>
<h3>Added Paths</h3>
<ul>
<li><a href="#releasesWebKitGTKwebkit26LayoutTestsaccessibilityarianamefromauthorexpectedtxt">releases/WebKitGTK/webkit-2.6/LayoutTests/accessibility/aria-namefrom-author-expected.txt</a></li>
<li><a href="#releasesWebKitGTKwebkit26LayoutTestsaccessibilityarianamefromauthorhtml">releases/WebKitGTK/webkit-2.6/LayoutTests/accessibility/aria-namefrom-author.html</a></li>
</ul>
</div>
<div id="patch">
<h3>Diff</h3>
<a id="releasesWebKitGTKwebkit26LayoutTestsChangeLog"></a>
<div class="modfile"><h4>Modified: releases/WebKitGTK/webkit-2.6/LayoutTests/ChangeLog (174445 => 174446)</h4>
<pre class="diff"><span>
<span class="info">--- releases/WebKitGTK/webkit-2.6/LayoutTests/ChangeLog        2014-10-08 13:11:20 UTC (rev 174445)
+++ releases/WebKitGTK/webkit-2.6/LayoutTests/ChangeLog        2014-10-08 13:16:35 UTC (rev 174446)
</span><span class="lines">@@ -1,3 +1,15 @@
</span><ins>+2014-09-29 Chris Fleizach <cfleizach@apple.com>
+
+ AX: in an aria-labelledby computation, do not traverse into elements whose nameFrom value does not include 'contents'
+ https://bugs.webkit.org/show_bug.cgi?id=136714
+
+ Reviewed by Darin Adler.
+
+ * accessibility/aria-labelledby-with-descendants-expected.txt:
+ * accessibility/aria-labelledby-with-descendants.html:
+ * accessibility/aria-namefrom-author-expected.txt: Added.
+ * accessibility/aria-namefrom-author.html: Added.
+
</ins><span class="cx"> 2014-09-25 Brian J. Burg <burg@cs.washington.edu>
</span><span class="cx">
</span><span class="cx"> StorageTracker::deleteOrigin being called off the main thread (ASSERTs in inspector/test-harness-trivially-works.html test)
</span></span></pre></div>
<a id="releasesWebKitGTKwebkit26LayoutTestsaccessibilityarialabelledbywithdescendantsexpectedtxt"></a>
<div class="modfile"><h4>Modified: releases/WebKitGTK/webkit-2.6/LayoutTests/accessibility/aria-labelledby-with-descendants-expected.txt (174445 => 174446)</h4>
<pre class="diff"><span>
<span class="info">--- releases/WebKitGTK/webkit-2.6/LayoutTests/accessibility/aria-labelledby-with-descendants-expected.txt        2014-10-08 13:11:20 UTC (rev 174445)
+++ releases/WebKitGTK/webkit-2.6/LayoutTests/accessibility/aria-labelledby-with-descendants-expected.txt        2014-10-08 13:16:35 UTC (rev 174446)
</span><span class="lines">@@ -1,3 +1,5 @@
</span><ins>+
+
</ins><span class="cx"> This tests that if aria-labelledby is pointing to nodes with descendants, it returns all text.
</span><span class="cx">
</span><span class="cx"> On success, you will see a series of "PASS" messages, followed by "TEST COMPLETE".
</span><span class="lines">@@ -3,5 +5,25 @@
</span><span class="cx">
</span><span class="cx">
</span><del>-aria-labelledby description: AXDescription: hello link world test1 test2 test3
</del><ins>+test 1: aria-labelledby description: AXDescription: hello link use world test1 test2 test3
+test 1: expected description: hello link use world test1 test2 test3
+
+test 2: aria-labelledby description: AXDescription: foo bar
+test 2: expected description: foo bar
+
+test 3: aria-labelledby description: AXDescription: foo bar
+test 3: expected description: foo bar
+
+test 4: aria-labelledby description: AXDescription: foo
+test 4: expected description: foo
+
+test 5: aria-labelledby description: AXDescription: Delete
+test 5: expected description: Delete
+
+test 6: aria-labelledby description: AXDescription: Delete product name
+test 6: expected description: Delete product name
+
+test 7: aria-labelledby description: AXDescription: foo bar baz bop bap boom
+test 7: expected description: foo bar baz bop bap boom
+
</ins><span class="cx"> PASS successfullyParsed is true
</span><span class="cx">
</span></span></pre></div>
<a id="releasesWebKitGTKwebkit26LayoutTestsaccessibilityarialabelledbywithdescendantshtml"></a>
<div class="modfile"><h4>Modified: releases/WebKitGTK/webkit-2.6/LayoutTests/accessibility/aria-labelledby-with-descendants.html (174445 => 174446)</h4>
<pre class="diff"><span>
<span class="info">--- releases/WebKitGTK/webkit-2.6/LayoutTests/accessibility/aria-labelledby-with-descendants.html        2014-10-08 13:11:20 UTC (rev 174445)
+++ releases/WebKitGTK/webkit-2.6/LayoutTests/accessibility/aria-labelledby-with-descendants.html        2014-10-08 13:16:35 UTC (rev 174446)
</span><span class="lines">@@ -7,19 +7,36 @@
</span><span class="cx">
</span><span class="cx"> <div id="content">
</span><span class="cx">
</span><del>-<div aria-labelledby="a b" id="group" role="group">
-group text
-</div>
</del><ins>+<div class="ex" data-label="hello link use world test1 test2 test3" aria-labelledby="a1 b1" id="test1" role="group">group text</div>
+<div id="a1">hello <a href="#">link</a> <div role="group">skip</div> <div role="group" aria-label="use">skip</div> world</div>
+<!-- paragraph role is ambiguous so okay to leave next example as it -->
+<div id="b1"><button>test1</button><p tabindex=0>test2 <span aria-hidden="true">hidden</span> test3</p></div>
</ins><span class="cx">
</span><del>-<div id="a">
-hello <a href="#">link</a> world
-</div>
</del><ins>+<input type="checkbox" aria-labelledby="reverselabelfor" id="test2" class="ex" data-label="foo bar" data-note="labelled by label element">
+<label id="reverselabelfor">foo <span role="text" aria-label="bar">skip</span></label>
+<br>
</ins><span class="cx">
</span><del>-<div id="b">
-<button>test1</button>
-<p tabindex=0>test2 <span aria-hidden="true">hidden</span> test3</p>
-</div>
</del><ins>+<input type="checkbox" aria-labelledby="reverselabelforwithdiv" id="test3" class="ex" data-label="foo bar" data-note="labelled by div element">
+<div id="reverselabelforwithdiv">foo <span role="text" aria-label="bar">skip</span></div>
+<br>
</ins><span class="cx">
</span><ins>+<!-- would be "bar" natively, but label explicitly overridden to "foo" by labelledby -->
+<div id="overridesnativelabel">foo</div><label for="nativelabeloverridden">bar</label>
+<input class="ex" data-label="foo" id="test4" type="text" aria-labelledby="overridesnativelabel" data-note="overrides native label">
+
+<!-- self-referencing labelledby in combination with external reference -->
+<div id="productname1"><nav role="navigation"><!-- nav does not get nameFrom:contents -->product name</nav></div>
+<button class="ex" data-label="Delete" aria-label="Delete" aria-labelledby="test5 productname1" id="test5" data-note="self-referencial labelledby includes nav">x</button>
+
+<!-- self-referencing labelledby in combination with external reference -->
+<div id="productname2"><nav role="heading"><!-- nav does not get nameFrom:contents, but heading does. -->product name</nav></div>
+<button class="ex" data-label="Delete product name" aria-label="Delete" aria-labelledby="test6 productname2" id="test6" data-note="self-referencial labelledby includes heading">x</button>
+
+<div class="ex" data-label="foo bar baz bop bap boom" aria-labelledby="a3 b3" id="test7" role="group" data-note="includes form elements">foo</div>
+<button id="a3"> foo <img src="#" alt="bar"> baz</button>
+<div id="b3">bop <input value="bap"> <input type="range" aria-valuetext="boom"></div>
+
+
</ins><span class="cx"> </div>
</span><span class="cx">
</span><span class="cx"> <p id="description"></p>
</span><span class="lines">@@ -30,8 +47,11 @@
</span><span class="cx"> description("This tests that if aria-labelledby is pointing to nodes with descendants, it returns all text.");
</span><span class="cx">
</span><span class="cx"> if (window.accessibilityController) {
</span><del>- var group = accessibilityController.accessibleElementById("group");
- debug("aria-labelledby description: " + group.description);
</del><ins>+ for (var k = 1; k < 8; k++) {
+ var test = accessibilityController.accessibleElementById("test" + k);
+ debug("test " + k + ": aria-labelledby description: " + test.description);
+ debug("test " + k + ": expected description: " + document.getElementById("test" + k).getAttribute("data-label") + "\n");
+ }
</ins><span class="cx"> document.getElementById("content").style.visibility = "hidden";
</span><span class="cx"> }
</span><span class="cx">
</span></span></pre></div>
<a id="releasesWebKitGTKwebkit26LayoutTestsaccessibilityarianamefromauthorexpectedtxt"></a>
<div class="addfile"><h4>Added: releases/WebKitGTK/webkit-2.6/LayoutTests/accessibility/aria-namefrom-author-expected.txt (0 => 174446)</h4>
<pre class="diff"><span>
<span class="info">--- releases/WebKitGTK/webkit-2.6/LayoutTests/accessibility/aria-namefrom-author-expected.txt         (rev 0)
+++ releases/WebKitGTK/webkit-2.6/LayoutTests/accessibility/aria-namefrom-author-expected.txt        2014-10-08 13:16:35 UTC (rev 174446)
</span><span class="lines">@@ -0,0 +1,10 @@
</span><ins>+This tests all the cases where nameFrom: author is used instead of nameFrom: contents. This means that if these elements are used in aria-labelledby they should not return their inner text. The button should retain its aria-label as the description.
+
+On success, you will see a series of "PASS" messages, followed by "TEST COMPLETE".
+
+
+Button description: AXDescription: text
+PASS successfullyParsed is true
+
+TEST COMPLETE
+
</ins></span></pre></div>
<a id="releasesWebKitGTKwebkit26LayoutTestsaccessibilityarianamefromauthorhtml"></a>
<div class="addfile"><h4>Added: releases/WebKitGTK/webkit-2.6/LayoutTests/accessibility/aria-namefrom-author.html (0 => 174446)</h4>
<pre class="diff"><span>
<span class="info">--- releases/WebKitGTK/webkit-2.6/LayoutTests/accessibility/aria-namefrom-author.html         (rev 0)
+++ releases/WebKitGTK/webkit-2.6/LayoutTests/accessibility/aria-namefrom-author.html        2014-10-08 13:16:35 UTC (rev 174446)
</span><span class="lines">@@ -0,0 +1,78 @@
</span><ins>+<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML//EN">
+<html>
+<head>
+<script src="../resources/js-test-pre.js"></script>
+</head>
+<body id="body">
+
+<div id="content">
+
+<div id="test1" class="test" role="alert">alert</div>
+<div id="test2" class="test" role="alertdialog">alertdialog</div>
+<div id="test3" class="test" role="dialog">dialog</div>
+<div id="test4" class="test" role="log">log</div>
+<div id="test5" class="test" role="marquee">marquee</div>
+<div id="test6" class="test" role="status">status</div>
+<div id="test7" class="test" role="timer">timer</div>
+<div id="test8" class="test" role="combobox">combobox</div>
+<div id="test9" class="test" role="definition">definition</div>
+<div id="test10" class="test" role="document">document</div>
+<div id="test11" class="test" role="article">article</div>
+<div id="test12" class="test" role="math">math</div>
+<div id="test13" class="test" role="note">note</div>
+<div id="test14" class="test" role="region">region</div>
+<div id="test15" class="test" role="form">form</div>
+<div id="test16" class="test" role="grid">grid</div>
+<div id="test17" class="test" role="group">group</div>
+<div id="test18" class="test" role="img">img</div>
+<div id="test19" class="test" role="list">list</div>
+<div id="test20" class="test" role="listbox">listbox</div>
+<div id="test21" class="test" role="application">application</div>
+<div id="test22" class="test" role="banner">banner</div>
+<div id="test23" class="test" role="complementary">complementary</div>
+<div id="test24" class="test" role="contentinfo">contentinfo</div>
+<div id="test25" class="test" role="navigation">navigation</div>
+<div id="test26" class="test" role="main">main</div>
+<div id="test27" class="test" role="search">search</div>
+<div id="test28" class="test" role="menu">menu</div>
+<div id="test29" class="test" role="menubar">menubar</div>
+<div id="test30" class="test" role="progressbar">progressbar</div>
+<div id="test31" class="test" role="radiogroup">radiogroup</div>
+<div id="test32" class="test" role="scrollbar">scrollbar</div>
+<div id="test33" class="test" role="slider">slider</div>
+<div id="test34" class="test" role="spinbutton">spinbutton</div>
+<div id="test35" class="test" role="separator">separator</div>
+<div id="test36" class="test" role="tablist">tablist</div>
+<div id="test37" class="test" role="tabpanel">tabpanel</div>
+<div id="test38" class="test" role="textbox">textbox</div>
+<div id="test39" class="test" role="toolbar">toolbar</div>
+<div id="test40" class="test" role="treegrid">treegrid</div>
+<div id="test41" class="test" role="tree">tree</div>
+
+
+<div role="button" id="button" aria-label="text">button text</div>
+</div>
+
+<p id="description"></p>
+<div id="console"></div>
+
+<script>
+
+ description("This tests all the cases where nameFrom: author is used instead of nameFrom: contents. This means that if these elements are used in aria-labelledby they should not return their inner text. The button should retain its aria-label as the description.");
+
+ var labelledby = "";
+ for (var k = 1; k < 42; k++) {
+ labelledby += "test" + k + " ";
+ }
+ document.getElementById("button").setAttribute("aria-labelledby", labelledby);
+
+ if (window.accessibilityController) {
+ debug("Button description: " + accessibilityController.accessibleElementById("button").description);
+ document.getElementById("content").style.visibility = "hidden";
+ }
+
+</script>
+
+<script src="../resources/js-test-post.js"></script>
+</body>
+</html>
</ins></span></pre></div>
<a id="releasesWebKitGTKwebkit26SourceWebCoreChangeLog"></a>
<div class="modfile"><h4>Modified: releases/WebKitGTK/webkit-2.6/Source/WebCore/ChangeLog (174445 => 174446)</h4>
<pre class="diff"><span>
<span class="info">--- releases/WebKitGTK/webkit-2.6/Source/WebCore/ChangeLog        2014-10-08 13:11:20 UTC (rev 174445)
+++ releases/WebKitGTK/webkit-2.6/Source/WebCore/ChangeLog        2014-10-08 13:16:35 UTC (rev 174446)
</span><span class="lines">@@ -1,3 +1,28 @@
</span><ins>+2014-09-29 Chris Fleizach <cfleizach@apple.com>
+
+ AX: in an aria-labelledby computation, do not traverse into elements whose nameFrom value does not include 'contents'
+ https://bugs.webkit.org/show_bug.cgi?id=136714
+
+ Reviewed by Darin Adler.
+
+ There are certain ARIA elements that tell us we should not query their children when determining the name of the object.
+ Those ones have the "nameFrom" property set to "author" instead of "contents." WebKit needs to honor that status.
+
+ Test: accessibility/aria-namefrom-author.html
+ Modified: accessibility/aria-labelledby-with-descendants.html
+
+ * accessibility/AccessibilityNodeObject.cpp:
+ (WebCore::shouldUseAccessiblityObjectInnerText):
+ (WebCore::shouldAddSpaceBeforeAppendingNextElement):
+ (WebCore::appendNameToStringBuilder):
+ (WebCore::AccessibilityNodeObject::textUnderElement):
+ (WebCore::accessibleNameForNode):
+ (WebCore::AccessibilityNodeObject::accessibilityDescriptionForElements):
+ * accessibility/AccessibilityObject.cpp:
+ (WebCore::AccessibilityObject::accessibleNameDerivesFromContent):
+ (WebCore::initializeRoleMap):
+ * accessibility/AccessibilityObject.h:
+
</ins><span class="cx"> 2014-09-27 Chris Dumez <cdumez@apple.com>
</span><span class="cx">
</span><span class="cx"> HTMLPlugInElement::isUserObservable() is causing layout
</span></span></pre></div>
<a id="releasesWebKitGTKwebkit26SourceWebCoreaccessibilityAccessibilityNodeObjectcpp"></a>
<div class="modfile"><h4>Modified: releases/WebKitGTK/webkit-2.6/Source/WebCore/accessibility/AccessibilityNodeObject.cpp (174445 => 174446)</h4>
<pre class="diff"><span>
<span class="info">--- releases/WebKitGTK/webkit-2.6/Source/WebCore/accessibility/AccessibilityNodeObject.cpp        2014-10-08 13:11:20 UTC (rev 174445)
+++ releases/WebKitGTK/webkit-2.6/Source/WebCore/accessibility/AccessibilityNodeObject.cpp        2014-10-08 13:16:35 UTC (rev 174446)
</span><span class="lines">@@ -1610,6 +1610,11 @@
</span><span class="cx"> // quite long. As a heuristic, skip links, controls, and elements that are usually
</span><span class="cx"> // containers with lots of children.
</span><span class="cx">
</span><ins>+ // ARIA states that certain elements are not allowed to expose their children content for name calculation.
+ if (mode.childrenInclusion == AccessibilityTextUnderElementMode::TextUnderElementModeIncludeNameFromContentsChildren
+ && !obj->accessibleNameDerivesFromContent())
+ return false;
+
</ins><span class="cx"> if (equalIgnoringCase(obj->getAttribute(aria_hiddenAttr), "true"))
</span><span class="cx"> return false;
</span><span class="cx">
</span><span class="lines">@@ -1629,7 +1634,7 @@
</span><span class="cx"> return true;
</span><span class="cx"> }
</span><span class="cx">
</span><del>-static bool shouldAddSpaceBeforeAppendingNextElement(StringBuilder& builder, String& childText)
</del><ins>+static bool shouldAddSpaceBeforeAppendingNextElement(StringBuilder& builder, const String& childText)
</ins><span class="cx"> {
</span><span class="cx"> if (!builder.length() || !childText.length())
</span><span class="cx"> return false;
</span><span class="lines">@@ -1637,6 +1642,13 @@
</span><span class="cx"> // We don't need to add an additional space before or after a line break.
</span><span class="cx"> return !(isHTMLLineBreak(childText[0]) || isHTMLLineBreak(builder[builder.length() - 1]));
</span><span class="cx"> }
</span><ins>+
+static void appendNameToStringBuilder(StringBuilder& builder, const String& text)
+{
+ if (shouldAddSpaceBeforeAppendingNextElement(builder, text))
+ builder.append(' ');
+ builder.append(text);
+}
</ins><span class="cx">
</span><span class="cx"> String AccessibilityNodeObject::textUnderElement(AccessibilityTextUnderElementMode mode) const
</span><span class="cx"> {
</span><span class="lines">@@ -1652,6 +1664,13 @@
</span><span class="cx">
</span><span class="cx"> StringBuilder builder;
</span><span class="cx"> for (AccessibilityObject* child = firstChild(); child; child = child->nextSibling()) {
</span><ins>+
+ bool shouldDeriveNameFromAuthor = (mode.childrenInclusion == AccessibilityTextUnderElementMode::TextUnderElementModeIncludeNameFromContentsChildren && !child->accessibleNameDerivesFromContent());
+ if (shouldDeriveNameFromAuthor) {
+ appendNameToStringBuilder(builder, accessibleNameForNode(child->node()));
+ continue;
+ }
+
</ins><span class="cx"> if (!shouldUseAccessiblityObjectInnerText(child, mode))
</span><span class="cx"> continue;
</span><span class="cx">
</span><span class="lines">@@ -1659,19 +1678,14 @@
</span><span class="cx"> Vector<AccessibilityText> textOrder;
</span><span class="cx"> toAccessibilityNodeObject(child)->alternativeText(textOrder);
</span><span class="cx"> if (textOrder.size() > 0 && textOrder[0].text.length()) {
</span><del>- if (shouldAddSpaceBeforeAppendingNextElement(builder, textOrder[0].text))
- builder.append(' ');
- builder.append(textOrder[0].text);
</del><ins>+ appendNameToStringBuilder(builder, textOrder[0].text);
</ins><span class="cx"> continue;
</span><span class="cx"> }
</span><span class="cx"> }
</span><del>-
</del><ins>+
</ins><span class="cx"> String childText = child->textUnderElement(mode);
</span><del>- if (childText.length()) {
- if (shouldAddSpaceBeforeAppendingNextElement(builder, childText))
- builder.append(' ');
- builder.append(childText);
- }
</del><ins>+ if (childText.length())
+ appendNameToStringBuilder(builder, childText);
</ins><span class="cx"> }
</span><span class="cx">
</span><span class="cx"> return builder.toString().stripWhiteSpace().simplifyWhiteSpace(isHTMLSpaceButNotLineBreak);
</span><span class="lines">@@ -1840,19 +1854,26 @@
</span><span class="cx"> const AtomicString& alt = element->fastGetAttribute(altAttr);
</span><span class="cx"> if (!alt.isEmpty())
</span><span class="cx"> return alt;
</span><ins>+
+ // If the node can be turned into an AX object, we can use standard name computation rules.
+ // If however, the node cannot (because there's no renderer e.g.) fallback to using the basic text underneath.
+ AccessibilityObject* axObject = node->document().axObjectCache()->getOrCreate(node);
+ if (axObject) {
+ String valueDescription = axObject->valueDescription();
+ if (!valueDescription.isEmpty())
+ return valueDescription;
+ }
</ins><span class="cx">
</span><span class="cx"> if (isHTMLInputElement(node))
</span><span class="cx"> return toHTMLInputElement(node)->value();
</span><span class="cx">
</span><del>- // If the node can be turned into an AX object, we can use standard name computation rules.
- // If however, the node cannot (because there's no renderer e.g.) fallback to using the basic text underneath.
- AccessibilityObject* axObject = node->document().axObjectCache()->getOrCreate(node);
</del><span class="cx"> String text;
</span><del>- if (axObject)
- text = axObject->textUnderElement(AccessibilityTextUnderElementMode(AccessibilityTextUnderElementMode::TextUnderElementModeSkipIgnoredChildren, true));
- else
</del><ins>+ if (axObject) {
+ if (axObject->accessibleNameDerivesFromContent())
+ text = axObject->textUnderElement(AccessibilityTextUnderElementMode(AccessibilityTextUnderElementMode::TextUnderElementModeIncludeNameFromContentsChildren, true));
+ } else
</ins><span class="cx"> text = element->innerText();
</span><del>-
</del><ins>+
</ins><span class="cx"> if (!text.isEmpty())
</span><span class="cx"> return text;
</span><span class="cx">
</span><span class="lines">@@ -1867,12 +1888,8 @@
</span><span class="cx"> {
</span><span class="cx"> StringBuilder builder;
</span><span class="cx"> unsigned size = elements.size();
</span><del>- for (unsigned i = 0; i < size; ++i) {
- if (i)
- builder.append(' ');
-
- builder.append(accessibleNameForNode(elements[i]));
- }
</del><ins>+ for (unsigned i = 0; i < size; ++i)
+ appendNameToStringBuilder(builder, accessibleNameForNode(elements[i]));
</ins><span class="cx"> return builder.toString();
</span><span class="cx"> }
</span><span class="cx">
</span></span></pre></div>
<a id="releasesWebKitGTKwebkit26SourceWebCoreaccessibilityAccessibilityObjectcpp"></a>
<div class="modfile"><h4>Modified: releases/WebKitGTK/webkit-2.6/Source/WebCore/accessibility/AccessibilityObject.cpp (174445 => 174446)</h4>
<pre class="diff"><span>
<span class="info">--- releases/WebKitGTK/webkit-2.6/Source/WebCore/accessibility/AccessibilityObject.cpp        2014-10-08 13:11:20 UTC (rev 174445)
+++ releases/WebKitGTK/webkit-2.6/Source/WebCore/accessibility/AccessibilityObject.cpp        2014-10-08 13:16:35 UTC (rev 174446)
</span><span class="lines">@@ -287,7 +287,71 @@
</span><span class="cx"> || accessibilityDescription().contains(*text, false)
</span><span class="cx"> || stringValue().contains(*text, false);
</span><span class="cx"> }
</span><ins>+
+// ARIA marks elements as having their accessible name derive from either their contents, or their author provide name.
+bool AccessibilityObject::accessibleNameDerivesFromContent() const
+{
+ // First check for objects specifically identified by ARIA.
+ switch (ariaRoleAttribute()) {
+ case ApplicationAlertRole:
+ case ApplicationAlertDialogRole:
+ case ApplicationDialogRole:
+ case ApplicationLogRole:
+ case ApplicationMarqueeRole:
+ case ApplicationStatusRole:
+ case ApplicationTimerRole:
+ case ComboBoxRole:
+ case DefinitionRole:
+ case DocumentRole:
+ case DocumentArticleRole:
+ case DocumentMathRole:
+ case DocumentNoteRole:
+ case DocumentRegionRole:
+ case FormRole:
+ case GridRole:
+ case GroupRole:
+ case ImageRole:
+ case ListRole:
+ case ListBoxRole:
+ case LandmarkApplicationRole:
+ case LandmarkBannerRole:
+ case LandmarkComplementaryRole:
+ case LandmarkContentInfoRole:
+ case LandmarkNavigationRole:
+ case LandmarkMainRole:
+ case LandmarkSearchRole:
+ case MenuRole:
+ case MenuBarRole:
+ case ProgressIndicatorRole:
+ case RadioGroupRole:
+ case ScrollBarRole:
+ case SliderRole:
+ case SpinButtonRole:
+ case SplitterRole:
+ case TableRole:
+ case TabListRole:
+ case TabPanelRole:
+ case TextAreaRole:
+ case TextFieldRole:
+ case ToolbarRole:
+ case TreeGridRole:
+ case TreeRole:
+ return false;
+ default:
+ break;
+ }
</ins><span class="cx">
</span><ins>+ // Now check for generically derived elements now that we know the element does not match a specific ARIA role.
+ switch (roleValue()) {
+ case SliderRole:
+ return false;
+ default:
+ break;
+ }
+
+ return true;
+}
+
</ins><span class="cx"> String AccessibilityObject::computedLabel()
</span><span class="cx"> {
</span><span class="cx"> // This method is being called by WebKit inspector, which may happen at any time, so we need to update our backing store now.
</span><span class="lines">@@ -1795,6 +1859,7 @@
</span><span class="cx"> { "combobox", ComboBoxRole },
</span><span class="cx"> { "definition", DefinitionRole },
</span><span class="cx"> { "document", DocumentRole },
</span><ins>+ { "form", FormRole },
</ins><span class="cx"> { "rowheader", RowHeaderRole },
</span><span class="cx"> { "group", GroupRole },
</span><span class="cx"> { "heading", HeadingRole },
</span></span></pre></div>
<a id="releasesWebKitGTKwebkit26SourceWebCoreaccessibilityAccessibilityObjecth"></a>
<div class="modfile"><h4>Modified: releases/WebKitGTK/webkit-2.6/Source/WebCore/accessibility/AccessibilityObject.h (174445 => 174446)</h4>
<pre class="diff"><span>
<span class="info">--- releases/WebKitGTK/webkit-2.6/Source/WebCore/accessibility/AccessibilityObject.h        2014-10-08 13:11:20 UTC (rev 174445)
+++ releases/WebKitGTK/webkit-2.6/Source/WebCore/accessibility/AccessibilityObject.h        2014-10-08 13:16:35 UTC (rev 174446)
</span><span class="lines">@@ -248,6 +248,7 @@
</span><span class="cx"> enum ChildrenInclusion {
</span><span class="cx"> TextUnderElementModeSkipIgnoredChildren,
</span><span class="cx"> TextUnderElementModeIncludeAllChildren,
</span><ins>+ TextUnderElementModeIncludeNameFromContentsChildren, // This corresponds to ARIA concept: nameFrom
</ins><span class="cx"> };
</span><span class="cx">
</span><span class="cx"> ChildrenInclusion childrenInclusion;
</span><span class="lines">@@ -667,6 +668,7 @@
</span><span class="cx"> virtual String ariaLabeledByAttribute() const { return String(); }
</span><span class="cx"> virtual String ariaDescribedByAttribute() const { return String(); }
</span><span class="cx"> const AtomicString& placeholderValue() const;
</span><ins>+ bool accessibleNameDerivesFromContent() const;
</ins><span class="cx">
</span><span class="cx"> // Abbreviations
</span><span class="cx"> virtual String expandedTextValue() const { return String(); }
</span></span></pre>
</div>
</div>
</body>
</html>