author | Ryan VanderMeulen <ryanvm@gmail.com> |
Fri, 17 Jul 2015 12:04:24 -0400 | |
changeset 253506 | 65c3a87e04fb7cf4250533fc16387af8d1a05c6b |
parent 253505 | f6a5ad7edc09a74e63596416315c82384201bc15 |
child 253507 | c5d8689db9b2c2e0b8bc6f2128ffc36554461ac7 |
push id | 29067 |
push user | kwierso@gmail.com |
push date | Sat, 18 Jul 2015 00:57:04 +0000 |
treeherder | mozilla-central@e2f2eb9ecca0 [default view] [failures only] |
perfherder | [talos] [build metrics] [platform microbench] (compared to previous push) |
bugs | 812899 |
milestone | 42.0a1 |
backs out | a5ea84a0a7792190ec90020e2c193eb963a3b145 |
first release with | nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
|
last release without | nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
|
layout/generic/nsHTMLReflowState.cpp | file | annotate | diff | comparison | revisions | |
layout/reftests/abs-pos/abs-pos-auto-margin-centered-ref.html | file | annotate | diff | comparison | revisions | |
layout/reftests/abs-pos/abs-pos-auto-margin-centered.html | file | annotate | diff | comparison | revisions | |
layout/reftests/abs-pos/reftest.list | file | annotate | diff | comparison | revisions |
--- a/layout/generic/nsHTMLReflowState.cpp +++ b/layout/generic/nsHTMLReflowState.cpp @@ -40,17 +40,17 @@ using namespace mozilla; using namespace mozilla::css; using namespace mozilla::dom; using namespace mozilla::layout; enum eNormalLineHeightControl { eUninitialized = -1, - eNoExternalLeading = 0, // does not include external leading + eNoExternalLeading = 0, // does not include external leading eIncludeExternalLeading, // use whatever value font vendor provides eCompensateLeading // compensate leading if leading provided by font vendor is not enough }; static eNormalLineHeightControl sNormalLineHeightControl = eUninitialized; // Initialize a <b>root</b> reflow state with a rendering context to // use for measuring things. @@ -480,21 +480,21 @@ void nsHTMLReflowState::InitCBReflowStat mCBReflowState = parentReflowState; } } else { mCBReflowState = parentReflowState->mCBReflowState; } } /* Check whether CalcQuirkContainingBlockHeight would stop on the - * given reflow state, using its block as a height. (essentially - * returns false for any case in which CalcQuirkContainingBlockHeight + * given reflow state, using its block as a height. (essentially + * returns false for any case in which CalcQuirkContainingBlockHeight * has a "continue" in its main loop.) * - * XXX Maybe refactor CalcQuirkContainingBlockHeight so it uses + * XXX Maybe refactor CalcQuirkContainingBlockHeight so it uses * this function as well */ static bool IsQuirkContainingBlockHeight(const nsHTMLReflowState* rs, nsIAtom* aFrameType) { if (nsGkAtoms::blockFrame == aFrameType || #ifdef MOZ_XUL nsGkAtoms::XULLabelFrame == aFrameType || @@ -664,19 +664,19 @@ nsHTMLReflowState::InitResizeFlags(nsPre // If we're the descendant of a table cell that performs special bsize // reflows and we could be the child that requires them, always set // the block-axis resize in case this is the first pass before the // special bsize reflow. However, don't do this if it actually is // the special bsize reflow, since in that case it will already be // set correctly above if we need it set. if (!IsBResize() && mCBReflowState && - (IS_TABLE_CELL(mCBReflowState->frame->GetType()) || + (IS_TABLE_CELL(mCBReflowState->frame->GetType()) || mCBReflowState->mFlags.mHeightDependsOnAncestorCell) && - !mCBReflowState->mFlags.mSpecialBSizeReflow && + !mCBReflowState->mFlags.mSpecialBSizeReflow && dependsOnCBBSize) { SetBResize(true); mFlags.mHeightDependsOnAncestorCell = true; } // Set NS_FRAME_CONTAINS_RELATIVE_BSIZE if it's needed. // It would be nice to check that |ComputedBSize != NS_AUTOHEIGHT| @@ -689,21 +689,21 @@ nsHTMLReflowState::InitResizeFlags(nsPre if (dependsOnCBBSize && mCBReflowState) { const nsHTMLReflowState *rs = this; bool hitCBReflowState = false; do { rs = rs->parentReflowState; if (!rs) { break; } - + if (rs->frame->GetStateBits() & NS_FRAME_CONTAINS_RELATIVE_BSIZE) break; // no need to go further rs->frame->AddStateBits(NS_FRAME_CONTAINS_RELATIVE_BSIZE); - + // Keep track of whether we've hit the containing block, because // we need to go at least that far. if (rs == mCBReflowState) { hitCBReflowState = true; } // XXX What about orthogonal flows? It doesn't make sense to // keep propagating this bit across an orthogonal boundary, @@ -711,17 +711,17 @@ nsHTMLReflowState::InitResizeFlags(nsPre } while (!hitCBReflowState || (eCompatibility_NavQuirks == aPresContext->CompatibilityMode() && !IsQuirkContainingBlockHeight(rs, rs->frame->GetType()))); // Note: We actually don't need to set the // NS_FRAME_CONTAINS_RELATIVE_BSIZE bit for the cases // where we hit the early break statements in // CalcQuirkContainingBlockHeight. But it doesn't hurt // us to set the bit in these cases. - + } if (frame->GetStateBits() & NS_FRAME_IS_DIRTY) { // If we're reflowing everything, then we'll find out if we need // to re-set this. frame->RemoveStateBits(NS_FRAME_CONTAINS_RELATIVE_BSIZE); } } @@ -1736,20 +1736,25 @@ nsHTMLReflowState::InitAbsoluteConstrain nscoord availMarginSpace = autoBSize - computedSize.BSize(cbwm); bool marginBStartIsAuto = eStyleUnit_Auto == mStyleMargin->mMargin.GetBStartUnit(cbwm); bool marginBEndIsAuto = eStyleUnit_Auto == mStyleMargin->mMargin.GetBEndUnit(cbwm); if (marginBStartIsAuto) { if (marginBEndIsAuto) { - // Both 'margin-top' and 'margin-bottom' are 'auto', so they get - // equal values - margin.BStart(cbwm) = availMarginSpace / 2; - margin.BEnd(cbwm) = availMarginSpace - margin.BStart(cbwm); + if (availMarginSpace < 0) { + // FIXME: Note that the spec doesn't actually say we should do this! + margin.BEnd(cbwm) = availMarginSpace; + } else { + // Both margin-block-start and -end are 'auto', so they get + // equal values + margin.BStart(cbwm) = availMarginSpace / 2; + margin.BEnd(cbwm) = availMarginSpace - margin.BStart(cbwm); + } } else { // Just margin-block-start is 'auto' margin.BStart(cbwm) = availMarginSpace; } } else { if (marginBEndIsAuto) { // Just margin-block-end is 'auto' margin.BEnd(cbwm) = availMarginSpace; @@ -1773,54 +1778,54 @@ nsHTMLReflowState::InitAbsoluteConstrain nscoord GetBlockMarginBorderPadding(const nsHTMLReflowState* aReflowState) { nscoord result = 0; if (!aReflowState) return result; // zero auto margins nsMargin margin = aReflowState->ComputedPhysicalMargin(); - if (NS_AUTOMARGIN == margin.top) + if (NS_AUTOMARGIN == margin.top) margin.top = 0; - if (NS_AUTOMARGIN == margin.bottom) + if (NS_AUTOMARGIN == margin.bottom) margin.bottom = 0; result += margin.top + margin.bottom; - result += aReflowState->ComputedPhysicalBorderPadding().top + + result += aReflowState->ComputedPhysicalBorderPadding().top + aReflowState->ComputedPhysicalBorderPadding().bottom; return result; } -/* Get the height based on the viewport of the containing block specified +/* Get the height based on the viewport of the containing block specified * in aReflowState when the containing block has mComputedHeight == NS_AUTOHEIGHT * This will walk up the chain of containing blocks looking for a computed height * until it finds the canvas frame, or it encounters a frame that is not a block, * area, or scroll frame. This handles compatibility with IE (see bug 85016 and bug 219693) * * When we encounter scrolledContent block frames, we skip over them, * since they are guaranteed to not be useful for computing the containing block. * * See also IsQuirkContainingBlockHeight. */ static nscoord CalcQuirkContainingBlockHeight(const nsHTMLReflowState* aCBReflowState) { const nsHTMLReflowState* firstAncestorRS = nullptr; // a candidate for html frame const nsHTMLReflowState* secondAncestorRS = nullptr; // a candidate for body frame - + // initialize the default to NS_AUTOHEIGHT as this is the containings block - // computed height when this function is called. It is possible that we + // computed height when this function is called. It is possible that we // don't alter this height especially if we are restricted to one level - nscoord result = NS_AUTOHEIGHT; - + nscoord result = NS_AUTOHEIGHT; + const nsHTMLReflowState* rs = aCBReflowState; for (; rs; rs = rs->parentReflowState) { nsIAtom* frameType = rs->frame->GetType(); - // if the ancestor is auto height then skip it and continue up if it + // if the ancestor is auto height then skip it and continue up if it // is the first block frame and possibly the body/html if (nsGkAtoms::blockFrame == frameType || #ifdef MOZ_XUL nsGkAtoms::XULLabelFrame == frameType || #endif nsGkAtoms::scrollFrame == frameType) { secondAncestorRS = firstAncestorRS; @@ -1839,33 +1844,33 @@ CalcQuirkContainingBlockHeight(const nsH } } else if (nsGkAtoms::canvasFrame == frameType) { // Always continue on to the height calculation } else if (nsGkAtoms::pageContentFrame == frameType) { nsIFrame* prevInFlow = rs->frame->GetPrevInFlow(); // only use the page content frame for a height basis if it is the first in flow - if (prevInFlow) + if (prevInFlow) break; } else { break; } - // if the ancestor is the page content frame then the percent base is + // if the ancestor is the page content frame then the percent base is // the avail height, otherwise it is the computed height result = (nsGkAtoms::pageContentFrame == frameType) ? rs->AvailableHeight() : rs->ComputedHeight(); // if unconstrained - don't sutract borders - would result in huge height if (NS_AUTOHEIGHT == result) return result; - // if we got to the canvas or page content frame, then subtract out + // if we got to the canvas or page content frame, then subtract out // margin/border/padding for the BODY and HTML elements - if ((nsGkAtoms::canvasFrame == frameType) || + if ((nsGkAtoms::canvasFrame == frameType) || (nsGkAtoms::pageContentFrame == frameType)) { result -= GetBlockMarginBorderPadding(firstAncestorRS); result -= GetBlockMarginBorderPadding(secondAncestorRS); #ifdef DEBUG // make sure the first ancestor is the HTML and the second is the BODY if (firstAncestorRS) { @@ -1878,17 +1883,17 @@ CalcQuirkContainingBlockHeight(const nsH if (secondAncestorRS) { nsIContent* frameContent = secondAncestorRS->frame->GetContent(); if (frameContent) { NS_ASSERTION(frameContent->IsHTMLElement(nsGkAtoms::body), "Second ancestor is not BODY"); } } #endif - + } // if we got to the html frame (a block child of the canvas) ... else if (nsGkAtoms::blockFrame == frameType && rs->parentReflowState && nsGkAtoms::canvasFrame == rs->parentReflowState->frame->GetType()) { // ... then subtract out margin/border/padding for the BODY element result -= GetBlockMarginBorderPadding(secondAncestorRS); @@ -2433,17 +2438,17 @@ nsCSSOffsetState::InitOffsets(WritingMod ::UpdateProp(props, nsIFrame::UsedPaddingProperty(), needPaddingProp, ComputedPhysicalPadding()); } // This code enforces section 10.3.3 of the CSS2 spec for this formula: // // 'margin-left' + 'border-left-width' + 'padding-left' + 'width' + // 'padding-right' + 'border-right-width' + 'margin-right' -// = width of containing block +// = width of containing block // // Note: the width unit is not auto when this is called void nsHTMLReflowState::CalculateBlockSideMargins(nsIAtom* aFrameType) { // Calculations here are done in the containing block's writing mode, // which is where margins will eventually be applied: we're calculating // margins that will be used by the container in its inline direction, @@ -2549,24 +2554,24 @@ nsHTMLReflowState::CalculateBlockSideMar margin.IStart(cbWM) += availMarginSpace; } } else if (isAutoEndMargin) { margin.IEnd(cbWM) += availMarginSpace; } SetComputedLogicalMargin(margin.ConvertTo(mWritingMode, cbWM)); } -#define NORMAL_LINE_HEIGHT_FACTOR 1.2f // in term of emHeight +#define NORMAL_LINE_HEIGHT_FACTOR 1.2f // in term of emHeight // For "normal" we use the font's normal line height (em height + leading). // If both internal leading and external leading specified by font itself -// are zeros, we should compensate this by creating extra (external) leading -// in eCompensateLeading mode. This is necessary because without this -// compensation, normal line height might looks too tight. +// are zeros, we should compensate this by creating extra (external) leading +// in eCompensateLeading mode. This is necessary because without this +// compensation, normal line height might looks too tight. -// For risk management, we use preference to control the behavior, and +// For risk management, we use preference to control the behavior, and // eNoExternalLeading is the old behavior. static nscoord GetNormalLineHeight(nsFontMetrics* aFontMetrics) { NS_PRECONDITION(nullptr != aFontMetrics, "no font metrics"); nscoord normalLineHeight; @@ -2601,26 +2606,26 @@ ComputeLineHeight(nsStyleContext* aStyle nscoord result = lhCoord.GetCoordValue(); if (aFontSizeInflation != 1.0f) { result = NSToCoordRound(result * aFontSizeInflation); } return result; } if (lhCoord.GetUnit() == eStyleUnit_Factor) - // For factor units the computed value of the line-height property + // For factor units the computed value of the line-height property // is found by multiplying the factor by the font's computed size // (adjusted for min-size prefs and text zoom). return NSToCoordRound(lhCoord.GetFactorValue() * aFontSizeInflation * aStyleContext->StyleFont()->mFont.size); NS_ASSERTION(lhCoord.GetUnit() == eStyleUnit_Normal || lhCoord.GetUnit() == eStyleUnit_Enumerated, "bad line-height unit"); - + if (lhCoord.GetUnit() == eStyleUnit_Enumerated) { NS_ASSERTION(lhCoord.GetIntValue() == NS_STYLE_LINE_HEIGHT_BLOCK_HEIGHT, "bad line-height value"); if (aBlockBSize != NS_AUTOHEIGHT) { return aBlockBSize; } } @@ -2865,9 +2870,9 @@ nsHTMLReflowState::IsFloating() const { return mStyleDisplay->IsFloating(frame); } uint8_t nsHTMLReflowState::GetDisplay() const { return mStyleDisplay->GetDisplay(frame); -} \ No newline at end of file +}
deleted file mode 100644 --- a/layout/reftests/abs-pos/abs-pos-auto-margin-centered-ref.html +++ /dev/null @@ -1,32 +0,0 @@ -<!DOCTYPE HTML> -<title> absolutely positioned element should be vertically centered even if the height is bigger than that of the containing block (reference) - bug 812899</title> -<style> -body > div { - font-size: 16px; - position: relative; - border: red solid; - margin-top: 5em; - width: 5em; - height: 5em; -} - -body > div > div { - position: absolute; - border: medium solid blue; - margin: -23px auto - height: 150%; - width: 150%; - left: 0px; - right: 0px; - top: 0px; - bottom: 0px; -} -</style> - -<body> - <div> - <div></div> - </div> -</body> - -</html>
deleted file mode 100644 --- a/layout/reftests/abs-pos/abs-pos-auto-margin-centered.html +++ /dev/null @@ -1,32 +0,0 @@ -<!DOCTYPE HTML> -<title> absolutely positioned element should be vertically centered even if the height is bigger than that of the containing block (reference) - bug 812899</title> -<style> -body > div { - font-size: 16px; - position: relative; - border: red solid; - margin-top: 5em; - width: 5em; - height: 5em; -} - -body > div > div { - position: absolute; - border: medium solid blue; - margin: auto auto; - height: 150%; - width: 150%; - left: 0px; - right: 0px; - top: 0px; - bottom: 0px; -} -</style> - -<body> - <div> - <div></div> - </div> -</body> - -</html>
--- a/layout/reftests/abs-pos/reftest.list +++ b/layout/reftests/abs-pos/reftest.list @@ -1,11 +1,10 @@ == font-size-wrap.html font-size-wrap-ref.html == abs-pos-auto-margin-1.html abs-pos-auto-margin-1-ref.html -== abs-pos-auto-margin-centered.html abs-pos-auto-margin-centered-ref.html fuzzy-if(/^Windows\x20NT\x206\.1/.test(http.oscpu)&&!layersGPUAccelerated&&!azureSkia,73,1) == auto-offset-inline-block-1.html auto-offset-inline-block-1-ref.html # bug 696670 == fieldset-1.html fieldset-1-ref.html == table-1.html table-1-ref.html == table-2.html table-2-ref.html == table-3.html table-3-ref.html == table-caption-1.html table-internal-1-ref.html == table-caption-2.html table-internal-2-ref.html == table-caption-3.html table-internal-3-ref.html