aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorbors-servo <lbergstrom+bors@mozilla.com>2016-03-11 23:19:43 +0530
committerbors-servo <lbergstrom+bors@mozilla.com>2016-03-11 23:19:43 +0530
commit059edc3287909ce705ba90804c778ee50f1e157e (patch)
tree3a7f86d64728ecec9dadc6cfb8a8f92e725e6f92
parent53aca4b80eef2890c43dd2d0e905b25588651191 (diff)
parent1e7d60e7b793f914696c6813502ea7d87a944ab3 (diff)
downloadservo-059edc3287909ce705ba90804c778ee50f1e157e.tar.gz
servo-059edc3287909ce705ba90804c778ee50f1e157e.zip
Auto merge of #9961 - mbrubeck:split-line-work-list, r=pcwalton
Fix work list order after split_line_at_last_known_good_position This fixes a bug in line splitting caused by the following actions when `LineBreaker::split_line_at_last_known_good_position` is called: 1. Push some number of previous fragments onto the front of the work list. 2. Push the current fragment back onto the front work list. This resulted in the work list being out of order. The correct order is action 2 followed by action 1. Fixes #9830. r? @pcwalton <!-- Reviewable:start --> --- This change is [<img src="https://reviewable.io/review_button.svg" height="35" align="absmiddle" alt="Review on Reviewable"/>](https://reviewable.io/reviews/servo/servo/9961) <!-- Reviewable:end -->
-rw-r--r--components/layout/inline.rs30
-rw-r--r--tests/wpt/mozilla/meta/MANIFEST.json24
-rw-r--r--tests/wpt/mozilla/tests/css/line_break_nowrap.html23
-rw-r--r--tests/wpt/mozilla/tests/css/line_break_nowrap_ref.html16
4 files changed, 77 insertions, 16 deletions
diff --git a/components/layout/inline.rs b/components/layout/inline.rs
index 1212f8a3cfc..90f2893554f 100644
--- a/components/layout/inline.rs
+++ b/components/layout/inline.rs
@@ -592,12 +592,7 @@ impl LineBreaker {
// known good split point.
if !fragment.white_space().allow_wrap() {
debug!("LineBreaker: fragment can't split; falling back to last known good split point");
- if !self.split_line_at_last_known_good_position() {
- // No line breaking opportunity exists at all for this line. Overflow.
- self.push_fragment_to_line(layout_context, fragment, line_flush_mode);
- } else {
- self.work_list.push_front(fragment);
- }
+ self.split_line_at_last_known_good_position(layout_context, fragment, line_flush_mode);
return;
}
@@ -616,14 +611,10 @@ impl LineBreaker {
debug!("LineBreaker: fragment was unsplittable; deferring to next line");
self.work_list.push_front(fragment);
self.flush_current_line();
- } else if self.split_line_at_last_known_good_position() {
- // We split the line at a known-good prior position. Restart with the current
- // fragment.
- self.work_list.push_front(fragment)
} else {
- // We failed to split and there is no known-good place on this line to split.
- // Overflow.
- self.push_fragment_to_line(layout_context, fragment, LineFlushMode::No)
+ self.split_line_at_last_known_good_position(layout_context,
+ fragment,
+ LineFlushMode::No);
}
return
}
@@ -724,13 +715,21 @@ impl LineBreaker {
self.new_fragments.push(fragment);
}
- fn split_line_at_last_known_good_position(&mut self) -> bool {
+ fn split_line_at_last_known_good_position(&mut self,
+ layout_context: &LayoutContext,
+ cur_fragment: Fragment,
+ line_flush_mode: LineFlushMode) {
let last_known_line_breaking_opportunity =
match self.last_known_line_breaking_opportunity {
- None => return false,
+ None => {
+ // No line breaking opportunity exists at all for this line. Overflow.
+ self.push_fragment_to_line(layout_context, cur_fragment, line_flush_mode);
+ return;
+ }
Some(last_known_line_breaking_opportunity) => last_known_line_breaking_opportunity,
};
+ self.work_list.push_front(cur_fragment);
for fragment_index in (last_known_line_breaking_opportunity.get()..
self.pending_line.range.end().get()).rev() {
debug_assert!(fragment_index == (self.new_fragments.len() as isize) - 1);
@@ -752,7 +751,6 @@ impl LineBreaker {
// need to add that feature to the API to handle this case correctly.
self.pending_line.range.extend_to(last_known_line_breaking_opportunity);
self.flush_current_line();
- true
}
/// Returns the indentation that needs to be applied before the fragment we're reflowing.
diff --git a/tests/wpt/mozilla/meta/MANIFEST.json b/tests/wpt/mozilla/meta/MANIFEST.json
index 42fae625fc0..7ea42099e65 100644
--- a/tests/wpt/mozilla/meta/MANIFEST.json
+++ b/tests/wpt/mozilla/meta/MANIFEST.json
@@ -2732,6 +2732,18 @@
"url": "/_mozilla/css/li_absolute_containing_block_a.html"
}
],
+ "css/line_break_nowrap.html": [
+ {
+ "path": "css/line_break_nowrap.html",
+ "references": [
+ [
+ "/_mozilla/css/line_break_nowrap_ref.html",
+ "=="
+ ]
+ ],
+ "url": "/_mozilla/css/line_break_nowrap.html"
+ }
+ ],
"css/line_breaking_whitespace_collapse_a.html": [
{
"path": "css/line_breaking_whitespace_collapse_a.html",
@@ -8920,6 +8932,18 @@
"url": "/_mozilla/css/li_absolute_containing_block_a.html"
}
],
+ "css/line_break_nowrap.html": [
+ {
+ "path": "css/line_break_nowrap.html",
+ "references": [
+ [
+ "/_mozilla/css/line_break_nowrap_ref.html",
+ "=="
+ ]
+ ],
+ "url": "/_mozilla/css/line_break_nowrap.html"
+ }
+ ],
"css/line_breaking_whitespace_collapse_a.html": [
{
"path": "css/line_breaking_whitespace_collapse_a.html",
diff --git a/tests/wpt/mozilla/tests/css/line_break_nowrap.html b/tests/wpt/mozilla/tests/css/line_break_nowrap.html
new file mode 100644
index 00000000000..3eb3fdeb652
--- /dev/null
+++ b/tests/wpt/mozilla/tests/css/line_break_nowrap.html
@@ -0,0 +1,23 @@
+<!doctype html>
+<html>
+ <head>
+ <meta charset="utf-8">
+ <title>nowrap line-breaking test</title>
+ <link rel="match" href="line_break_nowrap_ref.html">
+ <style>
+ body {
+ font-family: 'ahem';
+ width: 25em;
+ }
+ span {
+ white-space: nowrap;
+ }
+ </style>
+ </head>
+ <body>
+ <span>hello world</span>
+ <span>hello world</span>
+ <span>hello world</span>
+ <span>hello world</span>
+ </body>
+</html>
diff --git a/tests/wpt/mozilla/tests/css/line_break_nowrap_ref.html b/tests/wpt/mozilla/tests/css/line_break_nowrap_ref.html
new file mode 100644
index 00000000000..aac581da1df
--- /dev/null
+++ b/tests/wpt/mozilla/tests/css/line_break_nowrap_ref.html
@@ -0,0 +1,16 @@
+<!doctype html>
+<html>
+ <head>
+ <meta charset="utf-8">
+ <title>nowrap line-breaking reference</title>
+ <style>
+ body { font-family: 'ahem'; }
+ </style>
+ </head>
+ <body>
+ <div>
+ hello world hello world<br>
+ hello world hello world
+ </div>
+ </body>
+</html>