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

Side by Side Diff: third_party/WebKit/Source/core/editing/serializers/Serialization.cpp

Issue 2393243003: Reflow comments in //third_party/WebKit/Sourcecore/editing/serializers (Closed)
Patch Set: Address nits Created 4 years, 2 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) 2004, 2005, 2006, 2007, 2008, 2009 Apple Inc. All rights reserv ed. 2 * Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009 Apple Inc. All rights
3 * reserved.
3 * Copyright (C) 2008, 2009, 2010, 2011 Google Inc. All rights reserved. 4 * Copyright (C) 2008, 2009, 2010, 2011 Google Inc. All rights reserved.
4 * Copyright (C) 2011 Igalia S.L. 5 * Copyright (C) 2011 Igalia S.L.
5 * Copyright (C) 2011 Motorola Mobility. All rights reserved. 6 * Copyright (C) 2011 Motorola Mobility. All rights reserved.
6 * 7 *
7 * Redistribution and use in source and binary forms, with or without 8 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions 9 * modification, are permitted provided that the following conditions
9 * are met: 10 * are met:
10 * 1. Redistributions of source code must retain the above copyright 11 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer. 12 * notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright 13 * 2. Redistributions in binary form must reproduce the above copyright
(...skipping 157 matching lines...) Expand 10 before | Expand all | Expand 10 after
170 Node* constrainingAncestor) { 171 Node* constrainingAncestor) {
171 Node* firstNode = startPosition.nodeAsRangeFirstNode(); 172 Node* firstNode = startPosition.nodeAsRangeFirstNode();
172 // For compatibility reason, we use container node of start and end 173 // For compatibility reason, we use container node of start and end
173 // positions rather than first node and last node in selection. 174 // positions rather than first node and last node in selection.
174 Node* commonAncestor = 175 Node* commonAncestor =
175 Strategy::commonAncestor(*startPosition.computeContainerNode(), 176 Strategy::commonAncestor(*startPosition.computeContainerNode(),
176 *endPosition.computeContainerNode()); 177 *endPosition.computeContainerNode());
177 DCHECK(commonAncestor); 178 DCHECK(commonAncestor);
178 HTMLElement* specialCommonAncestor = nullptr; 179 HTMLElement* specialCommonAncestor = nullptr;
179 if (shouldAnnotate == AnnotateForInterchange) { 180 if (shouldAnnotate == AnnotateForInterchange) {
180 // Include ancestors that aren't completely inside the range but are require d to retain 181 // Include ancestors that aren't completely inside the range but are
181 // the structure and appearance of the copied markup. 182 // required to retain the structure and appearance of the copied markup.
182 specialCommonAncestor = 183 specialCommonAncestor =
183 ancestorToRetainStructureAndAppearance(commonAncestor); 184 ancestorToRetainStructureAndAppearance(commonAncestor);
184 if (Node* parentListNode = enclosingNodeOfType( 185 if (Node* parentListNode = enclosingNodeOfType(
185 firstPositionInOrBeforeNode(firstNode), isListItem)) { 186 firstPositionInOrBeforeNode(firstNode), isListItem)) {
186 EphemeralRangeTemplate<Strategy> markupRange = 187 EphemeralRangeTemplate<Strategy> markupRange =
187 EphemeralRangeTemplate<Strategy>(startPosition, endPosition); 188 EphemeralRangeTemplate<Strategy>(startPosition, endPosition);
188 EphemeralRangeTemplate<Strategy> nodeRange = normalizeRange( 189 EphemeralRangeTemplate<Strategy> nodeRange = normalizeRange(
189 EphemeralRangeTemplate<Strategy>::rangeOfContents(*parentListNode)); 190 EphemeralRangeTemplate<Strategy>::rangeOfContents(*parentListNode));
190 if (nodeRange == markupRange) { 191 if (nodeRange == markupRange) {
191 ContainerNode* ancestor = parentListNode->parentNode(); 192 ContainerNode* ancestor = parentListNode->parentNode();
(...skipping 16 matching lines...) Expand all
208 if (checkAncestor->layoutObject()) { 209 if (checkAncestor->layoutObject()) {
209 HTMLElement* newSpecialCommonAncestor = 210 HTMLElement* newSpecialCommonAncestor =
210 toHTMLElement(highestEnclosingNodeOfType( 211 toHTMLElement(highestEnclosingNodeOfType(
211 Position::firstPositionInNode(checkAncestor), 212 Position::firstPositionInNode(checkAncestor),
212 &isPresentationalHTMLElement, CanCrossEditingBoundary, 213 &isPresentationalHTMLElement, CanCrossEditingBoundary,
213 constrainingAncestor)); 214 constrainingAncestor));
214 if (newSpecialCommonAncestor) 215 if (newSpecialCommonAncestor)
215 specialCommonAncestor = newSpecialCommonAncestor; 216 specialCommonAncestor = newSpecialCommonAncestor;
216 } 217 }
217 218
218 // If a single tab is selected, commonAncestor will be a text node inside a ta b span. 219 // If a single tab is selected, commonAncestor will be a text node inside a
219 // If two or more tabs are selected, commonAncestor will be the tab span. 220 // tab span. If two or more tabs are selected, commonAncestor will be the tab
220 // In either case, if there is a specialCommonAncestor already, it will necess arily be above 221 // span. In either case, if there is a specialCommonAncestor already, it will
221 // any tab span that needs to be included. 222 // necessarily be above any tab span that needs to be included.
222 if (!specialCommonAncestor && isTabHTMLSpanElementTextNode(commonAncestor)) 223 if (!specialCommonAncestor && isTabHTMLSpanElementTextNode(commonAncestor))
223 specialCommonAncestor = 224 specialCommonAncestor =
224 toHTMLSpanElement(Strategy::parent(*commonAncestor)); 225 toHTMLSpanElement(Strategy::parent(*commonAncestor));
225 if (!specialCommonAncestor && isTabHTMLSpanElement(commonAncestor)) 226 if (!specialCommonAncestor && isTabHTMLSpanElement(commonAncestor))
226 specialCommonAncestor = toHTMLSpanElement(commonAncestor); 227 specialCommonAncestor = toHTMLSpanElement(commonAncestor);
227 228
228 if (HTMLAnchorElement* enclosingAnchor = 229 if (HTMLAnchorElement* enclosingAnchor =
229 toHTMLAnchorElement(enclosingElementWithTag( 230 toHTMLAnchorElement(enclosingElementWithTag(
230 Position::firstPositionInNode(specialCommonAncestor 231 Position::firstPositionInNode(specialCommonAncestor
231 ? specialCommonAncestor 232 ? specialCommonAncestor
232 : commonAncestor), 233 : commonAncestor),
233 aTag))) 234 aTag)))
234 specialCommonAncestor = enclosingAnchor; 235 specialCommonAncestor = enclosingAnchor;
235 236
236 return specialCommonAncestor; 237 return specialCommonAncestor;
237 } 238 }
238 239
239 template <typename Strategy> 240 template <typename Strategy>
240 class CreateMarkupAlgorithm { 241 class CreateMarkupAlgorithm {
241 public: 242 public:
242 static String createMarkup( 243 static String createMarkup(
243 const PositionTemplate<Strategy>& startPosition, 244 const PositionTemplate<Strategy>& startPosition,
244 const PositionTemplate<Strategy>& endPosition, 245 const PositionTemplate<Strategy>& endPosition,
245 EAnnotateForInterchange shouldAnnotate = DoNotAnnotateForInterchange, 246 EAnnotateForInterchange shouldAnnotate = DoNotAnnotateForInterchange,
246 ConvertBlocksToInlines = ConvertBlocksToInlines::NotConvert, 247 ConvertBlocksToInlines = ConvertBlocksToInlines::NotConvert,
247 EAbsoluteURLs shouldResolveURLs = DoNotResolveURLs, 248 EAbsoluteURLs shouldResolveURLs = DoNotResolveURLs,
248 Node* constrainingAncestor = nullptr); 249 Node* constrainingAncestor = nullptr);
249 }; 250 };
250 251
251 // FIXME: Shouldn't we omit style info when annotate == DoNotAnnotateForIntercha nge? 252 // FIXME: Shouldn't we omit style info when annotate ==
252 // FIXME: At least, annotation and style info should probably not be included in range.markupString() 253 // DoNotAnnotateForInterchange?
254 // FIXME: At least, annotation and style info should probably not be included in
255 // range.markupString()
253 template <typename Strategy> 256 template <typename Strategy>
254 String CreateMarkupAlgorithm<Strategy>::createMarkup( 257 String CreateMarkupAlgorithm<Strategy>::createMarkup(
255 const PositionTemplate<Strategy>& startPosition, 258 const PositionTemplate<Strategy>& startPosition,
256 const PositionTemplate<Strategy>& endPosition, 259 const PositionTemplate<Strategy>& endPosition,
257 EAnnotateForInterchange shouldAnnotate, 260 EAnnotateForInterchange shouldAnnotate,
258 ConvertBlocksToInlines convertBlocksToInlines, 261 ConvertBlocksToInlines convertBlocksToInlines,
259 EAbsoluteURLs shouldResolveURLs, 262 EAbsoluteURLs shouldResolveURLs,
260 Node* constrainingAncestor) { 263 Node* constrainingAncestor) {
261 if (startPosition.isNull() || endPosition.isNull()) 264 if (startPosition.isNull() || endPosition.isNull())
262 return emptyString(); 265 return emptyString();
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after
303 return CreateMarkupAlgorithm<EditingInFlatTreeStrategy>::createMarkup( 306 return CreateMarkupAlgorithm<EditingInFlatTreeStrategy>::createMarkup(
304 startPosition, endPosition, shouldAnnotate, convertBlocksToInlines, 307 startPosition, endPosition, shouldAnnotate, convertBlocksToInlines,
305 shouldResolveURLs, constrainingAncestor); 308 shouldResolveURLs, constrainingAncestor);
306 } 309 }
307 310
308 DocumentFragment* createFragmentFromMarkup( 311 DocumentFragment* createFragmentFromMarkup(
309 Document& document, 312 Document& document,
310 const String& markup, 313 const String& markup,
311 const String& baseURL, 314 const String& baseURL,
312 ParserContentPolicy parserContentPolicy) { 315 ParserContentPolicy parserContentPolicy) {
313 // We use a fake body element here to trick the HTML parser to using the InBod y insertion mode. 316 // We use a fake body element here to trick the HTML parser to using the
317 // InBody insertion mode.
314 HTMLBodyElement* fakeBody = HTMLBodyElement::create(document); 318 HTMLBodyElement* fakeBody = HTMLBodyElement::create(document);
315 DocumentFragment* fragment = DocumentFragment::create(document); 319 DocumentFragment* fragment = DocumentFragment::create(document);
316 320
317 fragment->parseHTML(markup, fakeBody, parserContentPolicy); 321 fragment->parseHTML(markup, fakeBody, parserContentPolicy);
318 322
319 if (!baseURL.isEmpty() && baseURL != blankURL() && 323 if (!baseURL.isEmpty() && baseURL != blankURL() &&
320 baseURL != document.baseURL()) 324 baseURL != document.baseURL())
321 completeURLs(*fragment, baseURL); 325 completeURLs(*fragment, baseURL);
322 326
323 return fragment; 327 return fragment;
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after
368 } 372 }
369 } 373 }
370 374
371 DocumentFragment* createFragmentFromMarkupWithContext( 375 DocumentFragment* createFragmentFromMarkupWithContext(
372 Document& document, 376 Document& document,
373 const String& markup, 377 const String& markup,
374 unsigned fragmentStart, 378 unsigned fragmentStart,
375 unsigned fragmentEnd, 379 unsigned fragmentEnd,
376 const String& baseURL, 380 const String& baseURL,
377 ParserContentPolicy parserContentPolicy) { 381 ParserContentPolicy parserContentPolicy) {
378 // FIXME: Need to handle the case where the markup already contains these mark ers. 382 // FIXME: Need to handle the case where the markup already contains these
383 // markers.
379 384
380 StringBuilder taggedMarkup; 385 StringBuilder taggedMarkup;
381 taggedMarkup.append(markup.left(fragmentStart)); 386 taggedMarkup.append(markup.left(fragmentStart));
382 MarkupFormatter::appendComment(taggedMarkup, fragmentMarkerTag); 387 MarkupFormatter::appendComment(taggedMarkup, fragmentMarkerTag);
383 taggedMarkup.append( 388 taggedMarkup.append(
384 markup.substring(fragmentStart, fragmentEnd - fragmentStart)); 389 markup.substring(fragmentStart, fragmentEnd - fragmentStart));
385 MarkupFormatter::appendComment(taggedMarkup, fragmentMarkerTag); 390 MarkupFormatter::appendComment(taggedMarkup, fragmentMarkerTag);
386 taggedMarkup.append(markup.substring(fragmentEnd)); 391 taggedMarkup.append(markup.substring(fragmentEnd));
387 392
388 DocumentFragment* taggedFragment = createFragmentFromMarkup( 393 DocumentFragment* taggedFragment = createFragmentFromMarkup(
(...skipping 14 matching lines...) Expand all
403 408
404 Range* range = Range::create( 409 Range* range = Range::create(
405 *taggedDocument, 410 *taggedDocument,
406 Position::afterNode(nodeBeforeContext).parentAnchoredEquivalent(), 411 Position::afterNode(nodeBeforeContext).parentAnchoredEquivalent(),
407 Position::beforeNode(nodeAfterContext).parentAnchoredEquivalent()); 412 Position::beforeNode(nodeAfterContext).parentAnchoredEquivalent());
408 413
409 Node* commonAncestor = range->commonAncestorContainer(); 414 Node* commonAncestor = range->commonAncestorContainer();
410 HTMLElement* specialCommonAncestor = 415 HTMLElement* specialCommonAncestor =
411 ancestorToRetainStructureAndAppearanceWithNoLayoutObject(commonAncestor); 416 ancestorToRetainStructureAndAppearanceWithNoLayoutObject(commonAncestor);
412 417
413 // When there's a special common ancestor outside of the fragment, we must inc lude it as well to 418 // When there's a special common ancestor outside of the fragment, we must
414 // preserve the structure and appearance of the fragment. For example, if the fragment contains 419 // include it as well to preserve the structure and appearance of the
415 // TD, we need to include the enclosing TABLE tag as well. 420 // fragment. For example, if the fragment contains TD, we need to include the
421 // enclosing TABLE tag as well.
416 DocumentFragment* fragment = DocumentFragment::create(document); 422 DocumentFragment* fragment = DocumentFragment::create(document);
417 if (specialCommonAncestor) 423 if (specialCommonAncestor)
418 fragment->appendChild(specialCommonAncestor); 424 fragment->appendChild(specialCommonAncestor);
419 else 425 else
420 fragment->parserTakeAllChildrenFrom(toContainerNode(*commonAncestor)); 426 fragment->parserTakeAllChildrenFrom(toContainerNode(*commonAncestor));
421 427
422 trimFragment(fragment, nodeBeforeContext, nodeAfterContext); 428 trimFragment(fragment, nodeBeforeContext, nodeAfterContext);
423 429
424 return fragment; 430 return fragment;
425 } 431 }
(...skipping 103 matching lines...) Expand 10 before | Expand all | Expand 10 after
529 shouldPreserveNewline(context)) { 535 shouldPreserveNewline(context)) {
530 fragment->appendChild(document.createTextNode(string)); 536 fragment->appendChild(document.createTextNode(string));
531 if (string.endsWith('\n')) { 537 if (string.endsWith('\n')) {
532 HTMLBRElement* element = HTMLBRElement::create(document); 538 HTMLBRElement* element = HTMLBRElement::create(document);
533 element->setAttribute(classAttr, AppleInterchangeNewline); 539 element->setAttribute(classAttr, AppleInterchangeNewline);
534 fragment->appendChild(element); 540 fragment->appendChild(element);
535 } 541 }
536 return fragment; 542 return fragment;
537 } 543 }
538 544
539 // A string with no newlines gets added inline, rather than being put into a p aragraph. 545 // A string with no newlines gets added inline, rather than being put into a
546 // paragraph.
540 if (string.find('\n') == kNotFound) { 547 if (string.find('\n') == kNotFound) {
541 fillContainerFromString(fragment, string); 548 fillContainerFromString(fragment, string);
542 return fragment; 549 return fragment;
543 } 550 }
544 551
545 // Break string into paragraphs. Extra line breaks turn into empty paragraphs. 552 // Break string into paragraphs. Extra line breaks turn into empty paragraphs.
546 Element* block = 553 Element* block =
547 enclosingBlock(context.startPosition().nodeAsRangeFirstNode()); 554 enclosingBlock(context.startPosition().nodeAsRangeFirstNode());
548 bool useClonesOfEnclosingBlock = 555 bool useClonesOfEnclosingBlock =
549 block && !isHTMLBodyElement(*block) && !isHTMLHtmlElement(*block) && 556 block && !isHTMLBodyElement(*block) && !isHTMLHtmlElement(*block) &&
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after
601 return fragment; 608 return fragment;
602 } 609 }
603 610
604 DocumentFragment* createFragmentForTransformToFragment( 611 DocumentFragment* createFragmentForTransformToFragment(
605 const String& sourceString, 612 const String& sourceString,
606 const String& sourceMIMEType, 613 const String& sourceMIMEType,
607 Document& outputDoc) { 614 Document& outputDoc) {
608 DocumentFragment* fragment = outputDoc.createDocumentFragment(); 615 DocumentFragment* fragment = outputDoc.createDocumentFragment();
609 616
610 if (sourceMIMEType == "text/html") { 617 if (sourceMIMEType == "text/html") {
611 // As far as I can tell, there isn't a spec for how transformToFragment is s upposed to work. 618 // As far as I can tell, there isn't a spec for how transformToFragment is
612 // Based on the documentation I can find, it looks like we want to start par sing the fragment in the InBody insertion mode. 619 // supposed to work. Based on the documentation I can find, it looks like we
613 // Unfortunately, that's an implementation detail of the parser. 620 // want to start parsing the fragment in the InBody insertion mode.
614 // We achieve that effect here by passing in a fake body element as context for the fragment. 621 // Unfortunately, that's an implementation detail of the parser. We achieve
622 // that effect here by passing in a fake body element as context for the
623 // fragment.
615 HTMLBodyElement* fakeBody = HTMLBodyElement::create(outputDoc); 624 HTMLBodyElement* fakeBody = HTMLBodyElement::create(outputDoc);
616 fragment->parseHTML(sourceString, fakeBody); 625 fragment->parseHTML(sourceString, fakeBody);
617 } else if (sourceMIMEType == "text/plain") { 626 } else if (sourceMIMEType == "text/plain") {
618 fragment->parserAppendChild(Text::create(outputDoc, sourceString)); 627 fragment->parserAppendChild(Text::create(outputDoc, sourceString));
619 } else { 628 } else {
620 bool successfulParse = fragment->parseXML(sourceString, 0); 629 bool successfulParse = fragment->parseXML(sourceString, 0);
621 if (!successfulParse) 630 if (!successfulParse)
622 return nullptr; 631 return nullptr;
623 } 632 }
624 633
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after
702 return; 711 return;
703 } 712 }
704 713
705 // FIXME: This is wrong if containerNode->firstChild() has more than one ref! 714 // FIXME: This is wrong if containerNode->firstChild() has more than one ref!
706 if (containerNode->hasOneTextChild() && fragment->hasOneTextChild()) { 715 if (containerNode->hasOneTextChild() && fragment->hasOneTextChild()) {
707 toText(containerNode->firstChild()) 716 toText(containerNode->firstChild())
708 ->setData(toText(fragment->firstChild())->data()); 717 ->setData(toText(fragment->firstChild())->data());
709 return; 718 return;
710 } 719 }
711 720
712 // FIXME: No need to replace the child it is a text node and its contents are already == text. 721 // FIXME: No need to replace the child it is a text node and its contents are
722 // already == text.
713 if (containerNode->hasOneChild()) { 723 if (containerNode->hasOneChild()) {
714 containerNode->replaceChild(fragment, containerNode->firstChild(), 724 containerNode->replaceChild(fragment, containerNode->firstChild(),
715 exceptionState); 725 exceptionState);
716 return; 726 return;
717 } 727 }
718 728
719 containerNode->removeChildren(); 729 containerNode->removeChildren();
720 containerNode->appendChild(fragment, exceptionState); 730 containerNode->appendChild(fragment, exceptionState);
721 } 731 }
722 732
723 void replaceChildrenWithText(ContainerNode* container, 733 void replaceChildrenWithText(ContainerNode* container,
724 const String& text, 734 const String& text,
725 ExceptionState& exceptionState) { 735 ExceptionState& exceptionState) {
726 DCHECK(container); 736 DCHECK(container);
727 ContainerNode* containerNode(container); 737 ContainerNode* containerNode(container);
728 738
729 ChildListMutationScope mutation(*containerNode); 739 ChildListMutationScope mutation(*containerNode);
730 740
731 // FIXME: This is wrong if containerNode->firstChild() has more than one ref! Example: 741 // FIXME: This is wrong if containerNode->firstChild() has more than one ref!
742 // Example:
732 // <div>foo</div> 743 // <div>foo</div>
733 // <script> 744 // <script>
734 // var oldText = div.firstChild; 745 // var oldText = div.firstChild;
735 // console.log(oldText.data); // foo 746 // console.log(oldText.data); // foo
736 // div.innerText = "bar"; 747 // div.innerText = "bar";
737 // console.log(oldText.data); // bar!?! 748 // console.log(oldText.data); // bar!?!
738 // </script> 749 // </script>
739 // I believe this is an intentional benchmark cheat from years ago. 750 // I believe this is an intentional benchmark cheat from years ago.
740 // We should re-visit if we actually want this still. 751 // We should re-visit if we actually want this still.
741 if (containerNode->hasOneTextChild()) { 752 if (containerNode->hasOneTextChild()) {
742 toText(containerNode->firstChild())->setData(text); 753 toText(containerNode->firstChild())->setData(text);
743 return; 754 return;
744 } 755 }
745 756
746 // NOTE: This method currently always creates a text node, even if that text n ode will be empty. 757 // NOTE: This method currently always creates a text node, even if that text
758 // node will be empty.
747 Text* textNode = Text::create(containerNode->document(), text); 759 Text* textNode = Text::create(containerNode->document(), text);
748 760
749 // FIXME: No need to replace the child it is a text node and its contents are already == text. 761 // FIXME: No need to replace the child it is a text node and its contents are
762 // already == text.
750 if (containerNode->hasOneChild()) { 763 if (containerNode->hasOneChild()) {
751 containerNode->replaceChild(textNode, containerNode->firstChild(), 764 containerNode->replaceChild(textNode, containerNode->firstChild(),
752 exceptionState); 765 exceptionState);
753 return; 766 return;
754 } 767 }
755 768
756 containerNode->removeChildren(); 769 containerNode->removeChildren();
757 containerNode->appendChild(textNode, exceptionState); 770 containerNode->appendChild(textNode, exceptionState);
758 } 771 }
759 772
760 void mergeWithNextTextNode(Text* textNode, ExceptionState& exceptionState) { 773 void mergeWithNextTextNode(Text* textNode, ExceptionState& exceptionState) {
761 DCHECK(textNode); 774 DCHECK(textNode);
762 Node* next = textNode->nextSibling(); 775 Node* next = textNode->nextSibling();
763 if (!next || !next->isTextNode()) 776 if (!next || !next->isTextNode())
764 return; 777 return;
765 778
766 Text* textNext = toText(next); 779 Text* textNext = toText(next);
767 textNode->appendData(textNext->data()); 780 textNode->appendData(textNext->data());
768 if (textNext->parentNode()) // Might have been removed by mutation event. 781 if (textNext->parentNode()) // Might have been removed by mutation event.
769 textNext->remove(exceptionState); 782 textNext->remove(exceptionState);
770 } 783 }
771 784
772 template class CORE_TEMPLATE_EXPORT CreateMarkupAlgorithm<EditingStrategy>; 785 template class CORE_TEMPLATE_EXPORT CreateMarkupAlgorithm<EditingStrategy>;
773 template class CORE_TEMPLATE_EXPORT 786 template class CORE_TEMPLATE_EXPORT
774 CreateMarkupAlgorithm<EditingInFlatTreeStrategy>; 787 CreateMarkupAlgorithm<EditingInFlatTreeStrategy>;
775 788
776 } // namespace blink 789 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698