OLD | NEW |
1 /* | 1 /* |
2 * Copyright (C) 2000 Lars Knoll (knoll@kde.org) | 2 * Copyright (C) 2000 Lars Knoll (knoll@kde.org) |
3 * Copyright (C) 2003, 2004, 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. | 3 * Copyright (C) 2003, 2004, 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. |
4 * All right reserved. | 4 * All right reserved. |
5 * Copyright (C) 2010 Google Inc. All rights reserved. | 5 * Copyright (C) 2010 Google Inc. All rights reserved. |
6 * | 6 * |
7 * This library is free software; you can redistribute it and/or | 7 * This library is free software; you can redistribute it and/or |
8 * modify it under the terms of the GNU Library General Public | 8 * modify it under the terms of the GNU Library General Public |
9 * License as published by the Free Software Foundation; either | 9 * License as published by the Free Software Foundation; either |
10 * version 2 of the License, or (at your option) any later version. | 10 * version 2 of the License, or (at your option) any later version. |
(...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
92 for (BidiRun* r = firstRun; r; r = r->next()) { | 92 for (BidiRun* r = firstRun; r; r = r->next()) { |
93 if (!r->m_box || r == trailingSpaceRun) | 93 if (!r->m_box || r == trailingSpaceRun) |
94 continue; | 94 continue; |
95 | 95 |
96 if (r->m_lineLayoutItem.isText()) { | 96 if (r->m_lineLayoutItem.isText()) { |
97 unsigned opportunitiesInRun = m_runsWithExpansions[i++]; | 97 unsigned opportunitiesInRun = m_runsWithExpansions[i++]; |
98 | 98 |
99 RELEASE_ASSERT(opportunitiesInRun <= m_totalOpportunities); | 99 RELEASE_ASSERT(opportunitiesInRun <= m_totalOpportunities); |
100 | 100 |
101 // Don't justify for white-space: pre. | 101 // Don't justify for white-space: pre. |
102 if (r->m_lineLayoutItem.style()->whiteSpace() != EWhiteSpace::Pre) { | 102 if (r->m_lineLayoutItem.style()->whiteSpace() != EWhiteSpace::kPre) { |
103 InlineTextBox* textBox = toInlineTextBox(r->m_box); | 103 InlineTextBox* textBox = toInlineTextBox(r->m_box); |
104 RELEASE_ASSERT(m_totalOpportunities); | 104 RELEASE_ASSERT(m_totalOpportunities); |
105 int expansion = ((availableLogicalWidth - totalLogicalWidth) * | 105 int expansion = ((availableLogicalWidth - totalLogicalWidth) * |
106 opportunitiesInRun / m_totalOpportunities) | 106 opportunitiesInRun / m_totalOpportunities) |
107 .toInt(); | 107 .toInt(); |
108 textBox->setExpansion(expansion); | 108 textBox->setExpansion(expansion); |
109 totalLogicalWidth += expansion; | 109 totalLogicalWidth += expansion; |
110 } | 110 } |
111 m_totalOpportunities -= opportunitiesInRun; | 111 m_totalOpportunities -= opportunitiesInRun; |
112 if (!m_totalOpportunities) | 112 if (!m_totalOpportunities) |
(...skipping 243 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
356 } | 356 } |
357 | 357 |
358 ETextAlign LayoutBlockFlow::textAlignmentForLine(bool endsWithSoftBreak) const { | 358 ETextAlign LayoutBlockFlow::textAlignmentForLine(bool endsWithSoftBreak) const { |
359 ETextAlign alignment = style()->textAlign(); | 359 ETextAlign alignment = style()->textAlign(); |
360 if (endsWithSoftBreak) | 360 if (endsWithSoftBreak) |
361 return alignment; | 361 return alignment; |
362 | 362 |
363 TextAlignLast alignmentLast = style()->getTextAlignLast(); | 363 TextAlignLast alignmentLast = style()->getTextAlignLast(); |
364 switch (alignmentLast) { | 364 switch (alignmentLast) { |
365 case TextAlignLastStart: | 365 case TextAlignLastStart: |
366 return ETextAlign::Start; | 366 return ETextAlign::kStart; |
367 case TextAlignLastEnd: | 367 case TextAlignLastEnd: |
368 return ETextAlign::End; | 368 return ETextAlign::kEnd; |
369 case TextAlignLastLeft: | 369 case TextAlignLastLeft: |
370 return ETextAlign::Left; | 370 return ETextAlign::kLeft; |
371 case TextAlignLastRight: | 371 case TextAlignLastRight: |
372 return ETextAlign::Right; | 372 return ETextAlign::kRight; |
373 case TextAlignLastCenter: | 373 case TextAlignLastCenter: |
374 return ETextAlign::Center; | 374 return ETextAlign::kCenter; |
375 case TextAlignLastJustify: | 375 case TextAlignLastJustify: |
376 return ETextAlign::Justify; | 376 return ETextAlign::kJustify; |
377 case TextAlignLastAuto: | 377 case TextAlignLastAuto: |
378 if (alignment == ETextAlign::Justify) | 378 if (alignment == ETextAlign::kJustify) |
379 return ETextAlign::Start; | 379 return ETextAlign::kStart; |
380 return alignment; | 380 return alignment; |
381 } | 381 } |
382 | 382 |
383 return alignment; | 383 return alignment; |
384 } | 384 } |
385 | 385 |
386 static void updateLogicalWidthForLeftAlignedBlock( | 386 static void updateLogicalWidthForLeftAlignedBlock( |
387 bool isLeftToRightDirection, | 387 bool isLeftToRightDirection, |
388 BidiRun* trailingSpaceRun, | 388 BidiRun* trailingSpaceRun, |
389 LayoutUnit& logicalLeft, | 389 LayoutUnit& logicalLeft, |
(...skipping 273 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
663 rootInlineBox->getLineLayoutItem().style()->unicodeBidi() == Plaintext) | 663 rootInlineBox->getLineLayoutItem().style()->unicodeBidi() == Plaintext) |
664 direction = rootInlineBox->direction(); | 664 direction = rootInlineBox->direction(); |
665 else | 665 else |
666 direction = style()->direction(); | 666 direction = style()->direction(); |
667 | 667 |
668 // Armed with the total width of the line (without justification), | 668 // Armed with the total width of the line (without justification), |
669 // we now examine our text-align property in order to determine where to | 669 // we now examine our text-align property in order to determine where to |
670 // position the objects horizontally. The total width of the line can be | 670 // position the objects horizontally. The total width of the line can be |
671 // increased if we end up justifying text. | 671 // increased if we end up justifying text. |
672 switch (textAlign) { | 672 switch (textAlign) { |
673 case ETextAlign::Left: | 673 case ETextAlign::kLeft: |
674 case ETextAlign::WebkitLeft: | 674 case ETextAlign::kWebkitLeft: |
675 updateLogicalWidthForLeftAlignedBlock( | 675 updateLogicalWidthForLeftAlignedBlock( |
676 style()->isLeftToRightDirection(), trailingSpaceRun, logicalLeft, | 676 style()->isLeftToRightDirection(), trailingSpaceRun, logicalLeft, |
677 totalLogicalWidth, availableLogicalWidth); | 677 totalLogicalWidth, availableLogicalWidth); |
678 break; | 678 break; |
679 case ETextAlign::Right: | 679 case ETextAlign::kRight: |
680 case ETextAlign::WebkitRight: | 680 case ETextAlign::kWebkitRight: |
681 updateLogicalWidthForRightAlignedBlock( | 681 updateLogicalWidthForRightAlignedBlock( |
682 style()->isLeftToRightDirection(), trailingSpaceRun, logicalLeft, | 682 style()->isLeftToRightDirection(), trailingSpaceRun, logicalLeft, |
683 totalLogicalWidth, availableLogicalWidth); | 683 totalLogicalWidth, availableLogicalWidth); |
684 break; | 684 break; |
685 case ETextAlign::Center: | 685 case ETextAlign::kCenter: |
686 case ETextAlign::WebkitCenter: | 686 case ETextAlign::kWebkitCenter: |
687 updateLogicalWidthForCenterAlignedBlock( | 687 updateLogicalWidthForCenterAlignedBlock( |
688 style()->isLeftToRightDirection(), trailingSpaceRun, logicalLeft, | 688 style()->isLeftToRightDirection(), trailingSpaceRun, logicalLeft, |
689 totalLogicalWidth, availableLogicalWidth); | 689 totalLogicalWidth, availableLogicalWidth); |
690 break; | 690 break; |
691 case ETextAlign::Justify: | 691 case ETextAlign::kJustify: |
692 adjustInlineDirectionLineBounds(expansionOpportunityCount, logicalLeft, | 692 adjustInlineDirectionLineBounds(expansionOpportunityCount, logicalLeft, |
693 availableLogicalWidth); | 693 availableLogicalWidth); |
694 if (expansionOpportunityCount) { | 694 if (expansionOpportunityCount) { |
695 if (trailingSpaceRun) { | 695 if (trailingSpaceRun) { |
696 totalLogicalWidth -= trailingSpaceRun->m_box->logicalWidth(); | 696 totalLogicalWidth -= trailingSpaceRun->m_box->logicalWidth(); |
697 trailingSpaceRun->m_box->setLogicalWidth(LayoutUnit()); | 697 trailingSpaceRun->m_box->setLogicalWidth(LayoutUnit()); |
698 } | 698 } |
699 break; | 699 break; |
700 } | 700 } |
701 // Fall through | 701 // Fall through |
702 case ETextAlign::Start: | 702 case ETextAlign::kStart: |
703 if (direction == TextDirection::Ltr) | 703 if (direction == TextDirection::kLtr) |
704 updateLogicalWidthForLeftAlignedBlock( | 704 updateLogicalWidthForLeftAlignedBlock( |
705 style()->isLeftToRightDirection(), trailingSpaceRun, logicalLeft, | 705 style()->isLeftToRightDirection(), trailingSpaceRun, logicalLeft, |
706 totalLogicalWidth, availableLogicalWidth); | 706 totalLogicalWidth, availableLogicalWidth); |
707 else | 707 else |
708 updateLogicalWidthForRightAlignedBlock( | 708 updateLogicalWidthForRightAlignedBlock( |
709 style()->isLeftToRightDirection(), trailingSpaceRun, logicalLeft, | 709 style()->isLeftToRightDirection(), trailingSpaceRun, logicalLeft, |
710 totalLogicalWidth, availableLogicalWidth); | 710 totalLogicalWidth, availableLogicalWidth); |
711 break; | 711 break; |
712 case ETextAlign::End: | 712 case ETextAlign::kEnd: |
713 if (direction == TextDirection::Ltr) | 713 if (direction == TextDirection::kLtr) |
714 updateLogicalWidthForRightAlignedBlock( | 714 updateLogicalWidthForRightAlignedBlock( |
715 style()->isLeftToRightDirection(), trailingSpaceRun, logicalLeft, | 715 style()->isLeftToRightDirection(), trailingSpaceRun, logicalLeft, |
716 totalLogicalWidth, availableLogicalWidth); | 716 totalLogicalWidth, availableLogicalWidth); |
717 else | 717 else |
718 updateLogicalWidthForLeftAlignedBlock( | 718 updateLogicalWidthForLeftAlignedBlock( |
719 style()->isLeftToRightDirection(), trailingSpaceRun, logicalLeft, | 719 style()->isLeftToRightDirection(), trailingSpaceRun, logicalLeft, |
720 totalLogicalWidth, availableLogicalWidth); | 720 totalLogicalWidth, availableLogicalWidth); |
721 break; | 721 break; |
722 } | 722 } |
723 if (shouldPlaceBlockDirectionScrollbarOnLogicalLeft()) | 723 if (shouldPlaceBlockDirectionScrollbarOnLogicalLeft()) |
(...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
813 for (; r; r = r->next()) { | 813 for (; r; r = r->next()) { |
814 if (!r->m_box || r->m_lineLayoutItem.isOutOfFlowPositioned() || | 814 if (!r->m_box || r->m_lineLayoutItem.isOutOfFlowPositioned() || |
815 r->m_box->isLineBreak()) { | 815 r->m_box->isLineBreak()) { |
816 continue; // Positioned objects are only participating to figure out | 816 continue; // Positioned objects are only participating to figure out |
817 // their correct static x position. They have no effect on the | 817 // their correct static x position. They have no effect on the |
818 // width. Similarly, line break boxes have no effect on the | 818 // width. Similarly, line break boxes have no effect on the |
819 // width. | 819 // width. |
820 } | 820 } |
821 if (r->m_lineLayoutItem.isText()) { | 821 if (r->m_lineLayoutItem.isText()) { |
822 LineLayoutText rt(r->m_lineLayoutItem); | 822 LineLayoutText rt(r->m_lineLayoutItem); |
823 if (textAlign == ETextAlign::Justify && r != trailingSpaceRun && | 823 if (textAlign == ETextAlign::kJustify && r != trailingSpaceRun && |
824 textJustify != TextJustifyNone) { | 824 textJustify != TextJustifyNone) { |
825 if (!isAfterExpansion) | 825 if (!isAfterExpansion) |
826 toInlineTextBox(r->m_box)->setCanHaveLeadingExpansion(true); | 826 toInlineTextBox(r->m_box)->setCanHaveLeadingExpansion(true); |
827 expansions.addRunWithExpansions(*r, isAfterExpansion, textJustify); | 827 expansions.addRunWithExpansions(*r, isAfterExpansion, textJustify); |
828 } | 828 } |
829 | 829 |
830 if (rt.textLength()) { | 830 if (rt.textLength()) { |
831 if (!r->m_start && needsWordSpacing && | 831 if (!r->m_start && needsWordSpacing && |
832 isSpaceOrNewline(rt.characterAt(r->m_start))) | 832 isSpaceOrNewline(rt.characterAt(r->m_start))) |
833 totalLogicalWidth += rt.style(lineInfo.isFirstLine()) | 833 totalLogicalWidth += rt.style(lineInfo.isFirstLine()) |
(...skipping 299 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1133 // This is a short-cut for empty lines. | 1133 // This is a short-cut for empty lines. |
1134 if (layoutState.lineInfo().isEmpty()) { | 1134 if (layoutState.lineInfo().isEmpty()) { |
1135 ASSERT(!paginationStrutFromDeletedLine); | 1135 ASSERT(!paginationStrutFromDeletedLine); |
1136 if (lastRootBox()) | 1136 if (lastRootBox()) |
1137 lastRootBox()->setLineBreakInfo(endOfLine.getLineLayoutItem(), | 1137 lastRootBox()->setLineBreakInfo(endOfLine.getLineLayoutItem(), |
1138 endOfLine.offset(), resolver.status()); | 1138 endOfLine.offset(), resolver.status()); |
1139 resolver.runs().deleteRuns(); | 1139 resolver.runs().deleteRuns(); |
1140 } else { | 1140 } else { |
1141 VisualDirectionOverride override = | 1141 VisualDirectionOverride override = |
1142 (styleToUse.rtlOrdering() == EOrder::Visual | 1142 (styleToUse.rtlOrdering() == EOrder::Visual |
1143 ? (styleToUse.direction() == TextDirection::Ltr | 1143 ? (styleToUse.direction() == TextDirection::kLtr |
1144 ? VisualLeftToRightOverride | 1144 ? VisualLeftToRightOverride |
1145 : VisualRightToLeftOverride) | 1145 : VisualRightToLeftOverride) |
1146 : NoVisualOverride); | 1146 : NoVisualOverride); |
1147 if (isNewUBAParagraph && styleToUse.unicodeBidi() == Plaintext && | 1147 if (isNewUBAParagraph && styleToUse.unicodeBidi() == Plaintext && |
1148 !resolver.context()->parent()) { | 1148 !resolver.context()->parent()) { |
1149 TextDirection direction = determinePlaintextDirectionality( | 1149 TextDirection direction = determinePlaintextDirectionality( |
1150 resolver.position().root(), resolver.position().getLineLayoutItem(), | 1150 resolver.position().root(), resolver.position().getLineLayoutItem(), |
1151 resolver.position().offset()); | 1151 resolver.position().offset()); |
1152 resolver.setStatus( | 1152 resolver.setStatus( |
1153 BidiStatus(direction, isOverride(styleToUse.unicodeBidi()))); | 1153 BidiStatus(direction, isOverride(styleToUse.unicodeBidi()))); |
(...skipping 511 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1665 childMinPreferredLogicalWidth, | 1665 childMinPreferredLogicalWidth, |
1666 childMaxPreferredLogicalWidth); | 1666 childMaxPreferredLogicalWidth); |
1667 childMin += childMinPreferredLogicalWidth; | 1667 childMin += childMinPreferredLogicalWidth; |
1668 childMax += childMaxPreferredLogicalWidth; | 1668 childMax += childMaxPreferredLogicalWidth; |
1669 | 1669 |
1670 bool clearPreviousFloat; | 1670 bool clearPreviousFloat; |
1671 if (child->isFloating()) { | 1671 if (child->isFloating()) { |
1672 const ComputedStyle& childStyle = child->styleRef(); | 1672 const ComputedStyle& childStyle = child->styleRef(); |
1673 clearPreviousFloat = | 1673 clearPreviousFloat = |
1674 (prevFloat && | 1674 (prevFloat && |
1675 ((prevFloat->styleRef().floating() == EFloat::Left && | 1675 ((prevFloat->styleRef().floating() == EFloat::kLeft && |
1676 (childStyle.clear() & ClearLeft)) || | 1676 (childStyle.clear() & ClearLeft)) || |
1677 (prevFloat->styleRef().floating() == EFloat::Right && | 1677 (prevFloat->styleRef().floating() == EFloat::kRight && |
1678 (childStyle.clear() & ClearRight)))); | 1678 (childStyle.clear() & ClearRight)))); |
1679 prevFloat = child; | 1679 prevFloat = child; |
1680 } else { | 1680 } else { |
1681 clearPreviousFloat = false; | 1681 clearPreviousFloat = false; |
1682 } | 1682 } |
1683 | 1683 |
1684 bool canBreakReplacedElement = !child->isImage() || allowImagesToBreak; | 1684 bool canBreakReplacedElement = !child->isImage() || allowImagesToBreak; |
1685 if ((canBreakReplacedElement && (autoWrap || oldAutoWrap) && | 1685 if ((canBreakReplacedElement && (autoWrap || oldAutoWrap) && |
1686 (!isPrevChildInlineFlow || shouldBreakLineAfterText)) || | 1686 (!isPrevChildInlineFlow || shouldBreakLineAfterText)) || |
1687 clearPreviousFloat) { | 1687 clearPreviousFloat) { |
(...skipping 662 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2350 fullstopCharacter}; | 2350 fullstopCharacter}; |
2351 DEFINE_STATIC_LOCAL(AtomicString, fullstopCharacterStr, | 2351 DEFINE_STATIC_LOCAL(AtomicString, fullstopCharacterStr, |
2352 (fullStopString, fullStopStringLength)); | 2352 (fullStopString, fullStopStringLength)); |
2353 DEFINE_STATIC_LOCAL(AtomicString, ellipsisStr, | 2353 DEFINE_STATIC_LOCAL(AtomicString, ellipsisStr, |
2354 (&horizontalEllipsisCharacter, 1)); | 2354 (&horizontalEllipsisCharacter, 1)); |
2355 AtomicString& selectedEllipsisStr = ellipsisStr; | 2355 AtomicString& selectedEllipsisStr = ellipsisStr; |
2356 | 2356 |
2357 const Font& firstLineFont = firstLineStyle()->font(); | 2357 const Font& firstLineFont = firstLineStyle()->font(); |
2358 // FIXME: We should probably not hard-code the direction here. | 2358 // FIXME: We should probably not hard-code the direction here. |
2359 // https://crbug.com/333004 | 2359 // https://crbug.com/333004 |
2360 TextDirection ellipsisDirection = TextDirection::Ltr; | 2360 TextDirection ellipsisDirection = TextDirection::kLtr; |
2361 float firstLineEllipsisWidth = 0; | 2361 float firstLineEllipsisWidth = 0; |
2362 float ellipsisWidth = 0; | 2362 float ellipsisWidth = 0; |
2363 | 2363 |
2364 // As per CSS3 http://www.w3.org/TR/2003/CR-css3-text-20030514/ sequence of | 2364 // As per CSS3 http://www.w3.org/TR/2003/CR-css3-text-20030514/ sequence of |
2365 // three Full Stops (002E) can be used. | 2365 // three Full Stops (002E) can be used. |
2366 const SimpleFontData* fontData = firstLineFont.primaryFont(); | 2366 const SimpleFontData* fontData = firstLineFont.primaryFont(); |
2367 DCHECK(fontData); | 2367 DCHECK(fontData); |
2368 if (fontData && fontData->glyphForCharacter(horizontalEllipsisCharacter)) { | 2368 if (fontData && fontData->glyphForCharacter(horizontalEllipsisCharacter)) { |
2369 firstLineEllipsisWidth = firstLineFont.width( | 2369 firstLineEllipsisWidth = firstLineFont.width( |
2370 constructTextRun(firstLineFont, &horizontalEllipsisCharacter, 1, | 2370 constructTextRun(firstLineFont, &horizontalEllipsisCharacter, 1, |
(...skipping 92 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2463 } | 2463 } |
2464 } | 2464 } |
2465 | 2465 |
2466 LayoutUnit LayoutBlockFlow::startAlignedOffsetForLine( | 2466 LayoutUnit LayoutBlockFlow::startAlignedOffsetForLine( |
2467 LayoutUnit position, | 2467 LayoutUnit position, |
2468 IndentTextOrNot indentText) { | 2468 IndentTextOrNot indentText) { |
2469 ETextAlign textAlign = style()->textAlign(); | 2469 ETextAlign textAlign = style()->textAlign(); |
2470 | 2470 |
2471 bool applyIndentText; | 2471 bool applyIndentText; |
2472 switch (textAlign) { // FIXME: Handle TAEND here | 2472 switch (textAlign) { // FIXME: Handle TAEND here |
2473 case ETextAlign::Left: | 2473 case ETextAlign::kLeft: |
2474 case ETextAlign::WebkitLeft: | 2474 case ETextAlign::kWebkitLeft: |
2475 applyIndentText = style()->isLeftToRightDirection(); | 2475 applyIndentText = style()->isLeftToRightDirection(); |
2476 break; | 2476 break; |
2477 case ETextAlign::Right: | 2477 case ETextAlign::kRight: |
2478 case ETextAlign::WebkitRight: | 2478 case ETextAlign::kWebkitRight: |
2479 applyIndentText = !style()->isLeftToRightDirection(); | 2479 applyIndentText = !style()->isLeftToRightDirection(); |
2480 break; | 2480 break; |
2481 case ETextAlign::Start: | 2481 case ETextAlign::kStart: |
2482 applyIndentText = true; | 2482 applyIndentText = true; |
2483 break; | 2483 break; |
2484 default: | 2484 default: |
2485 applyIndentText = false; | 2485 applyIndentText = false; |
2486 } | 2486 } |
2487 | 2487 |
2488 if (applyIndentText) | 2488 if (applyIndentText) |
2489 return startOffsetForLine(position, indentText); | 2489 return startOffsetForLine(position, indentText); |
2490 | 2490 |
2491 // updateLogicalWidthForAlignment() handles the direction of the block so no | 2491 // updateLogicalWidthForAlignment() handles the direction of the block so no |
(...skipping 19 matching lines...) Expand all Loading... |
2511 | 2511 |
2512 bool LayoutBlockFlow::paintedOutputOfObjectHasNoEffectRegardlessOfSize() const { | 2512 bool LayoutBlockFlow::paintedOutputOfObjectHasNoEffectRegardlessOfSize() const { |
2513 // LayoutBlockFlow is in charge of paint invalidation of the first line. | 2513 // LayoutBlockFlow is in charge of paint invalidation of the first line. |
2514 if (firstLineBox()) | 2514 if (firstLineBox()) |
2515 return false; | 2515 return false; |
2516 | 2516 |
2517 return LayoutBlock::paintedOutputOfObjectHasNoEffectRegardlessOfSize(); | 2517 return LayoutBlock::paintedOutputOfObjectHasNoEffectRegardlessOfSize(); |
2518 } | 2518 } |
2519 | 2519 |
2520 } // namespace blink | 2520 } // namespace blink |
OLD | NEW |