Add hack for custom re-rasterization buckets
bug:14083128 Moves all of the font transform management into OpenGLRenderer::findBestFontTransform(), and now simply passes down final rasterization transforms into the FontRenderer. Change-Id: Ie02752e6af863347b142367c7d628db5f9fc2998
This commit is contained in:
@@ -724,14 +724,18 @@ void Caches::setTempProperty(const char* name, const char* value) {
|
||||
propertyLightDiameter = fmin(fmax(atof(value), 0.0), 3000.0);
|
||||
ALOGD("lightDiameter = %.2f", propertyLightDiameter);
|
||||
return;
|
||||
} else if (!strcmp(name, "lightPosY")) {
|
||||
} else if (!strcmp(name, "lightPosY")) {
|
||||
propertyLightPosY = fmin(fmax(atof(value), 0.0), 3000.0);
|
||||
ALOGD("lightPos Y = %.2f", propertyLightPosY);
|
||||
return;
|
||||
} else if (!strcmp(name, "lightPosZ")) {
|
||||
} else if (!strcmp(name, "lightPosZ")) {
|
||||
propertyLightPosZ = fmin(fmax(atof(value), 0.0), 3000.0);
|
||||
ALOGD("lightPos Z = %.2f", propertyLightPosZ);
|
||||
return;
|
||||
} else if (!strcmp(name, "extraRasterBucket")) {
|
||||
float bucket = atof(value);
|
||||
propertyExtraRasterBuckets.push_back(bucket);
|
||||
return;
|
||||
}
|
||||
ALOGD(" failed");
|
||||
}
|
||||
|
||||
@@ -21,6 +21,8 @@
|
||||
#define LOG_TAG "OpenGLRenderer"
|
||||
#endif
|
||||
|
||||
#include <vector>
|
||||
|
||||
#include <GLES3/gl3.h>
|
||||
|
||||
#include <utils/KeyedVector.h>
|
||||
@@ -366,7 +368,7 @@ public:
|
||||
float propertyAmbientRatio;
|
||||
int propertyAmbientShadowStrength;
|
||||
int propertySpotShadowStrength;
|
||||
|
||||
std::vector<float> propertyExtraRasterBuckets;
|
||||
private:
|
||||
enum OverdrawColorSet {
|
||||
kColorSet_Default = 0,
|
||||
|
||||
@@ -1313,7 +1313,7 @@ public:
|
||||
const DeferredDisplayState& state) {
|
||||
const SkPaint* paint = getPaint(renderer);
|
||||
FontRenderer& fontRenderer = renderer.getCaches().fontRenderer->getFontRenderer(paint);
|
||||
fontRenderer.precache(paint, mText, mCount, mat4::identity());
|
||||
fontRenderer.precache(paint, mText, mCount, SkMatrix::I());
|
||||
|
||||
deferInfo.batchId = mPaint->getColor() == 0xff000000 ?
|
||||
DeferredDisplayList::kOpBatch_Text :
|
||||
@@ -1372,14 +1372,15 @@ public:
|
||||
const float* positions, const SkPaint* paint, float totalAdvance, const Rect& bounds)
|
||||
: DrawBoundedOp(bounds, paint), mText(text), mBytesCount(bytesCount), mCount(count),
|
||||
mX(x), mY(y), mPositions(positions), mTotalAdvance(totalAdvance) {
|
||||
memset(&mPrecacheTransform.data[0], 0xff, 16 * sizeof(float));
|
||||
mPrecacheTransform = SkMatrix::InvalidMatrix();
|
||||
}
|
||||
|
||||
virtual void onDefer(OpenGLRenderer& renderer, DeferInfo& deferInfo,
|
||||
const DeferredDisplayState& state) {
|
||||
const SkPaint* paint = getPaint(renderer);
|
||||
FontRenderer& fontRenderer = renderer.getCaches().fontRenderer->getFontRenderer(paint);
|
||||
const mat4& transform = renderer.findBestFontTransform(state.mMatrix);
|
||||
SkMatrix transform;
|
||||
renderer.findBestFontTransform(state.mMatrix, &transform);
|
||||
if (mPrecacheTransform != transform) {
|
||||
fontRenderer.precache(paint, mText, mCount, transform);
|
||||
mPrecacheTransform = transform;
|
||||
@@ -1436,7 +1437,7 @@ private:
|
||||
float mY;
|
||||
const float* mPositions;
|
||||
float mTotalAdvance;
|
||||
mat4 mPrecacheTransform;
|
||||
SkMatrix mPrecacheTransform;
|
||||
};
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
@@ -587,7 +587,7 @@ void FontRenderer::appendRotatedMeshQuad(float x1, float y1, float u1, float v1,
|
||||
}
|
||||
}
|
||||
|
||||
void FontRenderer::setFont(const SkPaint* paint, const mat4& matrix) {
|
||||
void FontRenderer::setFont(const SkPaint* paint, const SkMatrix& matrix) {
|
||||
mCurrentFont = Font::create(this, paint, matrix);
|
||||
}
|
||||
|
||||
@@ -678,7 +678,7 @@ void FontRenderer::finishRender() {
|
||||
}
|
||||
|
||||
void FontRenderer::precache(const SkPaint* paint, const char* text, int numGlyphs,
|
||||
const mat4& matrix) {
|
||||
const SkMatrix& matrix) {
|
||||
Font* font = Font::create(this, paint, matrix);
|
||||
font->precache(paint, text, numGlyphs);
|
||||
}
|
||||
|
||||
@@ -95,9 +95,9 @@ public:
|
||||
mGammaTable = gammaTable;
|
||||
}
|
||||
|
||||
void setFont(const SkPaint* paint, const mat4& matrix);
|
||||
void setFont(const SkPaint* paint, const SkMatrix& matrix);
|
||||
|
||||
void precache(const SkPaint* paint, const char* text, int numGlyphs, const mat4& matrix);
|
||||
void precache(const SkPaint* paint, const char* text, int numGlyphs, const SkMatrix& matrix);
|
||||
void endPrecaching();
|
||||
|
||||
// bounds is an out parameter
|
||||
|
||||
@@ -2699,7 +2699,7 @@ status_t OpenGLRenderer::drawPosText(const char* text, int bytesCount, int count
|
||||
}
|
||||
|
||||
FontRenderer& fontRenderer = mCaches.fontRenderer->getFontRenderer(paint);
|
||||
fontRenderer.setFont(paint, mat4::identity());
|
||||
fontRenderer.setFont(paint, SkMatrix::I());
|
||||
|
||||
int alpha;
|
||||
SkXfermode::Mode mode;
|
||||
@@ -2736,20 +2736,41 @@ status_t OpenGLRenderer::drawPosText(const char* text, int bytesCount, int count
|
||||
return DrawGlInfo::kStatusDrew;
|
||||
}
|
||||
|
||||
mat4 OpenGLRenderer::findBestFontTransform(const mat4& transform) const {
|
||||
mat4 fontTransform;
|
||||
bool OpenGLRenderer::findBestFontTransform(const mat4& transform, SkMatrix* outMatrix) const {
|
||||
if (CC_LIKELY(transform.isPureTranslate())) {
|
||||
fontTransform = mat4::identity();
|
||||
} else {
|
||||
if (CC_UNLIKELY(transform.isPerspective())) {
|
||||
fontTransform = mat4::identity();
|
||||
} else {
|
||||
float sx, sy;
|
||||
currentTransform()->decomposeScale(sx, sy);
|
||||
fontTransform.loadScale(sx, sy, 1.0f);
|
||||
}
|
||||
outMatrix->setIdentity();
|
||||
return false;
|
||||
} else if (CC_UNLIKELY(transform.isPerspective())) {
|
||||
outMatrix->setIdentity();
|
||||
return true;
|
||||
}
|
||||
return fontTransform;
|
||||
|
||||
/**
|
||||
* Input is a non-perspective, scaling transform. Generate a scale-only transform, based upon
|
||||
* bucketed scale values. Special case for 'extra raster buckets' - disable filtration in the
|
||||
* case of an exact match, and isSimple() transform
|
||||
*/
|
||||
float sx, sy;
|
||||
transform.decomposeScale(sx, sy);
|
||||
|
||||
float bestSx = roundf(fmaxf(1.0f, sx));
|
||||
float bestSy = roundf(fmaxf(1.0f, sy));
|
||||
bool filter = true;
|
||||
|
||||
for (unsigned int i = 0; i < mCaches.propertyExtraRasterBuckets.size(); i++) {
|
||||
float bucket = mCaches.propertyExtraRasterBuckets[i];
|
||||
if (sx == bucket && sy == bucket) {
|
||||
bestSx = bestSy = bucket;
|
||||
filter = !transform.isSimple(); // disable filter, if simple
|
||||
break;
|
||||
}
|
||||
|
||||
if (fabs(bucket - sx) < fabs(bestSx - sx)) bestSx = sx;
|
||||
if (fabs(bucket - sy) < fabs(bestSy - sy)) bestSy = sy;
|
||||
}
|
||||
|
||||
outMatrix->setScale(bestSx, bestSy);
|
||||
return filter;
|
||||
}
|
||||
|
||||
status_t OpenGLRenderer::drawText(const char* text, int bytesCount, int count, float x, float y,
|
||||
@@ -2783,7 +2804,7 @@ status_t OpenGLRenderer::drawText(const char* text, int bytesCount, int count, f
|
||||
FontRenderer& fontRenderer = mCaches.fontRenderer->getFontRenderer(paint);
|
||||
|
||||
if (CC_UNLIKELY(hasTextShadow(paint))) {
|
||||
fontRenderer.setFont(paint, mat4::identity());
|
||||
fontRenderer.setFont(paint, SkMatrix::I());
|
||||
drawTextShadow(paint, text, bytesCount, count, positions, fontRenderer,
|
||||
alpha, oldX, oldY);
|
||||
}
|
||||
@@ -2801,11 +2822,11 @@ status_t OpenGLRenderer::drawText(const char* text, int bytesCount, int count, f
|
||||
// Applying the full matrix in the shader is the easiest way to handle
|
||||
// rotation and perspective and allows us to always generated quads in the
|
||||
// font renderer which greatly simplifies the code, clipping in particular.
|
||||
mat4 fontTransform = findBestFontTransform(transform);
|
||||
SkMatrix fontTransform;
|
||||
bool linearFilter = findBestFontTransform(transform, &fontTransform)
|
||||
|| fabs(y - (int) y) > 0.0f
|
||||
|| fabs(x - (int) x) > 0.0f;
|
||||
fontRenderer.setFont(paint, fontTransform);
|
||||
|
||||
// Pick the appropriate texture filtering
|
||||
bool linearFilter = !pureTranslate || fabs(y - (int) y) > 0.0f || fabs(x - (int) x) > 0.0f;
|
||||
fontRenderer.setTextureFiltering(linearFilter);
|
||||
|
||||
// TODO: Implement better clipping for scaled/rotated text
|
||||
@@ -2849,7 +2870,7 @@ status_t OpenGLRenderer::drawTextOnPath(const char* text, int bytesCount, int co
|
||||
mCaches.enableScissor();
|
||||
|
||||
FontRenderer& fontRenderer = mCaches.fontRenderer->getFontRenderer(paint);
|
||||
fontRenderer.setFont(paint, mat4::identity());
|
||||
fontRenderer.setFont(paint, SkMatrix::I());
|
||||
fontRenderer.setTextureFiltering(true);
|
||||
|
||||
int alpha;
|
||||
|
||||
@@ -316,10 +316,12 @@ public:
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the best transform to use to rasterize text given a full
|
||||
* transform matrix.
|
||||
* Build the best transform to use to rasterize text given a full
|
||||
* transform matrix, and whether filteration is needed.
|
||||
*
|
||||
* Returns whether filtration is needed
|
||||
*/
|
||||
mat4 findBestFontTransform(const mat4& transform) const;
|
||||
bool findBestFontTransform(const mat4& transform, SkMatrix* outMatrix) const;
|
||||
|
||||
#if DEBUG_MERGE_BEHAVIOR
|
||||
void drawScreenSpaceColorRect(float left, float top, float right, float bottom, int color) {
|
||||
|
||||
@@ -45,7 +45,8 @@ Font::Font(FontRenderer* state, const Font::FontDescription& desc) :
|
||||
mDeviceProperties = SkDeviceProperties::Make(SkDeviceProperties::Geometry::MakeDefault(), 1.0f);
|
||||
}
|
||||
|
||||
Font::FontDescription::FontDescription(const SkPaint* paint, const mat4& matrix) {
|
||||
Font::FontDescription::FontDescription(const SkPaint* paint, const SkMatrix& rasterMatrix)
|
||||
: mLookupTransform(rasterMatrix) {
|
||||
mFontId = SkTypeface::UniqueID(paint->getTypeface());
|
||||
mFontSize = paint->getTextSize();
|
||||
mFlags = 0;
|
||||
@@ -58,9 +59,6 @@ Font::FontDescription::FontDescription(const SkPaint* paint, const mat4& matrix)
|
||||
mStrokeWidth = paint->getStrokeWidth();
|
||||
mAntiAliasing = paint->isAntiAlias();
|
||||
mHinting = paint->getHinting();
|
||||
mLookupTransform.reset();
|
||||
mLookupTransform[SkMatrix::kMScaleX] = roundf(fmaxf(1.0f, matrix[mat4::kScaleX]));
|
||||
mLookupTransform[SkMatrix::kMScaleY] = roundf(fmaxf(1.0f, matrix[mat4::kScaleY]));
|
||||
if (!mLookupTransform.invert(&mInverseLookupTransform)) {
|
||||
ALOGW("Could not query the inverse lookup transform for this font");
|
||||
}
|
||||
@@ -486,7 +484,7 @@ CachedGlyphInfo* Font::cacheGlyph(const SkPaint* paint, glyph_t glyph, bool prec
|
||||
return newGlyph;
|
||||
}
|
||||
|
||||
Font* Font::create(FontRenderer* state, const SkPaint* paint, const mat4& matrix) {
|
||||
Font* Font::create(FontRenderer* state, const SkPaint* paint, const SkMatrix& matrix) {
|
||||
FontDescription description(paint, matrix);
|
||||
Font* font = state->mActiveFonts.get(description);
|
||||
|
||||
|
||||
@@ -17,6 +17,8 @@
|
||||
#ifndef ANDROID_HWUI_FONT_H
|
||||
#define ANDROID_HWUI_FONT_H
|
||||
|
||||
#include <vector>
|
||||
|
||||
#include <utils/KeyedVector.h>
|
||||
|
||||
#include <SkScalar.h>
|
||||
@@ -50,7 +52,7 @@ public:
|
||||
};
|
||||
|
||||
struct FontDescription {
|
||||
FontDescription(const SkPaint* paint, const mat4& matrix);
|
||||
FontDescription(const SkPaint* paint, const SkMatrix& matrix);
|
||||
|
||||
static int compare(const FontDescription& lhs, const FontDescription& rhs);
|
||||
|
||||
@@ -92,7 +94,7 @@ public:
|
||||
/**
|
||||
* Creates a new font associated with the specified font state.
|
||||
*/
|
||||
static Font* create(FontRenderer* state, const SkPaint* paint, const mat4& matrix);
|
||||
static Font* create(FontRenderer* state, const SkPaint* paint, const SkMatrix& matrix);
|
||||
|
||||
private:
|
||||
friend class FontRenderer;
|
||||
|
||||
Reference in New Issue
Block a user