| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. | 2 * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. |
| 3 * | 3 * |
| 4 * Redistribution and use in source and binary forms, with or without | 4 * Redistribution and use in source and binary forms, with or without |
| 5 * modification, are permitted provided that the following conditions | 5 * modification, are permitted provided that the following conditions |
| 6 * are met: | 6 * are met: |
| 7 * 1. Redistributions of source code must retain the above copyright | 7 * 1. Redistributions of source code must retain the above copyright |
| 8 * notice, this list of conditions and the following disclaimer. | 8 * notice, this list of conditions and the following disclaimer. |
| 9 * 2. Redistributions in binary form must reproduce the above copyright | 9 * 2. Redistributions in binary form must reproduce the above copyright |
| 10 * notice, this list of conditions and the following disclaimer in the | 10 * notice, this list of conditions and the following disclaimer in the |
| (...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 60 if (endingSelection().isNone()) | 60 if (endingSelection().isNone()) |
| 61 return; | 61 return; |
| 62 | 62 |
| 63 VisiblePosition visiblePos = endingSelection().visibleStart(); | 63 VisiblePosition visiblePos = endingSelection().visibleStart(); |
| 64 | 64 |
| 65 // pos is a position equivalent to the caret. We use downstream() so that p
os will | 65 // pos is a position equivalent to the caret. We use downstream() so that p
os will |
| 66 // be in the first node that we need to move (there are a few exceptions to
this, see below). | 66 // be in the first node that we need to move (there are a few exceptions to
this, see below). |
| 67 Position pos = endingSelection().start().downstream(); | 67 Position pos = endingSelection().start().downstream(); |
| 68 | 68 |
| 69 // Find the top-most blockquote from the start. | 69 // Find the top-most blockquote from the start. |
| 70 Handle<Node> topBlockquote = adoptRawResult(highestEnclosingNodeOfType(pos,
isMailBlockquote)); | 70 Handle<Node> topBlockquote = highestEnclosingNodeOfType(pos, isMailBlockquot
e); |
| 71 if (!topBlockquote || !topBlockquote->parentNode() || !topBlockquote->isElem
entNode()) | 71 if (!topBlockquote || !topBlockquote->parentNode() || !topBlockquote->isElem
entNode()) |
| 72 return; | 72 return; |
| 73 | 73 |
| 74 Handle<Element> breakNode = createBreakElement(document()); | 74 Handle<Element> breakNode = createBreakElement(document()); |
| 75 | 75 |
| 76 bool isLastVisPosInNode = isLastVisiblePositionInNode(visiblePos, topBlockqu
ote.raw()); | 76 bool isLastVisPosInNode = isLastVisiblePositionInNode(visiblePos, topBlockqu
ote.raw()); |
| 77 | 77 |
| 78 // If the position is at the beginning of the top quoted content, we don't n
eed to break the quote. | 78 // If the position is at the beginning of the top quoted content, we don't n
eed to break the quote. |
| 79 // Instead, insert the break before the blockquote, unless the position is a
s the end of the the quoted content. | 79 // Instead, insert the break before the blockquote, unless the position is a
s the end of the the quoted content. |
| 80 if (isFirstVisiblePositionInNode(visiblePos, topBlockquote.raw()) && !isLast
VisPosInNode) { | 80 if (isFirstVisiblePositionInNode(visiblePos, topBlockquote.raw()) && !isLast
VisPosInNode) { |
| (...skipping 12 matching lines...) Expand all Loading... |
| 93 rebalanceWhitespace(); | 93 rebalanceWhitespace(); |
| 94 return; | 94 return; |
| 95 } | 95 } |
| 96 | 96 |
| 97 // Don't move a line break just after the caret. Doing so would create an e
xtra, empty paragraph | 97 // Don't move a line break just after the caret. Doing so would create an e
xtra, empty paragraph |
| 98 // in the new blockquote. | 98 // in the new blockquote. |
| 99 if (lineBreakExistsAtVisiblePosition(visiblePos)) | 99 if (lineBreakExistsAtVisiblePosition(visiblePos)) |
| 100 pos = pos.next(); | 100 pos = pos.next(); |
| 101 | 101 |
| 102 // Adjust the position so we don't split at the beginning of a quote. | 102 // Adjust the position so we don't split at the beginning of a quote. |
| 103 while (isFirstVisiblePositionInNode(VisiblePosition(pos), enclosingNodeOfTyp
e(pos, isMailBlockquote))) | 103 while (true) { |
| 104 HandleScope scope; |
| 105 if (!isFirstVisiblePositionInNode(VisiblePosition(pos), enclosingNodeOfT
ype(pos, isMailBlockquote).handle().raw())) |
| 106 break; |
| 104 pos = pos.previous(); | 107 pos = pos.previous(); |
| 108 } |
| 105 | 109 |
| 106 // startNode is the first node that we need to move to the new blockquote. | 110 // startNode is the first node that we need to move to the new blockquote. |
| 107 Handle<Node> startNode = pos.deprecatedNode(); | 111 Handle<Node> startNode = pos.deprecatedNode(); |
| 108 | 112 |
| 109 // Split at pos if in the middle of a text node. | 113 // Split at pos if in the middle of a text node. |
| 110 if (startNode->isTextNode()) { | 114 if (startNode->isTextNode()) { |
| 111 Handle<Text> textNode = toText(startNode); | 115 Handle<Text> textNode = toText(startNode); |
| 112 if ((unsigned)pos.deprecatedEditingOffset() >= textNode->length()) { | 116 if ((unsigned)pos.deprecatedEditingOffset() >= textNode->length()) { |
| 113 startNode = NodeTraversal::next(startNode); | 117 startNode = NodeTraversal::next(startNode); |
| 114 ASSERT(startNode); | 118 ASSERT(startNode); |
| 115 } else if (pos.deprecatedEditingOffset() > 0) | 119 } else if (pos.deprecatedEditingOffset() > 0) |
| 116 splitTextNode(textNode, pos.deprecatedEditingOffset()); | 120 splitTextNode(textNode, pos.deprecatedEditingOffset()); |
| 117 } else if (pos.deprecatedEditingOffset() > 0) { | 121 } else if (pos.deprecatedEditingOffset() > 0) { |
| 118 Handle<Node> childAtOffset = startNode->childNode(pos.deprecatedEditingO
ffset()); | 122 Handle<Node> childAtOffset = startNode->childNode(pos.deprecatedEditingO
ffset()); |
| 119 startNode = childAtOffset ? childAtOffset : Handle<Node>(NodeTraversal::
next(startNode)); | 123 startNode = childAtOffset ? childAtOffset : Handle<Node>(NodeTraversal::
next(startNode)); |
| 120 ASSERT(startNode); | 124 ASSERT(startNode); |
| 121 } | 125 } |
| 122 | 126 |
| 123 // If there's nothing inside topBlockquote to move, we're finished. | 127 // If there's nothing inside topBlockquote to move, we're finished. |
| 124 if (!startNode->isDescendantOf(topBlockquote.raw())) { | 128 if (!startNode->isDescendantOf(topBlockquote.raw())) { |
| 125 setEndingSelection(VisibleSelection(VisiblePosition(firstPositionInOrBef
oreNode(startNode.raw())), endingSelection().isDirectional())); | 129 setEndingSelection(VisibleSelection(VisiblePosition(firstPositionInOrBef
oreNode(startNode)), endingSelection().isDirectional())); |
| 126 return; | 130 return; |
| 127 } | 131 } |
| 128 | 132 |
| 129 // Build up list of ancestors in between the start node and the top blockquo
te. | 133 // Build up list of ancestors in between the start node and the top blockquo
te. |
| 130 CollectionRoot<Vector<Member<Element> > > ancestors; | 134 CollectionRoot<Vector<Member<Element> > > ancestors; |
| 131 for (Handle<Element> node = startNode->parentElement(); node && node != topB
lockquote; node = node->parentElement()) | 135 for (Handle<Element> node = startNode->parentElement(); node && node != topB
lockquote; node = node->parentElement()) |
| 132 ancestors->append(node); | 136 ancestors->append(node); |
| 133 | 137 |
| 134 // Insert a clone of the top blockquote after the break. | 138 // Insert a clone of the top blockquote after the break. |
| 135 Handle<Element> clonedBlockquote = toElement(topBlockquote)->cloneElementWit
houtChildren(); | 139 Handle<Element> clonedBlockquote = toElement(topBlockquote)->cloneElementWit
houtChildren(); |
| (...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 184 | 188 |
| 185 // Make sure the cloned block quote renders. | 189 // Make sure the cloned block quote renders. |
| 186 addBlockPlaceholderIfNeeded(clonedBlockquote); | 190 addBlockPlaceholderIfNeeded(clonedBlockquote); |
| 187 | 191 |
| 188 // Put the selection right before the break. | 192 // Put the selection right before the break. |
| 189 setEndingSelection(VisibleSelection(positionBeforeNode(breakNode), DOWNSTREA
M, endingSelection().isDirectional())); | 193 setEndingSelection(VisibleSelection(positionBeforeNode(breakNode), DOWNSTREA
M, endingSelection().isDirectional())); |
| 190 rebalanceWhitespace(); | 194 rebalanceWhitespace(); |
| 191 } | 195 } |
| 192 | 196 |
| 193 } // namespace WebCore | 197 } // namespace WebCore |
| OLD | NEW |