diff --git a/layout/html/table/src/nsTableFrame.cpp b/layout/html/table/src/nsTableFrame.cpp index 5644d6458eb..5672306a001 100644 --- a/layout/html/table/src/nsTableFrame.cpp +++ b/layout/html/table/src/nsTableFrame.cpp @@ -1741,7 +1741,7 @@ NS_METHOD nsTableFrame::Reflow(nsIPresContext* aPresContext, // See if we are supposed to compute our maximum width if (aDesiredSize.mFlags & NS_REFLOW_CALC_MAX_WIDTH) { - PRBool isAutoOrPctWidth = IsAutoLayout(&aReflowState) && + PRBool isAutoOrPctWidth = IsAutoLayout() && ((eStyleUnit_Auto == aReflowState.mStylePosition->mWidth.GetUnit() || (eStyleUnit_Percent == aReflowState.mStylePosition->mWidth.GetUnit()))); @@ -1827,7 +1827,7 @@ NS_METHOD nsTableFrame::ResizeReflowPass1(nsIPresContext* aPresContext, // Compute the insets (sum of border and padding) // XXX: since this is pass1 reflow and where we place the rowgroup frames is irrelevant, insets are probably a waste - if (IsAutoLayout(&aReflowState)) { + if (IsAutoLayout()) { nsVoidArray rowGroups; PRUint32 numRowGroups; OrderRowGroups(rowGroups, numRowGroups, nsnull); @@ -3059,7 +3059,7 @@ NS_METHOD nsTableFrame::ReflowMappedChildren(nsIPresContext* aPresContext nscoord cellSpacingY = GetCellSpacingY(); nsReflowReason reason; - if (!IsAutoLayout(&aReflowState.reflowState)) { + if (!IsAutoLayout()) { reason = aReflowState.reflowState.reason; if (eReflowReason_Incremental==reason) { reason = eReflowReason_Resize; @@ -3387,7 +3387,7 @@ void nsTableFrame::BalanceColumnWidths(nsIPresContext* aPresContext, if (nsnull == mTableLayoutStrategy) { nsCompatibility mode; aPresContext->GetCompatibilityMode(&mode); - if (!IsAutoLayout(&aReflowState)) + if (!IsAutoLayout()) mTableLayoutStrategy = new FixedTableLayoutStrategy(this); else mTableLayoutStrategy = new BasicTableLayoutStrategy(this, eCompatibility_NavQuirks == mode); @@ -3396,7 +3396,7 @@ void nsTableFrame::BalanceColumnWidths(nsIPresContext* aPresContext, } // fixed-layout tables need to reinitialize the layout strategy. When there are scroll bars // reflow gets called twice and the 2nd time has the correct space available. - else if (!IsAutoLayout(&aReflowState)) { + else if (!IsAutoLayout()) { mTableLayoutStrategy->Initialize(aPresContext, aMaxElementSize, boxWidth, aReflowState); } @@ -4263,20 +4263,15 @@ void nsTableFrame::SetMaxElementSize(nsSize* aMaxElementSize, } -PRBool nsTableFrame::IsAutoLayout(const nsHTMLReflowState* aReflowState) +PRBool +nsTableFrame::IsAutoLayout() { const nsStyleTable* tableStyle; GetStyleData(eStyleStruct_Table, (const nsStyleStruct *&)tableStyle); - // a fixed table-layout table with an auto width is not considered as such - // for purposes of requiring pass1 reflow and assigning a layout strategy if (NS_STYLE_TABLE_LAYOUT_FIXED == tableStyle->mLayoutStrategy) { const nsStylePosition* position; - if (aReflowState) { - position = aReflowState->mStylePosition; - } - else { - GetStyleData(eStyleStruct_Position, (const nsStyleStruct *&)position); - } + GetStyleData(eStyleStruct_Position, (const nsStyleStruct *&)position); + // a fixed-layout table must have a width if (eStyleUnit_Auto != position->mWidth.GetUnit()) { return PR_FALSE; } diff --git a/layout/html/table/src/nsTableFrame.h b/layout/html/table/src/nsTableFrame.h index b6c58277b8b..ea2eb6ebc44 100644 --- a/layout/html/table/src/nsTableFrame.h +++ b/layout/html/table/src/nsTableFrame.h @@ -807,7 +807,7 @@ public: /* ----- Cell Map public methods ----- */ const nsMargin& aPadding); /** returns PR_TRUE if table layout requires a preliminary pass over the content */ - virtual PRBool IsAutoLayout(const nsHTMLReflowState* aReflowState = nsnull); + virtual PRBool IsAutoLayout(); // compute the height of the table to be used as the basis for // percentage height cells diff --git a/layout/html/table/src/nsTableRowFrame.cpp b/layout/html/table/src/nsTableRowFrame.cpp index 7507961ebf6..bdefcdeee94 100644 --- a/layout/html/table/src/nsTableRowFrame.cpp +++ b/layout/html/table/src/nsTableRowFrame.cpp @@ -839,6 +839,8 @@ NS_METHOD nsTableRowFrame::ResizeReflow(nsIPresContext* aPresContext, PRInt32 prevColIndex; // remember the col index of the previous cell to handle rowspans into this row + nsTableFrame* tableFrame = nsnull; + rv = nsTableFrame::GetTableFrame(this, tableFrame); nsTableIteration dir = (aReflowState.reflowState.availableWidth == NS_UNCONSTRAINEDSIZE) ? eTableLTR : eTableDIR; nsTableIterator iter(aPresContext, *this, dir); @@ -846,14 +848,13 @@ NS_METHOD nsTableRowFrame::ResizeReflow(nsIPresContext* aPresContext, prevColIndex = -1; } else { - nsTableFrame* tableFrame = nsnull; - rv = nsTableFrame::GetTableFrame(this, tableFrame); if (NS_FAILED(rv) || (nsnull == tableFrame)) { return rv; } prevColIndex = tableFrame->GetColCount(); } + PRBool isAutoLayout = tableFrame->IsAutoLayout(); // Reflow each of our existing cell frames nsIFrame* kidFrame = iter.First(); while (nsnull != kidFrame) { @@ -870,9 +871,9 @@ NS_METHOD nsTableRowFrame::ResizeReflow(nsIPresContext* aPresContext, } // Reflow the child frame + const nsStyleDisplay *kidDisplay; + kidFrame->GetStyleData(eStyleStruct_Display, ((const nsStyleStruct *&)kidDisplay)); if (doReflowChild) { - const nsStyleDisplay *kidDisplay; - kidFrame->GetStyleData(eStyleStruct_Display, ((const nsStyleStruct *&)kidDisplay)); if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay) { PRInt32 cellColIndex; ((nsTableCellFrame *)kidFrame)->GetColIndex(cellColIndex); @@ -908,7 +909,7 @@ NS_METHOD nsTableRowFrame::ResizeReflow(nsIPresContext* aPresContext, // Calculate the available width for the table cell using the known // column widths nscoord availWidth; - if (!mPrevInFlow && (frameState & NS_FRAME_FIRST_REFLOW)) { + if (!mPrevInFlow && isAutoLayout && (frameState & NS_FRAME_FIRST_REFLOW)) { // This is the initial reflow for the cell and so we do an unconstrained // reflow. // Note: don't assume that we have known column widths. If we don't, then @@ -942,11 +943,9 @@ NS_METHOD nsTableRowFrame::ResizeReflow(nsIPresContext* aPresContext, nsSize kidAvailSize(availWidth, aReflowState.reflowState.availableHeight); // If it's a dirty frame, then check whether it's the initial reflow - nsReflowReason reason = eReflowReason_Resize; - if (!mPrevInFlow && (frameState & NS_FRAME_FIRST_REFLOW)) { - // Newly inserted frame - reason = eReflowReason_Initial; - + nsReflowReason reason = + (frameState & NS_FRAME_FIRST_REFLOW) ? eReflowReason_Initial :eReflowReason_Resize; + if (!mPrevInFlow && isAutoLayout && (frameState & NS_FRAME_FIRST_REFLOW)) { // Use an unconstrained width so we can get the child's maximum width // XXX What about fixed layout tables? kidAvailSize.SizeTo(NS_UNCONSTRAINEDSIZE, NS_UNCONSTRAINEDSIZE); @@ -983,6 +982,8 @@ NS_METHOD nsTableRowFrame::ResizeReflow(nsIPresContext* aPresContext, if (kidMaxElementSize) { ((nsTableCellFrame *)kidFrame)->SetPass1MaxElementSize(*kidMaxElementSize); } + // XXX if we did an unconstrained reflow, do we need to do another one + // there needs to be more test cases to show this } // If any of the cells are not complete, then we're not complete @@ -1037,6 +1038,12 @@ NS_METHOD nsTableRowFrame::ResizeReflow(nsIPresContext* aPresContext, kidFrame->DidReflow(aPresContext, NS_FRAME_REFLOW_FINISHED); } } + else if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay) { + // we need to account for the cell's width even if it isn't reflowed + nsRect rect; + kidFrame->GetRect(rect); + aReflowState.x += rect.width; + } kidFrame = iter.Next(); // Get the next child // if this was the last child, and it had a colspan>1, add in the cellSpacing for the colspan @@ -1082,7 +1089,7 @@ nsTableRowFrame::InitialReflow(nsIPresContext* aPresContext, nsSize kidMaxElementSize(0,0); nscoord x = 0; nsTableFrame* table = aReflowState.tableFrame; - PRBool isAutoLayout = table->IsAutoLayout(&aReflowState.reflowState); + PRBool isAutoLayout = table->IsAutoLayout(); nscoord cellSpacingX = table->GetCellSpacingX(); nsIFrame* kidFrame; diff --git a/layout/tables/nsTableFrame.cpp b/layout/tables/nsTableFrame.cpp index 5644d6458eb..5672306a001 100644 --- a/layout/tables/nsTableFrame.cpp +++ b/layout/tables/nsTableFrame.cpp @@ -1741,7 +1741,7 @@ NS_METHOD nsTableFrame::Reflow(nsIPresContext* aPresContext, // See if we are supposed to compute our maximum width if (aDesiredSize.mFlags & NS_REFLOW_CALC_MAX_WIDTH) { - PRBool isAutoOrPctWidth = IsAutoLayout(&aReflowState) && + PRBool isAutoOrPctWidth = IsAutoLayout() && ((eStyleUnit_Auto == aReflowState.mStylePosition->mWidth.GetUnit() || (eStyleUnit_Percent == aReflowState.mStylePosition->mWidth.GetUnit()))); @@ -1827,7 +1827,7 @@ NS_METHOD nsTableFrame::ResizeReflowPass1(nsIPresContext* aPresContext, // Compute the insets (sum of border and padding) // XXX: since this is pass1 reflow and where we place the rowgroup frames is irrelevant, insets are probably a waste - if (IsAutoLayout(&aReflowState)) { + if (IsAutoLayout()) { nsVoidArray rowGroups; PRUint32 numRowGroups; OrderRowGroups(rowGroups, numRowGroups, nsnull); @@ -3059,7 +3059,7 @@ NS_METHOD nsTableFrame::ReflowMappedChildren(nsIPresContext* aPresContext nscoord cellSpacingY = GetCellSpacingY(); nsReflowReason reason; - if (!IsAutoLayout(&aReflowState.reflowState)) { + if (!IsAutoLayout()) { reason = aReflowState.reflowState.reason; if (eReflowReason_Incremental==reason) { reason = eReflowReason_Resize; @@ -3387,7 +3387,7 @@ void nsTableFrame::BalanceColumnWidths(nsIPresContext* aPresContext, if (nsnull == mTableLayoutStrategy) { nsCompatibility mode; aPresContext->GetCompatibilityMode(&mode); - if (!IsAutoLayout(&aReflowState)) + if (!IsAutoLayout()) mTableLayoutStrategy = new FixedTableLayoutStrategy(this); else mTableLayoutStrategy = new BasicTableLayoutStrategy(this, eCompatibility_NavQuirks == mode); @@ -3396,7 +3396,7 @@ void nsTableFrame::BalanceColumnWidths(nsIPresContext* aPresContext, } // fixed-layout tables need to reinitialize the layout strategy. When there are scroll bars // reflow gets called twice and the 2nd time has the correct space available. - else if (!IsAutoLayout(&aReflowState)) { + else if (!IsAutoLayout()) { mTableLayoutStrategy->Initialize(aPresContext, aMaxElementSize, boxWidth, aReflowState); } @@ -4263,20 +4263,15 @@ void nsTableFrame::SetMaxElementSize(nsSize* aMaxElementSize, } -PRBool nsTableFrame::IsAutoLayout(const nsHTMLReflowState* aReflowState) +PRBool +nsTableFrame::IsAutoLayout() { const nsStyleTable* tableStyle; GetStyleData(eStyleStruct_Table, (const nsStyleStruct *&)tableStyle); - // a fixed table-layout table with an auto width is not considered as such - // for purposes of requiring pass1 reflow and assigning a layout strategy if (NS_STYLE_TABLE_LAYOUT_FIXED == tableStyle->mLayoutStrategy) { const nsStylePosition* position; - if (aReflowState) { - position = aReflowState->mStylePosition; - } - else { - GetStyleData(eStyleStruct_Position, (const nsStyleStruct *&)position); - } + GetStyleData(eStyleStruct_Position, (const nsStyleStruct *&)position); + // a fixed-layout table must have a width if (eStyleUnit_Auto != position->mWidth.GetUnit()) { return PR_FALSE; } diff --git a/layout/tables/nsTableFrame.h b/layout/tables/nsTableFrame.h index b6c58277b8b..ea2eb6ebc44 100644 --- a/layout/tables/nsTableFrame.h +++ b/layout/tables/nsTableFrame.h @@ -807,7 +807,7 @@ public: /* ----- Cell Map public methods ----- */ const nsMargin& aPadding); /** returns PR_TRUE if table layout requires a preliminary pass over the content */ - virtual PRBool IsAutoLayout(const nsHTMLReflowState* aReflowState = nsnull); + virtual PRBool IsAutoLayout(); // compute the height of the table to be used as the basis for // percentage height cells diff --git a/layout/tables/nsTableRowFrame.cpp b/layout/tables/nsTableRowFrame.cpp index 7507961ebf6..bdefcdeee94 100644 --- a/layout/tables/nsTableRowFrame.cpp +++ b/layout/tables/nsTableRowFrame.cpp @@ -839,6 +839,8 @@ NS_METHOD nsTableRowFrame::ResizeReflow(nsIPresContext* aPresContext, PRInt32 prevColIndex; // remember the col index of the previous cell to handle rowspans into this row + nsTableFrame* tableFrame = nsnull; + rv = nsTableFrame::GetTableFrame(this, tableFrame); nsTableIteration dir = (aReflowState.reflowState.availableWidth == NS_UNCONSTRAINEDSIZE) ? eTableLTR : eTableDIR; nsTableIterator iter(aPresContext, *this, dir); @@ -846,14 +848,13 @@ NS_METHOD nsTableRowFrame::ResizeReflow(nsIPresContext* aPresContext, prevColIndex = -1; } else { - nsTableFrame* tableFrame = nsnull; - rv = nsTableFrame::GetTableFrame(this, tableFrame); if (NS_FAILED(rv) || (nsnull == tableFrame)) { return rv; } prevColIndex = tableFrame->GetColCount(); } + PRBool isAutoLayout = tableFrame->IsAutoLayout(); // Reflow each of our existing cell frames nsIFrame* kidFrame = iter.First(); while (nsnull != kidFrame) { @@ -870,9 +871,9 @@ NS_METHOD nsTableRowFrame::ResizeReflow(nsIPresContext* aPresContext, } // Reflow the child frame + const nsStyleDisplay *kidDisplay; + kidFrame->GetStyleData(eStyleStruct_Display, ((const nsStyleStruct *&)kidDisplay)); if (doReflowChild) { - const nsStyleDisplay *kidDisplay; - kidFrame->GetStyleData(eStyleStruct_Display, ((const nsStyleStruct *&)kidDisplay)); if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay) { PRInt32 cellColIndex; ((nsTableCellFrame *)kidFrame)->GetColIndex(cellColIndex); @@ -908,7 +909,7 @@ NS_METHOD nsTableRowFrame::ResizeReflow(nsIPresContext* aPresContext, // Calculate the available width for the table cell using the known // column widths nscoord availWidth; - if (!mPrevInFlow && (frameState & NS_FRAME_FIRST_REFLOW)) { + if (!mPrevInFlow && isAutoLayout && (frameState & NS_FRAME_FIRST_REFLOW)) { // This is the initial reflow for the cell and so we do an unconstrained // reflow. // Note: don't assume that we have known column widths. If we don't, then @@ -942,11 +943,9 @@ NS_METHOD nsTableRowFrame::ResizeReflow(nsIPresContext* aPresContext, nsSize kidAvailSize(availWidth, aReflowState.reflowState.availableHeight); // If it's a dirty frame, then check whether it's the initial reflow - nsReflowReason reason = eReflowReason_Resize; - if (!mPrevInFlow && (frameState & NS_FRAME_FIRST_REFLOW)) { - // Newly inserted frame - reason = eReflowReason_Initial; - + nsReflowReason reason = + (frameState & NS_FRAME_FIRST_REFLOW) ? eReflowReason_Initial :eReflowReason_Resize; + if (!mPrevInFlow && isAutoLayout && (frameState & NS_FRAME_FIRST_REFLOW)) { // Use an unconstrained width so we can get the child's maximum width // XXX What about fixed layout tables? kidAvailSize.SizeTo(NS_UNCONSTRAINEDSIZE, NS_UNCONSTRAINEDSIZE); @@ -983,6 +982,8 @@ NS_METHOD nsTableRowFrame::ResizeReflow(nsIPresContext* aPresContext, if (kidMaxElementSize) { ((nsTableCellFrame *)kidFrame)->SetPass1MaxElementSize(*kidMaxElementSize); } + // XXX if we did an unconstrained reflow, do we need to do another one + // there needs to be more test cases to show this } // If any of the cells are not complete, then we're not complete @@ -1037,6 +1038,12 @@ NS_METHOD nsTableRowFrame::ResizeReflow(nsIPresContext* aPresContext, kidFrame->DidReflow(aPresContext, NS_FRAME_REFLOW_FINISHED); } } + else if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay) { + // we need to account for the cell's width even if it isn't reflowed + nsRect rect; + kidFrame->GetRect(rect); + aReflowState.x += rect.width; + } kidFrame = iter.Next(); // Get the next child // if this was the last child, and it had a colspan>1, add in the cellSpacing for the colspan @@ -1082,7 +1089,7 @@ nsTableRowFrame::InitialReflow(nsIPresContext* aPresContext, nsSize kidMaxElementSize(0,0); nscoord x = 0; nsTableFrame* table = aReflowState.tableFrame; - PRBool isAutoLayout = table->IsAutoLayout(&aReflowState.reflowState); + PRBool isAutoLayout = table->IsAutoLayout(); nscoord cellSpacingX = table->GetCellSpacingX(); nsIFrame* kidFrame;