OLD | NEW |
1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "core/paint/PaintPropertyTreeBuilder.h" | 5 #include "core/paint/PaintPropertyTreeBuilder.h" |
6 | 6 |
7 #include "core/frame/FrameView.h" | 7 #include "core/frame/FrameView.h" |
8 #include "core/frame/LocalFrame.h" | 8 #include "core/frame/LocalFrame.h" |
9 #include "core/frame/Settings.h" | 9 #include "core/frame/Settings.h" |
10 #include "core/layout/LayoutInline.h" | 10 #include "core/layout/LayoutInline.h" |
(...skipping 648 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
659 cssClip->clipRect()); | 659 cssClip->clipRect()); |
660 return; | 660 return; |
661 } | 661 } |
662 } | 662 } |
663 | 663 |
664 if (ObjectPaintProperties* properties = | 664 if (ObjectPaintProperties* properties = |
665 object.getMutableForPainting().objectPaintProperties()) | 665 object.getMutableForPainting().objectPaintProperties()) |
666 properties->clearCssClipFixedPosition(); | 666 properties->clearCssClipFixedPosition(); |
667 } | 667 } |
668 | 668 |
| 669 // Override ContainingBlockContext based on the properties of a containing block |
| 670 // that was previously walked in a subtree other than the current subtree being |
| 671 // walked. Used for out-of-flow positioned descendants of multi-column spanner |
| 672 // when the containing block is not in the normal tree walk order. |
| 673 // For example: |
| 674 // <div id="columns" style="columns: 2"> |
| 675 // <div id="relative" style="position: relative"> |
| 676 // <div id="spanner" style="column-span: all"> |
| 677 // <div id="absolute" style="position: absolute"></div> |
| 678 // </div> |
| 679 // </div> |
| 680 // <div> |
| 681 // The real containing block of "absolute" is "relative" which is not in the |
| 682 // tree-walk order of "columns" -> spanner placeholder -> spanner -> absolute. |
| 683 // Here we rebuild a ContainingBlockContext based on the properties of |
| 684 // "relative" for "absolute". |
| 685 static void overrideContaineringBlockContextFromRealContainingBlock( |
| 686 const LayoutBlock& containingBlock, |
| 687 PaintPropertyTreeBuilderContext::ContainingBlockContext& context) { |
| 688 const auto* properties = |
| 689 containingBlock.objectPaintProperties()->localBorderBoxProperties(); |
| 690 DCHECK(properties); |
| 691 |
| 692 context.transform = properties->propertyTreeState.transform(); |
| 693 context.paintOffset = properties->paintOffset; |
| 694 context.shouldFlattenInheritedTransform = |
| 695 context.transform && context.transform->flattensInheritedTransform(); |
| 696 context.renderingContextID = |
| 697 context.transform ? context.transform->renderingContextID() : 0; |
| 698 context.clip = properties->propertyTreeState.clip(); |
| 699 context.scroll = const_cast<ScrollPaintPropertyNode*>( |
| 700 properties->propertyTreeState.scroll()); |
| 701 } |
| 702 |
669 static void deriveBorderBoxFromContainerContext( | 703 static void deriveBorderBoxFromContainerContext( |
670 const LayoutObject& object, | 704 const LayoutObject& object, |
671 PaintPropertyTreeBuilderContext& context) { | 705 PaintPropertyTreeBuilderContext& context) { |
672 if (!object.isBoxModelObject()) | 706 if (!object.isBoxModelObject()) |
673 return; | 707 return; |
674 | 708 |
675 const LayoutBoxModelObject& boxModelObject = toLayoutBoxModelObject(object); | 709 const LayoutBoxModelObject& boxModelObject = toLayoutBoxModelObject(object); |
676 | 710 |
677 switch (object.styleRef().position()) { | 711 switch (object.styleRef().position()) { |
678 case StaticPosition: | 712 case StaticPosition: |
679 break; | 713 break; |
680 case RelativePosition: | 714 case RelativePosition: |
681 context.current.paintOffset += boxModelObject.offsetForInFlowPosition(); | 715 context.current.paintOffset += boxModelObject.offsetForInFlowPosition(); |
682 break; | 716 break; |
683 case AbsolutePosition: { | 717 case AbsolutePosition: { |
684 context.current = context.absolutePosition; | 718 if (context.isUnderMultiColumnSpanner) { |
| 719 const LayoutObject* container = boxModelObject.container(); |
| 720 if (container != context.containerForAbsolutePosition) { |
| 721 // The container of the absolute-position is not in the normal tree- |
| 722 // walk order. |
| 723 context.containerForAbsolutePosition = |
| 724 toLayoutBoxModelObject(container); |
| 725 // The container is never a LayoutInline. In the example above |
| 726 // overrideContaineringBlockContextFromRealContainingBlock(), if we |
| 727 // change the container to an inline, there will be an anonymous |
| 728 // blocks created because the spanner is always a block. |
| 729 overrideContaineringBlockContextFromRealContainingBlock( |
| 730 toLayoutBlock(*container), context.current); |
| 731 } |
| 732 } else { |
| 733 DCHECK(context.containerForAbsolutePosition == |
| 734 boxModelObject.container()); |
| 735 context.current = context.absolutePosition; |
| 736 } |
685 | 737 |
686 // Absolutely positioned content in an inline should be positioned | 738 // Absolutely positioned content in an inline should be positioned |
687 // relative to the inline. | 739 // relative to the inline. |
688 const LayoutObject* container = context.containerForAbsolutePosition; | 740 const LayoutObject* container = context.containerForAbsolutePosition; |
689 if (container && container->isInFlowPositioned() && | 741 if (container && container->isInFlowPositioned() && |
690 container->isLayoutInline()) { | 742 container->isLayoutInline()) { |
691 DCHECK(object.isBox()); | 743 DCHECK(object.isBox()); |
692 context.current.paintOffset += | 744 context.current.paintOffset += |
693 toLayoutInline(container)->offsetForInFlowPositionedInline( | 745 toLayoutInline(container)->offsetForInFlowPositionedInline( |
694 toLayoutBox(object)); | 746 toLayoutBox(object)); |
695 } | 747 } |
696 break; | 748 break; |
697 } | 749 } |
698 case StickyPosition: | 750 case StickyPosition: |
699 context.current.paintOffset += boxModelObject.offsetForInFlowPosition(); | 751 context.current.paintOffset += boxModelObject.offsetForInFlowPosition(); |
700 break; | 752 break; |
701 case FixedPosition: | 753 case FixedPosition: |
702 context.current = context.fixedPosition; | 754 if (context.isUnderMultiColumnSpanner) { |
| 755 // The container of the fixed-position object may or may not be in the |
| 756 // normal tree-walk order. |
| 757 overrideContaineringBlockContextFromRealContainingBlock( |
| 758 toLayoutBlock(*boxModelObject.container()), context.current); |
| 759 } else { |
| 760 context.current = context.fixedPosition; |
| 761 } |
703 break; | 762 break; |
704 default: | 763 default: |
705 ASSERT_NOT_REACHED(); | 764 ASSERT_NOT_REACHED(); |
706 } | 765 } |
707 | 766 |
708 // SVGForeignObject needs paint offset because its viewport offset is baked | 767 // SVGForeignObject needs paint offset because its viewport offset is baked |
709 // into its location(), while its localSVGTransform() doesn't contain the | 768 // into its location(), while its localSVGTransform() doesn't contain the |
710 // offset. | 769 // offset. |
711 if (boxModelObject.isBox() && | 770 if (boxModelObject.isBox() && |
712 (!boxModelObject.isSVG() || boxModelObject.isSVGRoot() || | 771 (!boxModelObject.isSVG() || boxModelObject.isSVGRoot() || |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
753 return; | 812 return; |
754 | 813 |
755 updateOverflowClip(object, context); | 814 updateOverflowClip(object, context); |
756 updatePerspective(object, context); | 815 updatePerspective(object, context); |
757 updateSvgLocalToBorderBoxTransform(object, context); | 816 updateSvgLocalToBorderBoxTransform(object, context); |
758 updateScrollAndScrollTranslation(object, context); | 817 updateScrollAndScrollTranslation(object, context); |
759 updateOutOfFlowContext(object, context); | 818 updateOutOfFlowContext(object, context); |
760 } | 819 } |
761 | 820 |
762 } // namespace blink | 821 } // namespace blink |
OLD | NEW |