Bug 379349. Add support for 'overflow containers' --- special frame continuations that do not map any content of their own, but serve only as containers for laying out children that overflowed their parents' content height. patch by fantasai, r+sr=eli,roc
This commit is contained in:
@@ -75,7 +75,14 @@ public:
|
||||
virtual nsIFrame* GetContentInsertionFrame() {
|
||||
return GetFirstChild(nsnull)->GetContentInsertionFrame();
|
||||
}
|
||||
|
||||
|
||||
virtual nsresult StealFrame(nsPresContext* aPresContext,
|
||||
nsIFrame* aChild,
|
||||
PRBool aForceNormal)
|
||||
{ // nsColumnSetFrame keeps overflow containers in main child list
|
||||
return nsContainerFrame::StealFrame(aPresContext, aChild, PR_TRUE);
|
||||
}
|
||||
|
||||
NS_IMETHOD BuildDisplayList(nsDisplayListBuilder* aBuilder,
|
||||
const nsRect& aDirtyRect,
|
||||
const nsDisplayListSet& aLists);
|
||||
@@ -440,9 +447,9 @@ nsColumnSetFrame::ReflowChildren(nsHTMLReflowMetrics& aDesiredSize,
|
||||
// might be pullable back to this column. We can't skip if it's the last child
|
||||
// because we need to obtain the bottom margin.
|
||||
PRBool skipIncremental = !(GetStateBits() & NS_FRAME_IS_DIRTY)
|
||||
&& !(child->GetStateBits() & NS_FRAME_IS_DIRTY)
|
||||
&& !NS_SUBTREE_DIRTY(child)
|
||||
&& child->GetNextSibling()
|
||||
&& !(child->GetNextSibling()->GetStateBits() & NS_FRAME_IS_DIRTY);
|
||||
&& !NS_SUBTREE_DIRTY(child->GetNextSibling());
|
||||
// If we need to pull up content from the prev-in-flow then this is not just
|
||||
// a height shrink. The prev in flow will have set the dirty bit.
|
||||
// Check the overflow rect YMost instead of just the child's content height. The child
|
||||
@@ -457,8 +464,11 @@ nsColumnSetFrame::ReflowChildren(nsHTMLReflowMetrics& aDesiredSize,
|
||||
MoveChildTo(this, child, childOrigin);
|
||||
|
||||
// If this is the last frame then make sure we get the right status
|
||||
if (child->GetNextSibling()) {
|
||||
aStatus = NS_FRAME_NOT_COMPLETE;
|
||||
nsIFrame* kidNext = child->GetNextSibling();
|
||||
if (kidNext) {
|
||||
aStatus = (kidNext->GetStateBits() & NS_FRAME_IS_OVERFLOW_CONTAINER)
|
||||
? NS_FRAME_OVERFLOW_INCOMPLETE
|
||||
: NS_FRAME_NOT_COMPLETE;
|
||||
} else {
|
||||
aStatus = mLastFrameStatus;
|
||||
}
|
||||
@@ -536,7 +546,7 @@ nsColumnSetFrame::ReflowChildren(nsHTMLReflowMetrics& aDesiredSize,
|
||||
// Build a continuation column if necessary
|
||||
nsIFrame* kidNextInFlow = child->GetNextInFlow();
|
||||
|
||||
if (NS_FRAME_IS_COMPLETE(aStatus) && !NS_FRAME_IS_TRUNCATED(aStatus)) {
|
||||
if (NS_FRAME_IS_FULLY_COMPLETE(aStatus) && !NS_FRAME_IS_TRUNCATED(aStatus)) {
|
||||
NS_ASSERTION(!kidNextInFlow, "next in flow should have been deleted");
|
||||
break;
|
||||
} else {
|
||||
@@ -557,6 +567,21 @@ nsColumnSetFrame::ReflowChildren(nsHTMLReflowMetrics& aDesiredSize,
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Make sure we reflow a next-in-flow when it switches between being
|
||||
// normal or overflow container
|
||||
if (NS_FRAME_OVERFLOW_IS_INCOMPLETE(aStatus)) {
|
||||
if (!(kidNextInFlow->GetStateBits() & NS_FRAME_IS_OVERFLOW_CONTAINER)) {
|
||||
aStatus |= NS_FRAME_REFLOW_NEXTINFLOW;
|
||||
reflowNext = PR_TRUE;
|
||||
kidNextInFlow->AddStateBits(NS_FRAME_IS_OVERFLOW_CONTAINER);
|
||||
}
|
||||
}
|
||||
else if (kidNextInFlow->GetStateBits() & NS_FRAME_IS_OVERFLOW_CONTAINER) {
|
||||
aStatus |= NS_FRAME_REFLOW_NEXTINFLOW;
|
||||
reflowNext = PR_TRUE;
|
||||
kidNextInFlow->RemoveStateBits(NS_FRAME_IS_OVERFLOW_CONTAINER);
|
||||
}
|
||||
|
||||
if (columnCount >= aConfig.mBalanceColCount) {
|
||||
// No more columns allowed here. Stop.
|
||||
|
||||
Reference in New Issue
Block a user