Stop using -moz-float-edge for list items, but offset the bullet position in the presence of floats. b=413840 (and numerous others) r+sr=roc a=blocking1.9+

This commit is contained in:
dbaron@dbaron.org 2008-02-10 13:49:24 -08:00
Родитель 03d06767e2
Коммит 123ba5e8cd
15 изменённых файлов: 355 добавлений и 32 удалений

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

@ -1066,13 +1066,18 @@ nsBlockFrame::Reflow(nsPresContext* aPresContext,
// rare case: an empty first line followed by a second line that
// contains a block (example: <LI>\n<P>... ). This is where
// the second case can happen.
if (mBullet && HaveOutsideBullet() &&
(mLines.empty() ||
mLines.front()->IsBlock() ||
0 == mLines.front()->mBounds.height)) {
if (mBullet && HaveOutsideBullet() && !mLines.empty() &&
(mLines.front()->IsBlock() ||
(0 == mLines.front()->mBounds.height &&
mLines.front() != mLines.back() &&
mLines.begin().next()->IsBlock()))) {
// Reflow the bullet
nsHTMLReflowMetrics metrics;
ReflowBullet(state, metrics);
// FIXME: aReflowState.mComputedBorderPadding.top isn't even the
// right place -- we really want the top of the line whose baseline
// we're using (or, actually, the entire line, once we fix bug
// 25888)
ReflowBullet(state, metrics, aReflowState.mComputedBorderPadding.top);
nscoord baseline;
if (nsLayoutUtils::GetFirstLineBaseline(this, &baseline)) {
@ -2189,7 +2194,8 @@ nsBlockFrame::ReflowDirtyLines(nsBlockReflowState& aState)
// Handle an odd-ball case: a list-item with no lines
if (mBullet && HaveOutsideBullet() && mLines.empty()) {
nsHTMLReflowMetrics metrics;
ReflowBullet(aState, metrics);
ReflowBullet(aState, metrics,
aState.mReflowState.mComputedBorderPadding.top);
// There are no lines so we have to fake up some y motion so that
// we end up with *some* height.
@ -3955,18 +3961,16 @@ nsBlockFrame::PlaceLine(nsBlockReflowState& aState,
//
// There are exactly two places a bullet can be placed: near the
// first or second line. It's only placed on the second line in a
// rare case: an empty first line followed by a second line that
// contains a block (example: <LI>\n<P>... ).
//
// For this code, only the first case is possible because this
// method is used for placing a line of inline frames. If the rare
// case is happening then the worst that will happen is that the
// bullet frame will be reflowed twice.
// rare case: when the first line is empty.
PRBool addedBullet = PR_FALSE;
if (mBullet && HaveOutsideBullet() && (aLine == mLines.front()) &&
(!aLineLayout.IsZeroHeight() || (aLine == mLines.back()))) {
if (mBullet && HaveOutsideBullet() &&
((aLine == mLines.front() &&
(!aLineLayout.IsZeroHeight() || (aLine == mLines.back()))) ||
(mLines.front() != mLines.back() &&
0 == mLines.front()->mBounds.height &&
aLine == mLines.begin().next()))) {
nsHTMLReflowMetrics metrics;
ReflowBullet(aState, metrics);
ReflowBullet(aState, metrics, aState.mY);
aLineLayout.AddBulletFrame(mBullet, metrics);
addedBullet = PR_TRUE;
}
@ -6542,7 +6546,8 @@ nsBlockFrame::RenumberListsFor(nsPresContext* aPresContext,
void
nsBlockFrame::ReflowBullet(nsBlockReflowState& aState,
nsHTMLReflowMetrics& aMetrics)
nsHTMLReflowMetrics& aMetrics,
nscoord aLineTop)
{
const nsHTMLReflowState &rs = aState.mReflowState;
@ -6561,19 +6566,39 @@ nsBlockFrame::ReflowBullet(nsBlockReflowState& aState,
mBullet->WillReflow(aState.mPresContext);
mBullet->Reflow(aState.mPresContext, aMetrics, reflowState, status);
// Place the bullet now; use its right margin to distance it
// from the rest of the frames in the line
nscoord x =
#ifdef IBMBIDI
(NS_STYLE_DIRECTION_RTL == GetStyleVisibility()->mDirection)
// According to the CSS2 spec, section 12.6.1, outside marker box
// is distanced from the associated principal box's border edge.
// |rs.availableWidth| reflects exactly a border edge: it includes
// border, padding, and content area, without margins.
? rs.ComputedWidth() + rs.mComputedBorderPadding.LeftRight() +
reflowState.mComputedMargin.left :
#endif
- reflowState.mComputedMargin.right - aMetrics.width;
// Place the bullet now. We want to place the bullet relative to the
// border-box of the associated box (using the right/left margin of
// the bullet frame as separation). However, if a line box would be
// displaced by floats, we want to displace it by the same amount.
// That is, we act as though the edge of the floats is the
// content-edge of the block, and place the bullet at a position
// offset from there by the block's padding, the block's border, and
// the bullet frame's margin.
// FIXME (bug 25888): need to check the entire region that the first
// line overlaps, not just the top pixel.
nscoord x;
aState.GetAvailableSpace(aLineTop, PR_FALSE);
if (rs.mStyleVisibility->mDirection == NS_STYLE_DIRECTION_LTR) {
// Note: mAvailSpaceRect.x is relative to the content box and never
// less than zero. Converting to frame coordinates and subtracting
// the padding and border cancel each other out, and the PR_MAX()
// with 0 (or with the left border+padding) is even implied in the
// right place.
x = aState.mAvailSpaceRect.x
- reflowState.mComputedMargin.right - aMetrics.width;
} else {
// The XMost() of the available space and the computed width both
// give us offsets from the left content edge. Then we add the left
// border/padding to get into frame coordinates, and the right
// border/padding and the bullet's margin to offset the position.
x = PR_MIN(rs.ComputedWidth(), aState.mAvailSpaceRect.XMost())
+ rs.mComputedBorderPadding.LeftRight()
+ reflowState.mComputedMargin.left;
}
// FIXME: come up with rules for when mAvailSpaceRect is valid so we
// don't need to do this.
aState.GetAvailableSpace();
// Approximate the bullets position; vertical alignment will provide
// the final vertical location.

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

@ -580,7 +580,8 @@ protected:
static PRBool FrameStartsCounterScope(nsIFrame* aFrame);
void ReflowBullet(nsBlockReflowState& aState,
nsHTMLReflowMetrics& aMetrics);
nsHTMLReflowMetrics& aMetrics,
nscoord aLineTop);
//----------------------------------------

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

@ -225,6 +225,7 @@ public:
nscoord mY;
// The available space within the current band.
// (relative to the *content*-rect of the block)
nsRect mAvailSpaceRect;
// The combined area of all floats placed so far

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

@ -0,0 +1,36 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">
<html lang="en-US">
<head>
<title>Test case for list items flowing around floats</title>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<meta http-equiv="Content-Style-Type" content="text/css">
<style type="text/css">
ul, ol, li { margin-top: 0; margin-bottom: 0; }
li { height: 2em; background: aqua; color: black; }
</style>
</head>
<body>
<div style="background: aqua; color: black; margin-left: 40px">
<div style="margin-left: -40px">
<div style="margin-left: 60px"><ol start="1"><li>one</li></ol></div>
<div style="margin-left: 60px"><ol start="2"><li>two</li></ol></div>
<ol start="3"><li>three</li></ol>
<ol start="4"><li>four</li></ol>
</div>
</div>
<div style="background: aqua; color: black; margin-left: 40px">
<div style="margin-left: -40px">
<div style="margin-left: 60px"><ul><li>one</li></ul></div>
<div style="margin-left: 60px"><ul><li>two</li></ul></div>
<ul><li>three</li></ul>
<ul><li>four</li></ul>
</div>
</div>
</body>
</html>

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

@ -0,0 +1,38 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">
<html lang="en-US">
<head>
<title>Test case for list items flowing around floats</title>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<meta http-equiv="Content-Style-Type" content="text/css">
<style type="text/css">
div { float: left; height: 3em; width: 100px; }
ul, ol, li { margin-top: 0; margin-bottom: 0; }
li { height: 2em; background: aqua; color: black; }
</style>
</head>
<body>
<div></div>
<ol>
<li>one</li>
<li>two</li>
<li>three</li>
<li>four</li>
</ol>
<div></div>
<ul>
<li>one</li>
<li>two</li>
<li>three</li>
<li>four</li>
</ul>
</body>
</html>

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

@ -0,0 +1,20 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">
<html lang="en-US">
<head>
<title>Test that bullet is on the first line!</title>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<meta http-equiv="Content-Style-Type" content="text/css">
<style type="text/css">
</style>
</head>
<body>
<ul>
<li>first line</li>
<li style="list-style-type:none">second line</li>
</ul>
</body>
</html>

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

@ -0,0 +1,19 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">
<html lang="en-US">
<head>
<title>Test that bullet is on the first line!</title>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<meta http-equiv="Content-Style-Type" content="text/css">
<style type="text/css">
</style>
</head>
<body>
<ul>
<li>first line<br>second line</li>
</ul>
</body>
</html>

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

@ -0,0 +1,29 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">
<html lang="en-US">
<head>
<title>Test case for list items flowing around floats</title>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<meta http-equiv="Content-Style-Type" content="text/css">
<meta http-equiv="Content-Script-Type" content="text/javascript">
<style type="text/css">
ul, ol, li { margin: 0; padding: 0; }
</style>
</head>
<body>
<div style="margin-left: 100px"><ul><li><div style="margin-left: 0px">item</li></ul></div>
<div style="margin-left: 100px"><ul><li><div style="margin-left: 0px">item</li></ul></div>
<div style="margin-left: 94px"><ul><li><div style="margin-left: 6px">item</li></ul></div>
<div style="margin-left: 150px"><ul><li><div style="margin-left: 6px">item</li></ul></div>
<div style="margin-left: 40px"><ul><li><div style="margin-left: 154px">item</li></ul></div>
<div style="margin-left: 40px"><ul><li><div style="margin-left: 152px">item</li></ul></div>
<div style="margin-left: 94px"><ol start="1"><li><div style="margin-left: 6px">item</li></ol></div>
<div style="margin-left: 150px"><ol start="2"><li><div style="margin-left: 6px">item</li></ol></div>
<div style="margin-left: 40px"><ol start="3"><li><div style="margin-left: 154px">item</li></ol></div>
<div style="margin-left: 40px"><ol start="4"><li><div style="margin-left: 152px">item</li></ol></div>
</body>
</html>

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

@ -0,0 +1,37 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">
<html lang="en-US">
<head>
<title>Test case for list items flowing around floats</title>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<meta http-equiv="Content-Style-Type" content="text/css">
<meta http-equiv="Content-Script-Type" content="text/javascript">
<style type="text/css">
#float { float: left; width: 100px; height: 20em; }
ul, ol, li { margin: 0; padding: 0; }
</style>
</head>
<body>
<div id="float"></div>
<ul><li>item</li></ul>
<ul style="margin-left: 1px; border-left: 2px solid transparent; padding-left: 4px; padding-right: 8px; border-right: 16px solid transparent; margin-right: 32px;"><li>item</li></ul>
<ul>
<li style="margin-left: 1px; border-left: 2px solid transparent; padding-left: 4px; padding-right: 8px; border-right: 16px solid transparent; margin-right: 32px;">item</li>
<li style="margin-left: 150px; border-left: 2px solid transparent; padding-left: 4px; padding-right: 8px; border-right: 16px solid transparent; margin-right: 32px;">item</li>
<li style="margin-left: 40px; border-left: 150px solid transparent; padding-left: 4px; padding-right: 8px; border-right: 16px solid transparent; margin-right: 32px;">item</li>
<li style="margin-left: 40px; border-left: 2px solid transparent; padding-left: 150px; padding-right: 8px; border-right: 16px solid transparent; margin-right: 32px;">item</li>
</ul>
<ol>
<li style="margin-left: 1px; border-left: 2px solid transparent; padding-left: 4px; padding-right: 8px; border-right: 16px solid transparent; margin-right: 32px;">item</li>
<li style="margin-left: 150px; border-left: 2px solid transparent; padding-left: 4px; padding-right: 8px; border-right: 16px solid transparent; margin-right: 32px;">item</li>
<li style="margin-left: 40px; border-left: 150px solid transparent; padding-left: 4px; padding-right: 8px; border-right: 16px solid transparent; margin-right: 32px;">item</li>
<li style="margin-left: 40px; border-left: 2px solid transparent; padding-left: 150px; padding-right: 8px; border-right: 16px solid transparent; margin-right: 32px;">item</li>
</ol>
</body>
</html>

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

@ -0,0 +1,22 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">
<html lang="en-US">
<head>
<title>Test for bullet lining up with element pushed past float</title>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<meta http-equiv="Content-Style-Type" content="text/css">
<style type="text/css">
html, body { margin: 0; }
</style>
</head>
<body>
<div style="width: 200px; display:list-item; margin-left: 50px; margin-top: 50px">
<select size="2">
<option>AAAAAAAAAAAAAAAAAAAAAAAAAAAAAA</option>
<option>BBBBBBBBBBBBBBBBBBBBBBBBBBBBBB</option>
</select>
</div>
</body>
</html>

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

@ -0,0 +1,23 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">
<html lang="en-US">
<head>
<title>Test for bullet lining up with element pushed past float</title>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<meta http-equiv="Content-Style-Type" content="text/css">
<style type="text/css">
html, body { margin: 0; }
</style>
</head>
<body>
<div style="float: left; width: 150px; height: 50px"></div>
<div style="width: 200px; display:list-item; margin-left: 50px">
<select size="2">
<option>AAAAAAAAAAAAAAAAAAAAAAAAAAAAAA</option>
<option>BBBBBBBBBBBBBBBBBBBBBBBBBBBBBB</option>
</select>
</div>
</body>
</html>

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

@ -0,0 +1,30 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">
<html lang="en-US">
<head>
<title>Test case for list items flowing around floats</title>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<meta http-equiv="Content-Style-Type" content="text/css">
<meta http-equiv="Content-Script-Type" content="text/javascript">
<style type="text/css">
body { direction: rtl; }
ul, ol, li { margin: 0; padding: 0; }
</style>
</head>
<body>
<div style="margin-right: 100px"><ul><li><div style="margin-right: 0px">item</li></ul></div>
<div style="margin-right: 100px"><ul><li><div style="margin-right: 0px">item</li></ul></div>
<div style="margin-right: 94px"><ul><li><div style="margin-right: 6px">item</li></ul></div>
<div style="margin-right: 150px"><ul><li><div style="margin-right: 6px">item</li></ul></div>
<div style="margin-right: 40px"><ul><li><div style="margin-right: 154px">item</li></ul></div>
<div style="margin-right: 40px"><ul><li><div style="margin-right: 152px">item</li></ul></div>
<div style="margin-right: 94px"><ol start="1"><li><div style="margin-right: 6px">item</li></ol></div>
<div style="margin-right: 150px"><ol start="2"><li><div style="margin-right: 6px">item</li></ol></div>
<div style="margin-right: 40px"><ol start="3"><li><div style="margin-right: 154px">item</li></ol></div>
<div style="margin-right: 40px"><ol start="4"><li><div style="margin-right: 152px">item</li></ol></div>
</body>
</html>

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

@ -0,0 +1,38 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">
<html lang="en-US">
<head>
<title>Test case for list items flowing around floats</title>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<meta http-equiv="Content-Style-Type" content="text/css">
<meta http-equiv="Content-Script-Type" content="text/javascript">
<style type="text/css">
body { direction: rtl; }
#float { float: right; width: 100px; height: 20em; }
ul, ol, li { margin: 0; padding: 0; }
</style>
</head>
<body>
<div id="float"></div>
<ul><li>item</li></ul>
<ul style="margin-right: 1px; border-right: 2px solid transparent; padding-right: 4px; padding-left: 8px; border-left: 16px solid transparent; margin-left: 32px;"><li>item</li></ul>
<ul>
<li style="margin-right: 1px; border-right: 2px solid transparent; padding-right: 4px; padding-left: 8px; border-left: 16px solid transparent; margin-left: 32px;">item</li>
<li style="margin-right: 150px; border-right: 2px solid transparent; padding-right: 4px; padding-left: 8px; border-left: 16px solid transparent; margin-left: 32px;">item</li>
<li style="margin-right: 40px; border-right: 150px solid transparent; padding-right: 4px; padding-left: 8px; border-left: 16px solid transparent; margin-left: 32px;">item</li>
<li style="margin-right: 40px; border-right: 2px solid transparent; padding-right: 150px; padding-left: 8px; border-left: 16px solid transparent; margin-left: 32px;">item</li>
</ul>
<ol>
<li style="margin-right: 1px; border-right: 2px solid transparent; padding-right: 4px; padding-left: 8px; border-left: 16px solid transparent; margin-left: 32px;">item</li>
<li style="margin-right: 150px; border-right: 2px solid transparent; padding-right: 4px; padding-left: 8px; border-left: 16px solid transparent; margin-left: 32px;">item</li>
<li style="margin-right: 40px; border-right: 150px solid transparent; padding-right: 4px; padding-left: 8px; border-left: 16px solid transparent; margin-left: 32px;">item</li>
<li style="margin-right: 40px; border-right: 2px solid transparent; padding-right: 150px; padding-left: 8px; border-left: 16px solid transparent; margin-left: 32px;">item</li>
</ol>
</body>
</html>

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

@ -691,5 +691,10 @@ random == 403134-1.html 403134-1-ref.html # bug 405377
== 411792-1.html 411792-1-ref.html
== 413292-1.html 413292-1-ref.html
== 413361-1.html 413361-1-ref.html
== 413840-background-unchanged.html 413840-background-unchanged-ref.html
== 413840-ltr-offsets.html 413840-ltr-offsets-ref.html
== 413840-rtl-offsets.html 413840-rtl-offsets-ref.html
== 413840-pushed-line-bullet.html 413840-pushed-line-bullet-ref.html
== 413840-bullet-first-line.html 413840-bullet-first-line-ref.html
== 414123.xhtml 414123-ref.xhtml
== 416106-1.xhtml 416106-1-ref.xhtml

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

@ -341,7 +341,6 @@ ol {
li {
display: list-item;
-moz-float-edge: margin-box;
}
/* nested lists have no top/bottom margins */