Commit c4427206 authored by msw@chromium.org's avatar msw@chromium.org

Support float widths in RenderTextHarfBuzz.

The gfx_unittests CanvasTestMac.* passes on Mac Views.
(can also run the tests with --enable-harfbuzz-rendertext)

BUG=391843
TEST=CanvasTestMac.* passes, no Mac text rendering changes.
R=asvitkine@chromium.org,ckocagil@chromium.org

Review URL: https://codereview.chromium.org/440213004

Cr-Commit-Position: refs/heads/master@{#288255}
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@288255 0039d316-1c4b-4281-b951-d872f2087c98
parent c9e3b203
...@@ -163,9 +163,8 @@ struct Line { ...@@ -163,9 +163,8 @@ struct Line {
// Segments that make up this line in visual order. // Segments that make up this line in visual order.
std::vector<LineSegment> segments; std::vector<LineSegment> segments;
// A line size is the sum of segment widths and the maximum of segment // The sum of segment widths and the maximum of segment heights.
// heights. SizeF size;
Size size;
// Sum of preceding lines' heights. // Sum of preceding lines' heights.
int preceding_heights; int preceding_heights;
......
...@@ -433,8 +433,8 @@ void GetClusterAtImpl(size_t pos, ...@@ -433,8 +433,8 @@ void GetClusterAtImpl(size_t pos,
namespace internal { namespace internal {
TextRunHarfBuzz::TextRunHarfBuzz() TextRunHarfBuzz::TextRunHarfBuzz()
: width(0), : width(0.0f),
preceding_run_widths(0), preceding_run_widths(0.0f),
is_rtl(false), is_rtl(false),
level(0), level(0),
script(USCRIPT_INVALID_CODE), script(USCRIPT_INVALID_CODE),
...@@ -497,8 +497,10 @@ Range TextRunHarfBuzz::GetGraphemeBounds( ...@@ -497,8 +497,10 @@ Range TextRunHarfBuzz::GetGraphemeBounds(
base::i18n::BreakIterator* grapheme_iterator, base::i18n::BreakIterator* grapheme_iterator,
size_t text_index) { size_t text_index) {
DCHECK_LT(text_index, range.end()); DCHECK_LT(text_index, range.end());
// TODO(msw): Support floating point grapheme bounds.
const int preceding_run_widths_int = SkScalarRoundToInt(preceding_run_widths);
if (glyph_count == 0) if (glyph_count == 0)
return Range(preceding_run_widths, preceding_run_widths + width); return Range(preceding_run_widths_int, preceding_run_widths_int + width);
Range chars; Range chars;
Range glyphs; Range glyphs;
...@@ -532,13 +534,13 @@ Range TextRunHarfBuzz::GetGraphemeBounds( ...@@ -532,13 +534,13 @@ Range TextRunHarfBuzz::GetGraphemeBounds(
cluster_width * before / static_cast<float>(total)); cluster_width * before / static_cast<float>(total));
const int grapheme_end_x = cluster_begin_x + static_cast<int>(0.5f + const int grapheme_end_x = cluster_begin_x + static_cast<int>(0.5f +
cluster_width * (before + 1) / static_cast<float>(total)); cluster_width * (before + 1) / static_cast<float>(total));
return Range(preceding_run_widths + grapheme_begin_x, return Range(preceding_run_widths_int + grapheme_begin_x,
preceding_run_widths + grapheme_end_x); preceding_run_widths_int + grapheme_end_x);
} }
} }
return Range(preceding_run_widths + cluster_begin_x, return Range(preceding_run_widths_int + cluster_begin_x,
preceding_run_widths + cluster_end_x); preceding_run_widths_int + cluster_end_x);
} }
} // namespace internal } // namespace internal
...@@ -550,6 +552,11 @@ RenderTextHarfBuzz::RenderTextHarfBuzz() ...@@ -550,6 +552,11 @@ RenderTextHarfBuzz::RenderTextHarfBuzz()
RenderTextHarfBuzz::~RenderTextHarfBuzz() {} RenderTextHarfBuzz::~RenderTextHarfBuzz() {}
Size RenderTextHarfBuzz::GetStringSize() { Size RenderTextHarfBuzz::GetStringSize() {
const SizeF size_f = GetStringSizeF();
return Size(std::ceil(size_f.width()), size_f.height());
}
SizeF RenderTextHarfBuzz::GetStringSizeF() {
EnsureLayout(); EnsureLayout();
return lines()[0].size; return lines()[0].size;
} }
...@@ -789,7 +796,7 @@ void RenderTextHarfBuzz::EnsureLayout() { ...@@ -789,7 +796,7 @@ void RenderTextHarfBuzz::EnsureLayout() {
ShapeRun(runs_[i]); ShapeRun(runs_[i]);
// Precalculate run width information. // Precalculate run width information.
size_t preceding_run_widths = 0; float preceding_run_widths = 0.0f;
for (size_t i = 0; i < runs_.size(); ++i) { for (size_t i = 0; i < runs_.size(); ++i) {
internal::TextRunHarfBuzz* run = runs_[visual_to_logical_[i]]; internal::TextRunHarfBuzz* run = runs_[visual_to_logical_[i]];
run->preceding_run_widths = preceding_run_widths; run->preceding_run_widths = preceding_run_widths;
...@@ -826,7 +833,7 @@ void RenderTextHarfBuzz::EnsureLayout() { ...@@ -826,7 +833,7 @@ void RenderTextHarfBuzz::EnsureLayout() {
lines[0].size.set_width(lines[0].size.width() + run.width); lines[0].size.set_width(lines[0].size.width() + run.width);
lines[0].size.set_height(std::max(lines[0].size.height(), lines[0].size.set_height(std::max(lines[0].size.height(),
SkScalarRoundToInt(metrics.fDescent - metrics.fAscent))); metrics.fDescent - metrics.fAscent));
lines[0].baseline = std::max(lines[0].baseline, lines[0].baseline = std::max(lines[0].baseline,
SkScalarRoundToInt(-metrics.fAscent)); SkScalarRoundToInt(-metrics.fAscent));
} }
...@@ -1071,7 +1078,7 @@ void RenderTextHarfBuzz::ShapeRun(internal::TextRunHarfBuzz* run) { ...@@ -1071,7 +1078,7 @@ void RenderTextHarfBuzz::ShapeRun(internal::TextRunHarfBuzz* run) {
} }
run->glyph_count = 0; run->glyph_count = 0;
run->width = 0; run->width = 0.0f;
} }
bool RenderTextHarfBuzz::ShapeRunWithFont(internal::TextRunHarfBuzz* run, bool RenderTextHarfBuzz::ShapeRunWithFont(internal::TextRunHarfBuzz* run,
...@@ -1109,17 +1116,14 @@ bool RenderTextHarfBuzz::ShapeRunWithFont(internal::TextRunHarfBuzz* run, ...@@ -1109,17 +1116,14 @@ bool RenderTextHarfBuzz::ShapeRunWithFont(internal::TextRunHarfBuzz* run,
run->glyphs.reset(new uint16[run->glyph_count]); run->glyphs.reset(new uint16[run->glyph_count]);
run->glyph_to_char.resize(run->glyph_count); run->glyph_to_char.resize(run->glyph_count);
run->positions.reset(new SkPoint[run->glyph_count]); run->positions.reset(new SkPoint[run->glyph_count]);
run->width = 0; run->width = 0.0f;
for (size_t i = 0; i < run->glyph_count; ++i) { for (size_t i = 0; i < run->glyph_count; ++i) {
run->glyphs[i] = infos[i].codepoint; run->glyphs[i] = infos[i].codepoint;
run->glyph_to_char[i] = infos[i].cluster; run->glyph_to_char[i] = infos[i].cluster;
const int x_offset = const int x_offset = SkFixedToScalar(hb_positions[i].x_offset);
SkScalarRoundToInt(SkFixedToScalar(hb_positions[i].x_offset)); const int y_offset = SkFixedToScalar(hb_positions[i].y_offset);
const int y_offset =
SkScalarRoundToInt(SkFixedToScalar(hb_positions[i].y_offset));
run->positions[i].set(run->width + x_offset, -y_offset); run->positions[i].set(run->width + x_offset, -y_offset);
run->width += run->width += SkFixedToScalar(hb_positions[i].x_advance);
SkScalarRoundToInt(SkFixedToScalar(hb_positions[i].x_advance));
} }
hb_buffer_destroy(buffer); hb_buffer_destroy(buffer);
......
...@@ -48,8 +48,8 @@ struct GFX_EXPORT TextRunHarfBuzz { ...@@ -48,8 +48,8 @@ struct GFX_EXPORT TextRunHarfBuzz {
// Returns whether the given shaped run contains any missing glyphs. // Returns whether the given shaped run contains any missing glyphs.
bool HasMissingGlyphs() const; bool HasMissingGlyphs() const;
int width; float width;
int preceding_run_widths; float preceding_run_widths;
Range range; Range range;
bool is_rtl; bool is_rtl;
UBiDiLevel level; UBiDiLevel level;
...@@ -80,6 +80,7 @@ class GFX_EXPORT RenderTextHarfBuzz : public RenderText { ...@@ -80,6 +80,7 @@ class GFX_EXPORT RenderTextHarfBuzz : public RenderText {
// Overridden from RenderText. // Overridden from RenderText.
virtual Size GetStringSize() OVERRIDE; virtual Size GetStringSize() OVERRIDE;
virtual SizeF GetStringSizeF() OVERRIDE;
virtual SelectionModel FindCursorPosition(const Point& point) OVERRIDE; virtual SelectionModel FindCursorPosition(const Point& point) OVERRIDE;
virtual std::vector<FontSpan> GetFontSpansForTesting() OVERRIDE; virtual std::vector<FontSpan> GetFontSpansForTesting() OVERRIDE;
virtual Range GetGlyphBounds(size_t index) OVERRIDE; virtual Range GetGlyphBounds(size_t index) OVERRIDE;
......
...@@ -17,6 +17,7 @@ ...@@ -17,6 +17,7 @@
#include "ui/gfx/canvas.h" #include "ui/gfx/canvas.h"
#include "ui/gfx/font_fallback_win.h" #include "ui/gfx/font_fallback_win.h"
#include "ui/gfx/font_render_params.h" #include "ui/gfx/font_render_params.h"
#include "ui/gfx/geometry/size_conversions.h"
#include "ui/gfx/platform_font_win.h" #include "ui/gfx/platform_font_win.h"
#include "ui/gfx/utf16_indexing.h" #include "ui/gfx/utf16_indexing.h"
...@@ -389,8 +390,9 @@ class LineBreaker { ...@@ -389,8 +390,9 @@ class LineBreaker {
line->baseline = line_ascent_; line->baseline = line_ascent_;
line->size.set_height(line_ascent_ + line_descent_); line->size.set_height(line_ascent_ + line_descent_);
line->preceding_heights = total_size_.height(); line->preceding_heights = total_size_.height();
total_size_.set_height(total_size_.height() + line->size.height()); const Size line_size(ToCeiledSize(line->size));
total_size_.set_width(std::max(total_size_.width(), line->size.width())); total_size_.set_height(total_size_.height() + line_size.height());
total_size_.set_width(std::max(total_size_.width(), line_size.width()));
} }
line_x_ = 0; line_x_ = 0;
line_ascent_ = 0; line_ascent_ = 0;
...@@ -762,7 +764,7 @@ void RenderTextWin::DrawVisualText(Canvas* canvas) { ...@@ -762,7 +764,7 @@ void RenderTextWin::DrawVisualText(Canvas* canvas) {
// Skip painting empty lines or lines outside the display rect area. // Skip painting empty lines or lines outside the display rect area.
if (!display_rect().Intersects(Rect(PointAtOffsetFromOrigin(line_offset), if (!display_rect().Intersects(Rect(PointAtOffsetFromOrigin(line_offset),
line.size))) ToCeiledSize(line.size))))
continue; continue;
const Vector2d text_offset = line_offset + Vector2d(0, line.baseline); const Vector2d text_offset = line_offset + Vector2d(0, line.baseline);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment