removed lots of assumptions about frame ordering and containership.

table frames no longer assume they are n levels below the inner table frame
table frames no longer assume their child frames are always the expected type of
frame.  Now they check the display type and use that as sufficient proof that the frame
is of the right type.  This implies a heavy reliance on the frame construction code to do
the right thing and always stamp out the right kind of frame for a given display type.
This commit is contained in:
buster%netscape.com 1998-09-24 16:37:22 +00:00
parent 5455f937e5
commit 0bec735087
16 changed files with 628 additions and 518 deletions

View File

@ -212,28 +212,6 @@ void nsTableCellFrame::CreatePsuedoFrame(nsIPresContext* aPresContext)
}
}
/*
* Should this be performanced tuned? This is called
* in resize/reflow. Maybe we should cache the table
* frame in the table cell frame.
*
*/
nsTableFrame* nsTableCellFrame::GetTableFrame()
{
nsIFrame* frame = nsnull;
nsresult result;
result = GetContentParent(frame); // Get RowFrame
if ((result == NS_OK) && (frame != nsnull))
frame->GetContentParent(frame); // Get RowGroupFrame
if ((result == NS_OK) && (frame != nsnull))
frame->GetContentParent(frame); // Get TableFrame
return (nsTableFrame*)frame;
}
PRInt32 nsTableCellFrame::GetRowSpan()
{
PRInt32 rowSpan=1;
@ -314,7 +292,8 @@ NS_METHOD nsTableCellFrame::Reflow(nsIPresContext& aPresContext,
// Get the margin information, available space should
// be reduced accordingly
nsMargin margin(0,0,0,0);
nsTableFrame* tableFrame = GetTableFrame();
nsTableFrame* tableFrame;
nsTableFrame::GetTableFrame(this, tableFrame);
tableFrame->GetCellMarginData(this,margin);
// get frame, creating one if needed
@ -341,7 +320,7 @@ NS_METHOD nsTableCellFrame::Reflow(nsIPresContext& aPresContext,
// fit or might need continuing.
if (availSize.height < 0)
availSize.height = 1;
nsSize maxKidElementSize;
if (gsDebug==PR_TRUE)
printf(" nsTableCellFrame::Reflow calling ReflowChild with availSize=%d,%d\n",
availSize.width, availSize.height);
@ -490,7 +469,8 @@ void nsTableCellFrame::MapHTMLBorderStyle(nsIPresContext* aPresContext, nsStyleS
aSpacingStyle.mBorderStyle[NS_SIDE_RIGHT] = NS_STYLE_BORDER_STYLE_SOLID;
#endif
nsTableFrame* tableFrame = GetTableFrame();
nsTableFrame* tableFrame;
nsTableFrame::GetTableFrame(this, tableFrame);
nsIStyleContext* styleContext = nsnull;
tableFrame->GetStyleContext(aPresContext,styleContext);
@ -545,7 +525,8 @@ void nsTableCellFrame::MapBorderMarginPadding(nsIPresContext* aPresContext)
nscoord spacing = 0;
nscoord border = 1;
nsTableFrame* tableFrame = GetTableFrame();
nsTableFrame* tableFrame;
nsTableFrame::GetTableFrame(this, tableFrame);
//tableFrame->GetGeometricParent((nsIFrame *&)tableFrame); // get the outer frame
NS_ASSERTION(tableFrame,"Table Must not be null");
if (!tableFrame)

View File

@ -137,11 +137,6 @@ public:
*/
virtual void SetPass1MaxElementSize(const nsSize & aMaxElementSize);
/** Get the TableFrame that contains this cell frame */
virtual nsTableFrame* GetTableFrame();
void RecalcLayoutData(nsTableFrame* aTableFrame,
nsVoidArray* aBoundaryCells[4]);

View File

@ -287,21 +287,21 @@ NS_METHOD nsTableColGroupFrame::SetStyleContextForFirstPass(nsIPresContext* aPre
int nsTableColGroupFrame::GetColumnCount ()
{
mColCount=0;
int count = LengthOf(mFirstChild);
if (0 < count)
nsIFrame *childFrame = mFirstChild;
while (nsnull!=childFrame)
{
nsIFrame * child = mFirstChild;
NS_ASSERTION(nsnull!=child, "bad child");
while (nsnull!=child)
const nsStyleDisplay *childDisplay;
childFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)childDisplay));
if (NS_STYLE_DISPLAY_TABLE_COLUMN == childDisplay->mDisplay)
{
nsTableColFrame *col = (nsTableColFrame *)child;
nsTableColFrame *col = (nsTableColFrame *)childFrame;
col->SetColumnIndex (mStartColIndex + mColCount);
mColCount += col->GetRepeat ();
child->GetNextSibling(child);
mColCount += col->GetRepeat();
}
childFrame->GetNextSibling(childFrame);
}
else
{
if (0==mColCount)
{ // there were no children of this colgroup that were columns. So use my span attribute
const nsStyleTable *tableStyle;
GetStyleData(eStyleStruct_Table, (nsStyleStruct *&)tableStyle);
mColCount = tableStyle->mSpan;
@ -309,6 +309,27 @@ int nsTableColGroupFrame::GetColumnCount ()
return mColCount;
}
nsTableColFrame * nsTableColGroupFrame::GetColumnAt (PRInt32 aColIndex)
{
nsTableColFrame *result = nsnull;
PRInt32 count=0;
nsIFrame *childFrame = mFirstChild;
while (nsnull!=childFrame)
{
const nsStyleDisplay *childDisplay;
childFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)childDisplay));
if (NS_STYLE_DISPLAY_TABLE_COLUMN == childDisplay->mDisplay)
{
nsTableColFrame *col = (nsTableColFrame *)childFrame;
count += col->GetRepeat();
if (aColIndex<=count)
result = col;
}
childFrame->GetNextSibling(childFrame);
}
return result;
}
PRInt32 nsTableColGroupFrame::GetSpan()
{
PRInt32 span=1;

View File

@ -21,6 +21,8 @@
#include "nscore.h"
#include "nsContainerFrame.h"
class nsTableColFrame;
/**
* nsTableColGroupFrame
@ -66,6 +68,8 @@ public:
*/
virtual PRInt32 GetColumnCount ();
virtual nsTableColFrame * GetColumnAt (PRInt32 aColIndex);
virtual PRInt32 GetStartColumnIndex ();
virtual void SetStartColumnIndex (PRInt32 aIndex);

View File

@ -1661,7 +1661,17 @@ nsReflowStatus nsTableFrame::ResizeReflowPass1(nsIPresContext* aPresContext,
GetStyleData(eStyleStruct_Table, (nsStyleStruct *&)tableStyle);
if (NS_STYLE_TABLE_LAYOUT_FIXED!=tableStyle->mLayoutStrategy)
{
for (nsIFrame* kidFrame = mFirstChild; nsnull != kidFrame; kidFrame->GetNextSibling(kidFrame)) {
for (nsIFrame* kidFrame = mFirstChild; nsnull != kidFrame; kidFrame->GetNextSibling(kidFrame))
{
const nsStyleDisplay *childDisplay;
kidFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)childDisplay));
if ((NS_STYLE_DISPLAY_TABLE_HEADER_GROUP != childDisplay->mDisplay) &&
(NS_STYLE_DISPLAY_TABLE_FOOTER_GROUP != childDisplay->mDisplay) &&
(NS_STYLE_DISPLAY_TABLE_ROW_GROUP != childDisplay->mDisplay) &&
(NS_STYLE_DISPLAY_TABLE_COLUMN_GROUP != childDisplay->mDisplay))
{
continue;
}
nsSize maxKidElementSize(0,0);
nsReflowState kidReflowState(kidFrame, aReflowState, availSize);
@ -1904,9 +1914,7 @@ void nsTableFrame::PlaceChild(nsIPresContext* aPresContext,
const nsStyleSpacing* tableSpacing;
// begin REMOVE_ME_WHEN_TABLE_STYLE_IS_RESOLVED!
nsIFrame * parent = nsnull;
GetGeometricParent(parent);
parent->GetStyleData(eStyleStruct_Spacing , ((nsStyleStruct *&)tableSpacing));
// end REMOVE_ME_WHEN_TABLE_STYLE_IS_RESOLVED!
GetStyleData(eStyleStruct_Spacing , ((nsStyleStruct *&)tableSpacing));
tableSpacing->CalcBorderPaddingFor(this, borderPadding);
nscoord cellSpacing = GetCellSpacing();
nscoord kidWidth = aKidMaxElementSize.width + borderPadding.left + borderPadding.right + cellSpacing*2;
@ -1948,7 +1956,8 @@ PRBool nsTableFrame::ReflowMappedChildren( nsIPresContext* aPresContext,
else
reason = eReflowReason_Resize;
for (nsIFrame* kidFrame = mFirstChild; nsnull != kidFrame; ) {
for (nsIFrame* kidFrame = mFirstChild; nsnull != kidFrame; )
{
nsSize kidAvailSize(aState.availSize);
nsReflowMetrics desiredSize(pKidMaxElementSize);
desiredSize.width=desiredSize.height=desiredSize.ascent=desiredSize.descent=0;
@ -1956,7 +1965,10 @@ PRBool nsTableFrame::ReflowMappedChildren( nsIPresContext* aPresContext,
const nsStyleDisplay *childDisplay;
kidFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)childDisplay));
if (NS_STYLE_DISPLAY_TABLE_CAPTION != childDisplay->mDisplay)
if ((NS_STYLE_DISPLAY_TABLE_HEADER_GROUP == childDisplay->mDisplay) ||
(NS_STYLE_DISPLAY_TABLE_FOOTER_GROUP == childDisplay->mDisplay) ||
(NS_STYLE_DISPLAY_TABLE_ROW_GROUP == childDisplay->mDisplay) ||
(NS_STYLE_DISPLAY_TABLE_COLUMN_GROUP == childDisplay->mDisplay))
{ // for all colgroups and rowgroups...
const nsStyleSpacing* kidSpacing;
kidFrame->GetStyleData(eStyleStruct_Spacing, ((nsStyleStruct *&)kidSpacing));
@ -2436,7 +2448,6 @@ NS_METHOD nsTableFrame::GetColumnFrame(PRInt32 aColIndex, nsTableColFrame *&aCol
if (nsnull!=cellMap)
{ // hooray, we get to do this the easy way because the info is cached
aColFrame = cellMap->GetColumnFrame(aColIndex);
NS_ASSERTION(nsnull!=aColFrame, "bad col frame");
}
else
{ // ah shucks, we have to go hunt for the column frame brute-force style
@ -2456,13 +2467,10 @@ NS_METHOD nsTableFrame::GetColumnFrame(PRInt32 aColIndex, nsTableColFrame *&aCol
PRInt32 colGroupStartingIndex = ((nsTableColGroupFrame *)childFrame)->GetStartColumnIndex();
if (aColIndex >= colGroupStartingIndex)
{ // the cell's col might be in this col group
// XXX FIX ME...
nsIFrame* firstChild;
childFrame->FirstChild(firstChild);
PRInt32 childCount = LengthOf(firstChild);
if (aColIndex < colGroupStartingIndex + childCount)
{ // yep, we've found it
aColFrame = (nsTableColFrame*)FrameAt(firstChild, aColIndex-colGroupStartingIndex);
PRInt32 colCount = ((nsTableColGroupFrame *)childFrame)->GetColumnCount();
if (aColIndex < colGroupStartingIndex + colCount)
{ // yep, we've found it. GetColumnAt gives us the column at the offset colCount, not the absolute colIndex for the whole table
aColFrame = ((nsTableColGroupFrame *)childFrame)->GetColumnAt(colCount);
break;
}
}
@ -2470,6 +2478,7 @@ NS_METHOD nsTableFrame::GetColumnFrame(PRInt32 aColIndex, nsTableColFrame *&aCol
childFrame->GetNextSibling(childFrame);
}
}
NS_POSTCONDITION(nsnull!=aColFrame, "no column frame could be found.");
return NS_OK;
}
@ -2519,16 +2528,24 @@ void nsTableFrame::BuildColumnCache( nsIPresContext* aPresContext,
childFrame->FirstChild(rowFrame);
while (nsnull!=rowFrame)
{
nsIFrame *cellFrame;
rowFrame->FirstChild(cellFrame);
while (nsnull!=cellFrame)
const nsStyleDisplay *rowDisplay;
rowFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)rowDisplay));
if (NS_STYLE_DISPLAY_TABLE_ROW == rowDisplay->mDisplay)
{
/* this is the first time we are guaranteed to have both the cell frames
* and the column frames, so it's a good time to
* set the column style from the cell's width attribute (if this is the first row)
*/
SetColumnStyleFromCell(aPresContext, (nsTableCellFrame *)cellFrame, (nsTableRowFrame *)rowFrame);
cellFrame->GetNextSibling(cellFrame);
nsIFrame *cellFrame;
rowFrame->FirstChild(cellFrame);
while (nsnull!=cellFrame)
{
/* this is the first time we are guaranteed to have both the cell frames
* and the column frames, so it's a good time to
* set the column style from the cell's width attribute (if this is the first row)
*/
const nsStyleDisplay *cellDisplay;
cellFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)cellDisplay));
if (NS_STYLE_DISPLAY_TABLE_CELL == cellDisplay->mDisplay)
SetColumnStyleFromCell(aPresContext, (nsTableCellFrame *)cellFrame, (nsTableRowFrame *)rowFrame);
cellFrame->GetNextSibling(cellFrame);
}
}
rowFrame->GetNextSibling(rowFrame);
}
@ -2551,9 +2568,14 @@ void nsTableFrame::BuildColumnCache( nsIPresContext* aPresContext,
while (nsnull!=colFrame)
{ // for every column, create an entry in the column cache
// assumes that the col style has been twiddled to account for first cell width attribute
const nsStylePosition* colPosition;
colFrame->GetStyleData(eStyleStruct_Position, ((nsStyleStruct *&)colPosition));
mColCache->AddColumnInfo(colPosition->mWidth.GetUnit(), colFrame->GetColumnIndex());
const nsStyleDisplay *colDisplay;
colFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)colDisplay));
if (NS_STYLE_DISPLAY_TABLE_COLUMN == colDisplay->mDisplay)
{
const nsStylePosition* colPosition;
colFrame->GetStyleData(eStyleStruct_Position, ((nsStyleStruct *&)colPosition));
mColCache->AddColumnInfo(colPosition->mWidth.GetUnit(), colFrame->GetColumnIndex());
}
colFrame->GetNextSibling((nsIFrame *&)colFrame);
}
}
@ -2618,7 +2640,8 @@ nsTableFrame::CreateContinuingFrame(nsIPresContext& aPresContext,
rg->GetContent(content); // content: REFCNT++
NS_ASSERTION(nsnull!=content, "bad frame, returned null content.");
const nsStyleDisplay* display;
GetStyleData(eStyleStruct_Display, (const nsStyleStruct*&)display);
//XXX: TROY: this was just this->GetStyleData which can't be right
rg->GetStyleData(eStyleStruct_Display, (const nsStyleStruct*&)display);
if ((display->mDisplay == NS_STYLE_DISPLAY_TABLE_HEADER_GROUP) ||
(display->mDisplay == NS_STYLE_DISPLAY_TABLE_FOOTER_GROUP))
{
@ -2670,9 +2693,6 @@ PRInt32 nsTableFrame::GetColumnWidth(PRInt32 aColIndex)
result = mColumnWidths[aColIndex];
}
//printf("GET_COL_WIDTH: %p, FIF=%p getting col %d and returning %d\n", this, firstInFlow, aColIndex, result);
// XXX hack
return result;
}
@ -2886,6 +2906,29 @@ NS_NewTableFrame(nsIContent* aContent,
return NS_OK;
}
NS_METHOD nsTableFrame::GetTableFrame(nsIFrame *aSourceFrame, nsTableFrame *& aOutFrame)
{
nsresult result = NS_OK;
aOutFrame = nsnull; // initialize out-param
if (nsnull!=aSourceFrame)
{
nsresult result = aSourceFrame->GetContentParent((nsIFrame *&)aOutFrame);
while ((NS_OK==result) && (nsnull!=aOutFrame))
{
const nsStyleDisplay *display;
aOutFrame->GetStyleData(eStyleStruct_Display, (nsStyleStruct *&)display);
if (NS_STYLE_DISPLAY_TABLE == display->mDisplay)
break;
result = aOutFrame->GetContentParent((nsIFrame *&)aOutFrame);
}
}
else
result = NS_ERROR_UNEXPECTED; // bad source param
NS_POSTCONDITION(nsnull!=aOutFrame, "unable to find table parent. aOutFrame null.");
NS_POSTCONDITION(NS_OK==result, "unable to find table parent. result!=NS_OK");
return result;
}
/* helper method for determining if this is a nested table or not */
PRBool nsTableFrame::IsNested(const nsReflowState& aReflowState, nsStylePosition *& aPosition) const
{
@ -2901,6 +2944,7 @@ PRBool nsTableFrame::IsNested(const nsReflowState& aReflowState, nsStylePosition
#ifdef NS_DEBUG
counter++;
NS_ASSERTION(counter<100000, "infinite loop in IsNested");
break;
#endif
nsIFrame* parentTable = nsnull;
rv = rs->frame->QueryInterface(kTableFrameCID, (void**) &parentTable);
@ -3007,13 +3051,9 @@ nscoord nsTableFrame::GetTableContainerWidth(const nsReflowState& aReflowState)
cell->GetStyleData(eStyleStruct_Position, ((nsStyleStruct *&)cellPosition));
if (eStyleUnit_Coord == cellPosition->mWidth.GetUnit())
{
// first, get pointers to the table frame parents of the cell
nsIFrame *rowParent, *rowGroupParent;
nsTableFrame *tableParent;
cell->GetGeometricParent(rowParent);
rowParent->GetGeometricParent(rowGroupParent);
rowGroupParent->GetGeometricParent((nsIFrame *&)tableParent);
if (nsnull != tableParent->mColumnWidths)
rv=GetTableFrame(cell, tableParent);
if ((NS_OK==rv) && (nsnull!=tableParent) && (nsnull!=tableParent->mColumnWidths))
{
parentWidth=0;
PRInt32 colIndex = ((nsTableCellFrame *)cell)->GetColIndex();

View File

@ -77,6 +77,9 @@ public:
/** helper method for determining if this is a nested table or not */
PRBool IsNested(const nsReflowState& aReflowState, nsStylePosition *& aPosition) const;
/** helper method to find the table parent of any table frame object */
static NS_METHOD GetTableFrame(nsIFrame *aSourceFrame, nsTableFrame *& aOutFrame);
/** helper method for getting the width of the table's containing block */
static nscoord GetTableContainerWidth(const nsReflowState& aState);

View File

@ -103,59 +103,48 @@ nsTableRowFrame::Init(nsIPresContext& aPresContext, nsIFrame* aChildList)
nsTableFrame* table = nsnull;
nsresult result;
result = GetTableFrame((nsIFrame *&)table);
result = nsTableFrame::GetTableFrame(this, table);
if ((NS_OK==result) && (table != nsnull))
{
SetRowIndex(table->GetNextAvailRowIndex());
PRInt32 colIndex = 0;
for (nsIFrame* kidFrame = mFirstChild; nsnull != kidFrame; kidFrame->GetNextSibling(kidFrame))
{
// what column does this cell belong to?
colIndex = table->GetNextAvailColIndex(mRowIndex, colIndex);
/* for style context optimization, set the content's column index if possible.
* this can only be done if we really have an nsTableCell.
* other tags mapped to table cell display won't benefit from this optimization
* see nsHTMLStyleSheet::RulesMatching
*/
nsIContent* cell;
kidFrame->GetContent(cell);
nsIHTMLTableCellElement *cellContent = nsnull;
nsresult rv = cell->QueryInterface(kIHTMLTableCellElementIID,
(void **)&cellContent); // cellContent: REFCNT++
NS_RELEASE(cell);
if (NS_SUCCEEDED(rv))
{ // we know it's a table cell
cellContent->SetColIndex(colIndex);
if (gsDebug) printf("%p : set cell content %p to col index = %d\n", this, cellContent, colIndex);
NS_RELEASE(cellContent);
const nsStyleDisplay *kidDisplay;
kidFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)kidDisplay));
if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay)
{
// what column does this cell belong to?
colIndex = table->GetNextAvailColIndex(mRowIndex, colIndex);
/* for style context optimization, set the content's column index if possible.
* this can only be done if we really have an nsTableCell.
* other tags mapped to table cell display won't benefit from this optimization
* see nsHTMLStyleSheet::RulesMatching
*/
nsIContent* cell;
kidFrame->GetContent(cell);
nsIHTMLTableCellElement *cellContent = nsnull;
nsresult rv = cell->QueryInterface(kIHTMLTableCellElementIID,
(void **)&cellContent); // cellContent: REFCNT++
NS_RELEASE(cell);
if (NS_SUCCEEDED(rv))
{ // we know it's a table cell
cellContent->SetColIndex(colIndex);
if (gsDebug) printf("%p : set cell content %p to col index = %d\n", this, cellContent, colIndex);
NS_RELEASE(cellContent);
}
// this sets the frame's notion of it's column index
((nsTableCellFrame *)kidFrame)->InitCellFrame(colIndex);
if (gsDebug) printf("%p : set cell frame %p to col index = %d\n", this, kidFrame, colIndex);
// add the cell frame to the table's cell map
table->AddCellToTable(this, (nsTableCellFrame *)kidFrame, kidFrame == mFirstChild);
}
// part of the style optimization is to ensure that the column frame for the cell exists
//table->EnsureColumnFrameAt(colIndex, &aPresContext);
// this sets the frame's notion of it's column index
((nsTableCellFrame *)kidFrame)->InitCellFrame(colIndex);
if (gsDebug) printf("%p : set cell frame %p to col index = %d\n", this, kidFrame, colIndex);
// add the cell frame to the table's cell map
table->AddCellToTable(this, (nsTableCellFrame *)kidFrame, kidFrame == mFirstChild);
}
}
return NS_OK;
}
NS_METHOD nsTableRowFrame::GetTableFrame(nsIFrame *& aFrame)
{
nsresult result = GetContentParent(aFrame);
while ((NS_OK==result) && (nsnull!=aFrame))
{
const nsStyleDisplay *display;
aFrame->GetStyleData(eStyleStruct_Display, (nsStyleStruct *&)display);
if (NS_STYLE_DISPLAY_TABLE == display->mDisplay)
break;
result = aFrame->GetContentParent(aFrame);
}
return result;
}
/**
* Post-reflow hook. This is where the table row does its post-processing
*/
@ -166,30 +155,29 @@ nsTableRowFrame::DidReflow(nsIPresContext& aPresContext,
if (NS_FRAME_REFLOW_FINISHED == aStatus) {
// Resize and re-align the cell frames based on our row height
nscoord cellHeight = mRect.height - mCellMaxTopMargin - mCellMaxBottomMargin;
// XXX
// every place in this module where we cast to nsTableCellFrame,
// we first have to check the display-type of the frame and skip non-cells.
nsTableCellFrame *cellFrame = (nsTableCellFrame*)mFirstChild;
nsTableFrame* tableFrame;
mContentParent->GetContentParent((nsIFrame*&)tableFrame);
nsIFrame *cellFrame = mFirstChild;
nsTableFrame* tableFrame;
nsTableFrame::GetTableFrame(this, tableFrame);
while (nsnull != cellFrame)
{
PRInt32 rowSpan = tableFrame->GetEffectiveRowSpan(mRowIndex, cellFrame);
if (1==rowSpan)
const nsStyleDisplay *kidDisplay;
cellFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)kidDisplay));
if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay)
{
// resize the cell's height
nsSize cellFrameSize;
cellFrame->GetSize(cellFrameSize);
cellFrame->SizeTo(cellFrameSize.width, cellHeight);
PRInt32 rowSpan = tableFrame->GetEffectiveRowSpan(mRowIndex, (nsTableCellFrame *)cellFrame);
if (1==rowSpan)
{
// resize the cell's height
nsSize cellFrameSize;
cellFrame->GetSize(cellFrameSize);
cellFrame->SizeTo(cellFrameSize.width, cellHeight);
// realign cell content based on the new height
cellFrame->VerticallyAlignChild(&aPresContext);
// realign cell content based on the new height
((nsTableCellFrame *)cellFrame)->VerticallyAlignChild(&aPresContext);
}
}
// Get the next cell
cellFrame->GetNextSibling((nsIFrame*&)cellFrame);
// Get the next cell
cellFrame->GetNextSibling(cellFrame);
}
}
@ -294,10 +282,16 @@ nscoord nsTableRowFrame::GetChildMaxBottomMargin() const
PRInt32 nsTableRowFrame::GetMaxColumns() const
{
int sum = 0;
nsTableCellFrame *cell=(nsTableCellFrame *)mFirstChild;
while (nsnull!=cell) {
sum += cell->GetColSpan();
cell->GetNextSibling((nsIFrame *&)cell);
nsIFrame *cell=mFirstChild;
while (nsnull!=cell)
{
const nsStyleDisplay *kidDisplay;
cell->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)kidDisplay));
if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay)
{
sum += ((nsTableCellFrame *)cell)->GetColSpan();
}
cell->GetNextSibling(cell);
}
return sum;
}
@ -311,11 +305,16 @@ void nsTableRowFrame::GetMinRowSpan(nsTableFrame *aTableFrame)
nsIFrame *frame=mFirstChild;
while (nsnull!=frame)
{
PRInt32 rowSpan = aTableFrame->GetEffectiveRowSpan(mRowIndex, ((nsTableCellFrame *)frame));
if (-1==minRowSpan)
minRowSpan = rowSpan;
else if (minRowSpan>rowSpan)
minRowSpan = rowSpan;
const nsStyleDisplay *kidDisplay;
frame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)kidDisplay));
if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay)
{
PRInt32 rowSpan = aTableFrame->GetEffectiveRowSpan(mRowIndex, ((nsTableCellFrame *)frame));
if (-1==minRowSpan)
minRowSpan = rowSpan;
else if (minRowSpan>rowSpan)
minRowSpan = rowSpan;
}
frame->GetNextSibling(frame);
}
mMinRowSpan = minRowSpan;
@ -326,13 +325,18 @@ void nsTableRowFrame::FixMinCellHeight(nsTableFrame *aTableFrame)
nsIFrame *frame=mFirstChild;
while (nsnull!=frame)
{
PRInt32 rowSpan = aTableFrame->GetEffectiveRowSpan(mRowIndex, ((nsTableCellFrame *)frame));
if (mMinRowSpan==rowSpan)
const nsStyleDisplay *kidDisplay;
frame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)kidDisplay));
if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay)
{
nsRect rect;
frame->GetRect(rect);
if (rect.height > mTallestCell)
mTallestCell = rect.height;
PRInt32 rowSpan = aTableFrame->GetEffectiveRowSpan(mRowIndex, ((nsTableCellFrame *)frame));
if (mMinRowSpan==rowSpan)
{
nsRect rect;
frame->GetRect(rect);
if (rect.height > mTallestCell)
mTallestCell = rect.height;
}
}
frame->GetNextSibling(frame);
}
@ -599,7 +603,7 @@ nsTableRowFrame::InitialReflow(nsIPresContext& aPresContext,
PRBool isFirst=PR_TRUE;
PRBool tableLayoutStrategy=NS_STYLE_TABLE_LAYOUT_AUTO;
nsTableFrame* table = nsnull;
nsresult result = GetTableFrame((nsIFrame *&)table);
nsresult result = nsTableFrame::GetTableFrame(this, table);
if ((NS_OK==result) && (table != nsnull))
{
nsStyleTable* tableStyle;
@ -611,66 +615,71 @@ nsTableRowFrame::InitialReflow(nsIPresContext& aPresContext,
for (nsIFrame* kidFrame = mFirstChild; nsnull != kidFrame; kidFrame->GetNextSibling(kidFrame))
{
// Get the child's margins
nsMargin margin;
nscoord topMargin = 0;
if (aState.tableFrame->GetCellMarginData((nsTableCellFrame *)kidFrame, margin) == NS_OK)
const nsStyleDisplay *kidDisplay;
kidFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)kidDisplay));
if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay)
{
topMargin = margin.top;
}
// Get the child's margins
nsMargin margin;
nscoord topMargin = 0;
if (aState.tableFrame->GetCellMarginData((nsTableCellFrame *)kidFrame, margin) == NS_OK)
{
topMargin = margin.top;
}
maxTopMargin = PR_MAX(margin.top, maxTopMargin);
maxBottomMargin = PR_MAX(margin.bottom, maxBottomMargin);
maxTopMargin = PR_MAX(margin.top, maxTopMargin);
maxBottomMargin = PR_MAX(margin.bottom, maxBottomMargin);
// Because we're not splittable always allow the child to be as high as
// it wants. The default available width is also unconstrained so we can
// get the child's maximum width
nsSize kidAvailSize;
nsReflowMetrics kidSize(nsnull);
if (NS_STYLE_TABLE_LAYOUT_AUTO==tableLayoutStrategy)
{
kidAvailSize.SizeTo(NS_UNCONSTRAINEDSIZE, NS_UNCONSTRAINEDSIZE);
kidSize.maxElementSize=&kidMaxElementSize;
// Because we're not splittable always allow the child to be as high as
// it wants. The default available width is also unconstrained so we can
// get the child's maximum width
nsSize kidAvailSize;
nsReflowMetrics kidSize(nsnull);
if (NS_STYLE_TABLE_LAYOUT_AUTO==tableLayoutStrategy)
{
kidAvailSize.SizeTo(NS_UNCONSTRAINEDSIZE, NS_UNCONSTRAINEDSIZE);
kidSize.maxElementSize=&kidMaxElementSize;
}
else
{
PRInt32 colIndex = ((nsTableCellFrame *)kidFrame)->GetColIndex();
kidAvailSize.SizeTo(table->GetColumnWidth(colIndex), NS_UNCONSTRAINEDSIZE);
}
nsReflowState kidReflowState(kidFrame, aState.reflowState, kidAvailSize,
eReflowReason_Initial);
kidFrame->WillReflow(aPresContext);
if (gsDebug) printf ("%p InitR: avail=%d\n", this, kidAvailSize.width);
nsresult status = ReflowChild(kidFrame, &aPresContext, kidSize, kidReflowState);
if (gsDebug)
printf ("TR %p for cell %p Initial Reflow: desired=%d, MES=%d\n",
this, kidFrame, kidSize.width, kidMaxElementSize.width);
//XXX: this is a hack, shouldn't it be the case that a min size is
// never larger than a desired size?
if (kidMaxElementSize.width>kidSize.width)
kidSize.width = kidMaxElementSize.width;
if (kidMaxElementSize.height>kidSize.height)
kidSize.height = kidMaxElementSize.height;
((nsTableCellFrame *)kidFrame)->SetPass1DesiredSize(kidSize);
((nsTableCellFrame *)kidFrame)->SetPass1MaxElementSize(kidMaxElementSize);
NS_ASSERTION(NS_FRAME_IS_COMPLETE(status), "unexpected child reflow status");
if (gsDebug)
{
printf("reflow of cell returned result = %s with desired=%d,%d, min = %d,%d\n",
NS_FRAME_IS_COMPLETE(status)?"complete":"NOT complete",
kidSize.width, kidSize.height,
kidMaxElementSize.width, kidMaxElementSize.height);
}
// Place the child
x += margin.left;
nsRect kidRect(x, topMargin, kidSize.width, kidSize.height);
PlaceChild(aPresContext, aState, kidFrame, kidRect, aDesiredSize.maxElementSize,
&kidMaxElementSize);
x += kidSize.width + margin.right;
}
else
{
PRInt32 colIndex = ((nsTableCellFrame *)kidFrame)->GetColIndex();
kidAvailSize.SizeTo(table->GetColumnWidth(colIndex), NS_UNCONSTRAINEDSIZE);
}
nsReflowState kidReflowState(kidFrame, aState.reflowState, kidAvailSize,
eReflowReason_Initial);
kidFrame->WillReflow(aPresContext);
if (gsDebug) printf ("%p InitR: avail=%d\n", this, kidAvailSize.width);
nsresult status = ReflowChild(kidFrame, &aPresContext, kidSize, kidReflowState);
if (gsDebug)
printf ("TR %p for cell %p Initial Reflow: desired=%d, MES=%d\n",
this, kidFrame, kidSize.width, kidMaxElementSize.width);
//XXX: this is a hack, shouldn't it be the case that a min size is
// never larger than a desired size?
if (kidMaxElementSize.width>kidSize.width)
kidSize.width = kidMaxElementSize.width;
if (kidMaxElementSize.height>kidSize.height)
kidSize.height = kidMaxElementSize.height;
((nsTableCellFrame *)kidFrame)->SetPass1DesiredSize(kidSize);
((nsTableCellFrame *)kidFrame)->SetPass1MaxElementSize(kidMaxElementSize);
NS_ASSERTION(NS_FRAME_IS_COMPLETE(status), "unexpected child reflow status");
if (gsDebug)
{
printf("reflow of cell returned result = %s with desired=%d,%d, min = %d,%d\n",
NS_FRAME_IS_COMPLETE(status)?"complete":"NOT complete",
kidSize.width, kidSize.height,
kidMaxElementSize.width, kidMaxElementSize.height);
}
// Place the child
x += margin.left;
nsRect kidRect(x, topMargin, kidSize.width, kidSize.height);
PlaceChild(aPresContext, aState, kidFrame, kidRect, aDesiredSize.maxElementSize,
&kidMaxElementSize);
x += kidSize.width + margin.right;
}
SetMaxChildHeight(aState.maxCellHeight, maxTopMargin, maxBottomMargin); // remember height of tallest child who doesn't have a row span
@ -702,62 +711,67 @@ nsresult nsTableRowFrame::RecoverState(nsIPresContext& aPresContext,
// frames except aKidFrame
// nsIFrame* prevKidFrame = nsnull;
for (nsIFrame* frame = mFirstChild; nsnull != frame;) {
if (frame != aKidFrame) {
// Update the max top and bottom margins
nsMargin kidMargin;
aState.tableFrame->GetCellMarginData((nsTableCellFrame *)frame, kidMargin);
if (kidMargin.top > aMaxCellTopMargin)
aMaxCellTopMargin = kidMargin.top;
if (kidMargin.bottom > aMaxCellBottomMargin)
aMaxCellBottomMargin = kidMargin.bottom;
const nsStyleDisplay *kidDisplay;
frame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)kidDisplay));
if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay)
{
if (frame != aKidFrame) {
// Update the max top and bottom margins
nsMargin kidMargin;
aState.tableFrame->GetCellMarginData((nsTableCellFrame *)frame, kidMargin);
if (kidMargin.top > aMaxCellTopMargin)
aMaxCellTopMargin = kidMargin.top;
if (kidMargin.bottom > aMaxCellBottomMargin)
aMaxCellBottomMargin = kidMargin.bottom;
PRInt32 rowSpan = aState.tableFrame->GetEffectiveRowSpan(mRowIndex, ((nsTableCellFrame *)frame));
if (mMinRowSpan == rowSpan) {
// Get the cell's desired height the last time it was reflowed
nsSize desiredSize = ((nsTableCellFrame *)frame)->GetDesiredSize();
PRInt32 rowSpan = aState.tableFrame->GetEffectiveRowSpan(mRowIndex, ((nsTableCellFrame *)frame));
if (mMinRowSpan == rowSpan) {
// Get the cell's desired height the last time it was reflowed
nsSize desiredSize = ((nsTableCellFrame *)frame)->GetDesiredSize();
// See if it has a specified height that overrides the desired size
nscoord specifiedHeight = 0;
nsIStyleContextPtr kidSC;
frame->GetStyleContext(&aPresContext, kidSC.AssignRef());
const nsStylePosition* kidPosition = (const nsStylePosition*)
kidSC->GetStyleData(eStyleStruct_Position);
switch (kidPosition->mHeight.GetUnit()) {
case eStyleUnit_Coord:
specifiedHeight = kidPosition->mHeight.GetCoordValue();
break;
// See if it has a specified height that overrides the desired size
nscoord specifiedHeight = 0;
nsIStyleContextPtr kidSC;
frame->GetStyleContext(&aPresContext, kidSC.AssignRef());
const nsStylePosition* kidPosition = (const nsStylePosition*)
kidSC->GetStyleData(eStyleStruct_Position);
switch (kidPosition->mHeight.GetUnit()) {
case eStyleUnit_Coord:
specifiedHeight = kidPosition->mHeight.GetCoordValue();
break;
case eStyleUnit_Inherit:
// XXX for now, do nothing
default:
case eStyleUnit_Auto:
break;
}
if (specifiedHeight > desiredSize.height)
desiredSize.height = specifiedHeight;
case eStyleUnit_Inherit:
// XXX for now, do nothing
default:
case eStyleUnit_Auto:
break;
}
if (specifiedHeight > desiredSize.height)
desiredSize.height = specifiedHeight;
// Update maxCellHeight
if (desiredSize.height > aState.maxCellHeight) {
aState.maxCellHeight = desiredSize.height;
}
// Update maxCellHeight
if (desiredSize.height > aState.maxCellHeight) {
aState.maxCellHeight = desiredSize.height;
}
// Update maxCellVertHeight
nsMargin margin;
// Update maxCellVertHeight
nsMargin margin;
if (aState.tableFrame->GetCellMarginData((nsTableCellFrame *)frame, margin) == NS_OK)
{
nscoord height = desiredSize.height + margin.top + margin.bottom;
if (height > aState.maxCellVertSpace) {
aState.maxCellVertSpace = height;
if (aState.tableFrame->GetCellMarginData((nsTableCellFrame *)frame, margin) == NS_OK)
{
nscoord height = desiredSize.height + margin.top + margin.bottom;
if (height > aState.maxCellVertSpace) {
aState.maxCellVertSpace = height;
}
}
}
}
// XXX We also need to recover the max element size if requested by the
// caller...
//
// We should be using GetReflowMetrics() to get information from the
// table cell, and that will include the max element size...
// XXX We also need to recover the max element size if requested by the
// caller...
//
// We should be using GetReflowMetrics() to get information from the
// table cell, and that will include the max element size...
}
}
// Remember the frame that precedes aKidFrame

View File

@ -114,9 +114,6 @@ public:
/** set this row's starting row index */
virtual void SetRowIndex (int aRowIndex);
/** get the row's enclosing table frame in a safe way */
NS_IMETHOD GetTableFrame(nsIFrame *& aFrame);
NS_IMETHOD List(FILE* out = stdout, PRInt32 aIndent = 0, nsIListFilter *aFilter = nsnull) const;
protected:

View File

@ -212,28 +212,6 @@ void nsTableCellFrame::CreatePsuedoFrame(nsIPresContext* aPresContext)
}
}
/*
* Should this be performanced tuned? This is called
* in resize/reflow. Maybe we should cache the table
* frame in the table cell frame.
*
*/
nsTableFrame* nsTableCellFrame::GetTableFrame()
{
nsIFrame* frame = nsnull;
nsresult result;
result = GetContentParent(frame); // Get RowFrame
if ((result == NS_OK) && (frame != nsnull))
frame->GetContentParent(frame); // Get RowGroupFrame
if ((result == NS_OK) && (frame != nsnull))
frame->GetContentParent(frame); // Get TableFrame
return (nsTableFrame*)frame;
}
PRInt32 nsTableCellFrame::GetRowSpan()
{
PRInt32 rowSpan=1;
@ -314,7 +292,8 @@ NS_METHOD nsTableCellFrame::Reflow(nsIPresContext& aPresContext,
// Get the margin information, available space should
// be reduced accordingly
nsMargin margin(0,0,0,0);
nsTableFrame* tableFrame = GetTableFrame();
nsTableFrame* tableFrame;
nsTableFrame::GetTableFrame(this, tableFrame);
tableFrame->GetCellMarginData(this,margin);
// get frame, creating one if needed
@ -341,7 +320,7 @@ NS_METHOD nsTableCellFrame::Reflow(nsIPresContext& aPresContext,
// fit or might need continuing.
if (availSize.height < 0)
availSize.height = 1;
nsSize maxKidElementSize;
if (gsDebug==PR_TRUE)
printf(" nsTableCellFrame::Reflow calling ReflowChild with availSize=%d,%d\n",
availSize.width, availSize.height);
@ -490,7 +469,8 @@ void nsTableCellFrame::MapHTMLBorderStyle(nsIPresContext* aPresContext, nsStyleS
aSpacingStyle.mBorderStyle[NS_SIDE_RIGHT] = NS_STYLE_BORDER_STYLE_SOLID;
#endif
nsTableFrame* tableFrame = GetTableFrame();
nsTableFrame* tableFrame;
nsTableFrame::GetTableFrame(this, tableFrame);
nsIStyleContext* styleContext = nsnull;
tableFrame->GetStyleContext(aPresContext,styleContext);
@ -545,7 +525,8 @@ void nsTableCellFrame::MapBorderMarginPadding(nsIPresContext* aPresContext)
nscoord spacing = 0;
nscoord border = 1;
nsTableFrame* tableFrame = GetTableFrame();
nsTableFrame* tableFrame;
nsTableFrame::GetTableFrame(this, tableFrame);
//tableFrame->GetGeometricParent((nsIFrame *&)tableFrame); // get the outer frame
NS_ASSERTION(tableFrame,"Table Must not be null");
if (!tableFrame)

View File

@ -137,11 +137,6 @@ public:
*/
virtual void SetPass1MaxElementSize(const nsSize & aMaxElementSize);
/** Get the TableFrame that contains this cell frame */
virtual nsTableFrame* GetTableFrame();
void RecalcLayoutData(nsTableFrame* aTableFrame,
nsVoidArray* aBoundaryCells[4]);

View File

@ -287,21 +287,21 @@ NS_METHOD nsTableColGroupFrame::SetStyleContextForFirstPass(nsIPresContext* aPre
int nsTableColGroupFrame::GetColumnCount ()
{
mColCount=0;
int count = LengthOf(mFirstChild);
if (0 < count)
nsIFrame *childFrame = mFirstChild;
while (nsnull!=childFrame)
{
nsIFrame * child = mFirstChild;
NS_ASSERTION(nsnull!=child, "bad child");
while (nsnull!=child)
const nsStyleDisplay *childDisplay;
childFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)childDisplay));
if (NS_STYLE_DISPLAY_TABLE_COLUMN == childDisplay->mDisplay)
{
nsTableColFrame *col = (nsTableColFrame *)child;
nsTableColFrame *col = (nsTableColFrame *)childFrame;
col->SetColumnIndex (mStartColIndex + mColCount);
mColCount += col->GetRepeat ();
child->GetNextSibling(child);
mColCount += col->GetRepeat();
}
childFrame->GetNextSibling(childFrame);
}
else
{
if (0==mColCount)
{ // there were no children of this colgroup that were columns. So use my span attribute
const nsStyleTable *tableStyle;
GetStyleData(eStyleStruct_Table, (nsStyleStruct *&)tableStyle);
mColCount = tableStyle->mSpan;
@ -309,6 +309,27 @@ int nsTableColGroupFrame::GetColumnCount ()
return mColCount;
}
nsTableColFrame * nsTableColGroupFrame::GetColumnAt (PRInt32 aColIndex)
{
nsTableColFrame *result = nsnull;
PRInt32 count=0;
nsIFrame *childFrame = mFirstChild;
while (nsnull!=childFrame)
{
const nsStyleDisplay *childDisplay;
childFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)childDisplay));
if (NS_STYLE_DISPLAY_TABLE_COLUMN == childDisplay->mDisplay)
{
nsTableColFrame *col = (nsTableColFrame *)childFrame;
count += col->GetRepeat();
if (aColIndex<=count)
result = col;
}
childFrame->GetNextSibling(childFrame);
}
return result;
}
PRInt32 nsTableColGroupFrame::GetSpan()
{
PRInt32 span=1;

View File

@ -21,6 +21,8 @@
#include "nscore.h"
#include "nsContainerFrame.h"
class nsTableColFrame;
/**
* nsTableColGroupFrame
@ -66,6 +68,8 @@ public:
*/
virtual PRInt32 GetColumnCount ();
virtual nsTableColFrame * GetColumnAt (PRInt32 aColIndex);
virtual PRInt32 GetStartColumnIndex ();
virtual void SetStartColumnIndex (PRInt32 aIndex);

View File

@ -1661,7 +1661,17 @@ nsReflowStatus nsTableFrame::ResizeReflowPass1(nsIPresContext* aPresContext,
GetStyleData(eStyleStruct_Table, (nsStyleStruct *&)tableStyle);
if (NS_STYLE_TABLE_LAYOUT_FIXED!=tableStyle->mLayoutStrategy)
{
for (nsIFrame* kidFrame = mFirstChild; nsnull != kidFrame; kidFrame->GetNextSibling(kidFrame)) {
for (nsIFrame* kidFrame = mFirstChild; nsnull != kidFrame; kidFrame->GetNextSibling(kidFrame))
{
const nsStyleDisplay *childDisplay;
kidFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)childDisplay));
if ((NS_STYLE_DISPLAY_TABLE_HEADER_GROUP != childDisplay->mDisplay) &&
(NS_STYLE_DISPLAY_TABLE_FOOTER_GROUP != childDisplay->mDisplay) &&
(NS_STYLE_DISPLAY_TABLE_ROW_GROUP != childDisplay->mDisplay) &&
(NS_STYLE_DISPLAY_TABLE_COLUMN_GROUP != childDisplay->mDisplay))
{
continue;
}
nsSize maxKidElementSize(0,0);
nsReflowState kidReflowState(kidFrame, aReflowState, availSize);
@ -1904,9 +1914,7 @@ void nsTableFrame::PlaceChild(nsIPresContext* aPresContext,
const nsStyleSpacing* tableSpacing;
// begin REMOVE_ME_WHEN_TABLE_STYLE_IS_RESOLVED!
nsIFrame * parent = nsnull;
GetGeometricParent(parent);
parent->GetStyleData(eStyleStruct_Spacing , ((nsStyleStruct *&)tableSpacing));
// end REMOVE_ME_WHEN_TABLE_STYLE_IS_RESOLVED!
GetStyleData(eStyleStruct_Spacing , ((nsStyleStruct *&)tableSpacing));
tableSpacing->CalcBorderPaddingFor(this, borderPadding);
nscoord cellSpacing = GetCellSpacing();
nscoord kidWidth = aKidMaxElementSize.width + borderPadding.left + borderPadding.right + cellSpacing*2;
@ -1948,7 +1956,8 @@ PRBool nsTableFrame::ReflowMappedChildren( nsIPresContext* aPresContext,
else
reason = eReflowReason_Resize;
for (nsIFrame* kidFrame = mFirstChild; nsnull != kidFrame; ) {
for (nsIFrame* kidFrame = mFirstChild; nsnull != kidFrame; )
{
nsSize kidAvailSize(aState.availSize);
nsReflowMetrics desiredSize(pKidMaxElementSize);
desiredSize.width=desiredSize.height=desiredSize.ascent=desiredSize.descent=0;
@ -1956,7 +1965,10 @@ PRBool nsTableFrame::ReflowMappedChildren( nsIPresContext* aPresContext,
const nsStyleDisplay *childDisplay;
kidFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)childDisplay));
if (NS_STYLE_DISPLAY_TABLE_CAPTION != childDisplay->mDisplay)
if ((NS_STYLE_DISPLAY_TABLE_HEADER_GROUP == childDisplay->mDisplay) ||
(NS_STYLE_DISPLAY_TABLE_FOOTER_GROUP == childDisplay->mDisplay) ||
(NS_STYLE_DISPLAY_TABLE_ROW_GROUP == childDisplay->mDisplay) ||
(NS_STYLE_DISPLAY_TABLE_COLUMN_GROUP == childDisplay->mDisplay))
{ // for all colgroups and rowgroups...
const nsStyleSpacing* kidSpacing;
kidFrame->GetStyleData(eStyleStruct_Spacing, ((nsStyleStruct *&)kidSpacing));
@ -2436,7 +2448,6 @@ NS_METHOD nsTableFrame::GetColumnFrame(PRInt32 aColIndex, nsTableColFrame *&aCol
if (nsnull!=cellMap)
{ // hooray, we get to do this the easy way because the info is cached
aColFrame = cellMap->GetColumnFrame(aColIndex);
NS_ASSERTION(nsnull!=aColFrame, "bad col frame");
}
else
{ // ah shucks, we have to go hunt for the column frame brute-force style
@ -2456,13 +2467,10 @@ NS_METHOD nsTableFrame::GetColumnFrame(PRInt32 aColIndex, nsTableColFrame *&aCol
PRInt32 colGroupStartingIndex = ((nsTableColGroupFrame *)childFrame)->GetStartColumnIndex();
if (aColIndex >= colGroupStartingIndex)
{ // the cell's col might be in this col group
// XXX FIX ME...
nsIFrame* firstChild;
childFrame->FirstChild(firstChild);
PRInt32 childCount = LengthOf(firstChild);
if (aColIndex < colGroupStartingIndex + childCount)
{ // yep, we've found it
aColFrame = (nsTableColFrame*)FrameAt(firstChild, aColIndex-colGroupStartingIndex);
PRInt32 colCount = ((nsTableColGroupFrame *)childFrame)->GetColumnCount();
if (aColIndex < colGroupStartingIndex + colCount)
{ // yep, we've found it. GetColumnAt gives us the column at the offset colCount, not the absolute colIndex for the whole table
aColFrame = ((nsTableColGroupFrame *)childFrame)->GetColumnAt(colCount);
break;
}
}
@ -2470,6 +2478,7 @@ NS_METHOD nsTableFrame::GetColumnFrame(PRInt32 aColIndex, nsTableColFrame *&aCol
childFrame->GetNextSibling(childFrame);
}
}
NS_POSTCONDITION(nsnull!=aColFrame, "no column frame could be found.");
return NS_OK;
}
@ -2519,16 +2528,24 @@ void nsTableFrame::BuildColumnCache( nsIPresContext* aPresContext,
childFrame->FirstChild(rowFrame);
while (nsnull!=rowFrame)
{
nsIFrame *cellFrame;
rowFrame->FirstChild(cellFrame);
while (nsnull!=cellFrame)
const nsStyleDisplay *rowDisplay;
rowFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)rowDisplay));
if (NS_STYLE_DISPLAY_TABLE_ROW == rowDisplay->mDisplay)
{
/* this is the first time we are guaranteed to have both the cell frames
* and the column frames, so it's a good time to
* set the column style from the cell's width attribute (if this is the first row)
*/
SetColumnStyleFromCell(aPresContext, (nsTableCellFrame *)cellFrame, (nsTableRowFrame *)rowFrame);
cellFrame->GetNextSibling(cellFrame);
nsIFrame *cellFrame;
rowFrame->FirstChild(cellFrame);
while (nsnull!=cellFrame)
{
/* this is the first time we are guaranteed to have both the cell frames
* and the column frames, so it's a good time to
* set the column style from the cell's width attribute (if this is the first row)
*/
const nsStyleDisplay *cellDisplay;
cellFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)cellDisplay));
if (NS_STYLE_DISPLAY_TABLE_CELL == cellDisplay->mDisplay)
SetColumnStyleFromCell(aPresContext, (nsTableCellFrame *)cellFrame, (nsTableRowFrame *)rowFrame);
cellFrame->GetNextSibling(cellFrame);
}
}
rowFrame->GetNextSibling(rowFrame);
}
@ -2551,9 +2568,14 @@ void nsTableFrame::BuildColumnCache( nsIPresContext* aPresContext,
while (nsnull!=colFrame)
{ // for every column, create an entry in the column cache
// assumes that the col style has been twiddled to account for first cell width attribute
const nsStylePosition* colPosition;
colFrame->GetStyleData(eStyleStruct_Position, ((nsStyleStruct *&)colPosition));
mColCache->AddColumnInfo(colPosition->mWidth.GetUnit(), colFrame->GetColumnIndex());
const nsStyleDisplay *colDisplay;
colFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)colDisplay));
if (NS_STYLE_DISPLAY_TABLE_COLUMN == colDisplay->mDisplay)
{
const nsStylePosition* colPosition;
colFrame->GetStyleData(eStyleStruct_Position, ((nsStyleStruct *&)colPosition));
mColCache->AddColumnInfo(colPosition->mWidth.GetUnit(), colFrame->GetColumnIndex());
}
colFrame->GetNextSibling((nsIFrame *&)colFrame);
}
}
@ -2618,7 +2640,8 @@ nsTableFrame::CreateContinuingFrame(nsIPresContext& aPresContext,
rg->GetContent(content); // content: REFCNT++
NS_ASSERTION(nsnull!=content, "bad frame, returned null content.");
const nsStyleDisplay* display;
GetStyleData(eStyleStruct_Display, (const nsStyleStruct*&)display);
//XXX: TROY: this was just this->GetStyleData which can't be right
rg->GetStyleData(eStyleStruct_Display, (const nsStyleStruct*&)display);
if ((display->mDisplay == NS_STYLE_DISPLAY_TABLE_HEADER_GROUP) ||
(display->mDisplay == NS_STYLE_DISPLAY_TABLE_FOOTER_GROUP))
{
@ -2670,9 +2693,6 @@ PRInt32 nsTableFrame::GetColumnWidth(PRInt32 aColIndex)
result = mColumnWidths[aColIndex];
}
//printf("GET_COL_WIDTH: %p, FIF=%p getting col %d and returning %d\n", this, firstInFlow, aColIndex, result);
// XXX hack
return result;
}
@ -2886,6 +2906,29 @@ NS_NewTableFrame(nsIContent* aContent,
return NS_OK;
}
NS_METHOD nsTableFrame::GetTableFrame(nsIFrame *aSourceFrame, nsTableFrame *& aOutFrame)
{
nsresult result = NS_OK;
aOutFrame = nsnull; // initialize out-param
if (nsnull!=aSourceFrame)
{
nsresult result = aSourceFrame->GetContentParent((nsIFrame *&)aOutFrame);
while ((NS_OK==result) && (nsnull!=aOutFrame))
{
const nsStyleDisplay *display;
aOutFrame->GetStyleData(eStyleStruct_Display, (nsStyleStruct *&)display);
if (NS_STYLE_DISPLAY_TABLE == display->mDisplay)
break;
result = aOutFrame->GetContentParent((nsIFrame *&)aOutFrame);
}
}
else
result = NS_ERROR_UNEXPECTED; // bad source param
NS_POSTCONDITION(nsnull!=aOutFrame, "unable to find table parent. aOutFrame null.");
NS_POSTCONDITION(NS_OK==result, "unable to find table parent. result!=NS_OK");
return result;
}
/* helper method for determining if this is a nested table or not */
PRBool nsTableFrame::IsNested(const nsReflowState& aReflowState, nsStylePosition *& aPosition) const
{
@ -2901,6 +2944,7 @@ PRBool nsTableFrame::IsNested(const nsReflowState& aReflowState, nsStylePosition
#ifdef NS_DEBUG
counter++;
NS_ASSERTION(counter<100000, "infinite loop in IsNested");
break;
#endif
nsIFrame* parentTable = nsnull;
rv = rs->frame->QueryInterface(kTableFrameCID, (void**) &parentTable);
@ -3007,13 +3051,9 @@ nscoord nsTableFrame::GetTableContainerWidth(const nsReflowState& aReflowState)
cell->GetStyleData(eStyleStruct_Position, ((nsStyleStruct *&)cellPosition));
if (eStyleUnit_Coord == cellPosition->mWidth.GetUnit())
{
// first, get pointers to the table frame parents of the cell
nsIFrame *rowParent, *rowGroupParent;
nsTableFrame *tableParent;
cell->GetGeometricParent(rowParent);
rowParent->GetGeometricParent(rowGroupParent);
rowGroupParent->GetGeometricParent((nsIFrame *&)tableParent);
if (nsnull != tableParent->mColumnWidths)
rv=GetTableFrame(cell, tableParent);
if ((NS_OK==rv) && (nsnull!=tableParent) && (nsnull!=tableParent->mColumnWidths))
{
parentWidth=0;
PRInt32 colIndex = ((nsTableCellFrame *)cell)->GetColIndex();

View File

@ -77,6 +77,9 @@ public:
/** helper method for determining if this is a nested table or not */
PRBool IsNested(const nsReflowState& aReflowState, nsStylePosition *& aPosition) const;
/** helper method to find the table parent of any table frame object */
static NS_METHOD GetTableFrame(nsIFrame *aSourceFrame, nsTableFrame *& aOutFrame);
/** helper method for getting the width of the table's containing block */
static nscoord GetTableContainerWidth(const nsReflowState& aState);

View File

@ -103,59 +103,48 @@ nsTableRowFrame::Init(nsIPresContext& aPresContext, nsIFrame* aChildList)
nsTableFrame* table = nsnull;
nsresult result;
result = GetTableFrame((nsIFrame *&)table);
result = nsTableFrame::GetTableFrame(this, table);
if ((NS_OK==result) && (table != nsnull))
{
SetRowIndex(table->GetNextAvailRowIndex());
PRInt32 colIndex = 0;
for (nsIFrame* kidFrame = mFirstChild; nsnull != kidFrame; kidFrame->GetNextSibling(kidFrame))
{
// what column does this cell belong to?
colIndex = table->GetNextAvailColIndex(mRowIndex, colIndex);
/* for style context optimization, set the content's column index if possible.
* this can only be done if we really have an nsTableCell.
* other tags mapped to table cell display won't benefit from this optimization
* see nsHTMLStyleSheet::RulesMatching
*/
nsIContent* cell;
kidFrame->GetContent(cell);
nsIHTMLTableCellElement *cellContent = nsnull;
nsresult rv = cell->QueryInterface(kIHTMLTableCellElementIID,
(void **)&cellContent); // cellContent: REFCNT++
NS_RELEASE(cell);
if (NS_SUCCEEDED(rv))
{ // we know it's a table cell
cellContent->SetColIndex(colIndex);
if (gsDebug) printf("%p : set cell content %p to col index = %d\n", this, cellContent, colIndex);
NS_RELEASE(cellContent);
const nsStyleDisplay *kidDisplay;
kidFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)kidDisplay));
if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay)
{
// what column does this cell belong to?
colIndex = table->GetNextAvailColIndex(mRowIndex, colIndex);
/* for style context optimization, set the content's column index if possible.
* this can only be done if we really have an nsTableCell.
* other tags mapped to table cell display won't benefit from this optimization
* see nsHTMLStyleSheet::RulesMatching
*/
nsIContent* cell;
kidFrame->GetContent(cell);
nsIHTMLTableCellElement *cellContent = nsnull;
nsresult rv = cell->QueryInterface(kIHTMLTableCellElementIID,
(void **)&cellContent); // cellContent: REFCNT++
NS_RELEASE(cell);
if (NS_SUCCEEDED(rv))
{ // we know it's a table cell
cellContent->SetColIndex(colIndex);
if (gsDebug) printf("%p : set cell content %p to col index = %d\n", this, cellContent, colIndex);
NS_RELEASE(cellContent);
}
// this sets the frame's notion of it's column index
((nsTableCellFrame *)kidFrame)->InitCellFrame(colIndex);
if (gsDebug) printf("%p : set cell frame %p to col index = %d\n", this, kidFrame, colIndex);
// add the cell frame to the table's cell map
table->AddCellToTable(this, (nsTableCellFrame *)kidFrame, kidFrame == mFirstChild);
}
// part of the style optimization is to ensure that the column frame for the cell exists
//table->EnsureColumnFrameAt(colIndex, &aPresContext);
// this sets the frame's notion of it's column index
((nsTableCellFrame *)kidFrame)->InitCellFrame(colIndex);
if (gsDebug) printf("%p : set cell frame %p to col index = %d\n", this, kidFrame, colIndex);
// add the cell frame to the table's cell map
table->AddCellToTable(this, (nsTableCellFrame *)kidFrame, kidFrame == mFirstChild);
}
}
return NS_OK;
}
NS_METHOD nsTableRowFrame::GetTableFrame(nsIFrame *& aFrame)
{
nsresult result = GetContentParent(aFrame);
while ((NS_OK==result) && (nsnull!=aFrame))
{
const nsStyleDisplay *display;
aFrame->GetStyleData(eStyleStruct_Display, (nsStyleStruct *&)display);
if (NS_STYLE_DISPLAY_TABLE == display->mDisplay)
break;
result = aFrame->GetContentParent(aFrame);
}
return result;
}
/**
* Post-reflow hook. This is where the table row does its post-processing
*/
@ -166,30 +155,29 @@ nsTableRowFrame::DidReflow(nsIPresContext& aPresContext,
if (NS_FRAME_REFLOW_FINISHED == aStatus) {
// Resize and re-align the cell frames based on our row height
nscoord cellHeight = mRect.height - mCellMaxTopMargin - mCellMaxBottomMargin;
// XXX
// every place in this module where we cast to nsTableCellFrame,
// we first have to check the display-type of the frame and skip non-cells.
nsTableCellFrame *cellFrame = (nsTableCellFrame*)mFirstChild;
nsTableFrame* tableFrame;
mContentParent->GetContentParent((nsIFrame*&)tableFrame);
nsIFrame *cellFrame = mFirstChild;
nsTableFrame* tableFrame;
nsTableFrame::GetTableFrame(this, tableFrame);
while (nsnull != cellFrame)
{
PRInt32 rowSpan = tableFrame->GetEffectiveRowSpan(mRowIndex, cellFrame);
if (1==rowSpan)
const nsStyleDisplay *kidDisplay;
cellFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)kidDisplay));
if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay)
{
// resize the cell's height
nsSize cellFrameSize;
cellFrame->GetSize(cellFrameSize);
cellFrame->SizeTo(cellFrameSize.width, cellHeight);
PRInt32 rowSpan = tableFrame->GetEffectiveRowSpan(mRowIndex, (nsTableCellFrame *)cellFrame);
if (1==rowSpan)
{
// resize the cell's height
nsSize cellFrameSize;
cellFrame->GetSize(cellFrameSize);
cellFrame->SizeTo(cellFrameSize.width, cellHeight);
// realign cell content based on the new height
cellFrame->VerticallyAlignChild(&aPresContext);
// realign cell content based on the new height
((nsTableCellFrame *)cellFrame)->VerticallyAlignChild(&aPresContext);
}
}
// Get the next cell
cellFrame->GetNextSibling((nsIFrame*&)cellFrame);
// Get the next cell
cellFrame->GetNextSibling(cellFrame);
}
}
@ -294,10 +282,16 @@ nscoord nsTableRowFrame::GetChildMaxBottomMargin() const
PRInt32 nsTableRowFrame::GetMaxColumns() const
{
int sum = 0;
nsTableCellFrame *cell=(nsTableCellFrame *)mFirstChild;
while (nsnull!=cell) {
sum += cell->GetColSpan();
cell->GetNextSibling((nsIFrame *&)cell);
nsIFrame *cell=mFirstChild;
while (nsnull!=cell)
{
const nsStyleDisplay *kidDisplay;
cell->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)kidDisplay));
if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay)
{
sum += ((nsTableCellFrame *)cell)->GetColSpan();
}
cell->GetNextSibling(cell);
}
return sum;
}
@ -311,11 +305,16 @@ void nsTableRowFrame::GetMinRowSpan(nsTableFrame *aTableFrame)
nsIFrame *frame=mFirstChild;
while (nsnull!=frame)
{
PRInt32 rowSpan = aTableFrame->GetEffectiveRowSpan(mRowIndex, ((nsTableCellFrame *)frame));
if (-1==minRowSpan)
minRowSpan = rowSpan;
else if (minRowSpan>rowSpan)
minRowSpan = rowSpan;
const nsStyleDisplay *kidDisplay;
frame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)kidDisplay));
if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay)
{
PRInt32 rowSpan = aTableFrame->GetEffectiveRowSpan(mRowIndex, ((nsTableCellFrame *)frame));
if (-1==minRowSpan)
minRowSpan = rowSpan;
else if (minRowSpan>rowSpan)
minRowSpan = rowSpan;
}
frame->GetNextSibling(frame);
}
mMinRowSpan = minRowSpan;
@ -326,13 +325,18 @@ void nsTableRowFrame::FixMinCellHeight(nsTableFrame *aTableFrame)
nsIFrame *frame=mFirstChild;
while (nsnull!=frame)
{
PRInt32 rowSpan = aTableFrame->GetEffectiveRowSpan(mRowIndex, ((nsTableCellFrame *)frame));
if (mMinRowSpan==rowSpan)
const nsStyleDisplay *kidDisplay;
frame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)kidDisplay));
if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay)
{
nsRect rect;
frame->GetRect(rect);
if (rect.height > mTallestCell)
mTallestCell = rect.height;
PRInt32 rowSpan = aTableFrame->GetEffectiveRowSpan(mRowIndex, ((nsTableCellFrame *)frame));
if (mMinRowSpan==rowSpan)
{
nsRect rect;
frame->GetRect(rect);
if (rect.height > mTallestCell)
mTallestCell = rect.height;
}
}
frame->GetNextSibling(frame);
}
@ -599,7 +603,7 @@ nsTableRowFrame::InitialReflow(nsIPresContext& aPresContext,
PRBool isFirst=PR_TRUE;
PRBool tableLayoutStrategy=NS_STYLE_TABLE_LAYOUT_AUTO;
nsTableFrame* table = nsnull;
nsresult result = GetTableFrame((nsIFrame *&)table);
nsresult result = nsTableFrame::GetTableFrame(this, table);
if ((NS_OK==result) && (table != nsnull))
{
nsStyleTable* tableStyle;
@ -611,66 +615,71 @@ nsTableRowFrame::InitialReflow(nsIPresContext& aPresContext,
for (nsIFrame* kidFrame = mFirstChild; nsnull != kidFrame; kidFrame->GetNextSibling(kidFrame))
{
// Get the child's margins
nsMargin margin;
nscoord topMargin = 0;
if (aState.tableFrame->GetCellMarginData((nsTableCellFrame *)kidFrame, margin) == NS_OK)
const nsStyleDisplay *kidDisplay;
kidFrame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)kidDisplay));
if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay)
{
topMargin = margin.top;
}
// Get the child's margins
nsMargin margin;
nscoord topMargin = 0;
if (aState.tableFrame->GetCellMarginData((nsTableCellFrame *)kidFrame, margin) == NS_OK)
{
topMargin = margin.top;
}
maxTopMargin = PR_MAX(margin.top, maxTopMargin);
maxBottomMargin = PR_MAX(margin.bottom, maxBottomMargin);
maxTopMargin = PR_MAX(margin.top, maxTopMargin);
maxBottomMargin = PR_MAX(margin.bottom, maxBottomMargin);
// Because we're not splittable always allow the child to be as high as
// it wants. The default available width is also unconstrained so we can
// get the child's maximum width
nsSize kidAvailSize;
nsReflowMetrics kidSize(nsnull);
if (NS_STYLE_TABLE_LAYOUT_AUTO==tableLayoutStrategy)
{
kidAvailSize.SizeTo(NS_UNCONSTRAINEDSIZE, NS_UNCONSTRAINEDSIZE);
kidSize.maxElementSize=&kidMaxElementSize;
// Because we're not splittable always allow the child to be as high as
// it wants. The default available width is also unconstrained so we can
// get the child's maximum width
nsSize kidAvailSize;
nsReflowMetrics kidSize(nsnull);
if (NS_STYLE_TABLE_LAYOUT_AUTO==tableLayoutStrategy)
{
kidAvailSize.SizeTo(NS_UNCONSTRAINEDSIZE, NS_UNCONSTRAINEDSIZE);
kidSize.maxElementSize=&kidMaxElementSize;
}
else
{
PRInt32 colIndex = ((nsTableCellFrame *)kidFrame)->GetColIndex();
kidAvailSize.SizeTo(table->GetColumnWidth(colIndex), NS_UNCONSTRAINEDSIZE);
}
nsReflowState kidReflowState(kidFrame, aState.reflowState, kidAvailSize,
eReflowReason_Initial);
kidFrame->WillReflow(aPresContext);
if (gsDebug) printf ("%p InitR: avail=%d\n", this, kidAvailSize.width);
nsresult status = ReflowChild(kidFrame, &aPresContext, kidSize, kidReflowState);
if (gsDebug)
printf ("TR %p for cell %p Initial Reflow: desired=%d, MES=%d\n",
this, kidFrame, kidSize.width, kidMaxElementSize.width);
//XXX: this is a hack, shouldn't it be the case that a min size is
// never larger than a desired size?
if (kidMaxElementSize.width>kidSize.width)
kidSize.width = kidMaxElementSize.width;
if (kidMaxElementSize.height>kidSize.height)
kidSize.height = kidMaxElementSize.height;
((nsTableCellFrame *)kidFrame)->SetPass1DesiredSize(kidSize);
((nsTableCellFrame *)kidFrame)->SetPass1MaxElementSize(kidMaxElementSize);
NS_ASSERTION(NS_FRAME_IS_COMPLETE(status), "unexpected child reflow status");
if (gsDebug)
{
printf("reflow of cell returned result = %s with desired=%d,%d, min = %d,%d\n",
NS_FRAME_IS_COMPLETE(status)?"complete":"NOT complete",
kidSize.width, kidSize.height,
kidMaxElementSize.width, kidMaxElementSize.height);
}
// Place the child
x += margin.left;
nsRect kidRect(x, topMargin, kidSize.width, kidSize.height);
PlaceChild(aPresContext, aState, kidFrame, kidRect, aDesiredSize.maxElementSize,
&kidMaxElementSize);
x += kidSize.width + margin.right;
}
else
{
PRInt32 colIndex = ((nsTableCellFrame *)kidFrame)->GetColIndex();
kidAvailSize.SizeTo(table->GetColumnWidth(colIndex), NS_UNCONSTRAINEDSIZE);
}
nsReflowState kidReflowState(kidFrame, aState.reflowState, kidAvailSize,
eReflowReason_Initial);
kidFrame->WillReflow(aPresContext);
if (gsDebug) printf ("%p InitR: avail=%d\n", this, kidAvailSize.width);
nsresult status = ReflowChild(kidFrame, &aPresContext, kidSize, kidReflowState);
if (gsDebug)
printf ("TR %p for cell %p Initial Reflow: desired=%d, MES=%d\n",
this, kidFrame, kidSize.width, kidMaxElementSize.width);
//XXX: this is a hack, shouldn't it be the case that a min size is
// never larger than a desired size?
if (kidMaxElementSize.width>kidSize.width)
kidSize.width = kidMaxElementSize.width;
if (kidMaxElementSize.height>kidSize.height)
kidSize.height = kidMaxElementSize.height;
((nsTableCellFrame *)kidFrame)->SetPass1DesiredSize(kidSize);
((nsTableCellFrame *)kidFrame)->SetPass1MaxElementSize(kidMaxElementSize);
NS_ASSERTION(NS_FRAME_IS_COMPLETE(status), "unexpected child reflow status");
if (gsDebug)
{
printf("reflow of cell returned result = %s with desired=%d,%d, min = %d,%d\n",
NS_FRAME_IS_COMPLETE(status)?"complete":"NOT complete",
kidSize.width, kidSize.height,
kidMaxElementSize.width, kidMaxElementSize.height);
}
// Place the child
x += margin.left;
nsRect kidRect(x, topMargin, kidSize.width, kidSize.height);
PlaceChild(aPresContext, aState, kidFrame, kidRect, aDesiredSize.maxElementSize,
&kidMaxElementSize);
x += kidSize.width + margin.right;
}
SetMaxChildHeight(aState.maxCellHeight, maxTopMargin, maxBottomMargin); // remember height of tallest child who doesn't have a row span
@ -702,62 +711,67 @@ nsresult nsTableRowFrame::RecoverState(nsIPresContext& aPresContext,
// frames except aKidFrame
// nsIFrame* prevKidFrame = nsnull;
for (nsIFrame* frame = mFirstChild; nsnull != frame;) {
if (frame != aKidFrame) {
// Update the max top and bottom margins
nsMargin kidMargin;
aState.tableFrame->GetCellMarginData((nsTableCellFrame *)frame, kidMargin);
if (kidMargin.top > aMaxCellTopMargin)
aMaxCellTopMargin = kidMargin.top;
if (kidMargin.bottom > aMaxCellBottomMargin)
aMaxCellBottomMargin = kidMargin.bottom;
const nsStyleDisplay *kidDisplay;
frame->GetStyleData(eStyleStruct_Display, ((nsStyleStruct *&)kidDisplay));
if (NS_STYLE_DISPLAY_TABLE_CELL == kidDisplay->mDisplay)
{
if (frame != aKidFrame) {
// Update the max top and bottom margins
nsMargin kidMargin;
aState.tableFrame->GetCellMarginData((nsTableCellFrame *)frame, kidMargin);
if (kidMargin.top > aMaxCellTopMargin)
aMaxCellTopMargin = kidMargin.top;
if (kidMargin.bottom > aMaxCellBottomMargin)
aMaxCellBottomMargin = kidMargin.bottom;
PRInt32 rowSpan = aState.tableFrame->GetEffectiveRowSpan(mRowIndex, ((nsTableCellFrame *)frame));
if (mMinRowSpan == rowSpan) {
// Get the cell's desired height the last time it was reflowed
nsSize desiredSize = ((nsTableCellFrame *)frame)->GetDesiredSize();
PRInt32 rowSpan = aState.tableFrame->GetEffectiveRowSpan(mRowIndex, ((nsTableCellFrame *)frame));
if (mMinRowSpan == rowSpan) {
// Get the cell's desired height the last time it was reflowed
nsSize desiredSize = ((nsTableCellFrame *)frame)->GetDesiredSize();
// See if it has a specified height that overrides the desired size
nscoord specifiedHeight = 0;
nsIStyleContextPtr kidSC;
frame->GetStyleContext(&aPresContext, kidSC.AssignRef());
const nsStylePosition* kidPosition = (const nsStylePosition*)
kidSC->GetStyleData(eStyleStruct_Position);
switch (kidPosition->mHeight.GetUnit()) {
case eStyleUnit_Coord:
specifiedHeight = kidPosition->mHeight.GetCoordValue();
break;
// See if it has a specified height that overrides the desired size
nscoord specifiedHeight = 0;
nsIStyleContextPtr kidSC;
frame->GetStyleContext(&aPresContext, kidSC.AssignRef());
const nsStylePosition* kidPosition = (const nsStylePosition*)
kidSC->GetStyleData(eStyleStruct_Position);
switch (kidPosition->mHeight.GetUnit()) {
case eStyleUnit_Coord:
specifiedHeight = kidPosition->mHeight.GetCoordValue();
break;
case eStyleUnit_Inherit:
// XXX for now, do nothing
default:
case eStyleUnit_Auto:
break;
}
if (specifiedHeight > desiredSize.height)
desiredSize.height = specifiedHeight;
case eStyleUnit_Inherit:
// XXX for now, do nothing
default:
case eStyleUnit_Auto:
break;
}
if (specifiedHeight > desiredSize.height)
desiredSize.height = specifiedHeight;
// Update maxCellHeight
if (desiredSize.height > aState.maxCellHeight) {
aState.maxCellHeight = desiredSize.height;
}
// Update maxCellHeight
if (desiredSize.height > aState.maxCellHeight) {
aState.maxCellHeight = desiredSize.height;
}
// Update maxCellVertHeight
nsMargin margin;
// Update maxCellVertHeight
nsMargin margin;
if (aState.tableFrame->GetCellMarginData((nsTableCellFrame *)frame, margin) == NS_OK)
{
nscoord height = desiredSize.height + margin.top + margin.bottom;
if (height > aState.maxCellVertSpace) {
aState.maxCellVertSpace = height;
if (aState.tableFrame->GetCellMarginData((nsTableCellFrame *)frame, margin) == NS_OK)
{
nscoord height = desiredSize.height + margin.top + margin.bottom;
if (height > aState.maxCellVertSpace) {
aState.maxCellVertSpace = height;
}
}
}
}
// XXX We also need to recover the max element size if requested by the
// caller...
//
// We should be using GetReflowMetrics() to get information from the
// table cell, and that will include the max element size...
// XXX We also need to recover the max element size if requested by the
// caller...
//
// We should be using GetReflowMetrics() to get information from the
// table cell, and that will include the max element size...
}
}
// Remember the frame that precedes aKidFrame

View File

@ -114,9 +114,6 @@ public:
/** set this row's starting row index */
virtual void SetRowIndex (int aRowIndex);
/** get the row's enclosing table frame in a safe way */
NS_IMETHOD GetTableFrame(nsIFrame *& aFrame);
NS_IMETHOD List(FILE* out = stdout, PRInt32 aIndent = 0, nsIListFilter *aFilter = nsnull) const;
protected: