Bug 1144096 part 6 - [css-grid] Add support for creating Grid container continuations and deal with overflow containers. r=dholbert
authorMats Palmgren <mats@mozilla.com>
Fri, 11 Mar 2016 17:39:26 +0100
changeset 288298 738a70d91d8c7c316c35274f75e61162fbd9d30f
parent 288297 6fa46d335b2817eeb4904390ab32b3ee45646a48
child 288299 1fbadb0b2f44ff5335e6cea6ed51cefcedf92ad5
push id30079
push userryanvm@gmail.com
push dateSat, 12 Mar 2016 20:24:19 +0000
treeherdermozilla-central@d1d47ba19ce9 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersdholbert
bugs1144096
milestone48.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1144096 part 6 - [css-grid] Add support for creating Grid container continuations and deal with overflow containers. r=dholbert
layout/base/nsCSSFrameConstructor.cpp
layout/generic/nsGridContainerFrame.cpp
layout/generic/nsGridContainerFrame.h
--- a/layout/base/nsCSSFrameConstructor.cpp
+++ b/layout/base/nsCSSFrameConstructor.cpp
@@ -8888,16 +8888,19 @@ nsCSSFrameConstructor::CreateContinuingF
     }
     newFrame = fieldset;
   } else if (nsGkAtoms::legendFrame == frameType) {
     newFrame = NS_NewLegendFrame(shell, styleContext);
     newFrame->Init(content, aParentFrame, aFrame);
   } else if (nsGkAtoms::flexContainerFrame == frameType) {
     newFrame = NS_NewFlexContainerFrame(shell, styleContext);
     newFrame->Init(content, aParentFrame, aFrame);
+  } else if (nsGkAtoms::gridContainerFrame == frameType) {
+    newFrame = NS_NewGridContainerFrame(shell, styleContext);
+    newFrame->Init(content, aParentFrame, aFrame);
   } else if (nsGkAtoms::rubyFrame == frameType) {
     newFrame = NS_NewRubyFrame(shell, styleContext);
     newFrame->Init(content, aParentFrame, aFrame);
   } else if (nsGkAtoms::rubyBaseContainerFrame == frameType) {
     newFrame = NS_NewRubyBaseContainerFrame(shell, styleContext);
     newFrame->Init(content, aParentFrame, aFrame);
   } else if (nsGkAtoms::rubyTextContainerFrame == frameType) {
     newFrame = NS_NewRubyTextContainerFrame(shell, styleContext);
--- a/layout/generic/nsGridContainerFrame.cpp
+++ b/layout/generic/nsGridContainerFrame.cpp
@@ -3737,16 +3737,24 @@ nsGridContainerFrame::GridReflowState::C
 void
 nsGridContainerFrame::ReflowChildren(GridReflowState&     aState,
                                      const LogicalRect&   aContentArea,
                                      nsHTMLReflowMetrics& aDesiredSize,
                                      nsReflowStatus&      aStatus)
 {
   MOZ_ASSERT(aState.mReflowState);
 
+  aStatus = NS_FRAME_COMPLETE;
+  nsOverflowAreas ocBounds;
+  nsReflowStatus ocStatus = NS_FRAME_COMPLETE;
+  if (GetPrevInFlow()) {
+    ReflowOverflowContainerChildren(PresContext(), *aState.mReflowState,
+                                    ocBounds, 0, ocStatus);
+  }
+
   WritingMode wm = aState.mReflowState->GetWritingMode();
   const LogicalPoint gridOrigin(aContentArea.Origin(wm));
   const nsSize containerSize =
     (aContentArea.Size(wm) +
      aState.mReflowState->ComputedLogicalBorderPadding().Size(wm)).GetPhysicalSize(wm);
   nsPresContext* pc = PresContext();
   nsStyleContext* containerSC = StyleContext();
   LogicalMargin pad(aState.mReflowState->ComputedLogicalPadding());
@@ -3823,16 +3831,20 @@ nsGridContainerFrame::ReflowChildren(Gri
     }
     childRS->ApplyRelativePositioning(&childPos, containerSize);
     FinishReflowChild(child, pc, *childSize, childRS.ptr(), childWM, childPos,
                       containerSize, 0);
     ConsiderChildOverflow(aDesiredSize.mOverflowAreas, child);
     // XXX deal with 'childStatus' not being COMPLETE (bug 1144096)
   }
 
+  // Merge overflow container bounds and status.
+  aDesiredSize.mOverflowAreas.UnionWith(ocBounds);
+  NS_MergeReflowStatusInto(&aStatus, ocStatus);
+
   if (IsAbsoluteContainer()) {
     nsFrameList children(GetChildList(GetAbsoluteListID()));
     if (!children.IsEmpty()) {
       // 'padStart' is the origin of the grid (the start of the first track),
       // with respect to the grid container's padding-box (CB).
       const LogicalRect gridCB(wm, 0, 0,
                                aContentArea.ISize(wm) + pad.IStartEnd(wm),
                                aContentArea.BSize(wm) + pad.BStartEnd(wm));
@@ -4043,16 +4055,19 @@ nsGridContainerFrame::GetType() const
 }
 
 void
 nsGridContainerFrame::BuildDisplayList(nsDisplayListBuilder*   aBuilder,
                                        const nsRect&           aDirtyRect,
                                        const nsDisplayListSet& aLists)
 {
   DisplayBorderBackgroundOutline(aBuilder, aLists);
+  if (GetPrevInFlow()) {
+    DisplayOverflowContainers(aBuilder, aDirtyRect, aLists);
+  }
 
   // Our children are all grid-level boxes, which behave the same as
   // inline-blocks in painting, so their borders/backgrounds all go on
   // the BlockBorderBackgrounds list.
   // Also, we capture positioned descendants so we can sort them by
   // CSS 'order'.
   nsDisplayList positionedDescendants;
   nsDisplayListSet childLists(aLists.BlockBorderBackgrounds(),
@@ -4097,19 +4112,18 @@ FrameWantsToBeInAnonymousGridItem(nsIFra
 // set up correctly -- in particular, we assert:
 //  (1) we don't have any inline non-replaced children
 //  (2) we don't have any consecutive anonymous grid items
 //  (3) we don't have any empty anonymous grid items
 //  (4) all children are on the expected child lists
 void
 nsGridContainerFrame::SanityCheckAnonymousGridItems() const
 {
-  // XXX handle kOverflowContainersList / kExcessOverflowContainersList
-  // when we implement fragmentation?
-  ChildListIDs noCheckLists = kAbsoluteList | kFixedList;
+  ChildListIDs noCheckLists = kAbsoluteList | kFixedList |
+    kOverflowContainersList | kExcessOverflowContainersList;
   ChildListIDs checkLists = kPrincipalList | kOverflowList;
   for (nsIFrame::ChildListIterator childLists(this);
        !childLists.IsDone(); childLists.Next()) {
     if (!checkLists.Contains(childLists.CurrentID())) {
       MOZ_ASSERT(noCheckLists.Contains(childLists.CurrentID()),
                  "unexpected non-empty child list");
       continue;
     }
--- a/layout/generic/nsGridContainerFrame.h
+++ b/layout/generic/nsGridContainerFrame.h
@@ -50,17 +50,22 @@ public:
   // nsIFrame overrides
   void Reflow(nsPresContext*           aPresContext,
               nsHTMLReflowMetrics&     aDesiredSize,
               const nsHTMLReflowState& aReflowState,
               nsReflowStatus&          aStatus) override;
   nscoord GetMinISize(nsRenderingContext* aRenderingContext) override;
   nscoord GetPrefISize(nsRenderingContext* aRenderingContext) override;
   void MarkIntrinsicISizesDirty() override;
-  virtual nsIAtom* GetType() const override;
+  nsIAtom* GetType() const override;
+  bool IsFrameOfType(uint32_t aFlags) const override
+  {
+    return nsContainerFrame::IsFrameOfType(aFlags &
+             ~nsIFrame::eCanContainOverflowContainers);
+  }
 
   void BuildDisplayList(nsDisplayListBuilder*   aBuilder,
                         const nsRect&           aDirtyRect,
                         const nsDisplayListSet& aLists) override;
 
 #ifdef DEBUG_FRAME_DUMP
   virtual nsresult GetFrameName(nsAString& aResult) const override;
 #endif