Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(2)

Side by Side Diff: third_party/WebKit/Source/core/editing/commands/ApplyStyleCommand.cpp

Issue 1878473002: ASSERT -> DCHECK in core/editing. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Rebase. Created 4 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2005, 2006, 2008, 2009 Apple Inc. All rights reserved. 2 * Copyright (C) 2005, 2006, 2008, 2009 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 68 matching lines...) Expand 10 before | Expand all | Expand 10 after
79 if (attributes.isEmpty()) 79 if (attributes.isEmpty())
80 return true; 80 return true;
81 81
82 unsigned matchedAttributes = 0; 82 unsigned matchedAttributes = 0;
83 if (element->getAttribute(classAttr) == styleSpanClassString()) 83 if (element->getAttribute(classAttr) == styleSpanClassString())
84 matchedAttributes++; 84 matchedAttributes++;
85 if (element->hasAttribute(styleAttr) && (shouldStyleAttributeBeEmpty == Allo wNonEmptyStyleAttribute 85 if (element->hasAttribute(styleAttr) && (shouldStyleAttributeBeEmpty == Allo wNonEmptyStyleAttribute
86 || !element->inlineStyle() || element->inlineStyle()->isEmpty())) 86 || !element->inlineStyle() || element->inlineStyle()->isEmpty()))
87 matchedAttributes++; 87 matchedAttributes++;
88 88
89 ASSERT(matchedAttributes <= attributes.size()); 89 DCHECK_LE(matchedAttributes, attributes.size());
90 return matchedAttributes == attributes.size(); 90 return matchedAttributes == attributes.size();
91 } 91 }
92 92
93 bool isStyleSpanOrSpanWithOnlyStyleAttribute(const Element* element) 93 bool isStyleSpanOrSpanWithOnlyStyleAttribute(const Element* element)
94 { 94 {
95 if (!isHTMLSpanElement(element)) 95 if (!isHTMLSpanElement(element))
96 return false; 96 return false;
97 return hasNoAttributeOrOnlyStyleAttribute(toHTMLSpanElement(element), AllowN onEmptyStyleAttribute); 97 return hasNoAttributeOrOnlyStyleAttribute(toHTMLSpanElement(element), AllowN onEmptyStyleAttribute);
98 } 98 }
99 99
(...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after
163 , m_end(mostBackwardCaretPosition(endingSelection().end())) 163 , m_end(mostBackwardCaretPosition(endingSelection().end()))
164 , m_useEndingSelection(true) 164 , m_useEndingSelection(true)
165 , m_styledInlineElement(nullptr) 165 , m_styledInlineElement(nullptr)
166 , m_removeOnly(true) 166 , m_removeOnly(true)
167 , m_isInlineElementToRemoveFunction(isInlineElementToRemoveFunction) 167 , m_isInlineElementToRemoveFunction(isInlineElementToRemoveFunction)
168 { 168 {
169 } 169 }
170 170
171 void ApplyStyleCommand::updateStartEnd(const Position& newStart, const Position& newEnd) 171 void ApplyStyleCommand::updateStartEnd(const Position& newStart, const Position& newEnd)
172 { 172 {
173 ASSERT(comparePositions(newEnd, newStart) >= 0); 173 DCHECK_GE(comparePositions(newEnd, newStart), 0);
174 174
175 if (!m_useEndingSelection && (newStart != m_start || newEnd != m_end)) 175 if (!m_useEndingSelection && (newStart != m_start || newEnd != m_end))
176 m_useEndingSelection = true; 176 m_useEndingSelection = true;
177 177
178 setEndingSelection(VisibleSelection(newStart, newEnd, VP_DEFAULT_AFFINITY, e ndingSelection().isDirectional())); 178 setEndingSelection(VisibleSelection(newStart, newEnd, VP_DEFAULT_AFFINITY, e ndingSelection().isDirectional()));
179 m_start = newStart; 179 m_start = newStart;
180 m_end = newEnd; 180 m_end = newEnd;
181 } 181 }
182 182
183 Position ApplyStyleCommand::startPosition() 183 Position ApplyStyleCommand::startPosition()
(...skipping 168 matching lines...) Expand 10 before | Expand all | Expand 10 after
352 if (isValidCaretPositionInTextNode(end)) { 352 if (isValidCaretPositionInTextNode(end)) {
353 splitTextAtEnd(start, end); 353 splitTextAtEnd(start, end);
354 start = startPosition(); 354 start = startPosition();
355 end = endPosition(); 355 end = endPosition();
356 } 356 }
357 357
358 // Calculate loop end point. 358 // Calculate loop end point.
359 // If the end node is before the start node (can only happen if the end node is 359 // If the end node is before the start node (can only happen if the end node is
360 // an ancestor of the start node), we gather nodes up to the next sibling of the end node 360 // an ancestor of the start node), we gather nodes up to the next sibling of the end node
361 Node* beyondEnd; 361 Node* beyondEnd;
362 ASSERT(start.anchorNode()); 362 DCHECK(start.anchorNode());
363 ASSERT(end.anchorNode()); 363 DCHECK(end.anchorNode());
364 if (start.anchorNode()->isDescendantOf(end.anchorNode())) 364 if (start.anchorNode()->isDescendantOf(end.anchorNode()))
365 beyondEnd = NodeTraversal::nextSkippingChildren(*end.anchorNode()); 365 beyondEnd = NodeTraversal::nextSkippingChildren(*end.anchorNode());
366 else 366 else
367 beyondEnd = NodeTraversal::next(*end.anchorNode()); 367 beyondEnd = NodeTraversal::next(*end.anchorNode());
368 368
369 start = mostBackwardCaretPosition(start); // Move upstream to ensure we do n ot add redundant spans. 369 start = mostBackwardCaretPosition(start); // Move upstream to ensure we do n ot add redundant spans.
370 Node* startNode = start.anchorNode(); 370 Node* startNode = start.anchorNode();
371 ASSERT(startNode); 371 DCHECK(startNode);
372 372
373 // Make sure we're not already at the end or the next NodeTraversal::next() will traverse 373 // Make sure we're not already at the end or the next NodeTraversal::next() will traverse
374 // past it. 374 // past it.
375 if (startNode == beyondEnd) 375 if (startNode == beyondEnd)
376 return; 376 return;
377 377
378 if (startNode->isTextNode() && start.computeOffsetInContainerNode() >= caret MaxOffset(startNode)) { 378 if (startNode->isTextNode() && start.computeOffsetInContainerNode() >= caret MaxOffset(startNode)) {
379 // Move out of text node if range does not include its characters. 379 // Move out of text node if range does not include its characters.
380 startNode = NodeTraversal::next(*startNode); 380 startNode = NodeTraversal::next(*startNode);
381 if (!startNode) 381 if (!startNode)
382 return; 382 return;
383 } 383 }
384 384
385 // Store away font size before making any changes to the document. 385 // Store away font size before making any changes to the document.
386 // This ensures that changes to one node won't effect another. 386 // This ensures that changes to one node won't effect another.
387 HeapHashMap<Member<Node>, float> startingFontSizes; 387 HeapHashMap<Member<Node>, float> startingFontSizes;
388 for (Node* node = startNode; node != beyondEnd; node = NodeTraversal::next(* node)) { 388 for (Node* node = startNode; node != beyondEnd; node = NodeTraversal::next(* node)) {
389 ASSERT(node); 389 DCHECK(node);
390 startingFontSizes.set(node, computedFontSize(node)); 390 startingFontSizes.set(node, computedFontSize(node));
391 } 391 }
392 392
393 // These spans were added by us. If empty after font size changes, they can be removed. 393 // These spans were added by us. If empty after font size changes, they can be removed.
394 HeapVector<Member<HTMLElement>> unstyledSpans; 394 HeapVector<Member<HTMLElement>> unstyledSpans;
395 395
396 Node* lastStyledNode = nullptr; 396 Node* lastStyledNode = nullptr;
397 for (Node* node = startNode; node != beyondEnd; node = NodeTraversal::next(* node)) { 397 for (Node* node = startNode; node != beyondEnd; node = NodeTraversal::next(* node)) {
398 ASSERT(node); 398 DCHECK(node);
399 HTMLElement* element = nullptr; 399 HTMLElement* element = nullptr;
400 if (node->isHTMLElement()) { 400 if (node->isHTMLElement()) {
401 // Only work on fully selected nodes. 401 // Only work on fully selected nodes.
402 if (!elementFullySelected(toHTMLElement(*node), start, end)) 402 if (!elementFullySelected(toHTMLElement(*node), start, end))
403 continue; 403 continue;
404 element = toHTMLElement(node); 404 element = toHTMLElement(node);
405 } else if (node->isTextNode() && node->layoutObject() && node->parentNod e() != lastStyledNode) { 405 } else if (node->isTextNode() && node->layoutObject() && node->parentNod e() != lastStyledNode) {
406 // Last styled node was not parent node of this text node, but we wi sh to style this 406 // Last styled node was not parent node of this text node, but we wi sh to style this
407 // text node. To make this possible, add a style span to surround th is text node. 407 // text node. To make this possible, add a style span to surround th is text node.
408 HTMLSpanElement* span = HTMLSpanElement::create(document()); 408 HTMLSpanElement* span = HTMLSpanElement::create(document());
(...skipping 287 matching lines...) Expand 10 before | Expand all | Expand 10 after
696 696
697 EditingStyle* styleToApply = style; 697 EditingStyle* styleToApply = style;
698 if (hasTextDirection) { 698 if (hasTextDirection) {
699 // Avoid applying the unicode-bidi and direction properties beneath ance stors that already have them. 699 // Avoid applying the unicode-bidi and direction properties beneath ance stors that already have them.
700 HTMLElement* embeddingStartElement = highestEmbeddingAncestor(start.anch orNode(), enclosingBlock(start.anchorNode())); 700 HTMLElement* embeddingStartElement = highestEmbeddingAncestor(start.anch orNode(), enclosingBlock(start.anchorNode()));
701 HTMLElement* embeddingEndElement = highestEmbeddingAncestor(end.anchorNo de(), enclosingBlock(end.anchorNode())); 701 HTMLElement* embeddingEndElement = highestEmbeddingAncestor(end.anchorNo de(), enclosingBlock(end.anchorNode()));
702 702
703 if (embeddingStartElement || embeddingEndElement) { 703 if (embeddingStartElement || embeddingEndElement) {
704 Position embeddingApplyStart = embeddingStartElement ? positionInPar entAfterNode(*embeddingStartElement) : start; 704 Position embeddingApplyStart = embeddingStartElement ? positionInPar entAfterNode(*embeddingStartElement) : start;
705 Position embeddingApplyEnd = embeddingEndElement ? positionInParentB eforeNode(*embeddingEndElement) : end; 705 Position embeddingApplyEnd = embeddingEndElement ? positionInParentB eforeNode(*embeddingEndElement) : end;
706 ASSERT(embeddingApplyStart.isNotNull() && embeddingApplyEnd.isNotNul l()); 706 DCHECK(embeddingApplyStart.isNotNull());
707 DCHECK(embeddingApplyEnd.isNotNull());
707 708
708 if (!embeddingStyle) { 709 if (!embeddingStyle) {
709 styleWithoutEmbedding = style->copy(); 710 styleWithoutEmbedding = style->copy();
710 embeddingStyle = styleWithoutEmbedding->extractAndRemoveTextDire ction(); 711 embeddingStyle = styleWithoutEmbedding->extractAndRemoveTextDire ction();
711 } 712 }
712 fixRangeAndApplyInlineStyle(embeddingStyle, embeddingApplyStart, emb eddingApplyEnd, editingState); 713 fixRangeAndApplyInlineStyle(embeddingStyle, embeddingApplyStart, emb eddingApplyEnd, editingState);
713 if (editingState->isAborted()) 714 if (editingState->isAborted())
714 return; 715 return;
715 716
716 styleToApply = styleWithoutEmbedding; 717 styleToApply = styleWithoutEmbedding;
717 } 718 }
718 } 719 }
719 720
720 fixRangeAndApplyInlineStyle(styleToApply, start, end, editingState); 721 fixRangeAndApplyInlineStyle(styleToApply, start, end, editingState);
721 if (editingState->isAborted()) 722 if (editingState->isAborted())
722 return; 723 return;
723 724
724 // Remove dummy style spans created by splitting text elements. 725 // Remove dummy style spans created by splitting text elements.
725 cleanupUnstyledAppleStyleSpans(startDummySpanAncestor, editingState); 726 cleanupUnstyledAppleStyleSpans(startDummySpanAncestor, editingState);
726 if (editingState->isAborted()) 727 if (editingState->isAborted())
727 return; 728 return;
728 if (endDummySpanAncestor != startDummySpanAncestor) 729 if (endDummySpanAncestor != startDummySpanAncestor)
729 cleanupUnstyledAppleStyleSpans(endDummySpanAncestor, editingState); 730 cleanupUnstyledAppleStyleSpans(endDummySpanAncestor, editingState);
730 } 731 }
731 732
732 void ApplyStyleCommand::fixRangeAndApplyInlineStyle(EditingStyle* style, const P osition& start, const Position& end, EditingState* editingState) 733 void ApplyStyleCommand::fixRangeAndApplyInlineStyle(EditingStyle* style, const P osition& start, const Position& end, EditingState* editingState)
733 { 734 {
734 Node* startNode = start.anchorNode(); 735 Node* startNode = start.anchorNode();
735 ASSERT(startNode); 736 DCHECK(startNode);
736 737
737 if (start.computeEditingOffset() >= caretMaxOffset(start.anchorNode())) { 738 if (start.computeEditingOffset() >= caretMaxOffset(start.anchorNode())) {
738 startNode = NodeTraversal::next(*startNode); 739 startNode = NodeTraversal::next(*startNode);
739 if (!startNode || comparePositions(end, firstPositionInOrBeforeNode(star tNode)) < 0) 740 if (!startNode || comparePositions(end, firstPositionInOrBeforeNode(star tNode)) < 0)
740 return; 741 return;
741 } 742 }
742 743
743 Node* pastEndNode = end.anchorNode(); 744 Node* pastEndNode = end.anchorNode();
744 if (end.computeEditingOffset() >= caretMaxOffset(end.anchorNode())) 745 if (end.computeEditingOffset() >= caretMaxOffset(end.anchorNode()))
745 pastEndNode = NodeTraversal::nextSkippingChildren(*end.anchorNode()); 746 pastEndNode = NodeTraversal::nextSkippingChildren(*end.anchorNode());
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
777 } 778 }
778 779
779 class InlineRunToApplyStyle { 780 class InlineRunToApplyStyle {
780 DISALLOW_NEW_EXCEPT_PLACEMENT_NEW(); 781 DISALLOW_NEW_EXCEPT_PLACEMENT_NEW();
781 public: 782 public:
782 InlineRunToApplyStyle(Node* start, Node* end, Node* pastEndNode) 783 InlineRunToApplyStyle(Node* start, Node* end, Node* pastEndNode)
783 : start(start) 784 : start(start)
784 , end(end) 785 , end(end)
785 , pastEndNode(pastEndNode) 786 , pastEndNode(pastEndNode)
786 { 787 {
787 ASSERT(start->parentNode() == end->parentNode()); 788 DCHECK_EQ(start->parentNode(), end->parentNode());
788 } 789 }
789 790
790 bool startAndEndAreStillInDocument() 791 bool startAndEndAreStillInDocument()
791 { 792 {
792 return start && end && start->inShadowIncludingDocument() && end->inShad owIncludingDocument(); 793 return start && end && start->inShadowIncludingDocument() && end->inShad owIncludingDocument();
793 } 794 }
794 795
795 DEFINE_INLINE_TRACE() 796 DEFINE_INLINE_TRACE()
796 { 797 {
797 visitor->trace(start); 798 visitor->trace(start);
(...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after
861 862
862 Node* runStart = node; 863 Node* runStart = node;
863 Node* runEnd = node; 864 Node* runEnd = node;
864 Node* sibling = node->nextSibling(); 865 Node* sibling = node->nextSibling();
865 while (sibling && sibling != pastEndNode && !sibling->contains(pastEndNo de) 866 while (sibling && sibling != pastEndNode && !sibling->contains(pastEndNo de)
866 && (!isEnclosingBlock(sibling) || isHTMLBRElement(*sibling)) 867 && (!isEnclosingBlock(sibling) || isHTMLBRElement(*sibling))
867 && !containsNonEditableRegion(*sibling)) { 868 && !containsNonEditableRegion(*sibling)) {
868 runEnd = sibling; 869 runEnd = sibling;
869 sibling = runEnd->nextSibling(); 870 sibling = runEnd->nextSibling();
870 } 871 }
871 ASSERT(runEnd); 872 DCHECK(runEnd);
872 next = NodeTraversal::nextSkippingChildren(*runEnd); 873 next = NodeTraversal::nextSkippingChildren(*runEnd);
873 874
874 Node* pastEndNode = NodeTraversal::nextSkippingChildren(*runEnd); 875 Node* pastEndNode = NodeTraversal::nextSkippingChildren(*runEnd);
875 if (!shouldApplyInlineStyleToRun(style, runStart, pastEndNode)) 876 if (!shouldApplyInlineStyleToRun(style, runStart, pastEndNode))
876 continue; 877 continue;
877 878
878 runs.append(InlineRunToApplyStyle(runStart, runEnd, pastEndNode)); 879 runs.append(InlineRunToApplyStyle(runStart, runEnd, pastEndNode));
879 } 880 }
880 881
881 for (auto& run : runs) { 882 for (auto& run : runs) {
(...skipping 29 matching lines...) Expand all
911 } 912 }
912 913
913 bool ApplyStyleCommand::isStyledInlineElementToRemove(Element* element) const 914 bool ApplyStyleCommand::isStyledInlineElementToRemove(Element* element) const
914 { 915 {
915 return (m_styledInlineElement && element->hasTagName(m_styledInlineElement-> tagQName())) 916 return (m_styledInlineElement && element->hasTagName(m_styledInlineElement-> tagQName()))
916 || (m_isInlineElementToRemoveFunction && m_isInlineElementToRemoveFuncti on(element)); 917 || (m_isInlineElementToRemoveFunction && m_isInlineElementToRemoveFuncti on(element));
917 } 918 }
918 919
919 bool ApplyStyleCommand::shouldApplyInlineStyleToRun(EditingStyle* style, Node* r unStart, Node* pastEndNode) 920 bool ApplyStyleCommand::shouldApplyInlineStyleToRun(EditingStyle* style, Node* r unStart, Node* pastEndNode)
920 { 921 {
921 ASSERT(style && runStart); 922 DCHECK(style);
923 DCHECK(runStart);
922 924
923 for (Node* node = runStart; node && node != pastEndNode; node = NodeTraversa l::next(*node)) { 925 for (Node* node = runStart; node && node != pastEndNode; node = NodeTraversa l::next(*node)) {
924 if (node->hasChildren()) 926 if (node->hasChildren())
925 continue; 927 continue;
926 // We don't consider m_isInlineElementToRemoveFunction here because we n ever apply style when m_isInlineElementToRemoveFunction is specified 928 // We don't consider m_isInlineElementToRemoveFunction here because we n ever apply style when m_isInlineElementToRemoveFunction is specified
927 if (!style->styleIsPresentInComputedStyleOfNode(node)) 929 if (!style->styleIsPresentInComputedStyleOfNode(node))
928 return true; 930 return true;
929 if (m_styledInlineElement && !enclosingElementWithTag(positionBeforeNode (node), m_styledInlineElement->tagQName())) 931 if (m_styledInlineElement && !enclosingElementWithTag(positionBeforeNode (node), m_styledInlineElement->tagQName()))
930 return true; 932 return true;
931 } 933 }
932 return false; 934 return false;
933 } 935 }
934 936
935 void ApplyStyleCommand::removeConflictingInlineStyleFromRun(EditingStyle* style, Member<Node>& runStart, Member<Node>& runEnd, Node* pastEndNode, EditingState* editingState) 937 void ApplyStyleCommand::removeConflictingInlineStyleFromRun(EditingStyle* style, Member<Node>& runStart, Member<Node>& runEnd, Node* pastEndNode, EditingState* editingState)
936 { 938 {
937 ASSERT(runStart && runEnd); 939 DCHECK(runStart);
940 DCHECK(runEnd);
938 Node* next = runStart; 941 Node* next = runStart;
939 for (Node* node = next; node && node->inShadowIncludingDocument() && node != pastEndNode; node = next) { 942 for (Node* node = next; node && node->inShadowIncludingDocument() && node != pastEndNode; node = next) {
940 if (editingIgnoresContent(node)) { 943 if (editingIgnoresContent(node)) {
941 ASSERT(!node->contains(pastEndNode)); 944 DCHECK(!node->contains(pastEndNode));
yosin_UTC9 2016/04/14 04:35:01 How about adding |<< node << ' ' << pastEnd|?
942 next = NodeTraversal::nextSkippingChildren(*node); 945 next = NodeTraversal::nextSkippingChildren(*node);
943 } else { 946 } else {
944 next = NodeTraversal::next(*node); 947 next = NodeTraversal::next(*node);
945 } 948 }
946 if (!node->isHTMLElement()) 949 if (!node->isHTMLElement())
947 continue; 950 continue;
948 951
949 HTMLElement& element = toHTMLElement(*node); 952 HTMLElement& element = toHTMLElement(*node);
950 Node* previousSibling = element.previousSibling(); 953 Node* previousSibling = element.previousSibling();
951 Node* nextSibling = element.nextSibling(); 954 Node* nextSibling = element.nextSibling();
952 ContainerNode* parent = element.parentNode(); 955 ContainerNode* parent = element.parentNode();
953 removeInlineStyleFromElement(style, &element, editingState, RemoveAlways ); 956 removeInlineStyleFromElement(style, &element, editingState, RemoveAlways );
954 if (editingState->isAborted()) 957 if (editingState->isAborted())
955 return; 958 return;
956 if (!element.inShadowIncludingDocument()) { 959 if (!element.inShadowIncludingDocument()) {
957 // FIXME: We might need to update the start and the end of current s election here but need a test. 960 // FIXME: We might need to update the start and the end of current s election here but need a test.
958 if (runStart == element) 961 if (runStart == element)
959 runStart = previousSibling ? previousSibling->nextSibling() : pa rent->firstChild(); 962 runStart = previousSibling ? previousSibling->nextSibling() : pa rent->firstChild();
960 if (runEnd == element) 963 if (runEnd == element)
961 runEnd = nextSibling ? nextSibling->previousSibling() : parent-> lastChild(); 964 runEnd = nextSibling ? nextSibling->previousSibling() : parent-> lastChild();
962 } 965 }
963 } 966 }
964 } 967 }
965 968
966 bool ApplyStyleCommand::removeInlineStyleFromElement(EditingStyle* style, HTMLEl ement* element, EditingState* editingState, InlineStyleRemovalMode mode, Editing Style* extractedStyle) 969 bool ApplyStyleCommand::removeInlineStyleFromElement(EditingStyle* style, HTMLEl ement* element, EditingState* editingState, InlineStyleRemovalMode mode, Editing Style* extractedStyle)
967 { 970 {
968 ASSERT(element); 971 DCHECK(element);
969 972
970 if (!element->parentNode() || !element->parentNode()->isContentEditable(Node ::UserSelectAllIsAlwaysNonEditable)) 973 if (!element->parentNode() || !element->parentNode()->isContentEditable(Node ::UserSelectAllIsAlwaysNonEditable))
971 return false; 974 return false;
972 975
973 if (isStyledInlineElementToRemove(element)) { 976 if (isStyledInlineElementToRemove(element)) {
974 if (mode == RemoveNone) 977 if (mode == RemoveNone)
975 return true; 978 return true;
976 if (extractedStyle) 979 if (extractedStyle)
977 extractedStyle->mergeInlineStyleOfElement(element, EditingStyle::Ove rrideValues); 980 extractedStyle->mergeInlineStyleOfElement(element, EditingStyle::Ove rrideValues);
978 removeNodePreservingChildren(element, editingState); 981 removeNodePreservingChildren(element, editingState);
(...skipping 22 matching lines...) Expand all
1001 void ApplyStyleCommand::replaceWithSpanOrRemoveIfWithoutAttributes(HTMLElement* elem, EditingState* editingState) 1004 void ApplyStyleCommand::replaceWithSpanOrRemoveIfWithoutAttributes(HTMLElement* elem, EditingState* editingState)
1002 { 1005 {
1003 if (hasNoAttributeOrOnlyStyleAttribute(elem, StyleAttributeShouldBeEmpty)) 1006 if (hasNoAttributeOrOnlyStyleAttribute(elem, StyleAttributeShouldBeEmpty))
1004 removeNodePreservingChildren(elem, editingState); 1007 removeNodePreservingChildren(elem, editingState);
1005 else 1008 else
1006 replaceElementWithSpanPreservingChildrenAndAttributes(elem); 1009 replaceElementWithSpanPreservingChildrenAndAttributes(elem);
1007 } 1010 }
1008 1011
1009 bool ApplyStyleCommand::removeImplicitlyStyledElement(EditingStyle* style, HTMLE lement* element, InlineStyleRemovalMode mode, EditingStyle* extractedStyle, Edit ingState* editingState) 1012 bool ApplyStyleCommand::removeImplicitlyStyledElement(EditingStyle* style, HTMLE lement* element, InlineStyleRemovalMode mode, EditingStyle* extractedStyle, Edit ingState* editingState)
1010 { 1013 {
1011 ASSERT(style); 1014 DCHECK(style);
1012 if (mode == RemoveNone) { 1015 if (mode == RemoveNone) {
1013 ASSERT(!extractedStyle); 1016 DCHECK(!extractedStyle);
1014 return style->conflictsWithImplicitStyleOfElement(element) || style->con flictsWithImplicitStyleOfAttributes(element); 1017 return style->conflictsWithImplicitStyleOfElement(element) || style->con flictsWithImplicitStyleOfAttributes(element);
1015 } 1018 }
1016 1019
1017 ASSERT(mode == RemoveIfNeeded || mode == RemoveAlways); 1020 DCHECK(mode == RemoveIfNeeded || mode == RemoveAlways);
1018 if (style->conflictsWithImplicitStyleOfElement(element, extractedStyle, mode == RemoveAlways ? EditingStyle::ExtractMatchingStyle : EditingStyle::DoNotExtra ctMatchingStyle)) { 1021 if (style->conflictsWithImplicitStyleOfElement(element, extractedStyle, mode == RemoveAlways ? EditingStyle::ExtractMatchingStyle : EditingStyle::DoNotExtra ctMatchingStyle)) {
1019 replaceWithSpanOrRemoveIfWithoutAttributes(element, editingState); 1022 replaceWithSpanOrRemoveIfWithoutAttributes(element, editingState);
1020 if (editingState->isAborted()) 1023 if (editingState->isAborted())
1021 return false; 1024 return false;
1022 return true; 1025 return true;
1023 } 1026 }
1024 1027
1025 // unicode-bidi and direction are pushed down separately so don't push down with other styles 1028 // unicode-bidi and direction are pushed down separately so don't push down with other styles
1026 Vector<QualifiedName> attributes; 1029 Vector<QualifiedName> attributes;
1027 if (!style->extractConflictingImplicitStyleOfAttributes(element, extractedSt yle ? EditingStyle::PreserveWritingDirection : EditingStyle::DoNotPreserveWritin gDirection, 1030 if (!style->extractConflictingImplicitStyleOfAttributes(element, extractedSt yle ? EditingStyle::PreserveWritingDirection : EditingStyle::DoNotPreserveWritin gDirection,
1028 extractedStyle, attributes, mode == RemoveAlways ? EditingStyle::Extract MatchingStyle : EditingStyle::DoNotExtractMatchingStyle)) 1031 extractedStyle, attributes, mode == RemoveAlways ? EditingStyle::Extract MatchingStyle : EditingStyle::DoNotExtractMatchingStyle))
1029 return false; 1032 return false;
1030 1033
1031 for (const auto& attribute : attributes) 1034 for (const auto& attribute : attributes)
1032 removeElementAttribute(element, attribute); 1035 removeElementAttribute(element, attribute);
1033 1036
1034 if (isEmptyFontTag(element) || isSpanWithoutAttributesOrUnstyledStyleSpan(el ement)) { 1037 if (isEmptyFontTag(element) || isSpanWithoutAttributesOrUnstyledStyleSpan(el ement)) {
1035 removeNodePreservingChildren(element, editingState); 1038 removeNodePreservingChildren(element, editingState);
1036 if (editingState->isAborted()) 1039 if (editingState->isAborted())
1037 return false; 1040 return false;
1038 } 1041 }
1039 1042
1040 return true; 1043 return true;
1041 } 1044 }
1042 1045
1043 bool ApplyStyleCommand::removeCSSStyle(EditingStyle* style, HTMLElement* element , EditingState* editingState, InlineStyleRemovalMode mode, EditingStyle* extract edStyle) 1046 bool ApplyStyleCommand::removeCSSStyle(EditingStyle* style, HTMLElement* element , EditingState* editingState, InlineStyleRemovalMode mode, EditingStyle* extract edStyle)
1044 { 1047 {
1045 ASSERT(style); 1048 DCHECK(style);
1046 ASSERT(element); 1049 DCHECK(element);
1047 1050
1048 if (mode == RemoveNone) 1051 if (mode == RemoveNone)
1049 return style->conflictsWithInlineStyleOfElement(element); 1052 return style->conflictsWithInlineStyleOfElement(element);
1050 1053
1051 Vector<CSSPropertyID> properties; 1054 Vector<CSSPropertyID> properties;
1052 if (!style->conflictsWithInlineStyleOfElement(element, extractedStyle, prope rties)) 1055 if (!style->conflictsWithInlineStyleOfElement(element, extractedStyle, prope rties))
1053 return false; 1056 return false;
1054 1057
1055 // FIXME: We should use a mass-removal function here but we don't have an un doable one yet. 1058 // FIXME: We should use a mass-removal function here but we don't have an un doable one yet.
1056 for (const auto& property : properties) 1059 for (const auto& property : properties)
(...skipping 20 matching lines...) Expand all
1077 // also stop at the unsplittable element to be consistent with other UAs 1080 // also stop at the unsplittable element to be consistent with other UAs
1078 if (n == unsplittableElement) 1081 if (n == unsplittableElement)
1079 break; 1082 break;
1080 } 1083 }
1081 1084
1082 return result; 1085 return result;
1083 } 1086 }
1084 1087
1085 void ApplyStyleCommand::applyInlineStyleToPushDown(Node* node, EditingStyle* sty le, EditingState* editingState) 1088 void ApplyStyleCommand::applyInlineStyleToPushDown(Node* node, EditingStyle* sty le, EditingState* editingState)
1086 { 1089 {
1087 ASSERT(node); 1090 DCHECK(node);
1088 1091
1089 node->document().updateLayoutTree(); 1092 node->document().updateLayoutTree();
1090 1093
1091 if (!style || style->isEmpty() || !node->layoutObject() || isHTMLIFrameEleme nt(*node)) 1094 if (!style || style->isEmpty() || !node->layoutObject() || isHTMLIFrameEleme nt(*node))
1092 return; 1095 return;
1093 1096
1094 EditingStyle* newInlineStyle = style; 1097 EditingStyle* newInlineStyle = style;
1095 if (node->isHTMLElement() && toHTMLElement(node)->inlineStyle()) { 1098 if (node->isHTMLElement() && toHTMLElement(node)->inlineStyle()) {
1096 newInlineStyle = style->copy(); 1099 newInlineStyle = style->copy();
1097 newInlineStyle->mergeInlineStyleOfElement(toHTMLElement(node), EditingSt yle::OverrideValues); 1100 newInlineStyle->mergeInlineStyleOfElement(toHTMLElement(node), EditingSt yle::OverrideValues);
(...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after
1171 // We found the next node for the outer loop (contains targetNode) 1174 // We found the next node for the outer loop (contains targetNode)
1172 // When reached targetNode, stop the outer loop upon the completion of the current inner loop 1175 // When reached targetNode, stop the outer loop upon the completion of the current inner loop
1173 if (child == targetNode || child->contains(targetNode)) 1176 if (child == targetNode || child->contains(targetNode))
1174 current = child; 1177 current = child;
1175 } 1178 }
1176 } 1179 }
1177 } 1180 }
1178 1181
1179 void ApplyStyleCommand::removeInlineStyle(EditingStyle* style, const Position &s tart, const Position &end, EditingState* editingState) 1182 void ApplyStyleCommand::removeInlineStyle(EditingStyle* style, const Position &s tart, const Position &end, EditingState* editingState)
1180 { 1183 {
1181 ASSERT(start.isNotNull()); 1184 DCHECK(start.isNotNull());
1182 ASSERT(end.isNotNull()); 1185 DCHECK(end.isNotNull());
1183 ASSERT(start.inShadowIncludingDocument()); 1186 DCHECK(start.inShadowIncludingDocument());
yosin_UTC9 2016/04/14 04:35:01 How about adding |<< start|?
1184 ASSERT(end.inShadowIncludingDocument()); 1187 DCHECK(end.inShadowIncludingDocument());
yosin_UTC9 2016/04/14 04:35:01 How about adding |<< end|?
1185 ASSERT(Position::commonAncestorTreeScope(start, end)); 1188 DCHECK(Position::commonAncestorTreeScope(start, end));
yosin_UTC9 2016/04/14 04:35:01 How about adding |<< start << ' ' << end|?
1186 ASSERT(comparePositions(start, end) <= 0); 1189 DCHECK_LE(comparePositions(start, end), 0);
yosin_UTC9 2016/04/14 04:35:01 How about adding |<< start << ' ' << end|? Could y
1187 // FIXME: We should assert that start/end are not in the middle of a text no de. 1190 // FIXME: We should assert that start/end are not in the middle of a text no de.
1188 1191
1189 Position pushDownStart = mostForwardCaretPosition(start); 1192 Position pushDownStart = mostForwardCaretPosition(start);
1190 // If the pushDownStart is at the end of a text node, then this node is not fully selected. 1193 // If the pushDownStart is at the end of a text node, then this node is not fully selected.
1191 // Move it to the next deep quivalent position to avoid removing the style f rom this node. 1194 // Move it to the next deep quivalent position to avoid removing the style f rom this node.
1192 // e.g. if pushDownStart was at Position("hello", 5) in <b>hello<div>world</ div></b>, we want Position("world", 0) instead. 1195 // e.g. if pushDownStart was at Position("hello", 5) in <b>hello<div>world</ div></b>, we want Position("world", 0) instead.
1193 Node* pushDownStartContainer = pushDownStart.computeContainerNode(); 1196 Node* pushDownStartContainer = pushDownStart.computeContainerNode();
1194 if (pushDownStartContainer && pushDownStartContainer->isTextNode() 1197 if (pushDownStartContainer && pushDownStartContainer->isTextNode()
1195 && pushDownStart.computeOffsetInContainerNode() == pushDownStartContaine r->maxCharacterOffset()) 1198 && pushDownStart.computeOffsetInContainerNode() == pushDownStartContaine r->maxCharacterOffset())
1196 pushDownStart = nextVisuallyDistinctCandidate(pushDownStart); 1199 pushDownStart = nextVisuallyDistinctCandidate(pushDownStart);
(...skipping 21 matching lines...) Expand all
1218 1221
1219 // Current ending selection resetting algorithm assumes |start| and |end| 1222 // Current ending selection resetting algorithm assumes |start| and |end|
1220 // are in a same DOM tree even if they are not in document. 1223 // are in a same DOM tree even if they are not in document.
1221 if (!Position::commonAncestorTreeScope(start, end)) 1224 if (!Position::commonAncestorTreeScope(start, end))
1222 return; 1225 return;
1223 1226
1224 Node* node = start.anchorNode(); 1227 Node* node = start.anchorNode();
1225 while (node) { 1228 while (node) {
1226 Node* next = nullptr; 1229 Node* next = nullptr;
1227 if (editingIgnoresContent(node)) { 1230 if (editingIgnoresContent(node)) {
1228 ASSERT(node == end.anchorNode() || !node->contains(end.anchorNode()) ); 1231 DCHECK(node == end.anchorNode() || !node->contains(end.anchorNode()) );
yosin_UTC9 2016/04/14 04:35:01 How about adding |<< node << ' ' << end|?
1229 next = NodeTraversal::nextSkippingChildren(*node); 1232 next = NodeTraversal::nextSkippingChildren(*node);
1230 } else { 1233 } else {
1231 next = NodeTraversal::next(*node); 1234 next = NodeTraversal::next(*node);
1232 } 1235 }
1233 if (node->isHTMLElement() && elementFullySelected(toHTMLElement(*node), start, end)) { 1236 if (node->isHTMLElement() && elementFullySelected(toHTMLElement(*node), start, end)) {
1234 HTMLElement* elem = toHTMLElement(node); 1237 HTMLElement* elem = toHTMLElement(node);
1235 Node* prev = NodeTraversal::previousPostOrder(*elem); 1238 Node* prev = NodeTraversal::previousPostOrder(*elem);
1236 Node* next = NodeTraversal::next(*elem); 1239 Node* next = NodeTraversal::next(*elem);
1237 EditingStyle* styleToPushDown = nullptr; 1240 EditingStyle* styleToPushDown = nullptr;
1238 Node* childNode = nullptr; 1241 Node* childNode = nullptr;
1239 if (isStyledInlineElementToRemove(elem)) { 1242 if (isStyledInlineElementToRemove(elem)) {
1240 styleToPushDown = EditingStyle::create(); 1243 styleToPushDown = EditingStyle::create();
1241 childNode = elem->firstChild(); 1244 childNode = elem->firstChild();
1242 } 1245 }
1243 1246
1244 removeInlineStyleFromElement(style, elem, editingState, RemoveIfNeed ed, styleToPushDown); 1247 removeInlineStyleFromElement(style, elem, editingState, RemoveIfNeed ed, styleToPushDown);
1245 if (editingState->isAborted()) 1248 if (editingState->isAborted())
1246 return; 1249 return;
1247 if (!elem->inShadowIncludingDocument()) { 1250 if (!elem->inShadowIncludingDocument()) {
1248 if (s.anchorNode() == elem) { 1251 if (s.anchorNode() == elem) {
1249 // Since elem must have been fully selected, and it is at th e start 1252 // Since elem must have been fully selected, and it is at th e start
1250 // of the selection, it is clear we can set the new s offset to 0. 1253 // of the selection, it is clear we can set the new s offset to 0.
1251 ASSERT(s.isBeforeAnchor() || s.isBeforeChildren() || s.offse tInContainerNode() <= 0); 1254 DCHECK(s.isBeforeAnchor() || s.isBeforeChildren() || s.offse tInContainerNode() <= 0);
yosin_UTC9 2016/04/14 04:35:00 How about adding |<< s|?
1252 s = firstPositionInOrBeforeNode(next); 1255 s = firstPositionInOrBeforeNode(next);
1253 } 1256 }
1254 if (e.anchorNode() == elem) { 1257 if (e.anchorNode() == elem) {
1255 // Since elem must have been fully selected, and it is at th e end 1258 // Since elem must have been fully selected, and it is at th e end
1256 // of the selection, it is clear we can set the new e offset to 1259 // of the selection, it is clear we can set the new e offset to
1257 // the max range offset of prev. 1260 // the max range offset of prev.
1258 ASSERT(s.isAfterAnchor() || !offsetIsBeforeLastNodeOffset(s. offsetInContainerNode(), s.computeContainerNode())); 1261 DCHECK(s.isAfterAnchor() || !offsetIsBeforeLastNodeOffset(s. offsetInContainerNode(), s.computeContainerNode()));
yosin_UTC9 2016/04/14 04:35:01 How about adding |<< s|?
1259 e = lastPositionInOrAfterNode(prev); 1262 e = lastPositionInOrAfterNode(prev);
1260 } 1263 }
1261 } 1264 }
1262 1265
1263 if (styleToPushDown) { 1266 if (styleToPushDown) {
1264 for (; childNode; childNode = childNode->nextSibling()) { 1267 for (; childNode; childNode = childNode->nextSibling()) {
1265 applyInlineStyleToPushDown(childNode, styleToPushDown, editi ngState); 1268 applyInlineStyleToPushDown(childNode, styleToPushDown, editi ngState);
1266 if (editingState->isAborted()) 1269 if (editingState->isAborted())
1267 return; 1270 return;
1268 } 1271 }
(...skipping 11 matching lines...) Expand all
1280 { 1283 {
1281 // The tree may have changed and Position::upstream() relies on an up-to-dat e layout. 1284 // The tree may have changed and Position::upstream() relies on an up-to-dat e layout.
1282 element.document().updateLayoutIgnorePendingStylesheets(); 1285 element.document().updateLayoutIgnorePendingStylesheets();
1283 1286
1284 return comparePositions(firstPositionInOrBeforeNode(&element), start) >= 0 1287 return comparePositions(firstPositionInOrBeforeNode(&element), start) >= 0
1285 && comparePositions(mostBackwardCaretPosition(lastPositionInOrAfterNode( &element)), end) <= 0; 1288 && comparePositions(mostBackwardCaretPosition(lastPositionInOrAfterNode( &element)), end) <= 0;
1286 } 1289 }
1287 1290
1288 void ApplyStyleCommand::splitTextAtStart(const Position& start, const Position& end) 1291 void ApplyStyleCommand::splitTextAtStart(const Position& start, const Position& end)
1289 { 1292 {
1290 ASSERT(start.computeContainerNode()->isTextNode()); 1293 DCHECK(start.computeContainerNode()->isTextNode());
yosin_UTC9 2016/04/14 04:35:01 How about adding |<< s|?
1291 1294
1292 Position newEnd; 1295 Position newEnd;
1293 if (end.isOffsetInAnchor() && start.computeContainerNode() == end.computeCon tainerNode()) 1296 if (end.isOffsetInAnchor() && start.computeContainerNode() == end.computeCon tainerNode())
1294 newEnd = Position(end.computeContainerNode(), end.offsetInContainerNode( ) - start.offsetInContainerNode()); 1297 newEnd = Position(end.computeContainerNode(), end.offsetInContainerNode( ) - start.offsetInContainerNode());
1295 else 1298 else
1296 newEnd = end; 1299 newEnd = end;
1297 1300
1298 Text* text = toText(start.computeContainerNode()); 1301 Text* text = toText(start.computeContainerNode());
1299 splitTextNode(text, start.offsetInContainerNode()); 1302 splitTextNode(text, start.offsetInContainerNode());
1300 updateStartEnd(firstPositionInNode(text), newEnd); 1303 updateStartEnd(firstPositionInNode(text), newEnd);
1301 } 1304 }
1302 1305
1303 void ApplyStyleCommand::splitTextAtEnd(const Position& start, const Position& en d) 1306 void ApplyStyleCommand::splitTextAtEnd(const Position& start, const Position& en d)
1304 { 1307 {
1305 ASSERT(end.computeContainerNode()->isTextNode()); 1308 DCHECK(end.computeContainerNode()->isTextNode());
yosin_UTC9 2016/04/14 04:35:01 How about adding |<< end|?
1306 1309
1307 bool shouldUpdateStart = start.isOffsetInAnchor() && start.computeContainerN ode() == end.computeContainerNode(); 1310 bool shouldUpdateStart = start.isOffsetInAnchor() && start.computeContainerN ode() == end.computeContainerNode();
1308 Text* text = toText(end.anchorNode()); 1311 Text* text = toText(end.anchorNode());
1309 splitTextNode(text, end.offsetInContainerNode()); 1312 splitTextNode(text, end.offsetInContainerNode());
1310 1313
1311 Node* prevNode = text->previousSibling(); 1314 Node* prevNode = text->previousSibling();
1312 if (!prevNode || !prevNode->isTextNode()) 1315 if (!prevNode || !prevNode->isTextNode())
1313 return; 1316 return;
1314 1317
1315 Position newStart = shouldUpdateStart ? Position(toText(prevNode), start.off setInContainerNode()) : start; 1318 Position newStart = shouldUpdateStart ? Position(toText(prevNode), start.off setInContainerNode()) : start;
1316 updateStartEnd(newStart, lastPositionInNode(prevNode)); 1319 updateStartEnd(newStart, lastPositionInNode(prevNode));
1317 } 1320 }
1318 1321
1319 void ApplyStyleCommand::splitTextElementAtStart(const Position& start, const Pos ition& end) 1322 void ApplyStyleCommand::splitTextElementAtStart(const Position& start, const Pos ition& end)
1320 { 1323 {
1321 ASSERT(start.computeContainerNode()->isTextNode()); 1324 DCHECK(start.computeContainerNode()->isTextNode());
yosin_UTC9 2016/04/14 04:35:01 How about adding |<< start|?
1322 1325
1323 Position newEnd; 1326 Position newEnd;
1324 if (start.computeContainerNode() == end.computeContainerNode()) 1327 if (start.computeContainerNode() == end.computeContainerNode())
1325 newEnd = Position(end.computeContainerNode(), end.offsetInContainerNode( ) - start.offsetInContainerNode()); 1328 newEnd = Position(end.computeContainerNode(), end.offsetInContainerNode( ) - start.offsetInContainerNode());
1326 else 1329 else
1327 newEnd = end; 1330 newEnd = end;
1328 1331
1329 splitTextNodeContainingElement(toText(start.computeContainerNode()), start.o ffsetInContainerNode()); 1332 splitTextNodeContainingElement(toText(start.computeContainerNode()), start.o ffsetInContainerNode());
1330 updateStartEnd(positionBeforeNode(start.computeContainerNode()), newEnd); 1333 updateStartEnd(positionBeforeNode(start.computeContainerNode()), newEnd);
1331 } 1334 }
1332 1335
1333 void ApplyStyleCommand::splitTextElementAtEnd(const Position& start, const Posit ion& end) 1336 void ApplyStyleCommand::splitTextElementAtEnd(const Position& start, const Posit ion& end)
1334 { 1337 {
1335 ASSERT(end.computeContainerNode()->isTextNode()); 1338 DCHECK(end.computeContainerNode()->isTextNode());
yosin_UTC9 2016/04/14 04:35:01 How about adding |<< end|?
1336 1339
1337 bool shouldUpdateStart = start.computeContainerNode() == end.computeContaine rNode(); 1340 bool shouldUpdateStart = start.computeContainerNode() == end.computeContaine rNode();
1338 splitTextNodeContainingElement(toText(end.computeContainerNode()), end.offse tInContainerNode()); 1341 splitTextNodeContainingElement(toText(end.computeContainerNode()), end.offse tInContainerNode());
1339 1342
1340 Node* parentElement = end.computeContainerNode()->parentNode(); 1343 Node* parentElement = end.computeContainerNode()->parentNode();
1341 if (!parentElement || !parentElement->previousSibling()) 1344 if (!parentElement || !parentElement->previousSibling())
1342 return; 1345 return;
1343 Node* firstTextNode = parentElement->previousSibling()->lastChild(); 1346 Node* firstTextNode = parentElement->previousSibling()->lastChild();
1344 if (!firstTextNode || !firstTextNode->isTextNode()) 1347 if (!firstTextNode || !firstTextNode->isTextNode())
1345 return; 1348 return;
1346 1349
1347 Position newStart = shouldUpdateStart ? Position(toText(firstTextNode), star t.offsetInContainerNode()) : start; 1350 Position newStart = shouldUpdateStart ? Position(toText(firstTextNode), star t.offsetInContainerNode()) : start;
1348 updateStartEnd(newStart, positionAfterNode(firstTextNode)); 1351 updateStartEnd(newStart, positionAfterNode(firstTextNode));
1349 } 1352 }
1350 1353
1351 bool ApplyStyleCommand::shouldSplitTextElement(Element* element, EditingStyle* s tyle) 1354 bool ApplyStyleCommand::shouldSplitTextElement(Element* element, EditingStyle* s tyle)
1352 { 1355 {
1353 if (!element || !element->isHTMLElement()) 1356 if (!element || !element->isHTMLElement())
1354 return false; 1357 return false;
1355 1358
1356 return shouldRemoveInlineStyleFromElement(style, toHTMLElement(element)); 1359 return shouldRemoveInlineStyleFromElement(style, toHTMLElement(element));
1357 } 1360 }
1358 1361
1359 bool ApplyStyleCommand::isValidCaretPositionInTextNode(const Position& position) 1362 bool ApplyStyleCommand::isValidCaretPositionInTextNode(const Position& position)
1360 { 1363 {
1361 ASSERT(position.isNotNull()); 1364 DCHECK(position.isNotNull());
1362 1365
1363 Node* node = position.computeContainerNode(); 1366 Node* node = position.computeContainerNode();
1364 if (!position.isOffsetInAnchor() || !node->isTextNode()) 1367 if (!position.isOffsetInAnchor() || !node->isTextNode())
1365 return false; 1368 return false;
1366 int offsetInText = position.offsetInContainerNode(); 1369 int offsetInText = position.offsetInContainerNode();
1367 return offsetInText > caretMinOffset(node) && offsetInText < caretMaxOffset( node); 1370 return offsetInText > caretMinOffset(node) && offsetInText < caretMaxOffset( node);
1368 } 1371 }
1369 1372
1370 bool ApplyStyleCommand::mergeStartWithPreviousIfIdentical(const Position& start, const Position& end, EditingState* editingState) 1373 bool ApplyStyleCommand::mergeStartWithPreviousIfIdentical(const Position& start, const Position& end, EditingState* editingState)
1371 { 1374 {
(...skipping 13 matching lines...) Expand all
1385 1388
1386 if (!startNode->isElementNode()) 1389 if (!startNode->isElementNode())
1387 return false; 1390 return false;
1388 1391
1389 Node* previousSibling = startNode->previousSibling(); 1392 Node* previousSibling = startNode->previousSibling();
1390 1393
1391 if (previousSibling && areIdenticalElements(*startNode, *previousSibling)) { 1394 if (previousSibling && areIdenticalElements(*startNode, *previousSibling)) {
1392 Element* previousElement = toElement(previousSibling); 1395 Element* previousElement = toElement(previousSibling);
1393 Element* element = toElement(startNode); 1396 Element* element = toElement(startNode);
1394 Node* startChild = element->firstChild(); 1397 Node* startChild = element->firstChild();
1395 ASSERT(startChild); 1398 DCHECK(startChild);
1396 mergeIdenticalElements(previousElement, element, editingState); 1399 mergeIdenticalElements(previousElement, element, editingState);
1397 if (editingState->isAborted()) 1400 if (editingState->isAborted())
1398 return false; 1401 return false;
1399 1402
1400 int startOffsetAdjustment = startChild->nodeIndex(); 1403 int startOffsetAdjustment = startChild->nodeIndex();
1401 int endOffsetAdjustment = startNode == end.anchorNode() ? startOffsetAdj ustment : 0; 1404 int endOffsetAdjustment = startNode == end.anchorNode() ? startOffsetAdj ustment : 0;
1402 updateStartEnd(Position(startNode, startOffsetAdjustment), 1405 updateStartEnd(Position(startNode, startOffsetAdjustment),
1403 Position(end.anchorNode(), end.computeEditingOffset() + endOffsetAdj ustment)); 1406 Position(end.anchorNode(), end.computeEditingOffset() + endOffsetAdj ustment));
1404 return true; 1407 return true;
1405 } 1408 }
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
1440 updateStartEnd(shouldUpdateStart ? Position(nextElement, start.offsetInC ontainerNode()) : start, 1443 updateStartEnd(shouldUpdateStart ? Position(nextElement, start.offsetInC ontainerNode()) : start,
1441 Position(nextElement, endOffset)); 1444 Position(nextElement, endOffset));
1442 return true; 1445 return true;
1443 } 1446 }
1444 1447
1445 return false; 1448 return false;
1446 } 1449 }
1447 1450
1448 void ApplyStyleCommand::surroundNodeRangeWithElement(Node* passedStartNode, Node * endNode, Element* elementToInsert, EditingState* editingState) 1451 void ApplyStyleCommand::surroundNodeRangeWithElement(Node* passedStartNode, Node * endNode, Element* elementToInsert, EditingState* editingState)
1449 { 1452 {
1450 ASSERT(passedStartNode); 1453 DCHECK(passedStartNode);
1451 ASSERT(endNode); 1454 DCHECK(endNode);
1452 ASSERT(elementToInsert); 1455 DCHECK(elementToInsert);
1453 Node* node = passedStartNode; 1456 Node* node = passedStartNode;
1454 Element* element = elementToInsert; 1457 Element* element = elementToInsert;
1455 1458
1456 insertNodeBefore(element, node, editingState); 1459 insertNodeBefore(element, node, editingState);
1457 if (editingState->isAborted()) 1460 if (editingState->isAborted())
1458 return; 1461 return;
1459 1462
1460 while (node) { 1463 while (node) {
1461 Node* next = node->nextSibling(); 1464 Node* next = node->nextSibling();
1462 if (node->isContentEditable(Node::UserSelectAllIsAlwaysNonEditable)) { 1465 if (node->isContentEditable(Node::UserSelectAllIsAlwaysNonEditable)) {
(...skipping 82 matching lines...) Expand 10 before | Expand all | Expand 10 after
1545 return positionBeforeNode(dummyElement); 1548 return positionBeforeNode(dummyElement);
1546 } 1549 }
1547 1550
1548 return firstPositionInOrBeforeNode(startNode); 1551 return firstPositionInOrBeforeNode(startNode);
1549 } 1552 }
1550 1553
1551 void ApplyStyleCommand::applyInlineStyleChange(Node* passedStart, Node* passedEn d, StyleChange& styleChange, EAddStyledElement addStyledElement, EditingState* e ditingState) 1554 void ApplyStyleCommand::applyInlineStyleChange(Node* passedStart, Node* passedEn d, StyleChange& styleChange, EAddStyledElement addStyledElement, EditingState* e ditingState)
1552 { 1555 {
1553 Node* startNode = passedStart; 1556 Node* startNode = passedStart;
1554 Node* endNode = passedEnd; 1557 Node* endNode = passedEnd;
1555 ASSERT(startNode->inShadowIncludingDocument()); 1558 DCHECK(startNode->inShadowIncludingDocument());
yosin_UTC9 2016/04/14 04:35:01 How about adding |<< startNode|?
1556 ASSERT(endNode->inShadowIncludingDocument()); 1559 DCHECK(endNode->inShadowIncludingDocument());
yosin_UTC9 2016/04/14 04:35:01 How about adding |<< endNode|?
1557 1560
1558 // Find appropriate font and span elements top-down. 1561 // Find appropriate font and span elements top-down.
1559 HTMLFontElement* fontContainer = nullptr; 1562 HTMLFontElement* fontContainer = nullptr;
1560 HTMLElement* styleContainer = nullptr; 1563 HTMLElement* styleContainer = nullptr;
1561 for (Node* container = startNode; container && startNode == endNode; contain er = container->firstChild()) { 1564 for (Node* container = startNode; container && startNode == endNode; contain er = container->firstChild()) {
1562 if (isHTMLFontElement(*container)) 1565 if (isHTMLFontElement(*container))
1563 fontContainer = toHTMLFontElement(container); 1566 fontContainer = toHTMLFontElement(container);
1564 bool styleContainerIsNotSpan = !isHTMLSpanElement(styleContainer); 1567 bool styleContainerIsNotSpan = !isHTMLSpanElement(styleContainer);
1565 if (container->isHTMLElement()) { 1568 if (container->isHTMLElement()) {
1566 HTMLElement* containerElement = toHTMLElement(container); 1569 HTMLElement* containerElement = toHTMLElement(container);
(...skipping 95 matching lines...) Expand 10 before | Expand all | Expand 10 after
1662 return 0; 1665 return 0;
1663 1666
1664 CSSComputedStyleDeclaration* style = CSSComputedStyleDeclaration::create(nod e); 1667 CSSComputedStyleDeclaration* style = CSSComputedStyleDeclaration::create(nod e);
1665 if (!style) 1668 if (!style)
1666 return 0; 1669 return 0;
1667 1670
1668 CSSPrimitiveValue* value = toCSSPrimitiveValue(style->getPropertyCSSValue(CS SPropertyFontSize)); 1671 CSSPrimitiveValue* value = toCSSPrimitiveValue(style->getPropertyCSSValue(CS SPropertyFontSize));
1669 if (!value) 1672 if (!value)
1670 return 0; 1673 return 0;
1671 1674
1672 ASSERT(value->typeWithCalcResolved() == CSSPrimitiveValue::UnitType::Pixels) ; 1675 DCHECK(value->typeWithCalcResolved() == CSSPrimitiveValue::UnitType::Pixels) ;
yosin_UTC9 2016/04/14 04:35:01 Could you add |TODO(yosin): We should have printer
1673 return value->getFloatValue(); 1676 return value->getFloatValue();
1674 } 1677 }
1675 1678
1676 void ApplyStyleCommand::joinChildTextNodes(ContainerNode* node, const Position& start, const Position& end) 1679 void ApplyStyleCommand::joinChildTextNodes(ContainerNode* node, const Position& start, const Position& end)
1677 { 1680 {
1678 if (!node) 1681 if (!node)
1679 return; 1682 return;
1680 1683
1681 Position newStart = start; 1684 Position newStart = start;
1682 Position newEnd = end; 1685 Position newEnd = end;
(...skipping 30 matching lines...) Expand all
1713 DEFINE_TRACE(ApplyStyleCommand) 1716 DEFINE_TRACE(ApplyStyleCommand)
1714 { 1717 {
1715 visitor->trace(m_style); 1718 visitor->trace(m_style);
1716 visitor->trace(m_start); 1719 visitor->trace(m_start);
1717 visitor->trace(m_end); 1720 visitor->trace(m_end);
1718 visitor->trace(m_styledInlineElement); 1721 visitor->trace(m_styledInlineElement);
1719 CompositeEditCommand::trace(visitor); 1722 CompositeEditCommand::trace(visitor);
1720 } 1723 }
1721 1724
1722 } // namespace blink 1725 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698