additional patch for bug 97138 to cache pct height info on row and constrain sum of row height pcts <= 100.

This commit is contained in:
karnaze%netscape.com 2001-11-05 15:15:24 +00:00
Родитель a3b85aa75c
Коммит 5bc05378ef
6 изменённых файлов: 120 добавлений и 26 удалений

Просмотреть файл

@ -35,6 +35,7 @@
*
* ***** END LICENSE BLOCK ***** */
#include "nsTableRowFrame.h"
#include "nsTableRowGroupFrame.h"
#include "nsIRenderingContext.h"
#include "nsIPresShell.h"
#include "nsIPresContext.h"
@ -114,11 +115,12 @@ nsTableRowFrame::SetFixedHeight(nscoord aValue)
}
void
nsTableRowFrame::SetPctHeight(float aPctValue)
nsTableRowFrame::SetPctHeight(float aPctValue,
PRBool aForce)
{
nscoord height = PR_MAX(0, NSToCoordRound(aPctValue * 100.0f));
if (HasPctHeight()) {
if (height > mStyleHeight) {
if ((height > mStyleHeight) || aForce) {
mStyleHeight = height;
}
}
@ -520,6 +522,15 @@ nsTableRowFrame::CalcHeight(const nsHTMLReflowState& aReflowState)
? 0 : aReflowState.mComputedHeight;
ResetHeight(computedHeight);
const nsStylePosition* position;
GetStyleData(eStyleStruct_Position, (const nsStyleStruct*&)position);
if (eStyleUnit_Coord == position->mHeight.GetUnit()) {
SetFixedHeight(position->mHeight.GetCoordValue());
}
else if (eStyleUnit_Percent == position->mHeight.GetUnit()) {
SetPctHeight(position->mHeight.GetPercentValue());
}
for (nsIFrame* kidFrame = mFrames.FirstChild(); kidFrame; kidFrame->GetNextSibling(&kidFrame)) {
nsCOMPtr<nsIAtom> frameType;
kidFrame->GetFrameType(getter_AddRefs(frameType));
@ -1336,12 +1347,22 @@ nsTableRowFrame::Reflow(nsIPresContext* aPresContext,
if (!tableFrame) return NS_ERROR_NULL_POINTER;
if ((NS_UNCONSTRAINEDSIZE != aReflowState.availableWidth) && !mPrevInFlow) {
// see if an extra reflow will be necessary when there is a pct height but no height on the parent
// see if an extra reflow will be necessary when there is a pct height but no height basis
if ( ((NS_UNCONSTRAINEDSIZE == aReflowState.mComputedHeight) ||
(0 == aReflowState.mComputedHeight)) &&
(0 == aReflowState.mComputedHeight)) &&
nsTableFrame::IsPctHeight(mStyleContext)) {
nsTableFrame::NotifyAncestorsOfSpecialReflow(aReflowState);
SetNeedSpecialReflow(PR_TRUE);
const nsHTMLReflowState* parentRS = aReflowState.parentReflowState;
if (parentRS && parentRS->frame) {
nsCOMPtr<nsIAtom> fType;
parentRS->frame->GetFrameType(getter_AddRefs(fType));
if (nsLayoutAtoms::tableRowGroupFrame == fType.get()) {
nscoord pctBasis = ((nsTableRowGroupFrame*)parentRS->frame)->GetHeightBasis(*parentRS);
if (0 == pctBasis) {
nsTableFrame::NotifyAncestorsOfSpecialReflow(aReflowState);
SetNeedSpecialReflow(PR_TRUE);
}
}
}
}
}

Просмотреть файл

@ -236,7 +236,8 @@ public:
void SetFixedHeight(nscoord aValue);
float GetPctHeight() const;
void SetPctHeight(float aPctValue);
void SetPctHeight(float aPctValue,
PRBool aForce = PR_FALSE);
nscoord GetHeight(nscoord aBasis = 0) const;

Просмотреть файл

@ -560,6 +560,20 @@ nsTableRowGroupFrame::CalculateRowHeights(nsIPresContext* aPresContext,
float p2t;
aPresContext->GetPixelsToTwips(&p2t);
// make sure that pct height rows do not exceed 100%
nscoord pctTotal = 0;
nsTableRowFrame* rowFrame;
for (rowFrame = GetFirstRow(); rowFrame; rowFrame = rowFrame->GetNextRow()) {
if (rowFrame->HasPctHeight()) {
nscoord pctHeight = NSToCoordRound(rowFrame->GetPctHeight() * 100.0f);
if ((pctHeight + pctTotal) > 100) {
pctHeight = PR_MAX(0, NSToCoordRound(100.0f - (float)pctTotal));
rowFrame->SetPctHeight((float)pctHeight / 100.0f, PR_TRUE);
}
pctTotal += pctHeight;
}
}
// find the nearest row at or before aStartRowFrameIn that isn't spanned into.
// If we have a computed height, then we can't compute the heights
// incrementally from aStartRowFrameIn, and we must start at the first row.
@ -605,7 +619,6 @@ nsTableRowGroupFrame::CalculateRowHeights(nsIPresContext* aPresContext,
// the largest desired height of each cell, the largest style height of each cell,
// the style height of the row.
nscoord pctHeightBasis = GetHeightBasis(aReflowState);
nsTableRowFrame* rowFrame;
PRInt32 rowIndex; // the index in rowInfo, not among the rows in the row group
for (rowFrame = startRowFrame, rowIndex = 0; rowFrame; rowFrame = rowFrame->GetNextRow(), rowIndex++) {
UpdateHeights(rowInfo[rowIndex], nsTableFrame::RoundToPixel(rowFrame->GetHeight(pctHeightBasis), p2t),
@ -1326,14 +1339,26 @@ nscoord
nsTableRowGroupFrame::GetHeightBasis(const nsHTMLReflowState& aReflowState)
{
nscoord result = 0;
if ((aReflowState.mComputedHeight > 0) && (aReflowState.mComputedHeight < NS_UNCONSTRAINEDSIZE)) {
nsTableFrame* tableFrame = nsnull;
nsTableFrame::GetTableFrame((nsIFrame*)this, tableFrame);
if (tableFrame) {
nsTableFrame* tableFrame = nsnull;
nsTableFrame::GetTableFrame((nsIFrame*)this, tableFrame);
if (tableFrame) {
if ((aReflowState.mComputedHeight > 0) && (aReflowState.mComputedHeight < NS_UNCONSTRAINEDSIZE)) {
nscoord cellSpacing = PR_MAX(0, GetRowCount() - 1) * tableFrame->GetCellSpacingY();
result -= cellSpacing;
result = aReflowState.mComputedHeight - cellSpacing;
}
else {
const nsHTMLReflowState* parentRS = aReflowState.parentReflowState;
if (parentRS && (tableFrame != parentRS->frame)) {
parentRS = parentRS->parentReflowState;
}
if (parentRS && (tableFrame == parentRS->frame) &&
(parentRS->mComputedHeight > 0) && (parentRS->mComputedHeight < NS_UNCONSTRAINEDSIZE)) {
nscoord cellSpacing = PR_MAX(0, tableFrame->GetRowCount() - 1) * tableFrame->GetCellSpacingY();
result = parentRS->mComputedHeight - cellSpacing;
}
}
}
return result;
}

Просмотреть файл

@ -35,6 +35,7 @@
*
* ***** END LICENSE BLOCK ***** */
#include "nsTableRowFrame.h"
#include "nsTableRowGroupFrame.h"
#include "nsIRenderingContext.h"
#include "nsIPresShell.h"
#include "nsIPresContext.h"
@ -114,11 +115,12 @@ nsTableRowFrame::SetFixedHeight(nscoord aValue)
}
void
nsTableRowFrame::SetPctHeight(float aPctValue)
nsTableRowFrame::SetPctHeight(float aPctValue,
PRBool aForce)
{
nscoord height = PR_MAX(0, NSToCoordRound(aPctValue * 100.0f));
if (HasPctHeight()) {
if (height > mStyleHeight) {
if ((height > mStyleHeight) || aForce) {
mStyleHeight = height;
}
}
@ -520,6 +522,15 @@ nsTableRowFrame::CalcHeight(const nsHTMLReflowState& aReflowState)
? 0 : aReflowState.mComputedHeight;
ResetHeight(computedHeight);
const nsStylePosition* position;
GetStyleData(eStyleStruct_Position, (const nsStyleStruct*&)position);
if (eStyleUnit_Coord == position->mHeight.GetUnit()) {
SetFixedHeight(position->mHeight.GetCoordValue());
}
else if (eStyleUnit_Percent == position->mHeight.GetUnit()) {
SetPctHeight(position->mHeight.GetPercentValue());
}
for (nsIFrame* kidFrame = mFrames.FirstChild(); kidFrame; kidFrame->GetNextSibling(&kidFrame)) {
nsCOMPtr<nsIAtom> frameType;
kidFrame->GetFrameType(getter_AddRefs(frameType));
@ -1336,12 +1347,22 @@ nsTableRowFrame::Reflow(nsIPresContext* aPresContext,
if (!tableFrame) return NS_ERROR_NULL_POINTER;
if ((NS_UNCONSTRAINEDSIZE != aReflowState.availableWidth) && !mPrevInFlow) {
// see if an extra reflow will be necessary when there is a pct height but no height on the parent
// see if an extra reflow will be necessary when there is a pct height but no height basis
if ( ((NS_UNCONSTRAINEDSIZE == aReflowState.mComputedHeight) ||
(0 == aReflowState.mComputedHeight)) &&
(0 == aReflowState.mComputedHeight)) &&
nsTableFrame::IsPctHeight(mStyleContext)) {
nsTableFrame::NotifyAncestorsOfSpecialReflow(aReflowState);
SetNeedSpecialReflow(PR_TRUE);
const nsHTMLReflowState* parentRS = aReflowState.parentReflowState;
if (parentRS && parentRS->frame) {
nsCOMPtr<nsIAtom> fType;
parentRS->frame->GetFrameType(getter_AddRefs(fType));
if (nsLayoutAtoms::tableRowGroupFrame == fType.get()) {
nscoord pctBasis = ((nsTableRowGroupFrame*)parentRS->frame)->GetHeightBasis(*parentRS);
if (0 == pctBasis) {
nsTableFrame::NotifyAncestorsOfSpecialReflow(aReflowState);
SetNeedSpecialReflow(PR_TRUE);
}
}
}
}
}

Просмотреть файл

@ -236,7 +236,8 @@ public:
void SetFixedHeight(nscoord aValue);
float GetPctHeight() const;
void SetPctHeight(float aPctValue);
void SetPctHeight(float aPctValue,
PRBool aForce = PR_FALSE);
nscoord GetHeight(nscoord aBasis = 0) const;

Просмотреть файл

@ -560,6 +560,20 @@ nsTableRowGroupFrame::CalculateRowHeights(nsIPresContext* aPresContext,
float p2t;
aPresContext->GetPixelsToTwips(&p2t);
// make sure that pct height rows do not exceed 100%
nscoord pctTotal = 0;
nsTableRowFrame* rowFrame;
for (rowFrame = GetFirstRow(); rowFrame; rowFrame = rowFrame->GetNextRow()) {
if (rowFrame->HasPctHeight()) {
nscoord pctHeight = NSToCoordRound(rowFrame->GetPctHeight() * 100.0f);
if ((pctHeight + pctTotal) > 100) {
pctHeight = PR_MAX(0, NSToCoordRound(100.0f - (float)pctTotal));
rowFrame->SetPctHeight((float)pctHeight / 100.0f, PR_TRUE);
}
pctTotal += pctHeight;
}
}
// find the nearest row at or before aStartRowFrameIn that isn't spanned into.
// If we have a computed height, then we can't compute the heights
// incrementally from aStartRowFrameIn, and we must start at the first row.
@ -605,7 +619,6 @@ nsTableRowGroupFrame::CalculateRowHeights(nsIPresContext* aPresContext,
// the largest desired height of each cell, the largest style height of each cell,
// the style height of the row.
nscoord pctHeightBasis = GetHeightBasis(aReflowState);
nsTableRowFrame* rowFrame;
PRInt32 rowIndex; // the index in rowInfo, not among the rows in the row group
for (rowFrame = startRowFrame, rowIndex = 0; rowFrame; rowFrame = rowFrame->GetNextRow(), rowIndex++) {
UpdateHeights(rowInfo[rowIndex], nsTableFrame::RoundToPixel(rowFrame->GetHeight(pctHeightBasis), p2t),
@ -1326,14 +1339,26 @@ nscoord
nsTableRowGroupFrame::GetHeightBasis(const nsHTMLReflowState& aReflowState)
{
nscoord result = 0;
if ((aReflowState.mComputedHeight > 0) && (aReflowState.mComputedHeight < NS_UNCONSTRAINEDSIZE)) {
nsTableFrame* tableFrame = nsnull;
nsTableFrame::GetTableFrame((nsIFrame*)this, tableFrame);
if (tableFrame) {
nsTableFrame* tableFrame = nsnull;
nsTableFrame::GetTableFrame((nsIFrame*)this, tableFrame);
if (tableFrame) {
if ((aReflowState.mComputedHeight > 0) && (aReflowState.mComputedHeight < NS_UNCONSTRAINEDSIZE)) {
nscoord cellSpacing = PR_MAX(0, GetRowCount() - 1) * tableFrame->GetCellSpacingY();
result -= cellSpacing;
result = aReflowState.mComputedHeight - cellSpacing;
}
else {
const nsHTMLReflowState* parentRS = aReflowState.parentReflowState;
if (parentRS && (tableFrame != parentRS->frame)) {
parentRS = parentRS->parentReflowState;
}
if (parentRS && (tableFrame == parentRS->frame) &&
(parentRS->mComputedHeight > 0) && (parentRS->mComputedHeight < NS_UNCONSTRAINEDSIZE)) {
nscoord cellSpacing = PR_MAX(0, tableFrame->GetRowCount() - 1) * tableFrame->GetCellSpacingY();
result = parentRS->mComputedHeight - cellSpacing;
}
}
}
return result;
}