| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright (C) 2004, 2005, 2006, 2007 Apple Inc. All rights reserved. | 2 * Copyright (C) 2004, 2005, 2006, 2007 Apple 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 69 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 80 // Atomic means that the node has no children, or has children which are ignored
for the | 80 // Atomic means that the node has no children, or has children which are ignored
for the |
| 81 // purposes of editing. | 81 // purposes of editing. |
| 82 bool isAtomicNode(const Node *node) | 82 bool isAtomicNode(const Node *node) |
| 83 { | 83 { |
| 84 return node && (!node->hasChildren() || editingIgnoresContent(node)); | 84 return node && (!node->hasChildren() || editingIgnoresContent(node)); |
| 85 } | 85 } |
| 86 | 86 |
| 87 template <typename Traversal> | 87 template <typename Traversal> |
| 88 static int comparePositions(Node* containerA, int offsetA, Node* containerB, int
offsetB, bool* disconnected) | 88 static int comparePositions(Node* containerA, int offsetA, Node* containerB, int
offsetB, bool* disconnected) |
| 89 { | 89 { |
| 90 ASSERT(containerA); | 90 DCHECK(containerA); |
| 91 ASSERT(containerB); | 91 DCHECK(containerB); |
| 92 | 92 |
| 93 if (disconnected) | 93 if (disconnected) |
| 94 *disconnected = false; | 94 *disconnected = false; |
| 95 | 95 |
| 96 if (!containerA) | 96 if (!containerA) |
| 97 return -1; | 97 return -1; |
| 98 if (!containerB) | 98 if (!containerB) |
| 99 return 1; | 99 return 1; |
| 100 | 100 |
| 101 // see DOM2 traversal & range section 2.5 | 101 // see DOM2 traversal & range section 2.5 |
| (...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 186 | 186 |
| 187 int comparePositionsInFlatTree(Node* containerA, int offsetA, Node* containerB,
int offsetB, bool* disconnected) | 187 int comparePositionsInFlatTree(Node* containerA, int offsetA, Node* containerB,
int offsetB, bool* disconnected) |
| 188 { | 188 { |
| 189 return comparePositions<FlatTreeTraversal>(containerA, offsetA, containerB,
offsetB, disconnected); | 189 return comparePositions<FlatTreeTraversal>(containerA, offsetA, containerB,
offsetB, disconnected); |
| 190 } | 190 } |
| 191 | 191 |
| 192 // Compare two positions, taking into account the possibility that one or both | 192 // Compare two positions, taking into account the possibility that one or both |
| 193 // could be inside a shadow tree. Only works for non-null values. | 193 // could be inside a shadow tree. Only works for non-null values. |
| 194 int comparePositions(const Position& a, const Position& b) | 194 int comparePositions(const Position& a, const Position& b) |
| 195 { | 195 { |
| 196 ASSERT(a.isNotNull()); | 196 DCHECK(a.isNotNull()); |
| 197 ASSERT(b.isNotNull()); | 197 DCHECK(b.isNotNull()); |
| 198 const TreeScope* commonScope = Position::commonAncestorTreeScope(a, b); | 198 const TreeScope* commonScope = Position::commonAncestorTreeScope(a, b); |
| 199 | 199 |
| 200 ASSERT(commonScope); | 200 DCHECK(commonScope); |
| 201 if (!commonScope) | 201 if (!commonScope) |
| 202 return 0; | 202 return 0; |
| 203 | 203 |
| 204 Node* nodeA = commonScope->ancestorInThisScope(a.computeContainerNode()); | 204 Node* nodeA = commonScope->ancestorInThisScope(a.computeContainerNode()); |
| 205 ASSERT(nodeA); | 205 DCHECK(nodeA); |
| 206 bool hasDescendentA = nodeA != a.computeContainerNode(); | 206 bool hasDescendentA = nodeA != a.computeContainerNode(); |
| 207 int offsetA = hasDescendentA ? 0 : a.computeOffsetInContainerNode(); | 207 int offsetA = hasDescendentA ? 0 : a.computeOffsetInContainerNode(); |
| 208 | 208 |
| 209 Node* nodeB = commonScope->ancestorInThisScope(b.computeContainerNode()); | 209 Node* nodeB = commonScope->ancestorInThisScope(b.computeContainerNode()); |
| 210 ASSERT(nodeB); | 210 DCHECK(nodeB); |
| 211 bool hasDescendentB = nodeB != b.computeContainerNode(); | 211 bool hasDescendentB = nodeB != b.computeContainerNode(); |
| 212 int offsetB = hasDescendentB ? 0 : b.computeOffsetInContainerNode(); | 212 int offsetB = hasDescendentB ? 0 : b.computeOffsetInContainerNode(); |
| 213 | 213 |
| 214 int bias = 0; | 214 int bias = 0; |
| 215 if (nodeA == nodeB) { | 215 if (nodeA == nodeB) { |
| 216 if (hasDescendentA) | 216 if (hasDescendentA) |
| 217 bias = -1; | 217 bias = -1; |
| 218 else if (hasDescendentB) | 218 else if (hasDescendentB) |
| 219 bias = 1; | 219 bias = 1; |
| 220 } | 220 } |
| (...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 263 } | 263 } |
| 264 | 264 |
| 265 bool isEditablePosition(const Position& p, EditableType editableType, EUpdateSty
le updateStyle) | 265 bool isEditablePosition(const Position& p, EditableType editableType, EUpdateSty
le updateStyle) |
| 266 { | 266 { |
| 267 Node* node = p.parentAnchoredEquivalent().anchorNode(); | 267 Node* node = p.parentAnchoredEquivalent().anchorNode(); |
| 268 if (!node) | 268 if (!node) |
| 269 return false; | 269 return false; |
| 270 if (updateStyle == UpdateStyle) | 270 if (updateStyle == UpdateStyle) |
| 271 node->document().updateLayoutIgnorePendingStylesheets(); | 271 node->document().updateLayoutIgnorePendingStylesheets(); |
| 272 else | 272 else |
| 273 ASSERT(updateStyle == DoNotUpdateStyle); | 273 DCHECK_EQ(updateStyle, DoNotUpdateStyle); |
| 274 | 274 |
| 275 if (isDisplayInsideTable(node)) | 275 if (isDisplayInsideTable(node)) |
| 276 node = node->parentNode(); | 276 node = node->parentNode(); |
| 277 | 277 |
| 278 if (node->isDocumentNode()) | 278 if (node->isDocumentNode()) |
| 279 return false; | 279 return false; |
| 280 return node->hasEditableStyle(editableType); | 280 return node->hasEditableStyle(editableType); |
| 281 } | 281 } |
| 282 | 282 |
| 283 bool isEditablePosition(const PositionInFlatTree& p, EditableType editableType,
EUpdateStyle updateStyle) | 283 bool isEditablePosition(const PositionInFlatTree& p, EditableType editableType,
EUpdateStyle updateStyle) |
| (...skipping 388 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 672 } | 672 } |
| 673 | 673 |
| 674 PositionInFlatTree previousPositionOf(const PositionInFlatTree& position, Positi
onMoveType moveType) | 674 PositionInFlatTree previousPositionOf(const PositionInFlatTree& position, Positi
onMoveType moveType) |
| 675 { | 675 { |
| 676 return previousPositionOfAlgorithm<EditingInFlatTreeStrategy>(position, move
Type); | 676 return previousPositionOfAlgorithm<EditingInFlatTreeStrategy>(position, move
Type); |
| 677 } | 677 } |
| 678 | 678 |
| 679 template <typename Strategy> | 679 template <typename Strategy> |
| 680 PositionTemplate<Strategy> nextPositionOfAlgorithm(const PositionTemplate<Strate
gy>& position, PositionMoveType moveType) | 680 PositionTemplate<Strategy> nextPositionOfAlgorithm(const PositionTemplate<Strate
gy>& position, PositionMoveType moveType) |
| 681 { | 681 { |
| 682 ASSERT(moveType != PositionMoveType::BackwardDeletion); | 682 // TODO(yosin): We should have printer for PositionMoveType. |
| 683 DCHECK(moveType != PositionMoveType::BackwardDeletion); |
| 683 | 684 |
| 684 Node* node = position.anchorNode(); | 685 Node* node = position.anchorNode(); |
| 685 if (!node) | 686 if (!node) |
| 686 return position; | 687 return position; |
| 687 | 688 |
| 688 const int offset = position.computeEditingOffset(); | 689 const int offset = position.computeEditingOffset(); |
| 689 | 690 |
| 690 if (Node* child = Strategy::childAt(*node, offset)) | 691 if (Node* child = Strategy::childAt(*node, offset)) |
| 691 return PositionTemplate<Strategy>::firstPositionInOrBeforeNode(child); | 692 return PositionTemplate<Strategy>::firstPositionInOrBeforeNode(child); |
| 692 | 693 |
| (...skipping 143 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 836 | 837 |
| 837 if (previousCharacterWasSpace || (!i && startIsStartOfParagraph) || (i +
1 == length && endIsEndOfParagraph)) { | 838 if (previousCharacterWasSpace || (!i && startIsStartOfParagraph) || (i +
1 == length && endIsEndOfParagraph)) { |
| 838 rebalancedString.append(noBreakSpaceCharacter); | 839 rebalancedString.append(noBreakSpaceCharacter); |
| 839 previousCharacterWasSpace = false; | 840 previousCharacterWasSpace = false; |
| 840 } else { | 841 } else { |
| 841 rebalancedString.append(' '); | 842 rebalancedString.append(' '); |
| 842 previousCharacterWasSpace = true; | 843 previousCharacterWasSpace = true; |
| 843 } | 844 } |
| 844 } | 845 } |
| 845 | 846 |
| 846 ASSERT(rebalancedString.length() == length); | 847 DCHECK_EQ(rebalancedString.length(), length); |
| 847 | 848 |
| 848 return rebalancedString.toString(); | 849 return rebalancedString.toString(); |
| 849 } | 850 } |
| 850 | 851 |
| 851 bool isTableStructureNode(const Node *node) | 852 bool isTableStructureNode(const Node *node) |
| 852 { | 853 { |
| 853 LayoutObject* layoutObject = node->layoutObject(); | 854 LayoutObject* layoutObject = node->layoutObject(); |
| 854 return (layoutObject && (layoutObject->isTableCell() || layoutObject->isTabl
eRow() || layoutObject->isTableSection() || layoutObject->isLayoutTableCol())); | 855 return (layoutObject && (layoutObject->isTableCell() || layoutObject->isTabl
eRow() || layoutObject->isTableSection() || layoutObject->isLayoutTableCol())); |
| 855 } | 856 } |
| 856 | 857 |
| (...skipping 159 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1016 node = nextNodeConsideringAtomicNodes(*node); | 1017 node = nextNodeConsideringAtomicNodes(*node); |
| 1017 } | 1018 } |
| 1018 return nullptr; | 1019 return nullptr; |
| 1019 } | 1020 } |
| 1020 | 1021 |
| 1021 // Returns the visible position at the beginning of a node | 1022 // Returns the visible position at the beginning of a node |
| 1022 VisiblePosition visiblePositionBeforeNode(Node& node) | 1023 VisiblePosition visiblePositionBeforeNode(Node& node) |
| 1023 { | 1024 { |
| 1024 if (node.hasChildren()) | 1025 if (node.hasChildren()) |
| 1025 return createVisiblePosition(firstPositionInOrBeforeNode(&node)); | 1026 return createVisiblePosition(firstPositionInOrBeforeNode(&node)); |
| 1026 ASSERT(node.parentNode()); | 1027 DCHECK(node.parentNode()) << node; |
| 1027 ASSERT(!node.parentNode()->isShadowRoot()); | 1028 DCHECK(!node.parentNode()->isShadowRoot()) << node.parentNode(); |
| 1028 return createVisiblePosition(positionInParentBeforeNode(node)); | 1029 return createVisiblePosition(positionInParentBeforeNode(node)); |
| 1029 } | 1030 } |
| 1030 | 1031 |
| 1031 // Returns the visible position at the ending of a node | 1032 // Returns the visible position at the ending of a node |
| 1032 VisiblePosition visiblePositionAfterNode(Node& node) | 1033 VisiblePosition visiblePositionAfterNode(Node& node) |
| 1033 { | 1034 { |
| 1034 if (node.hasChildren()) | 1035 if (node.hasChildren()) |
| 1035 return createVisiblePosition(lastPositionInOrAfterNode(&node)); | 1036 return createVisiblePosition(lastPositionInOrAfterNode(&node)); |
| 1036 ASSERT(node.parentNode()); | 1037 DCHECK(node.parentNode()) << node.parentNode(); |
| 1037 ASSERT(!node.parentNode()->isShadowRoot()); | 1038 DCHECK(!node.parentNode()->isShadowRoot()) << node.parentNode(); |
| 1038 return createVisiblePosition(positionInParentAfterNode(node)); | 1039 return createVisiblePosition(positionInParentAfterNode(node)); |
| 1039 } | 1040 } |
| 1040 | 1041 |
| 1041 bool isHTMLListElement(Node* n) | 1042 bool isHTMLListElement(Node* n) |
| 1042 { | 1043 { |
| 1043 return (n && (isHTMLUListElement(*n) || isHTMLOListElement(*n) || isHTMLDLis
tElement(*n))); | 1044 return (n && (isHTMLUListElement(*n) || isHTMLOListElement(*n) || isHTMLDLis
tElement(*n))); |
| 1044 } | 1045 } |
| 1045 | 1046 |
| 1046 bool isListItem(const Node* n) | 1047 bool isListItem(const Node* n) |
| 1047 { | 1048 { |
| (...skipping 25 matching lines...) Expand all Loading... |
| 1073 return 0; | 1074 return 0; |
| 1074 } | 1075 } |
| 1075 | 1076 |
| 1076 return 0; | 1077 return 0; |
| 1077 } | 1078 } |
| 1078 | 1079 |
| 1079 template <typename Strategy> | 1080 template <typename Strategy> |
| 1080 static Node* enclosingNodeOfTypeAlgorithm(const PositionTemplate<Strategy>& p, b
ool (*nodeIsOfType)(const Node*), EditingBoundaryCrossingRule rule) | 1081 static Node* enclosingNodeOfTypeAlgorithm(const PositionTemplate<Strategy>& p, b
ool (*nodeIsOfType)(const Node*), EditingBoundaryCrossingRule rule) |
| 1081 { | 1082 { |
| 1082 // TODO(yosin) support CanSkipCrossEditingBoundary | 1083 // TODO(yosin) support CanSkipCrossEditingBoundary |
| 1083 ASSERT(rule == CanCrossEditingBoundary || rule == CannotCrossEditingBoundary
); | 1084 DCHECK(rule == CanCrossEditingBoundary || rule == CannotCrossEditingBoundary
) << rule; |
| 1084 if (p.isNull()) | 1085 if (p.isNull()) |
| 1085 return nullptr; | 1086 return nullptr; |
| 1086 | 1087 |
| 1087 ContainerNode* const root = rule == CannotCrossEditingBoundary ? highestEdit
ableRoot(p) : nullptr; | 1088 ContainerNode* const root = rule == CannotCrossEditingBoundary ? highestEdit
ableRoot(p) : nullptr; |
| 1088 for (Node* n = p.anchorNode(); n; n = Strategy::parent(*n)) { | 1089 for (Node* n = p.anchorNode(); n; n = Strategy::parent(*n)) { |
| 1089 // Don't return a non-editable node if the input position was editable,
since | 1090 // Don't return a non-editable node if the input position was editable,
since |
| 1090 // the callers from editing will no doubt want to perform editing inside
the returned node. | 1091 // the callers from editing will no doubt want to perform editing inside
the returned node. |
| 1091 if (root && !n->hasEditableStyle()) | 1092 if (root && !n->hasEditableStyle()) |
| 1092 continue; | 1093 continue; |
| 1093 if (nodeIsOfType(n)) | 1094 if (nodeIsOfType(n)) |
| (...skipping 167 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1261 { | 1262 { |
| 1262 if (!node || !node->isElementNode()) | 1263 if (!node || !node->isElementNode()) |
| 1263 return false; | 1264 return false; |
| 1264 | 1265 |
| 1265 LayoutObject* layoutObject = node->layoutObject(); | 1266 LayoutObject* layoutObject = node->layoutObject(); |
| 1266 return (layoutObject && layoutObject->isTable()); | 1267 return (layoutObject && layoutObject->isTable()); |
| 1267 } | 1268 } |
| 1268 | 1269 |
| 1269 bool isTableCell(const Node* node) | 1270 bool isTableCell(const Node* node) |
| 1270 { | 1271 { |
| 1271 ASSERT(node); | 1272 DCHECK(node); |
| 1272 LayoutObject* r = node->layoutObject(); | 1273 LayoutObject* r = node->layoutObject(); |
| 1273 return r ? r->isTableCell() : isHTMLTableCellElement(*node); | 1274 return r ? r->isTableCell() : isHTMLTableCellElement(*node); |
| 1274 } | 1275 } |
| 1275 | 1276 |
| 1276 bool isEmptyTableCell(const Node* node) | 1277 bool isEmptyTableCell(const Node* node) |
| 1277 { | 1278 { |
| 1278 // Returns true IFF the passed in node is one of: | 1279 // Returns true IFF the passed in node is one of: |
| 1279 // .) a table cell with no children, | 1280 // .) a table cell with no children, |
| 1280 // .) a table cell with a single BR child, and which has no other child la
youtObject, including :before and :after layoutObject | 1281 // .) a table cell with a single BR child, and which has no other child la
youtObject, including :before and :after layoutObject |
| 1281 // .) the BR child of such a table cell | 1282 // .) the BR child of such a table cell |
| (...skipping 123 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1405 return currentPos; | 1406 return currentPos; |
| 1406 } | 1407 } |
| 1407 } | 1408 } |
| 1408 | 1409 |
| 1409 return position; | 1410 return position; |
| 1410 } | 1411 } |
| 1411 | 1412 |
| 1412 // This assumes that it starts in editable content. | 1413 // This assumes that it starts in editable content. |
| 1413 Position leadingWhitespacePosition(const Position& position, TextAffinity affini
ty, WhitespacePositionOption option) | 1414 Position leadingWhitespacePosition(const Position& position, TextAffinity affini
ty, WhitespacePositionOption option) |
| 1414 { | 1415 { |
| 1415 ASSERT(isEditablePosition(position, ContentIsEditable, DoNotUpdateStyle)); | 1416 DCHECK(isEditablePosition(position, ContentIsEditable, DoNotUpdateStyle)) <<
position; |
| 1416 if (position.isNull()) | 1417 if (position.isNull()) |
| 1417 return Position(); | 1418 return Position(); |
| 1418 | 1419 |
| 1419 if (isHTMLBRElement(*mostBackwardCaretPosition(position).anchorNode())) | 1420 if (isHTMLBRElement(*mostBackwardCaretPosition(position).anchorNode())) |
| 1420 return Position(); | 1421 return Position(); |
| 1421 | 1422 |
| 1422 const Position& prev = previousCharacterPosition(position, affinity); | 1423 const Position& prev = previousCharacterPosition(position, affinity); |
| 1423 if (prev == position) | 1424 if (prev == position) |
| 1424 return Position(); | 1425 return Position(); |
| 1425 const Node* const anchorNode = prev.anchorNode(); | 1426 const Node* const anchorNode = prev.anchorNode(); |
| 1426 if (!anchorNode || !anchorNode->isTextNode()) | 1427 if (!anchorNode || !anchorNode->isTextNode()) |
| 1427 return Position(); | 1428 return Position(); |
| 1428 if (enclosingBlockFlowElement(*anchorNode) != enclosingBlockFlowElement(*pos
ition.anchorNode())) | 1429 if (enclosingBlockFlowElement(*anchorNode) != enclosingBlockFlowElement(*pos
ition.anchorNode())) |
| 1429 return Position(); | 1430 return Position(); |
| 1430 if (option == NotConsiderNonCollapsibleWhitespace && anchorNode->layoutObjec
t() && !anchorNode->layoutObject()->style()->collapseWhiteSpace()) | 1431 if (option == NotConsiderNonCollapsibleWhitespace && anchorNode->layoutObjec
t() && !anchorNode->layoutObject()->style()->collapseWhiteSpace()) |
| 1431 return Position(); | 1432 return Position(); |
| 1432 const String& string = toText(anchorNode)->data(); | 1433 const String& string = toText(anchorNode)->data(); |
| 1433 const UChar previousCharacter = string[prev.computeOffsetInContainerNode()]; | 1434 const UChar previousCharacter = string[prev.computeOffsetInContainerNode()]; |
| 1434 const bool isSpace = option == ConsiderNonCollapsibleWhitespace ? (isSpaceOr
Newline(previousCharacter) || previousCharacter == noBreakSpaceCharacter) : isCo
llapsibleWhitespace(previousCharacter); | 1435 const bool isSpace = option == ConsiderNonCollapsibleWhitespace ? (isSpaceOr
Newline(previousCharacter) || previousCharacter == noBreakSpaceCharacter) : isCo
llapsibleWhitespace(previousCharacter); |
| 1435 if (!isSpace || !isEditablePosition(prev)) | 1436 if (!isSpace || !isEditablePosition(prev)) |
| 1436 return Position(); | 1437 return Position(); |
| 1437 return prev; | 1438 return prev; |
| 1438 } | 1439 } |
| 1439 | 1440 |
| 1440 // This assumes that it starts in editable content. | 1441 // This assumes that it starts in editable content. |
| 1441 Position trailingWhitespacePosition(const Position& position, TextAffinity, Whit
espacePositionOption option) | 1442 Position trailingWhitespacePosition(const Position& position, TextAffinity, Whit
espacePositionOption option) |
| 1442 { | 1443 { |
| 1443 ASSERT(isEditablePosition(position, ContentIsEditable, DoNotUpdateStyle)); | 1444 DCHECK(isEditablePosition(position, ContentIsEditable, DoNotUpdateStyle)) <<
position; |
| 1444 if (position.isNull()) | 1445 if (position.isNull()) |
| 1445 return Position(); | 1446 return Position(); |
| 1446 | 1447 |
| 1447 VisiblePosition visiblePosition = createVisiblePosition(position); | 1448 VisiblePosition visiblePosition = createVisiblePosition(position); |
| 1448 UChar characterAfterVisiblePosition = characterAfter(visiblePosition); | 1449 UChar characterAfterVisiblePosition = characterAfter(visiblePosition); |
| 1449 bool isSpace = option == ConsiderNonCollapsibleWhitespace ? (isSpaceOrNewlin
e(characterAfterVisiblePosition) || characterAfterVisiblePosition == noBreakSpac
eCharacter) : isCollapsibleWhitespace(characterAfterVisiblePosition); | 1450 bool isSpace = option == ConsiderNonCollapsibleWhitespace ? (isSpaceOrNewlin
e(characterAfterVisiblePosition) || characterAfterVisiblePosition == noBreakSpac
eCharacter) : isCollapsibleWhitespace(characterAfterVisiblePosition); |
| 1450 // The space must not be in another paragraph and it must be editable. | 1451 // The space must not be in another paragraph and it must be editable. |
| 1451 if (isSpace && !isEndOfParagraph(visiblePosition) && nextPositionOf(visibleP
osition, CannotCrossEditingBoundary).isNotNull()) | 1452 if (isSpace && !isEndOfParagraph(visiblePosition) && nextPositionOf(visibleP
osition, CannotCrossEditingBoundary).isNotNull()) |
| 1452 return position; | 1453 return position; |
| 1453 return Position(); | 1454 return Position(); |
| (...skipping 136 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1590 Position e = end.deepEquivalent().parentAnchoredEquivalent(); | 1591 Position e = end.deepEquivalent().parentAnchoredEquivalent(); |
| 1591 if (s.isNull() || e.isNull()) | 1592 if (s.isNull() || e.isNull()) |
| 1592 return EphemeralRange(); | 1593 return EphemeralRange(); |
| 1593 | 1594 |
| 1594 return EphemeralRange(s, e); | 1595 return EphemeralRange(s, e); |
| 1595 } | 1596 } |
| 1596 | 1597 |
| 1597 template <typename Strategy> | 1598 template <typename Strategy> |
| 1598 static EphemeralRangeTemplate<Strategy> normalizeRangeAlgorithm(const EphemeralR
angeTemplate<Strategy>& range) | 1599 static EphemeralRangeTemplate<Strategy> normalizeRangeAlgorithm(const EphemeralR
angeTemplate<Strategy>& range) |
| 1599 { | 1600 { |
| 1600 ASSERT(range.isNotNull()); | 1601 DCHECK(range.isNotNull()); |
| 1601 range.document().updateLayoutIgnorePendingStylesheets(); | 1602 range.document().updateLayoutIgnorePendingStylesheets(); |
| 1602 | 1603 |
| 1603 // TODO(yosin) We should not call |parentAnchoredEquivalent()|, it is | 1604 // TODO(yosin) We should not call |parentAnchoredEquivalent()|, it is |
| 1604 // redundant. | 1605 // redundant. |
| 1605 const PositionTemplate<Strategy> normalizedStart = mostForwardCaretPosition(
range.startPosition()).parentAnchoredEquivalent(); | 1606 const PositionTemplate<Strategy> normalizedStart = mostForwardCaretPosition(
range.startPosition()).parentAnchoredEquivalent(); |
| 1606 const PositionTemplate<Strategy> normalizedEnd = mostBackwardCaretPosition(r
ange.endPosition()).parentAnchoredEquivalent(); | 1607 const PositionTemplate<Strategy> normalizedEnd = mostBackwardCaretPosition(r
ange.endPosition()).parentAnchoredEquivalent(); |
| 1607 // The order of the positions of |start| and |end| can be swapped after | 1608 // The order of the positions of |start| and |end| can be swapped after |
| 1608 // upstream/downstream. e.g. editing/pasteboard/copy-display-none.html | 1609 // upstream/downstream. e.g. editing/pasteboard/copy-display-none.html |
| 1609 if (normalizedStart.compareTo(normalizedEnd) > 0) | 1610 if (normalizedStart.compareTo(normalizedEnd) > 0) |
| 1610 return EphemeralRangeTemplate<Strategy>(normalizedEnd, normalizedStart); | 1611 return EphemeralRangeTemplate<Strategy>(normalizedEnd, normalizedStart); |
| (...skipping 114 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1725 // instead of possibly at the end of the last node before the selection | 1726 // instead of possibly at the end of the last node before the selection |
| 1726 return mostForwardCaretPosition(visiblePosition.deepEquivalent()); | 1727 return mostForwardCaretPosition(visiblePosition.deepEquivalent()); |
| 1727 } | 1728 } |
| 1728 | 1729 |
| 1729 bool isTextSecurityNode(const Node* node) | 1730 bool isTextSecurityNode(const Node* node) |
| 1730 { | 1731 { |
| 1731 return node && node->layoutObject() && node->layoutObject()->style()->textSe
curity() != TSNONE; | 1732 return node && node->layoutObject() && node->layoutObject()->style()->textSe
curity() != TSNONE; |
| 1732 } | 1733 } |
| 1733 | 1734 |
| 1734 } // namespace blink | 1735 } // namespace blink |
| OLD | NEW |