summaryrefslogtreecommitdiffstats
path: root/libs
diff options
context:
space:
mode:
authorRaph Levien <raph@google.com>2014-05-30 23:38:56 -0700
committerRaph Levien <raph@google.com>2014-06-03 17:05:51 -0700
commit448b0fd720d7ba902b9be224a287d08abe3ebea8 (patch)
tree8474d0b8258f84b63a4f17cb96619ae7870cce4d /libs
parent066e8575af64fb452617ac6005de6ccf6509553b (diff)
downloadandroid_frameworks_minikin-448b0fd720d7ba902b9be224a287d08abe3ebea8.tar.gz
android_frameworks_minikin-448b0fd720d7ba902b9be224a287d08abe3ebea8.tar.bz2
android_frameworks_minikin-448b0fd720d7ba902b9be224a287d08abe3ebea8.zip
Support for scaleX and skewX
Adds pseudo-css properties for scaleX and skewX, as well as paint flags, and plumb them through to the MinikinPaint abstraction and to Harfbuzz, to support nontrivial scale and stretch of text. This is the Minikin part of the fix for bug 15186705 "Usability of the suggestion strip in recent OTA's is severely reduced" Change-Id: Ifa60355e086e4691ff92c5d50d84eb7cea0fea95
Diffstat (limited to 'libs')
-rw-r--r--libs/minikin/CssParse.cpp3
-rw-r--r--libs/minikin/Layout.cpp43
2 files changed, 33 insertions, 13 deletions
diff --git a/libs/minikin/CssParse.cpp b/libs/minikin/CssParse.cpp
index 5e96007..147f330 100644
--- a/libs/minikin/CssParse.cpp
+++ b/libs/minikin/CssParse.cpp
@@ -37,7 +37,9 @@ static CssTag parseTag(const string str, size_t off, size_t len) {
if (len == 0) return unknown;
char c = str[off];
if (c == 'f') {
+ if (strEqC(str, off, len, "font-scale-x")) return fontScaleX;
if (strEqC(str, off, len, "font-size")) return fontSize;
+ if (strEqC(str, off, len, "font-skew-x")) return fontSkewX;
if (strEqC(str, off, len, "font-weight")) return fontWeight;
if (strEqC(str, off, len, "font-style")) return fontStyle;
} else if (c == 'l') {
@@ -46,6 +48,7 @@ static CssTag parseTag(const string str, size_t off, size_t len) {
if (strEqC(str, off, len, "-minikin-bidi")) return minikinBidi;
if (strEqC(str, off, len, "-minikin-hinting")) return minikinHinting;
if (strEqC(str, off, len, "-minikin-variant")) return minikinVariant;
+ if (strEqC(str, off, len, "-paint-flags")) return paintFlags;
}
return unknown;
}
diff --git a/libs/minikin/Layout.cpp b/libs/minikin/Layout.cpp
index 4028d9e..c13aed8 100644
--- a/libs/minikin/Layout.cpp
+++ b/libs/minikin/Layout.cpp
@@ -63,7 +63,8 @@ public:
LayoutCacheKey(const FontCollection* collection, const MinikinPaint& paint, FontStyle style,
const uint16_t* chars, size_t start, size_t count, size_t nchars, bool dir)
: mStart(start), mCount(count), mId(collection->getId()), mStyle(style),
- mSize(paint.size), mIsRtl(dir) {
+ mSize(paint.size), mScaleX(paint.scaleX), mSkewX(paint.skewX),
+ mPaintFlags(paint.paintFlags), mIsRtl(dir) {
mText.setTo(chars, nchars);
}
bool operator==(const LayoutCacheKey &other) const;
@@ -78,6 +79,9 @@ private:
uint32_t mId; // for the font collection
FontStyle mStyle;
float mSize;
+ float mScaleX;
+ float mSkewX;
+ int mPaintFlags;
bool mIsRtl;
// Note: any fields added to MinikinPaint must also be reflected here.
// TODO: language matching (possibly integrate into style)
@@ -133,13 +137,16 @@ public:
ANDROID_SINGLETON_STATIC_INSTANCE(LayoutEngine);
bool LayoutCacheKey::operator==(const LayoutCacheKey& other) const {
- return mId == other.mId &&
- mStart == other.mStart &&
- mCount == other.mCount &&
- mStyle == other.mStyle &&
- mSize == other.mSize &&
- mIsRtl == other.mIsRtl &&
- mText == other.mText;
+ return mId == other.mId
+ && mStart == other.mStart
+ && mCount == other.mCount
+ && mStyle == other.mStyle
+ && mSize == other.mSize
+ && mScaleX == other.mScaleX
+ && mSkewX == other.mSkewX
+ && mPaintFlags == other.mPaintFlags
+ && mIsRtl == other.mIsRtl
+ && mText == other.mText;
}
hash_t LayoutCacheKey::hash() const {
@@ -148,6 +155,9 @@ hash_t LayoutCacheKey::hash() const {
hash = JenkinsHashMix(hash, mCount);
hash = JenkinsHashMix(hash, hash_type(mStyle));
hash = JenkinsHashMix(hash, hash_type(mSize));
+ hash = JenkinsHashMix(hash, hash_type(mScaleX));
+ hash = JenkinsHashMix(hash, hash_type(mSkewX));
+ hash = JenkinsHashMix(hash, hash_type(mPaintFlags));
hash = JenkinsHashMix(hash, hash_type(mIsRtl));
hash = JenkinsHashMixShorts(hash, mText.string(), mText.size());
return JenkinsHashWhiten(hash);
@@ -502,8 +512,13 @@ void Layout::doLayout(const uint16_t* buf, size_t start, size_t count, size_t bu
ctx.props.parse(css);
ctx.style = styleFromCss(ctx.props);
- double size = ctx.props.value(fontSize).getFloatValue();
- ctx.paint.size = size;
+ ctx.paint.size = ctx.props.value(fontSize).getFloatValue();
+ ctx.paint.scaleX = ctx.props.hasTag(fontScaleX)
+ ? ctx.props.value(fontScaleX).getFloatValue() : 1;
+ ctx.paint.skewX = ctx.props.hasTag(fontSkewX)
+ ? ctx.props.value(fontSkewX).getFloatValue() : 0;
+ ctx.paint.paintFlags = ctx.props.hasTag(paintFlags)
+ ?ctx.props.value(paintFlags).getIntValue() : 0;
int bidiFlags = ctx.props.hasTag(minikinBidi) ? ctx.props.value(minikinBidi).getIntValue() : 0;
bool isRtl = (bidiFlags & kDirection_Mask) != 0;
bool doSingleRun = true;
@@ -635,8 +650,9 @@ void Layout::doLayoutRun(const uint16_t* buf, size_t start, size_t count, size_t
" [" << run.start << ":" << run.end << "]" << std::endl;
#endif
double size = ctx->paint.size;
- hb_font_set_ppem(hbFont, size, size);
- hb_font_set_scale(hbFont, HBFloatToFixed(size), HBFloatToFixed(size));
+ double scaleX = ctx->paint.scaleX;
+ hb_font_set_ppem(hbFont, size * scaleX, size);
+ hb_font_set_scale(hbFont, HBFloatToFixed(size * scaleX), HBFloatToFixed(size));
// TODO: if there are multiple scripts within a font in an RTL run,
// we need to reorder those runs. This is unlikely with our current
@@ -665,7 +681,8 @@ void Layout::doLayoutRun(const uint16_t* buf, size_t start, size_t count, size_t
#endif
hb_codepoint_t glyph_ix = info[i].codepoint;
float xoff = HBFixedToFloat(positions[i].x_offset);
- float yoff = HBFixedToFloat(positions[i].y_offset);
+ float yoff = -HBFixedToFloat(positions[i].y_offset);
+ xoff += yoff * ctx->paint.skewX;
LayoutGlyph glyph = {font_ix, glyph_ix, x + xoff, y + yoff};
mGlyphs.push_back(glyph);
float xAdvance = HBFixedToFloat(positions[i].x_advance);