Bug 478956. Merge pseudo-frame handling for outer tables and non-table frames. r=bernd, sr=roc
This commit is contained in:
@@ -2990,12 +2990,12 @@ nsCSSFrameConstructor::GetPseudoCellFrame(PRInt32 aNameSpaceID,
|
|||||||
}
|
}
|
||||||
|
|
||||||
nsresult
|
nsresult
|
||||||
nsCSSFrameConstructor::GetParentFrame(PRInt32 aNameSpaceID,
|
nsCSSFrameConstructor::CreateRequiredPseudoFrames(PRInt32 aNameSpaceID,
|
||||||
nsIFrame& aParentFrameIn,
|
nsIFrame& aParentFrameIn,
|
||||||
nsIAtom* aChildFrameType,
|
nsIAtom* aChildFrameType,
|
||||||
nsFrameConstructorState& aState,
|
nsFrameConstructorState& aState,
|
||||||
nsIFrame*& aParentFrame,
|
nsIFrame*& aParentFrame,
|
||||||
PRBool& aIsPseudoParent)
|
PRBool& aIsPseudoParent)
|
||||||
{
|
{
|
||||||
nsresult rv = NS_OK;
|
nsresult rv = NS_OK;
|
||||||
|
|
||||||
@@ -3008,15 +3008,7 @@ nsCSSFrameConstructor::GetParentFrame(PRInt32 aNameSpaceID,
|
|||||||
nsFrameState savedStateBits = aState.mAdditionalStateBits;
|
nsFrameState savedStateBits = aState.mAdditionalStateBits;
|
||||||
aState.mAdditionalStateBits &= ~NS_FRAME_GENERATED_CONTENT;
|
aState.mAdditionalStateBits &= ~NS_FRAME_GENERATED_CONTENT;
|
||||||
|
|
||||||
if (nsGkAtoms::tableOuterFrame == aChildFrameType) { // table child
|
if (nsGkAtoms::tableCaptionFrame == aChildFrameType) { // caption child
|
||||||
if (IsTableRelated(parentFrameType, PR_TRUE) &&
|
|
||||||
(nsGkAtoms::tableCaptionFrame != parentFrameType) ) { // need pseudo cell parent
|
|
||||||
rv = GetPseudoCellFrame(aNameSpaceID, aState, aParentFrameIn);
|
|
||||||
if (NS_FAILED(rv)) return rv;
|
|
||||||
pseudoParentFrame = pseudoFrames.mCellInner.mFrame;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (nsGkAtoms::tableCaptionFrame == aChildFrameType) { // caption child
|
|
||||||
if (nsGkAtoms::tableOuterFrame != parentFrameType) { // need pseudo table parent
|
if (nsGkAtoms::tableOuterFrame != parentFrameType) { // need pseudo table parent
|
||||||
rv = GetPseudoTableFrame(aNameSpaceID, aState, aParentFrameIn);
|
rv = GetPseudoTableFrame(aNameSpaceID, aState, aParentFrameIn);
|
||||||
if (NS_FAILED(rv)) return rv;
|
if (NS_FAILED(rv)) return rv;
|
||||||
@@ -3060,16 +3052,11 @@ nsCSSFrameConstructor::GetParentFrame(PRInt32 aNameSpaceID,
|
|||||||
pseudoParentFrame = pseudoFrames.mRow.mFrame;
|
pseudoParentFrame = pseudoFrames.mRow.mFrame;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (nsGkAtoms::tableFrame == aChildFrameType) { // invalid
|
#ifdef DEBUG
|
||||||
NS_ASSERTION(PR_FALSE, "GetParentFrame called on nsGkAtoms::tableFrame child");
|
else {
|
||||||
}
|
NS_ERROR("Unexpected frame type in CreateRequiredPseudoFrames");
|
||||||
else { // foreign frame
|
|
||||||
if (IsTableRelated(parentFrameType, PR_FALSE)) { // need pseudo cell parent
|
|
||||||
rv = GetPseudoCellFrame(aNameSpaceID, aState, aParentFrameIn);
|
|
||||||
if (NS_FAILED(rv)) return rv;
|
|
||||||
pseudoParentFrame = pseudoFrames.mCellInner.mFrame;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
if (pseudoParentFrame) {
|
if (pseudoParentFrame) {
|
||||||
aParentFrame = pseudoParentFrame;
|
aParentFrame = pseudoParentFrame;
|
||||||
@@ -3139,6 +3126,15 @@ nsCSSFrameConstructor::AdjustParentFrame(nsFrameConstructorState& aState,
|
|||||||
// needs to become the float containing block.
|
// needs to become the float containing block.
|
||||||
aState.PushFloatContainingBlock(aParentFrame, aSaveState);
|
aState.PushFloatContainingBlock(aParentFrame, aSaveState);
|
||||||
aCreatedPseudo = PR_TRUE;
|
aCreatedPseudo = PR_TRUE;
|
||||||
|
|
||||||
|
// Now it might be that we had existing pseudo-frames and in particular an
|
||||||
|
// existing pseudo-cell (so that the pseudo cell we just got is not the
|
||||||
|
// lowest pseudo-frame). If that's the case, we need to process everythign
|
||||||
|
// below that cell, so that our later siblings don't see those
|
||||||
|
// pseudo-frames.
|
||||||
|
if (aState.mPseudoFrames.mTableOuter.mFrame) {
|
||||||
|
ProcessPseudoFrames(aState, nsGkAtoms::tableOuterFrame);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
}
|
}
|
||||||
@@ -3194,30 +3190,13 @@ nsCSSFrameConstructor::ConstructTableFrame(nsFrameConstructorState& aState,
|
|||||||
#endif
|
#endif
|
||||||
aNewOuterFrame = NS_NewTableOuterFrame(mPresShell, outerStyleContext);
|
aNewOuterFrame = NS_NewTableOuterFrame(mPresShell, outerStyleContext);
|
||||||
|
|
||||||
nsIFrame* parentFrame = aContentParent;
|
NS_ASSERTION(!IsTableRelated(aContentParent->GetType(), PR_TRUE) ||
|
||||||
nsFrameItems* frameItems = &aChildItems;
|
aContentParent->GetType() == nsGkAtoms::tableCaptionFrame,
|
||||||
// We may need to push a float containing block
|
"Unexpected parent frame for table");
|
||||||
nsFrameConstructorSaveState floatSaveState;
|
|
||||||
if (!aIsPseudo) {
|
|
||||||
// this frame may have a pseudo parent
|
|
||||||
PRBool hasPseudoParent = PR_FALSE;
|
|
||||||
GetParentFrame(aNameSpaceID,*parentFrame, nsGkAtoms::tableOuterFrame,
|
|
||||||
aState, parentFrame, hasPseudoParent);
|
|
||||||
if (!hasPseudoParent && !aState.mPseudoFrames.IsEmpty()) {
|
|
||||||
ProcessPseudoFrames(aState, aChildItems);
|
|
||||||
}
|
|
||||||
if (hasPseudoParent) {
|
|
||||||
aState.PushFloatContainingBlock(parentFrame, floatSaveState);
|
|
||||||
frameItems = &aState.mPseudoFrames.mCellInner.mChildList;
|
|
||||||
if (aState.mPseudoFrames.mTableOuter.mFrame) {
|
|
||||||
ProcessPseudoFrames(aState, nsGkAtoms::tableOuterFrame);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
nsIFrame* geometricParent = aState.GetGeometricParent
|
nsIFrame* geometricParent = aState.GetGeometricParent
|
||||||
(outerStyleContext->GetStyleDisplay(),
|
(outerStyleContext->GetStyleDisplay(),
|
||||||
parentFrame);
|
aContentParent);
|
||||||
|
|
||||||
// Init the table outer frame and see if we need to create a view, e.g.
|
// Init the table outer frame and see if we need to create a view, e.g.
|
||||||
// the frame is absolutely positioned
|
// the frame is absolutely positioned
|
||||||
@@ -3239,8 +3218,8 @@ nsCSSFrameConstructor::ConstructTableFrame(nsFrameConstructorState& aState,
|
|||||||
// Put the newly created frames into the right child list
|
// Put the newly created frames into the right child list
|
||||||
aNewOuterFrame->SetInitialChildList(nsnull, aNewInnerFrame);
|
aNewOuterFrame->SetInitialChildList(nsnull, aNewInnerFrame);
|
||||||
|
|
||||||
rv = aState.AddChild(aNewOuterFrame, *frameItems, aContent,
|
rv = aState.AddChild(aNewOuterFrame, aChildItems, aContent,
|
||||||
aStyleContext, parentFrame);
|
aStyleContext, aContentParent);
|
||||||
if (NS_FAILED(rv)) {
|
if (NS_FAILED(rv)) {
|
||||||
return rv;
|
return rv;
|
||||||
}
|
}
|
||||||
@@ -3289,9 +3268,9 @@ nsCSSFrameConstructor::ConstructTableCaptionFrame(nsFrameConstructorState& aStat
|
|||||||
nsIFrame* parentFrame = aParentFrameIn;
|
nsIFrame* parentFrame = aParentFrameIn;
|
||||||
*aHasPseudoParent = PR_FALSE;
|
*aHasPseudoParent = PR_FALSE;
|
||||||
// this frame may have a pseudo parent
|
// this frame may have a pseudo parent
|
||||||
GetParentFrame(aNameSpaceID, *aParentFrameIn,
|
CreateRequiredPseudoFrames(aNameSpaceID, *aParentFrameIn,
|
||||||
nsGkAtoms::tableCaptionFrame, aState, parentFrame,
|
nsGkAtoms::tableCaptionFrame, aState, parentFrame,
|
||||||
*aHasPseudoParent);
|
*aHasPseudoParent);
|
||||||
if (!*aHasPseudoParent && !aState.mPseudoFrames.IsEmpty()) {
|
if (!*aHasPseudoParent && !aState.mPseudoFrames.IsEmpty()) {
|
||||||
ProcessPseudoFrames(aState, aChildItems);
|
ProcessPseudoFrames(aState, aChildItems);
|
||||||
}
|
}
|
||||||
@@ -3333,9 +3312,9 @@ nsCSSFrameConstructor::ConstructTableRowGroupFrame(nsFrameConstructorState& aSta
|
|||||||
*aHasPseudoParent = PR_FALSE;
|
*aHasPseudoParent = PR_FALSE;
|
||||||
if (!aIsPseudo) {
|
if (!aIsPseudo) {
|
||||||
// this frame may have a pseudo parent
|
// this frame may have a pseudo parent
|
||||||
GetParentFrame(aNameSpaceID, *aParentFrameIn,
|
CreateRequiredPseudoFrames(aNameSpaceID, *aParentFrameIn,
|
||||||
nsGkAtoms::tableRowGroupFrame, aState, parentFrame,
|
nsGkAtoms::tableRowGroupFrame, aState,
|
||||||
*aHasPseudoParent);
|
parentFrame, *aHasPseudoParent);
|
||||||
if (!*aHasPseudoParent && !aState.mPseudoFrames.IsEmpty()) {
|
if (!*aHasPseudoParent && !aState.mPseudoFrames.IsEmpty()) {
|
||||||
ProcessPseudoFrames(aState, aChildItems);
|
ProcessPseudoFrames(aState, aChildItems);
|
||||||
}
|
}
|
||||||
@@ -3403,9 +3382,9 @@ nsCSSFrameConstructor::ConstructTableColGroupFrame(nsFrameConstructorState& aSta
|
|||||||
*aHasPseudoParent = PR_FALSE;
|
*aHasPseudoParent = PR_FALSE;
|
||||||
if (!aIsPseudo) {
|
if (!aIsPseudo) {
|
||||||
// this frame may have a pseudo parent
|
// this frame may have a pseudo parent
|
||||||
GetParentFrame(aNameSpaceID, *aParentFrameIn,
|
CreateRequiredPseudoFrames(aNameSpaceID, *aParentFrameIn,
|
||||||
nsGkAtoms::tableColGroupFrame, aState, parentFrame,
|
nsGkAtoms::tableColGroupFrame, aState,
|
||||||
*aHasPseudoParent);
|
parentFrame, *aHasPseudoParent);
|
||||||
if (!*aHasPseudoParent && !aState.mPseudoFrames.IsEmpty()) {
|
if (!*aHasPseudoParent && !aState.mPseudoFrames.IsEmpty()) {
|
||||||
ProcessPseudoFrames(aState, aChildItems);
|
ProcessPseudoFrames(aState, aChildItems);
|
||||||
}
|
}
|
||||||
@@ -3452,9 +3431,9 @@ nsCSSFrameConstructor::ConstructTableRowFrame(nsFrameConstructorState& aState,
|
|||||||
*aHasPseudoParent = PR_FALSE;
|
*aHasPseudoParent = PR_FALSE;
|
||||||
if (!aIsPseudo) {
|
if (!aIsPseudo) {
|
||||||
// this frame may have a pseudo parent
|
// this frame may have a pseudo parent
|
||||||
GetParentFrame(aNameSpaceID, *aParentFrameIn,
|
CreateRequiredPseudoFrames(aNameSpaceID, *aParentFrameIn,
|
||||||
nsGkAtoms::tableRowFrame, aState, parentFrame,
|
nsGkAtoms::tableRowFrame, aState, parentFrame,
|
||||||
*aHasPseudoParent);
|
*aHasPseudoParent);
|
||||||
if (!*aHasPseudoParent && !aState.mPseudoFrames.IsEmpty()) {
|
if (!*aHasPseudoParent && !aState.mPseudoFrames.IsEmpty()) {
|
||||||
ProcessPseudoFrames(aState, aChildItems);
|
ProcessPseudoFrames(aState, aChildItems);
|
||||||
}
|
}
|
||||||
@@ -3507,9 +3486,9 @@ nsCSSFrameConstructor::ConstructTableColFrame(nsFrameConstructorState& aState,
|
|||||||
*aHasPseudoParent = PR_FALSE;
|
*aHasPseudoParent = PR_FALSE;
|
||||||
if (!aIsPseudo) {
|
if (!aIsPseudo) {
|
||||||
// this frame may have a pseudo parent
|
// this frame may have a pseudo parent
|
||||||
GetParentFrame(aNameSpaceID, *aParentFrameIn,
|
CreateRequiredPseudoFrames(aNameSpaceID, *aParentFrameIn,
|
||||||
nsGkAtoms::tableColFrame, aState, parentFrame,
|
nsGkAtoms::tableColFrame, aState, parentFrame,
|
||||||
*aHasPseudoParent);
|
*aHasPseudoParent);
|
||||||
if (!*aHasPseudoParent && !aState.mPseudoFrames.IsEmpty()) {
|
if (!*aHasPseudoParent && !aState.mPseudoFrames.IsEmpty()) {
|
||||||
ProcessPseudoFrames(aState, aChildItems);
|
ProcessPseudoFrames(aState, aChildItems);
|
||||||
}
|
}
|
||||||
@@ -3568,9 +3547,9 @@ nsCSSFrameConstructor::ConstructTableCellFrame(nsFrameConstructorState& aState,
|
|||||||
if (!aIsPseudo) {
|
if (!aIsPseudo) {
|
||||||
// this frame may have a pseudo parent
|
// this frame may have a pseudo parent
|
||||||
// use nsGkAtoms::tableCellFrame which will match if it is really nsGkAtoms::bcTableCellFrame
|
// use nsGkAtoms::tableCellFrame which will match if it is really nsGkAtoms::bcTableCellFrame
|
||||||
GetParentFrame(aNameSpaceID, *aParentFrameIn,
|
CreateRequiredPseudoFrames(aNameSpaceID, *aParentFrameIn,
|
||||||
nsGkAtoms::tableCellFrame, aState, parentFrame,
|
nsGkAtoms::tableCellFrame, aState, parentFrame,
|
||||||
*aHasPseudoParent);
|
*aHasPseudoParent);
|
||||||
if (!*aHasPseudoParent && !aState.mPseudoFrames.IsEmpty()) {
|
if (!*aHasPseudoParent && !aState.mPseudoFrames.IsEmpty()) {
|
||||||
ProcessPseudoFrames(aState, aChildItems);
|
ProcessPseudoFrames(aState, aChildItems);
|
||||||
}
|
}
|
||||||
@@ -5881,8 +5860,7 @@ nsCSSFrameConstructor::FindDisplayData(const nsStyleDisplay* aDisplay,
|
|||||||
if (NS_STYLE_DISPLAY_TABLE == aDisplay->mDisplay ||
|
if (NS_STYLE_DISPLAY_TABLE == aDisplay->mDisplay ||
|
||||||
NS_STYLE_DISPLAY_INLINE_TABLE == aDisplay->mDisplay) {
|
NS_STYLE_DISPLAY_INLINE_TABLE == aDisplay->mDisplay) {
|
||||||
static const FrameConstructionData sTableData =
|
static const FrameConstructionData sTableData =
|
||||||
FULL_CTOR_FCDATA(FCDATA_IS_TABLE_PART,
|
FULL_CTOR_FCDATA(0, &nsCSSFrameConstructor::ConstructTable);
|
||||||
&nsCSSFrameConstructor::ConstructTable);
|
|
||||||
return &sTableData;
|
return &sTableData;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -539,12 +539,12 @@ private:
|
|||||||
nsFrameConstructorState& aState,
|
nsFrameConstructorState& aState,
|
||||||
nsIFrame& aParentFrameIn);
|
nsIFrame& aParentFrameIn);
|
||||||
|
|
||||||
nsresult GetParentFrame(PRInt32 aNameSpaceID,
|
nsresult CreateRequiredPseudoFrames(PRInt32 aNameSpaceID,
|
||||||
nsIFrame& aParentFrameIn,
|
nsIFrame& aParentFrameIn,
|
||||||
nsIAtom* aChildFrameType,
|
nsIAtom* aChildFrameType,
|
||||||
nsFrameConstructorState& aState,
|
nsFrameConstructorState& aState,
|
||||||
nsIFrame*& aParentFrame,
|
nsIFrame*& aParentFrame,
|
||||||
PRBool& aIsPseudoParent);
|
PRBool& aIsPseudoParent);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
/* A constructor function that just creates an nsIFrame object. The caller
|
/* A constructor function that just creates an nsIFrame object. The caller
|
||||||
|
|||||||
17
layout/reftests/bugs/478956-1-ref.html
Normal file
17
layout/reftests/bugs/478956-1-ref.html
Normal file
@@ -0,0 +1,17 @@
|
|||||||
|
<!DOCTYPE html>
|
||||||
|
<html>
|
||||||
|
<body>
|
||||||
|
<table cellpadding="0" cellspacing="0">
|
||||||
|
<tr>
|
||||||
|
<td>Long long cell</td>
|
||||||
|
<td>cell</td>
|
||||||
|
</tr>
|
||||||
|
</table>
|
||||||
|
<table cellpadding="0" cellspacing="0">
|
||||||
|
<tr>
|
||||||
|
<td>cell</td>
|
||||||
|
<td>cell</td>
|
||||||
|
</tr>
|
||||||
|
</table>
|
||||||
|
</body>
|
||||||
|
</html>
|
||||||
16
layout/reftests/bugs/478956-1a.html
Normal file
16
layout/reftests/bugs/478956-1a.html
Normal file
@@ -0,0 +1,16 @@
|
|||||||
|
<!DOCTYPE html>
|
||||||
|
<html>
|
||||||
|
<body>
|
||||||
|
<div style="display: table-row">
|
||||||
|
<div style="display: table-row">
|
||||||
|
<div style="display: table-cell">Long long cell</div>
|
||||||
|
<div style="display: table-cell">cell</div>
|
||||||
|
</div>
|
||||||
|
<span style="display: table"></span>
|
||||||
|
<div style="display: table-row">
|
||||||
|
<div style="display: table-cell">cell</div>
|
||||||
|
<div style="display: table-cell">cell</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
||||||
16
layout/reftests/bugs/478956-1b.html
Normal file
16
layout/reftests/bugs/478956-1b.html
Normal file
@@ -0,0 +1,16 @@
|
|||||||
|
<!DOCTYPE html>
|
||||||
|
<html>
|
||||||
|
<body>
|
||||||
|
<div style="display: table-row">
|
||||||
|
<div style="display: table-row">
|
||||||
|
<div style="display: table-cell">Long long cell</div>
|
||||||
|
<div style="display: table-cell">cell</div>
|
||||||
|
</div>
|
||||||
|
<span style="display: block"></span>
|
||||||
|
<div style="display: table-row">
|
||||||
|
<div style="display: table-cell">cell</div>
|
||||||
|
<div style="display: table-cell">cell</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
||||||
@@ -1092,3 +1092,5 @@ fails == 461512-1.html 461512-1-ref.html # Bug 461512
|
|||||||
== 478811-2.html 478811-2-ref.html
|
== 478811-2.html 478811-2-ref.html
|
||||||
== 478811-3.html 478811-3-ref.html
|
== 478811-3.html 478811-3-ref.html
|
||||||
== 478811-4.html 478811-4-ref.html
|
== 478811-4.html 478811-4-ref.html
|
||||||
|
== 478956-1a.html 478956-1-ref.html
|
||||||
|
== 478956-1b.html 478956-1-ref.html
|
||||||
|
|||||||
Reference in New Issue
Block a user