summaryrefslogtreecommitdiffstats
path: root/ui/gfx/render_text_harfbuzz.cc
diff options
context:
space:
mode:
authormukai <mukai@chromium.org>2015-02-10 13:10:57 -0800
committerCommit bot <commit-bot@chromium.org>2015-02-10 21:11:45 +0000
commit8a9231d90a62da8563ea983336d5c73d0b210dd1 (patch)
treeb928afdaa2cfbd542084f264374266e7a4fbae32 /ui/gfx/render_text_harfbuzz.cc
parent0a7a3314bd50725e8327f22afd5517e6a1325c89 (diff)
downloadchromium_src-8a9231d90a62da8563ea983336d5c73d0b210dd1.zip
chromium_src-8a9231d90a62da8563ea983336d5c73d0b210dd1.tar.gz
chromium_src-8a9231d90a62da8563ea983336d5c73d0b210dd1.tar.bz2
Add float 'width' for LineSegment for fractional width.
My patch uses segment's x_range.length() for preceding widths, which is floored due to type coercion of float -> size_t, which causes the bug crbug.com/456692. This CL adds 'width' for this purpose, and stops unnecessary flooring/coercions during computing line segments. BUG=456692 R=msw@chromium.org, ckocagil@chromium.org TEST=None Review URL: https://codereview.chromium.org/890543004 Cr-Commit-Position: refs/heads/master@{#315640}
Diffstat (limited to 'ui/gfx/render_text_harfbuzz.cc')
-rw-r--r--ui/gfx/render_text_harfbuzz.cc36
1 files changed, 20 insertions, 16 deletions
diff --git a/ui/gfx/render_text_harfbuzz.cc b/ui/gfx/render_text_harfbuzz.cc
index 387d3ea..e864ff7 100644
--- a/ui/gfx/render_text_harfbuzz.cc
+++ b/ui/gfx/render_text_harfbuzz.cc
@@ -222,8 +222,7 @@ class HarfBuzzLineBreaker {
const base::string16& text,
const BreakList<size_t>* words,
const ScopedVector<internal::TextRunHarfBuzz>& runs)
- : max_width_((max_width == 0) ? std::numeric_limits<size_t>::max()
- : max_width),
+ : max_width_((max_width == 0) ? SK_ScalarMax : SkIntToScalar(max_width)),
min_baseline_(min_baseline),
min_height_(min_height),
multiline_(multiline),
@@ -242,12 +241,14 @@ class HarfBuzzLineBreaker {
void AddRun(int run_index) {
const internal::TextRunHarfBuzz* run = runs_[run_index];
base::char16 first_char = text_[run->range.start()];
- if (multiline_ && first_char == '\n')
+ if (multiline_ && first_char == '\n') {
AdvanceLine();
- else if (multiline_ && (line_x_ + run->width) > max_width_)
+ } else if (multiline_ && (line_x_ + SkFloatToScalar(run->width)) >
+ max_width_) {
BreakRun(run_index);
- else
+ } else {
AddSegment(run_index, run->range, run->width);
+ }
}
// Finishes line breaking and outputs the results. Can be called at most once.
@@ -304,7 +305,7 @@ class HarfBuzzLineBreaker {
size_t* next_char) {
DCHECK(words_);
DCHECK(run.range.Contains(Range(start_char, start_char + 1)));
- SkScalar available_width = SkIntToScalar(max_width_ - line_x_);
+ SkScalar available_width = max_width_ - line_x_;
BreakList<size_t>::const_iterator word = words_->GetBreak(start_char);
BreakList<size_t>::const_iterator next_word = word + 1;
// Width from |std::max(word->first, start_char)| to the current character.
@@ -357,10 +358,10 @@ class HarfBuzzLineBreaker {
void UpdateRTLSegmentRanges() {
if (rtl_segments_.empty())
return;
- int x = SegmentFromHandle(rtl_segments_[0])->x_range.start();
+ float x = SegmentFromHandle(rtl_segments_[0])->x_range.start();
for (size_t i = rtl_segments_.size(); i > 0; --i) {
internal::LineSegment* segment = SegmentFromHandle(rtl_segments_[i - 1]);
- const size_t segment_width = segment->x_range.length();
+ const float segment_width = segment->width;
segment->x_range = Range(x, x + segment_width);
x += segment_width;
}
@@ -396,7 +397,10 @@ class HarfBuzzLineBreaker {
internal::LineSegment segment;
segment.run = run_index;
segment.char_range = char_range;
- segment.x_range = Range(text_x_, text_x_ + width);
+ segment.x_range = Range(
+ SkScalarCeilToInt(text_x_),
+ SkScalarCeilToInt(text_x_ + SkFloatToScalar(width)));
+ segment.width = width;
internal::Line* line = &lines_.back();
line->segments.push_back(segment);
@@ -421,11 +425,11 @@ class HarfBuzzLineBreaker {
if (char_range.end() == run.range.end())
UpdateRTLSegmentRanges();
}
- text_x_ += width;
- line_x_ += width;
+ text_x_ += SkFloatToScalar(width);
+ line_x_ += SkFloatToScalar(width);
}
- const size_t max_width_;
+ const SkScalar max_width_;
const int min_baseline_;
const float min_height_;
const bool multiline_;
@@ -437,8 +441,8 @@ class HarfBuzzLineBreaker {
std::vector<internal::Line> lines_;
// Text space and line space x coordinates of the next segment to be added.
- int text_x_;
- int line_x_;
+ SkScalar text_x_;
+ SkScalar line_x_;
float max_descent_;
float max_ascent_;
@@ -988,14 +992,14 @@ void RenderTextHarfBuzz::DrawVisualText(Canvas* canvas) {
positions[colored_glyphs.start() - glyphs_range.start()].x());
int end_x = SkScalarRoundToInt(
(colored_glyphs.end() == glyphs_range.end())
- ? (segment.x_range.length() + preceding_segment_widths +
+ ? (SkFloatToScalar(segment.width) + preceding_segment_widths +
SkIntToScalar(origin.x()))
: positions[colored_glyphs.end() - glyphs_range.start()].x());
renderer.DrawDecorations(start_x, origin.y(), end_x - start_x,
run.underline, run.strike,
run.diagonal_strike);
}
- preceding_segment_widths += SkIntToScalar(segment.x_range.length());
+ preceding_segment_widths += SkFloatToScalar(segment.width);
}
}