underline and hiliteColor somewhat work now
authorAryeh Gregor <AryehGregor+gitcommit@gmail.com>
Mon, 21 Mar 2011 15:18:03 -0600
changeset 23 a6e401031af5
parent 22 a88df2f75682
child 24 dfe1df743d5c
underline and hiliteColor somewhat work now

Still needs carefuly thought and testing, especially hiliteColor (since
it does something different on blocks and text).
autoimplementation.html
editcommands.html
implementation.js
source.html
--- a/autoimplementation.html	Mon Mar 21 14:27:53 2011 -0600
+++ b/autoimplementation.html	Mon Mar 21 15:18:03 2011 -0600
@@ -30,7 +30,9 @@
 	<li><a href=#bold>bold</a>
 	<li><a href=#fontname>fontname</a>
 	<li><a href=#forecolor>forecolor</a>
+	<li><a href=#hilitecolor>hilitecolor</a>
 	<li><a href=#italic>italic</a>
+	<li><a href=#underline>underline</a>
 </ul>
 
 <div id=bold>
@@ -39,7 +41,7 @@
 <table border=1><tr><th>Input <th>Spec <th>Browser <th>Same?</table>
 
 <p><label>Enter new test here: <input></label>
-<button onclick="addTest('bold', document.querySelector('input').value)">Add test</button>
+<button onclick="addTest('bold', document.querySelector('#bold input').value)">Add test</button>
 </div>
 
 <div id=fontname>
@@ -50,7 +52,7 @@
 <table border=1><tr><th>Input <th>Spec <th>Browser <th>Same?</table>
 
 <p><label>Enter new test here: <input></label>
-<button onclick="addTest('bold', document.querySelector('input').value)">Add test</button>
+<button onclick="addTest('bold', document.querySelector('#fontname input').value)">Add test</button>
 </div>
 
 <div id=forecolor>
@@ -61,7 +63,18 @@
 <table border=1><tr><th>Input <th>Spec <th>Browser <th>Same?</table>
 
 <p><label>Enter new test here: <input></label>
-<button onclick="addTest('forecolor', document.querySelector('input').value)">Add test</button>
+<button onclick="addTest('forecolor', document.querySelector('#forecolor input').value)">Add test</button>
+</div>
+
+<div id=hilitecolor>
+<h1>hilitecolor</h1>
+
+<p>Tests set the color to "#FF8888".
+
+<table border=1><tr><th>Input <th>Spec <th>Browser <th>Same?</table>
+
+<p><label>Enter new test here: <input></label>
+<button onclick="addTest('hilitecolor', document.querySelector('#hilitecolor input').value)">Add test</button>
 </div>
 
 <div id=italic>
@@ -70,11 +83,29 @@
 <table border=1><tr><th>Input <th>Spec <th>Browser <th>Same?</table>
 
 <p><label>Enter new test here: <input></label>
-<button onclick="addTest('italic', document.querySelector('input').value)">Add test</button>
+<button onclick="addTest('italic', document.querySelector('#italic input').value)">Add test</button>
+</div>
+
+<div id=underline>
+<h1>underline</h1>
+
+<table border=1><tr><th>Input <th>Spec <th>Browser <th>Same?</table>
+
+<p><label>Enter new test here: <input></label>
+<button onclick="addTest('underline', document.querySelector('#underline input').value)">Add test</button>
 </div>
 
 <script src=implementation.js></script>
 <script>
+var values = {
+	bold: null,
+	fontname: "serif",
+	forecolor: "#FF0000",
+	hilitecolor: "#FF8888",
+	italic: null,
+	underline: null,
+};
+
 var tests = {
 	bold: [
 		'foo[bar]baz',
@@ -86,6 +117,8 @@
 		'foo[<b>bar</b>]baz',
 		'foo[<b>bar]</b>baz',
 		'foo<b>[bar</b>]baz',
+		'foo<span style="font-weight: normal"><b>{bar}</b></span>baz',
+		'foo{<b></b>}baz',
 		'foo<strong>[bar]</strong>baz',
 		'foo[<strong>bar</strong>]baz',
 		'foo[<strong>bar]</strong>baz',
@@ -198,6 +231,16 @@
 		'foo<span id=purple>ba[r</span>ba]z',
 		'<span style="color: rgb(255, 0, 0)">foo<span id=purple>b[a]r</span>baz</span>',
 	],
+	hilitecolor: [
+		'foo[bar]baz',
+		'foo]bar[baz',
+		'{<p><p> <p>Foo</p>}',
+		'foo[bar<i>baz]qoz</i>quz',
+		'<p style="background-color: rgb(255, 136, 136)">foo[bar]baz</p>',
+		'<p style="background-color: #ff8888">foo[bar]baz</p>',
+		'<p style="background-color: aqua">foo[bar]baz</p>',
+		'{<p style="background-color: aqua">foo</p><p>bar</p>}',
+	],
 	italic: [
 		'foo[bar]baz',
 		'foo]bar[baz',
@@ -250,6 +293,16 @@
 		'foo [bar <i>baz] qoz</i> quz sic',
 		'foo bar <i>baz [qoz</i> quz] sic',
 	],
+	underline: [
+		'foo[bar]baz',
+		'foo]bar[baz',
+		'{<p><p> <p>Foo</p>}',
+		'foo[bar<b>baz]qoz</b>quz',
+		'foo<u>[bar]</u>baz',
+		'foo<span style="text-decoration: underline">[bar]</span>baz',
+		'<u>foo[bar]baz</u>',
+		'<u>foo[b<span style="color:red">ar]ba</span>z</u>',
+	],
 };
 
 for (testCat in tests) {
@@ -296,12 +349,7 @@
 }
 
 function doSpecCell(tr, test, command) {
-	var value = {
-		bold: null,
-		fontname: "serif",
-		forecolor: "#FF0000",
-		italic: null,
-	}[command];
+	var value = values[command];
 
 	var specCell = document.createElement("td");
 	specCell.innerHTML = "<div></div><div></div>";
@@ -324,18 +372,8 @@
 }
 
 function doBrowserCell(tr, test, command) {
-	var value = {
-		bold: null,
-		fontname: "serif",
-		forecolor: "#FF0000",
-		italic: null,
-	}[command];
-	var styleWithCss = {
-		bold: false,
-		fontname: true,
-		forecolor: true,
-		italic: false,
-	}[command];
+	var value = values[command];
+	var styleWithCss = command != "bold" && command != "italic" && command != "underline";
 
 	var browserCell = document.createElement("td");
 	browserCell.innerHTML = "<div></div><div></div>";
--- a/editcommands.html	Mon Mar 21 14:27:53 2011 -0600
+++ b/editcommands.html	Mon Mar 21 15:18:03 2011 -0600
@@ -181,10 +181,11 @@
 <a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#concept-boundary-point-node title=concept-boundary-point-node>node</a>, it is a <a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#text><code class=external data-anolis-spec=domcore>Text</code></a> node, and its <a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#concept-node-length title=concept-node-length>length</a> is different from the
 <a href=http://html5.org/specs/dom-range.html#range><code class=external data-anolis-spec=domrange>Range</code></a>'s <a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#concept-range-start title=concept-range-start>start</a> <a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#concept-boundary-point-offset title=concept-boundary-point-offset>offset</a>; or it is the <a href=http://html5.org/specs/dom-range.html#range><code class=external data-anolis-spec=domrange>Range</code></a>'s <a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#concept-range-end title=concept-range-end>end</a>
 <a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#concept-boundary-point-node title=concept-boundary-point-node>node</a>, it is a <a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#text><code class=external data-anolis-spec=domcore>Text</code></a> node, and the <a href=http://html5.org/specs/dom-range.html#range><code class=external data-anolis-spec=domrange>Range</code></a>'s <a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#concept-range-end title=concept-range-end>end</a>
-<a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#concept-boundary-point-offset title=concept-boundary-point-offset>offset</a> is not 0.
+<a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#concept-boundary-point-offset title=concept-boundary-point-offset>offset</a> is not 0; or it has at least one <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-child title=concept-tree-child>child</a>, and all its
+<a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-child title=concept-tree-child>children</a> are <a href=#effectively-contained>effectively contained</a> in the <a href=http://html5.org/specs/dom-range.html#range><code class=external data-anolis-spec=domrange>Range</code></a>.
 
-<p class=note>A node is <a href=#effectively-contained>effectively contained</a> in a range if and
-only if it would be <a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#contained>contained</a> after the range is <a href=#decompose title=decompose>decomposed</a>.
+<p class=XXX>A node is supposed to be <a href=#effectively-contained>effectively contained</a> in a
+range if and only if it would be <a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#contained>contained</a> after the range is <a href=#decompose title=decompose>decomposed</a>.  Is this actually right?
 
 <p>The <dfn id=active-range>active range</dfn> of a <a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#document><code class=external data-anolis-spec=domcore>Document</code></a> is the value returned by the
 following algorithm:
@@ -886,44 +887,6 @@
 <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#ascii-case-insensitive>ASCII case-insensitive</a> manner.
 
 <dl>
-<dt><code title=""><dfn id=command-backcolor title=command-backColor>backColor</dfn></code>
-
-<dd><p><strong>Action</strong>: If <var title="">value</var> is not a valid CSS color,
-the user agent must do nothing and abort these steps.  Otherwise, it must
-<a href=#decompose>decompose</a> the <a href=http://html5.org/specs/dom-range.html#range><code class=external data-anolis-spec=domrange>Range</code></a>, then <a href=#style>style</a> each returned
-<a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#node><code class=external data-anolis-spec=domcore>Node</code></a> with <var title="">property</var> equal to "background-color" and <var title="">new
-value</var> equal to <var title="">value</var>.
-<!-- Firefox documentation says it normally sets the background color of the
-document, but I can't get it to work at all in brief testing in 4b11.  (It says
-it behaves differently in styleWithCss mode.)  Opera 11 appears to set the
-background color of the nearest block container of the cursor, or something.
-IE 9 RC and Chrome 10 behave as I'd expect, namely, they set the background of
-the selection, just like all the other styling features.  I go with IE/WebKit.
-
-Invalid colors are probably the same craziness as with foreColor.
-
-Chrome 10 dev actually sets background, not background-color, so it resets all
-the other background stuff.  I go with IE 9 RC and Opera 11, which only set
-background-color. -->
-
-<p class=XXX>Firefox and Opera use backColor to set the background color of the
-whole document.  The hiliteColor command can then be used to set the background
-of the selection (supported in all my test browsers except IE).  This
-terminology is inconsistent with foreColor, but the model I've specced leaves
-no way to change the document's overall background color.  I'm not sure how
-important this is, but maybe I should switch, since hiliteColor is more
-interoperably implemented than backColor.
-
-<dd><p><strong>State</strong>: Always false.
-
-<dd><p><strong>Value</strong>: The <a href=#effective-style>effective style</a> for
-"background-color" on . . .
-<!-- Chrome 10 returns rgba(0, 0, 0, 0) if there's no background defined
-anywhere.  Opera 11 returns rgb(255, 255, 255) as I'd like.  Firefox 4b11 just
-throws an exception for some reason.  IE 9 RC seems to return the number 0
-across the board, as with foreColor. -->
-
-
 <dt><code title=""><dfn id=command-bold title=command-bold>bold</dfn></code>
 
 <dd><p><strong>Action</strong>: <a href=#decompose>Decompose</a> the <a href=http://html5.org/specs/dom-range.html#range><code class=external data-anolis-spec=domrange>Range</code></a>.  If the
@@ -932,9 +895,9 @@
 value</var> "normal".  Otherwise, <a href=#style>style</a> them with <var title="">new
 value</var> "bold".
 
-<dd><p><strong>State</strong>: True if every <a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#node><code class=external data-anolis-spec=domcore>Node</code></a> that is <a href=#effectively-contained>effectively
-contained</a> in the <a href=http://html5.org/specs/dom-range.html#range><code class=external data-anolis-spec=domrange>Range</code></a> has <a href=#effective-style>effective style</a> either null
-or at least 700 for font-weight.  Otherwise false.
+<dd><p><strong>State</strong>: True if every <a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#text><code class=external data-anolis-spec=domcore>Text</code></a> node that is
+<a href=#effectively-contained>effectively contained</a> in the <a href=http://html5.org/specs/dom-range.html#range><code class=external data-anolis-spec=domrange>Range</code></a> has <a href=#effective-style>effective
+style</a> either null or at least 700 for font-weight.  Otherwise false.
 
 <dd><p><strong>Value</strong>: Always the empty string.
 <!-- We have lots of options here (and presumably for all the others where
@@ -1116,6 +1079,20 @@
 matches the other browsers. -->
 
 
+<dt><code title=""><dfn id=command-hilitecolor title=command-hiliteColor>hiliteColor</dfn></code>
+
+<dd><p><strong>Action</strong>: If <var title="">value</var> is not a valid CSS color,
+do nothing and abort these steps.  Otherwise, <a href=#decompose>decompose</a> the
+<a href=http://html5.org/specs/dom-range.html#range><code class=external data-anolis-spec=domrange>Range</code></a>, then <a href=#style>style</a> each returned <a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#node><code class=external data-anolis-spec=domcore>Node</code></a> with
+<var title="">property</var> equal to "background-color" and <var title="">new value</var> equal
+to <var title="">value</var>.
+
+<dd><p><strong>State</strong>: Always false.
+
+<dd><p><strong>Value</strong>: The <a href=#effective-style>effective style</a> for
+"background-color" on . . .
+
+
 <dt><code title=""><dfn id=command-insertimage title=command-insertimage>insertImage</dfn></code>
 
 <dd><p><strong>Action</strong>: The user agent must run the following steps:
@@ -1166,9 +1143,10 @@
 value</var> "normal".  Otherwise, <a href=#style>style</a> them with <var title="">new
 value</var> "italic".
 
-<dd><p><strong>State</strong>: True if every <a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#node><code class=external data-anolis-spec=domcore>Node</code></a> that is <a href=#effectively-contained>effectively
-contained</a> in the <a href=http://html5.org/specs/dom-range.html#range><code class=external data-anolis-spec=domrange>Range</code></a> has <a href=#effective-style>effective style</a> either null,
-"italic", or "oblique" for font-style.  Otherwise false.
+<dd><p><strong>State</strong>: True if every <a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#text><code class=external data-anolis-spec=domcore>Text</code></a> node that is
+<a href=#effectively-contained>effectively contained</a> in the <a href=http://html5.org/specs/dom-range.html#range><code class=external data-anolis-spec=domrange>Range</code></a> has <a href=#effective-style>effective
+style</a> either null, "italic", or "oblique" for font-style.  Otherwise
+false.
 
 <dd><p><strong>Value</strong>: Always the empty string.
 
@@ -1181,9 +1159,41 @@
 value</var> "none".  Otherwise, <a href=#style>style</a> them with <var title="">new
 value</var> "underline".
 
-<dd><p><strong>State</strong>: True if every <a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#node><code class=external data-anolis-spec=domcore>Node</code></a> that is <a href=#effectively-contained>effectively
-contained</a> in the <a href=http://html5.org/specs/dom-range.html#range><code class=external data-anolis-spec=domrange>Range</code></a> has <a href=#effective-style>effective style</a> either null
-or "underline" for text-decoration.  Otherwise false.
+<div class=XXX>
+<p>This can change the color of underlines if it pushes them down.
+The right way to fix this is probably to require text-decoration-color&nbsp;&ndash;
+granted it won't work in old (or current) browsers, but the only other way
+would be to turn something like
+
+</p><xmp><u><span style="color: red" id=x>
+foo
+bar
+baz
+</span></u></xmp>
+
+<p>into something like
+
+</p><xmp><span style="color: red" id=x><u style="color: black"><span style="color:
+red">
+foo
+</span></u>bar<u style="color: black"><span style="color: red">
+baz
+</span></u></span></xmp>
+
+<p>which is totally not worth it for a corner case.  Instead we could do
+
+</p><xmp><span style="color: red" id=x><u style="text-decoration-color: black">
+foo
+</u>bar<u style="text-decoration-color: black">
+baz
+</u></span></xmp>
+
+<p>although that's not a whole lot better . . .
+</div>
+
+<dd><p><strong>State</strong>: True if every <a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#text><code class=external data-anolis-spec=domcore>Text</code></a> node that is
+<a href=#effectively-contained>effectively contained</a> in the <a href=http://html5.org/specs/dom-range.html#range><code class=external data-anolis-spec=domrange>Range</code></a> has <a href=#effective-style>effective
+style</a> either null or "underline" for text-decoration.  Otherwise false.
 
 <dd><p><strong>Value</strong>: Always the empty string.
 </dl>
@@ -1249,8 +1259,8 @@
   <li>Ian Hickson, for overseeing it
   <li>Julie Parent, Ojan Vafai, Alex Russel, and Eric Seidel for their <a href=http://lists.whatwg.org/htdig.cgi/whatwg-whatwg.org/2009-December/024627.html>research</a>
   on how browsers and other rich text editors behave in many common scenarios
-  <li>Ryosuke Niwa, Julie Parent, and Roland Steiner for their feedback on
-  drafts of this document
+  <li>Ehsan Akhgari, Ryosuke Niwa, Julie Parent, and Roland Steiner for their
+  feedback on drafts of this document
 </ul>
 
 <script src=http://www.whatwg.org/specs/web-apps/current-work/dfn.js></script>
--- a/implementation.js	Mon Mar 21 14:27:53 2011 -0600
+++ b/implementation.js	Mon Mar 21 15:18:03 2011 -0600
@@ -192,7 +192,8 @@
  * "A Node is effectively contained in a Range if either it is contained in the
  * Range; or it is the Range's start node, it is a Text node, and its length is
  * different from the Range's start offset; or it is the Range's end node, it
- * is a Text node, and the Range's end offset is not 0."
+ * is a Text node, and the Range's end offset is not 0; or it has at least one
+ * child, and all its children are effectively contained in the Range."
  */
 function isEffectivelyContained(node, range) {
 	if (isContained(node, range)) {
@@ -208,6 +209,14 @@
 	&& range.endOffset != 0) {
 		return true;
 	}
+	if (node.childNodes.length != 0) {
+		for (var i = 0; i < node.childNodes.length; i++) {
+			if (!isEffectivelyContained(node.childNodes[i], range)) {
+				return false;
+			}
+		}
+		return true;
+	}
 	return false;
 }
 
@@ -1075,6 +1084,19 @@
 		}
 		break;
 
+		case "hilitecolor":
+		// "If value is not a valid CSS color, do nothing and abort these
+		// steps. Otherwise, decompose the Range, then style each returned Node
+		// with property equal to "background-color" and new value equal to
+		// value."
+		//
+		// Ignore validation for now.
+		var nodeList = decomposeRange(range);
+		for (var i = 0; i < nodeList.length; i++) {
+			styleNode(nodeList[i], "backgroundColor", value);
+		}
+		break;
+
 		case "italic":
 		// "Decompose the Range. If the state of the Range for this command is
 		// then true, style each returned Node with property "font-style" and
@@ -1116,22 +1138,32 @@
 
 function getState(commandId, range) {
 	if (commandId != "bold"
-	&& commandId != "italic") {
+	&& commandId != "italic"
+	&& commandId != "underline") {
 		return false;
 	}
 
+	// XXX: This algorithm for getting all effectively contained nodes might be
+	// wrong . . .
 	var node = range.startContainer;
+	while (node.parentNode && node.parentNode.firstChild == node) {
+		node = node.parentNode;
+	}
 	var stop = nextNode(range.endContainer);
 
-	for (node = range.startContainer; node && node != nextNodeDescendants(range.endContainer); node = nextNode(node)) {
+	for (; node && node != nextNodeDescendants(range.endContainer); node = nextNode(node)) {
 		if (!isEffectivelyContained(node, range)) {
 			continue;
 		}
 
+		if (node.nodeType != Node.TEXT_NODE) {
+			continue;
+		}
+
 		if (commandId == "bold") {
-			// "True if every Node that is effectively contained in the Range
-			// has effective style either null or at least 700 for font-weight.
-			// Otherwise false."
+			// "True if every Text node that is effectively contained in the
+			// Range has effective style either null or at least 700 for
+			// font-weight. Otherwise false."
 			var weight = getEffectiveStyle(node, "fontWeight");
 			if (weight !== null
 			&& weight !== "bold"
@@ -1141,9 +1173,9 @@
 				return false;
 			}
 		} else if (commandId == "italic") {
-			// "True if every Node that is effectively contained in the Range
-			// has effective style either null, "italic", or "oblique" for
-			// font-style. Otherwise false."
+			// "True if every Text node that is effectively contained in the
+			// Range has effective style either null, "italic", or "oblique"
+			// for font-style. Otherwise false."
 			var style = getEffectiveStyle(node, "fontStyle");
 			if (style !== null
 			&& style !== "italic"
@@ -1151,8 +1183,8 @@
 				return false;
 			}
 		} else if (commandId == "underline") {
-			// "True if every Node that is effectively contained in the Range
-			// has effective style either null or "underline" for
+			// "True if every Text node that is effectively contained in the
+			// Range has effective style either null or "underline" for
 			// text-decoration. Otherwise false."
 			var decoration = getEffectiveStyle(node, "textDecoration");
 			if (decoration !== null && decoration !== "underline") {
--- a/source.html	Mon Mar 21 14:27:53 2011 -0600
+++ b/source.html	Mon Mar 21 15:18:03 2011 -0600
@@ -170,11 +170,12 @@
 [[bpnode]], it is a [[text]] node, and its [[nodelength]] is different from the
 [[range]]'s [[rangestart]] [[bpoffset]]; or it is the [[range]]'s [[rangeend]]
 [[bpnode]], it is a [[text]] node, and the [[range]]'s [[rangeend]]
-[[bpoffset]] is not 0.
+[[bpoffset]] is not 0; or it has at least one [[child]], and all its
+[[children]] are <span>effectively contained</span> in the [[range]].
 
-<p class=note>A node is <span>effectively contained</span> in a range if and
-only if it would be [[contained]] after the range is <span
-title=decompose>decomposed</span>.
+<p class=XXX>A node is supposed to be <span>effectively contained</span> in a
+range if and only if it would be [[contained]] after the range is <span
+title=decompose>decomposed</span>.  Is this actually right?
 
 <p>The <dfn>active range</dfn> of a [[document]] is the value returned by the
 following algorithm:
@@ -888,44 +889,6 @@
 <span data-anolis-spec=domcore>ASCII case-insensitive</span> manner.
 
 <dl>
-<dt><code title><dfn title=command-backColor>backColor</dfn></code>
-
-<dd><p><strong>Action</strong>: If <var>value</var> is not a valid CSS color,
-the user agent must do nothing and abort these steps.  Otherwise, it must
-<span>decompose</span> the [[range]], then <span>style</span> each returned
-[[node]] with <var>property</var> equal to "background-color" and <var>new
-value</var> equal to <var>value</var>.
-<!-- Firefox documentation says it normally sets the background color of the
-document, but I can't get it to work at all in brief testing in 4b11.  (It says
-it behaves differently in styleWithCss mode.)  Opera 11 appears to set the
-background color of the nearest block container of the cursor, or something.
-IE 9 RC and Chrome 10 behave as I'd expect, namely, they set the background of
-the selection, just like all the other styling features.  I go with IE/WebKit.
-
-Invalid colors are probably the same craziness as with foreColor.
-
-Chrome 10 dev actually sets background, not background-color, so it resets all
-the other background stuff.  I go with IE 9 RC and Opera 11, which only set
-background-color. -->
-
-<p class=XXX>Firefox and Opera use backColor to set the background color of the
-whole document.  The hiliteColor command can then be used to set the background
-of the selection (supported in all my test browsers except IE).  This
-terminology is inconsistent with foreColor, but the model I've specced leaves
-no way to change the document's overall background color.  I'm not sure how
-important this is, but maybe I should switch, since hiliteColor is more
-interoperably implemented than backColor.
-
-<dd><p><strong>State</strong>: Always false.
-
-<dd><p><strong>Value</strong>: The <span>effective style</span> for
-"background-color" on . . .
-<!-- Chrome 10 returns rgba(0, 0, 0, 0) if there's no background defined
-anywhere.  Opera 11 returns rgb(255, 255, 255) as I'd like.  Firefox 4b11 just
-throws an exception for some reason.  IE 9 RC seems to return the number 0
-across the board, as with foreColor. -->
-
-
 <dt><code title><dfn title=command-bold>bold</dfn></code>
 
 <dd><p><strong>Action</strong>: <span>Decompose</span> the [[range]].  If the
@@ -934,9 +897,9 @@
 value</var> "normal".  Otherwise, <span>style</span> them with <var>new
 value</var> "bold".
 
-<dd><p><strong>State</strong>: True if every [[node]] that is <span>effectively
-contained</span> in the [[range]] has <span>effective style</span> either null
-or at least 700 for font-weight.  Otherwise false.
+<dd><p><strong>State</strong>: True if every [[text]] node that is
+<span>effectively contained</span> in the [[range]] has <span>effective
+style</span> either null or at least 700 for font-weight.  Otherwise false.
 
 <dd><p><strong>Value</strong>: Always the empty string.
 <!-- We have lots of options here (and presumably for all the others where
@@ -1122,6 +1085,20 @@
 matches the other browsers. -->
 
 
+<dt><code title><dfn title=command-hiliteColor>hiliteColor</dfn></code>
+
+<dd><p><strong>Action</strong>: If <var>value</var> is not a valid CSS color,
+do nothing and abort these steps.  Otherwise, <span>decompose</span> the
+[[range]], then <span>style</span> each returned [[node]] with
+<var>property</var> equal to "background-color" and <var>new value</var> equal
+to <var>value</var>.
+
+<dd><p><strong>State</strong>: Always false.
+
+<dd><p><strong>Value</strong>: The <span>effective style</span> for
+"background-color" on . . .
+
+
 <dt><code title><dfn title=command-insertimage>insertImage</dfn></code>
 
 <dd><p><strong>Action</strong>: The user agent must run the following steps:
@@ -1178,9 +1155,10 @@
 value</var> "normal".  Otherwise, <span>style</span> them with <var>new
 value</var> "italic".
 
-<dd><p><strong>State</strong>: True if every [[node]] that is <span>effectively
-contained</span> in the [[range]] has <span>effective style</span> either null,
-"italic", or "oblique" for font-style.  Otherwise false.
+<dd><p><strong>State</strong>: True if every [[text]] node that is
+<span>effectively contained</span> in the [[range]] has <span>effective
+style</span> either null, "italic", or "oblique" for font-style.  Otherwise
+false.
 
 <dd><p><strong>Value</strong>: Always the empty string.
 
@@ -1193,9 +1171,41 @@
 value</var> "none".  Otherwise, <span>style</span> them with <var>new
 value</var> "underline".
 
-<dd><p><strong>State</strong>: True if every [[node]] that is <span>effectively
-contained</span> in the [[range]] has <span>effective style</span> either null
-or "underline" for text-decoration.  Otherwise false.
+<div class=XXX>
+<p>This can change the color of underlines if it pushes them down.
+The right way to fix this is probably to require text-decoration-color&nbsp;&ndash;
+granted it won't work in old (or current) browsers, but the only other way
+would be to turn something like
+
+<xmp><u><span style="color: red" id=x>
+foo
+bar
+baz
+</span></u></xmp>
+
+<p>into something like
+
+<xmp><span style="color: red" id=x><u style="color: black"><span style="color:
+red">
+foo
+</span></u>bar<u style="color: black"><span style="color: red">
+baz
+</span></u></span></xmp>
+
+<p>which is totally not worth it for a corner case.  Instead we could do
+
+<xmp><span style="color: red" id=x><u style="text-decoration-color: black">
+foo
+</u>bar<u style="text-decoration-color: black">
+baz
+</u></span></xmp>
+
+<p>although that's not a whole lot better . . .
+</div>
+
+<dd><p><strong>State</strong>: True if every [[text]] node that is
+<span>effectively contained</span> in the [[range]] has <span>effective
+style</span> either null or "underline" for text-decoration.  Otherwise false.
 
 <dd><p><strong>Value</strong>: Always the empty string.
 </dl>
@@ -1262,8 +1272,8 @@
   <li>Julie Parent, Ojan Vafai, Alex Russel, and Eric Seidel for their <a
   href=http://lists.whatwg.org/htdig.cgi/whatwg-whatwg.org/2009-December/024627.html>research</a>
   on how browsers and other rich text editors behave in many common scenarios
-  <li>Ryosuke Niwa, Julie Parent, and Roland Steiner for their feedback on
-  drafts of this document
+  <li>Ehsan Akhgari, Ryosuke Niwa, Julie Parent, and Roland Steiner for their
+  feedback on drafts of this document
 </ul>
 
 <script src=http://www.whatwg.org/specs/web-apps/current-work/dfn.js></script>