--- a/editcommands.html Tue Jul 05 15:42:44 2011 -0600
+++ b/editcommands.html Tue Jul 05 15:56:37 2011 -0600
@@ -890,144 +890,6 @@
(<var title="">node</var>, <var title="">offset</var>), true otherwise.
</ol>
-<p>To <dfn id=split-the-parent>split the parent</dfn> of a list <var title="">node list</var> of consecutive
-<a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-sibling title=concept-tree-sibling>sibling</a> <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-node title=concept-node>nodes</a>:
-
-<p class=XXX>Pretty much any time we call this algorithm, it can cause trouble
-if the parent had styles, classes, etc. There's not going to be any general
-way to handle this, but we should at least try to handle the special case of
-inline styles, because Firefox does actually add them to arbitrary elements.
-Also, when splitting out of an inline parent, it might be good to wrap all the
-inline descendants in a clone of the former parent.
-
-<ol>
- <li>Let <var title="">original parent</var> be the <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a> of the first member of
- <var title="">node list</var>.
-
- <li>If <var title="">original parent</var> is not <a href=#editable>editable</a> or its
- <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a> is null, do nothing and abort these steps.
-
- <li>If the first <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> of <var title="">original parent</var> is in <var title="">node
- list</var>, <a href=#remove-extraneous-line-breaks-before>remove extraneous line breaks before</a> <var title="">original
- parent</var>.
-
- <li>If the first <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> of <var title="">original parent</var> is in <var title="">node
- list</var>, and <var title="">original parent</var> <a href=#follows-a-line-break>follows a line break</a>,
- set <var title="">follows line break</var> to true. Otherwise, set <var title="">follows line
- break</var> to false.
-
- <li>If the last <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> of <var title="">original parent</var> is in <var title="">node
- list</var>, and <var title="">original parent</var> <a href=#precedes-a-line-break>precedes a line
- break</a>, set <var title="">precedes line break</var> to true. Otherwise, set
- <var title="">precedes line break</var> to false.
-
- <li>If the first <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> of <var title="">original parent</var> is not in <var title="">node
- list</var>, but its last <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> is:
-
- <div class=XXX>
- <p>We insert things after the parent. This is bad, because it will cause
- them to become part of any ranges that immediately follow. For instance, if
- we're hitting "bar" in
-
- </p><xmp><div><p>foo<p>bar</div>{<p>baz}</xmp>
-
- <p>it becomes
-
- </p><xmp><div><p>foo</div>{<p>bar<p>baz}</xmp>
-
- <p>instead of
-
- </p><xmp><div><p>foo</div><p>bar{<p>baz}</xmp>
-
- <p>because of how range mutation rules work. This doesn't happen if we
- insert before. Probably this isn't important enough to try working around,
- though.
- </div>
-
- <ol>
- <li>For each <var title="">node</var> in <var title="">node list</var>, <em>in reverse
- order</em>, insert <var title="">node</var> into the <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a> of <var title="">original
- parent</var> immediately after <var title="">original parent</var>, <a href=#preserving-ranges>preserving
- ranges</a>.
-
- <li>If <var title="">precedes line break</var> is true, and the last member of
- <var title="">node list</var> does not <a href=#precedes-a-line-break title="precedes a line break">precede a
- line break</a>, call <code class=external data-anolis-spec=domcore title=dom-Document-createElement><a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#dom-document-createelement>createElement("br")</a></code> on the <a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#context-object>context object</a> and
- insert the result immediately after the last member of <var title="">node
- list</var>.
-
- <li><a href=#remove-extraneous-line-breaks-at-the-end-of>Remove extraneous line breaks at the end of</a> <var title="">original
- parent</var>.
-
- <li>Abort these steps.
- </ol>
-
- <li>If the first <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> of <var title="">original parent</var> is not in <var title="">node
- list</var>:
-
- <ol>
- <li>Let <var title="">cloned parent</var> be the result of calling <code class=external data-anolis-spec=domcore title=dom-Node-cloneNode><a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#dom-node-clonenode>cloneNode(false)</a></code>
- on <var title="">original parent</var>.
-
- <li>If <var title="">original parent</var> has an <code class=external data-anolis-spec=html title="the id attribute"><a href=http://www.whatwg.org/html/#the-id-attribute>id</a></code> attribute, unset it.
-
- <li>Insert <var title="">cloned parent</var> into the <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a> of <var title="">original
- parent</var> immediately before <var title="">original parent</var>.
-
- <li>While the <code class=external data-anolis-spec=domcore title=dom-Node-previousSibling><a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#dom-node-previoussibling>previousSibling</a></code> of the first member of <var title="">node
- list</var> is not null, append the first <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> of <var title="">original
- parent</var> as the last <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> of <var title="">cloned parent</var>,
- <a href=#preserving-ranges>preserving ranges</a>.
- </ol>
-
- <li>For each <var title="">node</var> in <var title="">node list</var>, insert <var title="">node</var>
- into the <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a> of <var title="">original parent</var> immediately before
- <var title="">original parent</var>, <a href=#preserving-ranges>preserving ranges</a>.
- <!-- Notice that a boundary point that was immediately before the element
- will now be immediately before its children, just because of the regular
- range mutation rules, without needing to worry about preserving ranges.
- Likewise for boundary points immediately after the element, if we wind up
- removing the element in the final step. Preserving ranges is only necessary
- for the sake of boundary points in the element or its descendants. -->
-
- <li>If <var title="">follows line break</var> is true, and the first member of
- <var title="">node list</var> does not <a href=#follows-a-line-break title="follows a line break">follow a
- line break</a>, call <code class=external data-anolis-spec=domcore title=dom-Document-createElement><a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#dom-document-createelement>createElement("br")</a></code> on the <a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#context-object>context object</a> and
- insert the result immediately before the first member of <var title="">node
- list</var>.
-
- <li>If the last member of <var title="">node list</var> is an <a href=#inline-node>inline node</a>
- other than a <code class=external data-anolis-spec=html title="the br element"><a href=http://www.whatwg.org/html/#the-br-element>br</a></code>, and the first <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> of <var title="">original parent</var> is
- a <code class=external data-anolis-spec=html title="the br element"><a href=http://www.whatwg.org/html/#the-br-element>br</a></code>, and <var title="">original parent</var> is not an <a href=#inline-node>inline node</a>,
- remove the first <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> of <var title="">original parent</var> from <var title="">original
- parent</var>.
-
- <li>If <var title="">original parent</var> has no <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>:
-
- <ol>
- <li>Remove <var title="">original parent</var> from its <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a>.
-
- <li>If <var title="">precedes line break</var> is true, and the last member of
- <var title="">node list</var> does not <a href=#precedes-a-line-break title="precedes a line break">precede a
- line break</a>, call <code class=external data-anolis-spec=domcore title=dom-Document-createElement><a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#dom-document-createelement>createElement("br")</a></code> on the <a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#context-object>context object</a> and
- insert the result immediately after the last member of <var title="">node
- list</var>.
- </ol>
-
- <li>Otherwise, <a href=#remove-extraneous-line-breaks-before>remove extraneous line breaks before</a>
- <var title="">original parent</var>.
-
- <li>If <var title="">node list</var>'s last member's <code class=external data-anolis-spec=domcore title=dom-Node-nextSibling><a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#dom-node-nextsibling>nextSibling</a></code> is null,
- but its <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a> is not null, <a href=#remove-extraneous-line-breaks-at-the-end-of>remove extraneous line breaks at the
- end of</a> <var title="">node list</var>'s last member's <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a>.
- <!-- The parent might be null if it's a br that we removed in the last step,
- in which case this step isn't necessary. -->
-</ol>
-
-<p>To remove a <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-node title=concept-node>node</a> <var title="">node</var> while <dfn id=preserving-its-descendants>preserving its
-descendants</dfn>, <a href=#split-the-parent>split the parent</a> of <var title="">node</var>'s
-<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>.
-
<h3 id=wrapping-a-list-of-nodes><span class=secno>6.2 </span>Wrapping a list of nodes</h3>
@@ -1553,7 +1415,11 @@
<ol>
<li>Let <var title="">children</var> be the <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> of <var title="">element</var>.
- <li>Remove <var title="">element</var>, <a href=#preserving-its-descendants>preserving its descendants</a>.
+ <li>For each <var title="">child</var> in <var title="">children</var>, insert
+ <var title="">child</var> into <var title="">element</var>'s <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a> immediately before
+ <var title="">element</var>, <a href=#preserving-ranges>preserving ranges</a>.
+
+ <li>Remove <var title="">element</var> from its <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a>.
<li>Return <var title="">children</var>.
</ol>
@@ -3140,6 +3006,144 @@
of <var title="">node</var>.
</ol>
+<p>To <dfn id=split-the-parent>split the parent</dfn> of a list <var title="">node list</var> of consecutive
+<a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-sibling title=concept-tree-sibling>sibling</a> <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-node title=concept-node>nodes</a>:
+
+<p class=XXX>Pretty much any time we call this algorithm, it can cause trouble
+if the parent had styles, classes, etc. There's not going to be any general
+way to handle this, but we should at least try to handle the special case of
+inline styles, because Firefox does actually add them to arbitrary elements.
+Also, when splitting out of an inline parent, it might be good to wrap all the
+inline descendants in a clone of the former parent.
+
+<ol>
+ <li>Let <var title="">original parent</var> be the <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a> of the first member of
+ <var title="">node list</var>.
+
+ <li>If <var title="">original parent</var> is not <a href=#editable>editable</a> or its
+ <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a> is null, do nothing and abort these steps.
+
+ <li>If the first <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> of <var title="">original parent</var> is in <var title="">node
+ list</var>, <a href=#remove-extraneous-line-breaks-before>remove extraneous line breaks before</a> <var title="">original
+ parent</var>.
+
+ <li>If the first <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> of <var title="">original parent</var> is in <var title="">node
+ list</var>, and <var title="">original parent</var> <a href=#follows-a-line-break>follows a line break</a>,
+ set <var title="">follows line break</var> to true. Otherwise, set <var title="">follows line
+ break</var> to false.
+
+ <li>If the last <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> of <var title="">original parent</var> is in <var title="">node
+ list</var>, and <var title="">original parent</var> <a href=#precedes-a-line-break>precedes a line
+ break</a>, set <var title="">precedes line break</var> to true. Otherwise, set
+ <var title="">precedes line break</var> to false.
+
+ <li>If the first <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> of <var title="">original parent</var> is not in <var title="">node
+ list</var>, but its last <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> is:
+
+ <div class=XXX>
+ <p>We insert things after the parent. This is bad, because it will cause
+ them to become part of any ranges that immediately follow. For instance, if
+ we're hitting "bar" in
+
+ </p><xmp><div><p>foo<p>bar</div>{<p>baz}</xmp>
+
+ <p>it becomes
+
+ </p><xmp><div><p>foo</div>{<p>bar<p>baz}</xmp>
+
+ <p>instead of
+
+ </p><xmp><div><p>foo</div><p>bar{<p>baz}</xmp>
+
+ <p>because of how range mutation rules work. This doesn't happen if we
+ insert before. Probably this isn't important enough to try working around,
+ though.
+ </div>
+
+ <ol>
+ <li>For each <var title="">node</var> in <var title="">node list</var>, <em>in reverse
+ order</em>, insert <var title="">node</var> into the <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a> of <var title="">original
+ parent</var> immediately after <var title="">original parent</var>, <a href=#preserving-ranges>preserving
+ ranges</a>.
+
+ <li>If <var title="">precedes line break</var> is true, and the last member of
+ <var title="">node list</var> does not <a href=#precedes-a-line-break title="precedes a line break">precede a
+ line break</a>, call <code class=external data-anolis-spec=domcore title=dom-Document-createElement><a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#dom-document-createelement>createElement("br")</a></code> on the <a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#context-object>context object</a> and
+ insert the result immediately after the last member of <var title="">node
+ list</var>.
+
+ <li><a href=#remove-extraneous-line-breaks-at-the-end-of>Remove extraneous line breaks at the end of</a> <var title="">original
+ parent</var>.
+
+ <li>Abort these steps.
+ </ol>
+
+ <li>If the first <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> of <var title="">original parent</var> is not in <var title="">node
+ list</var>:
+
+ <ol>
+ <li>Let <var title="">cloned parent</var> be the result of calling <code class=external data-anolis-spec=domcore title=dom-Node-cloneNode><a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#dom-node-clonenode>cloneNode(false)</a></code>
+ on <var title="">original parent</var>.
+
+ <li>If <var title="">original parent</var> has an <code class=external data-anolis-spec=html title="the id attribute"><a href=http://www.whatwg.org/html/#the-id-attribute>id</a></code> attribute, unset it.
+
+ <li>Insert <var title="">cloned parent</var> into the <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a> of <var title="">original
+ parent</var> immediately before <var title="">original parent</var>.
+
+ <li>While the <code class=external data-anolis-spec=domcore title=dom-Node-previousSibling><a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#dom-node-previoussibling>previousSibling</a></code> of the first member of <var title="">node
+ list</var> is not null, append the first <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> of <var title="">original
+ parent</var> as the last <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> of <var title="">cloned parent</var>,
+ <a href=#preserving-ranges>preserving ranges</a>.
+ </ol>
+
+ <li>For each <var title="">node</var> in <var title="">node list</var>, insert <var title="">node</var>
+ into the <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a> of <var title="">original parent</var> immediately before
+ <var title="">original parent</var>, <a href=#preserving-ranges>preserving ranges</a>.
+ <!-- Notice that a boundary point that was immediately before the element
+ will now be immediately before its children, just because of the regular
+ range mutation rules, without needing to worry about preserving ranges.
+ Likewise for boundary points immediately after the element, if we wind up
+ removing the element in the final step. Preserving ranges is only necessary
+ for the sake of boundary points in the element or its descendants. -->
+
+ <li>If <var title="">follows line break</var> is true, and the first member of
+ <var title="">node list</var> does not <a href=#follows-a-line-break title="follows a line break">follow a
+ line break</a>, call <code class=external data-anolis-spec=domcore title=dom-Document-createElement><a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#dom-document-createelement>createElement("br")</a></code> on the <a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#context-object>context object</a> and
+ insert the result immediately before the first member of <var title="">node
+ list</var>.
+
+ <li>If the last member of <var title="">node list</var> is an <a href=#inline-node>inline node</a>
+ other than a <code class=external data-anolis-spec=html title="the br element"><a href=http://www.whatwg.org/html/#the-br-element>br</a></code>, and the first <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> of <var title="">original parent</var> is
+ a <code class=external data-anolis-spec=html title="the br element"><a href=http://www.whatwg.org/html/#the-br-element>br</a></code>, and <var title="">original parent</var> is not an <a href=#inline-node>inline node</a>,
+ remove the first <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> of <var title="">original parent</var> from <var title="">original
+ parent</var>.
+
+ <li>If <var title="">original parent</var> has no <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>:
+
+ <ol>
+ <li>Remove <var title="">original parent</var> from its <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a>.
+
+ <li>If <var title="">precedes line break</var> is true, and the last member of
+ <var title="">node list</var> does not <a href=#precedes-a-line-break title="precedes a line break">precede a
+ line break</a>, call <code class=external data-anolis-spec=domcore title=dom-Document-createElement><a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#dom-document-createelement>createElement("br")</a></code> on the <a class=external data-anolis-spec=domrange href=http://html5.org/specs/dom-range.html#context-object>context object</a> and
+ insert the result immediately after the last member of <var title="">node
+ list</var>.
+ </ol>
+
+ <li>Otherwise, <a href=#remove-extraneous-line-breaks-before>remove extraneous line breaks before</a>
+ <var title="">original parent</var>.
+
+ <li>If <var title="">node list</var>'s last member's <code class=external data-anolis-spec=domcore title=dom-Node-nextSibling><a href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#dom-node-nextsibling>nextSibling</a></code> is null,
+ but its <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a> is not null, <a href=#remove-extraneous-line-breaks-at-the-end-of>remove extraneous line breaks at the
+ end of</a> <var title="">node list</var>'s last member's <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-parent title=concept-tree-parent>parent</a>.
+ <!-- The parent might be null if it's a br that we removed in the last step,
+ in which case this step isn't necessary. -->
+</ol>
+
+<p>To remove a <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-node title=concept-node>node</a> <var title="">node</var> while <dfn id=preserving-its-descendants>preserving its
+descendants</dfn>, <a href=#split-the-parent>split the parent</a> of <var title="">node</var>'s
+<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>.
+
<p>To <dfn id=indent>indent</dfn> a list <var title="">node list</var> of consecutive <a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-tree-sibling title=concept-tree-sibling>sibling</a>
<a class=external data-anolis-spec=domcore href=http://dvcs.w3.org/hg/domcore/raw-file/tip/Overview.html#concept-node title=concept-node>nodes</a>:
<!--
--- a/implementation.js Tue Jul 05 15:42:44 2011 -0600
+++ b/implementation.js Tue Jul 05 15:56:37 2011 -0600
@@ -1141,142 +1141,6 @@
return getPosition(newRange.endContainer, newRange.endOffset, node, offset) != "after";
}
-function splitParent(nodeList) {
- // "Let original parent be the parent of the first member of node list."
- var originalParent = nodeList[0].parentNode;
-
- // "If original parent is not editable or its parent is null, do nothing
- // and abort these steps."
- if (!isEditable(originalParent)
- || !originalParent.parentNode) {
- return;
- }
-
- // "If the first child of original parent is in node list, remove
- // extraneous line breaks before original parent."
- if (nodeList.indexOf(originalParent.firstChild) != -1) {
- removeExtraneousLineBreaksBefore(originalParent);
- }
-
- // "If the first child of original parent is in node list, and original
- // parent follows a line break, set follows line break to true. Otherwise,
- // set follows line break to false."
- var followsLineBreak_ = nodeList.indexOf(originalParent.firstChild) != -1
- && followsLineBreak(originalParent);
-
- // "If the last child of original parent is in node list, and original
- // parent precedes a line break, set precedes line break to true.
- // Otherwise, set precedes line break to false."
- var precedesLineBreak_ = nodeList.indexOf(originalParent.lastChild) != -1
- && precedesLineBreak(originalParent);
-
- // "If the first child of original parent is not in node list, but its last
- // child is:"
- if (nodeList.indexOf(originalParent.firstChild) == -1
- && nodeList.indexOf(originalParent.lastChild) != -1) {
- // "For each node in node list, in reverse order, insert node into the
- // parent of original parent immediately after original parent,
- // preserving ranges."
- for (var i = nodeList.length - 1; i >= 0; i--) {
- movePreservingRanges(nodeList[i], originalParent.parentNode, 1 + getNodeIndex(originalParent));
- }
-
- // "If precedes line break is true, and the last member of node list
- // does not precede a line break, call createElement("br") on the
- // context object and insert the result immediately after the last
- // member of node list."
- if (precedesLineBreak_
- && !precedesLineBreak(nodeList[nodeList.length - 1])) {
- nodeList[nodeList.length - 1].parentNode.insertBefore(document.createElement("br"), nodeList[nodeList.length - 1].nextSibling);
- }
-
- // "Remove extraneous line breaks at the end of original parent."
- removeExtraneousLineBreaksAtTheEndOf(originalParent);
-
- // "Abort these steps."
- return;
- }
-
- // "If the first child of original parent is not in node list:"
- if (nodeList.indexOf(originalParent.firstChild) == -1) {
- // "Let cloned parent be the result of calling cloneNode(false) on
- // original parent."
- var clonedParent = originalParent.cloneNode(false);
-
- // "If original parent has an id attribute, unset it."
- originalParent.removeAttribute("id");
-
- // "Insert cloned parent into the parent of original parent immediately
- // before original parent."
- originalParent.parentNode.insertBefore(clonedParent, originalParent);
-
- // "While the previousSibling of the first member of node list is not
- // null, append the first child of original parent as the last child of
- // cloned parent, preserving ranges."
- while (nodeList[0].previousSibling) {
- movePreservingRanges(originalParent.firstChild, clonedParent, clonedParent.childNodes.length);
- }
- }
-
- // "For each node in node list, insert node into the parent of original
- // parent immediately before original parent, preserving ranges."
- for (var i = 0; i < nodeList.length; i++) {
- movePreservingRanges(nodeList[i], originalParent.parentNode, getNodeIndex(originalParent));
- }
-
- // "If follows line break is true, and the first member of node list does
- // not follow a line break, call createElement("br") on the context object
- // and insert the result immediately before the first member of node list."
- if (followsLineBreak_
- && !followsLineBreak(nodeList[0])) {
- nodeList[0].parentNode.insertBefore(document.createElement("br"), nodeList[0]);
- }
-
- // "If the last member of node list is an inline node other than a br, and
- // the first child of original parent is a br, and original parent is not
- // an inline node, remove the first child of original parent from original
- // parent."
- if (isInlineNode(nodeList[nodeList.length - 1])
- && !isHtmlElement(nodeList[nodeList.length - 1], "br")
- && isHtmlElement(originalParent.firstChild, "br")
- && !isInlineNode(originalParent)) {
- originalParent.removeChild(originalParent.firstChild);
- }
-
- // "If original parent has no children:"
- if (!originalParent.hasChildNodes()) {
- // "Remove original parent from its parent."
- originalParent.parentNode.removeChild(originalParent);
-
- // "If precedes line break is true, and the last member of node list
- // does not precede a line break, call createElement("br") on the
- // context object and insert the result immediately after the last
- // member of node list."
- if (precedesLineBreak_
- && !precedesLineBreak(nodeList[nodeList.length - 1])) {
- nodeList[nodeList.length - 1].parentNode.insertBefore(document.createElement("br"), nodeList[nodeList.length - 1].nextSibling);
- }
-
- // "Otherwise, remove extraneous line breaks before original parent."
- } else {
- removeExtraneousLineBreaksBefore(originalParent);
- }
-
- // "If node list's last member's nextSibling is null, but its parent is not
- // null, remove extraneous line breaks at the end of node list's last
- // member's parent."
- if (!nodeList[nodeList.length - 1].nextSibling
- && nodeList[nodeList.length - 1].parentNode) {
- removeExtraneousLineBreaksAtTheEndOf(nodeList[nodeList.length - 1].parentNode);
- }
-}
-
-// "To remove a node node while preserving its descendants, split the parent of
-// node's children."
-function removePreservingDescendants(node) {
- splitParent([].slice.call(node.childNodes));
-}
-
//@}
///// Wrapping a list of nodes /////
@@ -2088,10 +1952,10 @@
// "Let children be the children of element."
var children = Array.prototype.slice.call(element.childNodes);
- // "While element has children, insert its first child into its parent
- // immediately before it, preserving ranges."
- while (element.childNodes.length) {
- movePreservingRanges(element.firstChild, element.parentNode, getNodeIndex(element));
+ // "For each child in children, insert child into element's parent
+ // immediately before element, preserving ranges."
+ for (var i = 0; i < children.length; i++) {
+ movePreservingRanges(children[i], element.parentNode, getNodeIndex(element));
}
// "Remove element from its parent."
@@ -3489,6 +3353,142 @@
}
}
+function splitParent(nodeList) {
+ // "Let original parent be the parent of the first member of node list."
+ var originalParent = nodeList[0].parentNode;
+
+ // "If original parent is not editable or its parent is null, do nothing
+ // and abort these steps."
+ if (!isEditable(originalParent)
+ || !originalParent.parentNode) {
+ return;
+ }
+
+ // "If the first child of original parent is in node list, remove
+ // extraneous line breaks before original parent."
+ if (nodeList.indexOf(originalParent.firstChild) != -1) {
+ removeExtraneousLineBreaksBefore(originalParent);
+ }
+
+ // "If the first child of original parent is in node list, and original
+ // parent follows a line break, set follows line break to true. Otherwise,
+ // set follows line break to false."
+ var followsLineBreak_ = nodeList.indexOf(originalParent.firstChild) != -1
+ && followsLineBreak(originalParent);
+
+ // "If the last child of original parent is in node list, and original
+ // parent precedes a line break, set precedes line break to true.
+ // Otherwise, set precedes line break to false."
+ var precedesLineBreak_ = nodeList.indexOf(originalParent.lastChild) != -1
+ && precedesLineBreak(originalParent);
+
+ // "If the first child of original parent is not in node list, but its last
+ // child is:"
+ if (nodeList.indexOf(originalParent.firstChild) == -1
+ && nodeList.indexOf(originalParent.lastChild) != -1) {
+ // "For each node in node list, in reverse order, insert node into the
+ // parent of original parent immediately after original parent,
+ // preserving ranges."
+ for (var i = nodeList.length - 1; i >= 0; i--) {
+ movePreservingRanges(nodeList[i], originalParent.parentNode, 1 + getNodeIndex(originalParent));
+ }
+
+ // "If precedes line break is true, and the last member of node list
+ // does not precede a line break, call createElement("br") on the
+ // context object and insert the result immediately after the last
+ // member of node list."
+ if (precedesLineBreak_
+ && !precedesLineBreak(nodeList[nodeList.length - 1])) {
+ nodeList[nodeList.length - 1].parentNode.insertBefore(document.createElement("br"), nodeList[nodeList.length - 1].nextSibling);
+ }
+
+ // "Remove extraneous line breaks at the end of original parent."
+ removeExtraneousLineBreaksAtTheEndOf(originalParent);
+
+ // "Abort these steps."
+ return;
+ }
+
+ // "If the first child of original parent is not in node list:"
+ if (nodeList.indexOf(originalParent.firstChild) == -1) {
+ // "Let cloned parent be the result of calling cloneNode(false) on
+ // original parent."
+ var clonedParent = originalParent.cloneNode(false);
+
+ // "If original parent has an id attribute, unset it."
+ originalParent.removeAttribute("id");
+
+ // "Insert cloned parent into the parent of original parent immediately
+ // before original parent."
+ originalParent.parentNode.insertBefore(clonedParent, originalParent);
+
+ // "While the previousSibling of the first member of node list is not
+ // null, append the first child of original parent as the last child of
+ // cloned parent, preserving ranges."
+ while (nodeList[0].previousSibling) {
+ movePreservingRanges(originalParent.firstChild, clonedParent, clonedParent.childNodes.length);
+ }
+ }
+
+ // "For each node in node list, insert node into the parent of original
+ // parent immediately before original parent, preserving ranges."
+ for (var i = 0; i < nodeList.length; i++) {
+ movePreservingRanges(nodeList[i], originalParent.parentNode, getNodeIndex(originalParent));
+ }
+
+ // "If follows line break is true, and the first member of node list does
+ // not follow a line break, call createElement("br") on the context object
+ // and insert the result immediately before the first member of node list."
+ if (followsLineBreak_
+ && !followsLineBreak(nodeList[0])) {
+ nodeList[0].parentNode.insertBefore(document.createElement("br"), nodeList[0]);
+ }
+
+ // "If the last member of node list is an inline node other than a br, and
+ // the first child of original parent is a br, and original parent is not
+ // an inline node, remove the first child of original parent from original
+ // parent."
+ if (isInlineNode(nodeList[nodeList.length - 1])
+ && !isHtmlElement(nodeList[nodeList.length - 1], "br")
+ && isHtmlElement(originalParent.firstChild, "br")
+ && !isInlineNode(originalParent)) {
+ originalParent.removeChild(originalParent.firstChild);
+ }
+
+ // "If original parent has no children:"
+ if (!originalParent.hasChildNodes()) {
+ // "Remove original parent from its parent."
+ originalParent.parentNode.removeChild(originalParent);
+
+ // "If precedes line break is true, and the last member of node list
+ // does not precede a line break, call createElement("br") on the
+ // context object and insert the result immediately after the last
+ // member of node list."
+ if (precedesLineBreak_
+ && !precedesLineBreak(nodeList[nodeList.length - 1])) {
+ nodeList[nodeList.length - 1].parentNode.insertBefore(document.createElement("br"), nodeList[nodeList.length - 1].nextSibling);
+ }
+
+ // "Otherwise, remove extraneous line breaks before original parent."
+ } else {
+ removeExtraneousLineBreaksBefore(originalParent);
+ }
+
+ // "If node list's last member's nextSibling is null, but its parent is not
+ // null, remove extraneous line breaks at the end of node list's last
+ // member's parent."
+ if (!nodeList[nodeList.length - 1].nextSibling
+ && nodeList[nodeList.length - 1].parentNode) {
+ removeExtraneousLineBreaksAtTheEndOf(nodeList[nodeList.length - 1].parentNode);
+ }
+}
+
+// "To remove a node node while preserving its descendants, split the parent of
+// node's children."
+function removePreservingDescendants(node) {
+ splitParent([].slice.call(node.childNodes));
+}
+
function indentNodes(nodeList) {
// "If node list is empty, do nothing and abort these steps."
if (!nodeList.length) {
--- a/source.html Tue Jul 05 15:42:44 2011 -0600
+++ b/source.html Tue Jul 05 15:56:37 2011 -0600
@@ -839,145 +839,6 @@
<li>Return false if <var>new range</var>'s [[rangeend]] is [[bpafter]]
(<var>node</var>, <var>offset</var>), true otherwise.
</ol>
-
-<p>To <dfn>split the parent</dfn> of a list <var>node list</var> of consecutive
-[[sibling]] [[nodes]]:
-
-<p class=XXX>Pretty much any time we call this algorithm, it can cause trouble
-if the parent had styles, classes, etc. There's not going to be any general
-way to handle this, but we should at least try to handle the special case of
-inline styles, because Firefox does actually add them to arbitrary elements.
-Also, when splitting out of an inline parent, it might be good to wrap all the
-inline descendants in a clone of the former parent.
-
-<ol>
- <li>Let <var>original parent</var> be the [[parent]] of the first member of
- <var>node list</var>.
-
- <li>If <var>original parent</var> is not <span>editable</span> or its
- [[parent]] is null, do nothing and abort these steps.
-
- <li>If the first [[child]] of <var>original parent</var> is in <var>node
- list</var>, <span>remove extraneous line breaks before</span> <var>original
- parent</var>.
-
- <li>If the first [[child]] of <var>original parent</var> is in <var>node
- list</var>, and <var>original parent</var> <span>follows a line break</span>,
- set <var>follows line break</var> to true. Otherwise, set <var>follows line
- break</var> to false.
-
- <li>If the last [[child]] of <var>original parent</var> is in <var>node
- list</var>, and <var>original parent</var> <span>precedes a line
- break</span>, set <var>precedes line break</var> to true. Otherwise, set
- <var>precedes line break</var> to false.
-
- <li>If the first [[child]] of <var>original parent</var> is not in <var>node
- list</var>, but its last [[child]] is:
-
- <div class=XXX>
- <p>We insert things after the parent. This is bad, because it will cause
- them to become part of any ranges that immediately follow. For instance, if
- we're hitting "bar" in
-
- <xmp><div><p>foo<p>bar</div>{<p>baz}</xmp>
-
- <p>it becomes
-
- <xmp><div><p>foo</div>{<p>bar<p>baz}</xmp>
-
- <p>instead of
-
- <xmp><div><p>foo</div><p>bar{<p>baz}</xmp>
-
- <p>because of how range mutation rules work. This doesn't happen if we
- insert before. Probably this isn't important enough to try working around,
- though.
- </div>
-
- <ol>
- <li>For each <var>node</var> in <var>node list</var>, <em>in reverse
- order</em>, insert <var>node</var> into the [[parent]] of <var>original
- parent</var> immediately after <var>original parent</var>, <span>preserving
- ranges</span>.
-
- <li>If <var>precedes line break</var> is true, and the last member of
- <var>node list</var> does not <span title="precedes a line break">precede a
- line break</span>, call [[createelement|"br"]] on the [[contextobject]] and
- insert the result immediately after the last member of <var>node
- list</var>.
-
- <li><span>Remove extraneous line breaks at the end of</span> <var>original
- parent</var>.
-
- <li>Abort these steps.
- </ol>
-
- <li>If the first [[child]] of <var>original parent</var> is not in <var>node
- list</var>:
-
- <ol>
- <li>Let <var>cloned parent</var> be the result of calling <code
- data-anolis-spec=domcore title=dom-Node-cloneNode>cloneNode(false)</code>
- on <var>original parent</var>.
-
- <li>If <var>original parent</var> has an [[id]] attribute, unset it.
-
- <li>Insert <var>cloned parent</var> into the [[parent]] of <var>original
- parent</var> immediately before <var>original parent</var>.
-
- <li>While the [[previoussibling]] of the first member of <var>node
- list</var> is not null, append the first [[child]] of <var>original
- parent</var> as the last [[child]] of <var>cloned parent</var>,
- <span>preserving ranges</span>.
- </ol>
-
- <li>For each <var>node</var> in <var>node list</var>, insert <var>node</var>
- into the [[parent]] of <var>original parent</var> immediately before
- <var>original parent</var>, <span>preserving ranges</span>.
- <!-- Notice that a boundary point that was immediately before the element
- will now be immediately before its children, just because of the regular
- range mutation rules, without needing to worry about preserving ranges.
- Likewise for boundary points immediately after the element, if we wind up
- removing the element in the final step. Preserving ranges is only necessary
- for the sake of boundary points in the element or its descendants. -->
-
- <li>If <var>follows line break</var> is true, and the first member of
- <var>node list</var> does not <span title="follows a line break">follow a
- line break</span>, call [[createelement|"br"]] on the [[contextobject]] and
- insert the result immediately before the first member of <var>node
- list</var>.
-
- <li>If the last member of <var>node list</var> is an <span>inline node</span>
- other than a [[br]], and the first [[child]] of <var>original parent</var> is
- a [[br]], and <var>original parent</var> is not an <span>inline node</span>,
- remove the first [[child]] of <var>original parent</var> from <var>original
- parent</var>.
-
- <li>If <var>original parent</var> has no [[children]]:
-
- <ol>
- <li>Remove <var>original parent</var> from its [[parent]].
-
- <li>If <var>precedes line break</var> is true, and the last member of
- <var>node list</var> does not <span title="precedes a line break">precede a
- line break</span>, call [[createelement|"br"]] on the [[contextobject]] and
- insert the result immediately after the last member of <var>node
- list</var>.
- </ol>
-
- <li>Otherwise, <span>remove extraneous line breaks before</span>
- <var>original parent</var>.
-
- <li>If <var>node list</var>'s last member's [[nextsibling]] is null,
- but its [[parent]] is not null, <span>remove extraneous line breaks at the
- end of</span> <var>node list</var>'s last member's [[parent]].
- <!-- The parent might be null if it's a br that we removed in the last step,
- in which case this step isn't necessary. -->
-</ol>
-
-<p>To remove a [[node]] <var>node</var> while <dfn>preserving its
-descendants</dfn>, <span>split the parent</span> of <var>node</var>'s
-[[children]].
<!-- @} -->
<h3>Wrapping a list of nodes</h3>
@@ -1512,7 +1373,11 @@
<ol>
<li>Let <var>children</var> be the [[children]] of <var>element</var>.
- <li>Remove <var>element</var>, <span>preserving its descendants</span>.
+ <li>For each <var>child</var> in <var>children</var>, insert
+ <var>child</var> into <var>element</var>'s [[parent]] immediately before
+ <var>element</var>, <span>preserving ranges</span>.
+
+ <li>Remove <var>element</var> from its [[parent]].
<li>Return <var>children</var>.
</ol>
@@ -3121,6 +2986,145 @@
of <var>node</var>.
</ol>
+<p>To <dfn>split the parent</dfn> of a list <var>node list</var> of consecutive
+[[sibling]] [[nodes]]:
+
+<p class=XXX>Pretty much any time we call this algorithm, it can cause trouble
+if the parent had styles, classes, etc. There's not going to be any general
+way to handle this, but we should at least try to handle the special case of
+inline styles, because Firefox does actually add them to arbitrary elements.
+Also, when splitting out of an inline parent, it might be good to wrap all the
+inline descendants in a clone of the former parent.
+
+<ol>
+ <li>Let <var>original parent</var> be the [[parent]] of the first member of
+ <var>node list</var>.
+
+ <li>If <var>original parent</var> is not <span>editable</span> or its
+ [[parent]] is null, do nothing and abort these steps.
+
+ <li>If the first [[child]] of <var>original parent</var> is in <var>node
+ list</var>, <span>remove extraneous line breaks before</span> <var>original
+ parent</var>.
+
+ <li>If the first [[child]] of <var>original parent</var> is in <var>node
+ list</var>, and <var>original parent</var> <span>follows a line break</span>,
+ set <var>follows line break</var> to true. Otherwise, set <var>follows line
+ break</var> to false.
+
+ <li>If the last [[child]] of <var>original parent</var> is in <var>node
+ list</var>, and <var>original parent</var> <span>precedes a line
+ break</span>, set <var>precedes line break</var> to true. Otherwise, set
+ <var>precedes line break</var> to false.
+
+ <li>If the first [[child]] of <var>original parent</var> is not in <var>node
+ list</var>, but its last [[child]] is:
+
+ <div class=XXX>
+ <p>We insert things after the parent. This is bad, because it will cause
+ them to become part of any ranges that immediately follow. For instance, if
+ we're hitting "bar" in
+
+ <xmp><div><p>foo<p>bar</div>{<p>baz}</xmp>
+
+ <p>it becomes
+
+ <xmp><div><p>foo</div>{<p>bar<p>baz}</xmp>
+
+ <p>instead of
+
+ <xmp><div><p>foo</div><p>bar{<p>baz}</xmp>
+
+ <p>because of how range mutation rules work. This doesn't happen if we
+ insert before. Probably this isn't important enough to try working around,
+ though.
+ </div>
+
+ <ol>
+ <li>For each <var>node</var> in <var>node list</var>, <em>in reverse
+ order</em>, insert <var>node</var> into the [[parent]] of <var>original
+ parent</var> immediately after <var>original parent</var>, <span>preserving
+ ranges</span>.
+
+ <li>If <var>precedes line break</var> is true, and the last member of
+ <var>node list</var> does not <span title="precedes a line break">precede a
+ line break</span>, call [[createelement|"br"]] on the [[contextobject]] and
+ insert the result immediately after the last member of <var>node
+ list</var>.
+
+ <li><span>Remove extraneous line breaks at the end of</span> <var>original
+ parent</var>.
+
+ <li>Abort these steps.
+ </ol>
+
+ <li>If the first [[child]] of <var>original parent</var> is not in <var>node
+ list</var>:
+
+ <ol>
+ <li>Let <var>cloned parent</var> be the result of calling <code
+ data-anolis-spec=domcore title=dom-Node-cloneNode>cloneNode(false)</code>
+ on <var>original parent</var>.
+
+ <li>If <var>original parent</var> has an [[id]] attribute, unset it.
+
+ <li>Insert <var>cloned parent</var> into the [[parent]] of <var>original
+ parent</var> immediately before <var>original parent</var>.
+
+ <li>While the [[previoussibling]] of the first member of <var>node
+ list</var> is not null, append the first [[child]] of <var>original
+ parent</var> as the last [[child]] of <var>cloned parent</var>,
+ <span>preserving ranges</span>.
+ </ol>
+
+ <li>For each <var>node</var> in <var>node list</var>, insert <var>node</var>
+ into the [[parent]] of <var>original parent</var> immediately before
+ <var>original parent</var>, <span>preserving ranges</span>.
+ <!-- Notice that a boundary point that was immediately before the element
+ will now be immediately before its children, just because of the regular
+ range mutation rules, without needing to worry about preserving ranges.
+ Likewise for boundary points immediately after the element, if we wind up
+ removing the element in the final step. Preserving ranges is only necessary
+ for the sake of boundary points in the element or its descendants. -->
+
+ <li>If <var>follows line break</var> is true, and the first member of
+ <var>node list</var> does not <span title="follows a line break">follow a
+ line break</span>, call [[createelement|"br"]] on the [[contextobject]] and
+ insert the result immediately before the first member of <var>node
+ list</var>.
+
+ <li>If the last member of <var>node list</var> is an <span>inline node</span>
+ other than a [[br]], and the first [[child]] of <var>original parent</var> is
+ a [[br]], and <var>original parent</var> is not an <span>inline node</span>,
+ remove the first [[child]] of <var>original parent</var> from <var>original
+ parent</var>.
+
+ <li>If <var>original parent</var> has no [[children]]:
+
+ <ol>
+ <li>Remove <var>original parent</var> from its [[parent]].
+
+ <li>If <var>precedes line break</var> is true, and the last member of
+ <var>node list</var> does not <span title="precedes a line break">precede a
+ line break</span>, call [[createelement|"br"]] on the [[contextobject]] and
+ insert the result immediately after the last member of <var>node
+ list</var>.
+ </ol>
+
+ <li>Otherwise, <span>remove extraneous line breaks before</span>
+ <var>original parent</var>.
+
+ <li>If <var>node list</var>'s last member's [[nextsibling]] is null,
+ but its [[parent]] is not null, <span>remove extraneous line breaks at the
+ end of</span> <var>node list</var>'s last member's [[parent]].
+ <!-- The parent might be null if it's a br that we removed in the last step,
+ in which case this step isn't necessary. -->
+</ol>
+
+<p>To remove a [[node]] <var>node</var> while <dfn>preserving its
+descendants</dfn>, <span>split the parent</span> of <var>node</var>'s
+[[children]].
+
<p>To <dfn>indent</dfn> a list <var>node list</var> of consecutive [[sibling]]
[[nodes]]:
<!--