Glop text shadows, clearLayerRegions, and rectangleList

Change-Id: I83b36d1ee5d8f05f41acf244639019f9b8da79cd
This commit is contained in:
Chris Craik
2015-02-17 16:42:02 -08:00
parent 922d3a7f6f
commit 2bb8f5606d
4 changed files with 131 additions and 39 deletions

View File

@@ -31,6 +31,13 @@ struct FloatColor {
b = a * ((color ) & 0xff) / 255.0f;
}
bool isNotBlack() {
return a < 1.0f
|| r > 0.0f
|| g > 0.0f
|| b > 0.0f;
}
float r;
float g;
float b;

View File

@@ -271,10 +271,7 @@ GlopBuilder& GlopBuilder::setFillTexturePaint(Texture& texture, bool isAlphaMask
}
if (isAlphaMaskTexture) {
mDescription.modulate = mOutGlop->fill.color.a < 1.0f
|| mOutGlop->fill.color.r > 0.0f
|| mOutGlop->fill.color.g > 0.0f
|| mOutGlop->fill.color.b > 0.0f;
mDescription.modulate = mOutGlop->fill.color.isNotBlack();
} else {
mDescription.modulate = mOutGlop->fill.color.a < 1.0f;
}
@@ -295,27 +292,74 @@ GlopBuilder& GlopBuilder::setFillPaint(const SkPaint& paint, float alphaScale) {
return *this;
}
GlopBuilder& GlopBuilder::setFillPathTexturePaint(Texture& texture,
GlopBuilder& GlopBuilder::setFillPathTexturePaint(PathTexture& texture,
const SkPaint& paint, float alphaScale) {
TRIGGER_STAGE(kFillStage);
REQUIRE_STAGES(kMeshStage);
mOutGlop->fill.texture = &texture;
//specify invalid, since these are always static for path textures
//specify invalid, since these are always static for PathTextures
mOutGlop->fill.textureFilter = GL_INVALID_ENUM;
mOutGlop->fill.textureClamp = GL_INVALID_ENUM;
setFill(paint.getColor(), alphaScale, PaintUtils::getXfermode(paint.getXfermode()),
paint.getShader(), paint.getColorFilter());
mDescription.modulate = mOutGlop->fill.color.a < 1.0f
|| mOutGlop->fill.color.r > 0.0f
|| mOutGlop->fill.color.g > 0.0f
|| mOutGlop->fill.color.b > 0.0f;
mDescription.modulate = mOutGlop->fill.color.isNotBlack();
return *this;
}
GlopBuilder& GlopBuilder::setFillShadowTexturePaint(ShadowTexture& texture, int shadowColor,
const SkPaint& paint, float alphaScale) {
TRIGGER_STAGE(kFillStage);
REQUIRE_STAGES(kMeshStage);
mOutGlop->fill.texture = &texture;
//specify invalid, since these are always static for ShadowTextures
mOutGlop->fill.textureFilter = GL_INVALID_ENUM;
mOutGlop->fill.textureClamp = GL_INVALID_ENUM;
const int ALPHA_BITMASK = SK_ColorBLACK;
const int COLOR_BITMASK = ~ALPHA_BITMASK;
if ((shadowColor & ALPHA_BITMASK) == ALPHA_BITMASK) {
// shadow color is fully opaque: override its alpha with that of paint
shadowColor &= paint.getColor() | COLOR_BITMASK;
}
setFill(shadowColor, alphaScale, PaintUtils::getXfermode(paint.getXfermode()),
paint.getShader(), paint.getColorFilter());
mDescription.modulate = mOutGlop->fill.color.isNotBlack();
return *this;
}
GlopBuilder& GlopBuilder::setFillBlack() {
TRIGGER_STAGE(kFillStage);
REQUIRE_STAGES(kMeshStage);
mOutGlop->fill.texture = nullptr;
mOutGlop->fill.textureFilter = GL_INVALID_ENUM;
mOutGlop->fill.textureClamp = GL_INVALID_ENUM;
setFill(SK_ColorBLACK, 1.0f, SkXfermode::kSrcOver_Mode, nullptr, nullptr);
return *this;
}
GlopBuilder& GlopBuilder::setFillClear() {
TRIGGER_STAGE(kFillStage);
REQUIRE_STAGES(kMeshStage);
mOutGlop->fill.texture = nullptr;
mOutGlop->fill.textureFilter = GL_INVALID_ENUM;
mOutGlop->fill.textureClamp = GL_INVALID_ENUM;
setFill(SK_ColorBLACK, 1.0f, SkXfermode::kClear_Mode, nullptr, nullptr);
return *this;
}
////////////////////////////////////////////////////////////////////////////////
// Transform
////////////////////////////////////////////////////////////////////////////////

View File

@@ -46,8 +46,12 @@ public:
GlopBuilder& setFillPaint(const SkPaint& paint, float alphaScale);
GlopBuilder& setFillTexturePaint(Texture& texture, bool isAlphaMaskTexture,
const SkPaint* paint, float alphaScale);
GlopBuilder& setFillPathTexturePaint(Texture& texture,
GlopBuilder& setFillPathTexturePaint(PathTexture& texture,
const SkPaint& paint, float alphaScale);
GlopBuilder& setFillShadowTexturePaint(ShadowTexture& texture, int shadowColor,
const SkPaint& paint, float alphaScale);
GlopBuilder& setFillBlack();
GlopBuilder& setFillClear();
GlopBuilder& setTransformClip(const Matrix4& ortho, const Matrix4& transform, bool fudgingOffset);

View File

@@ -1198,8 +1198,8 @@ void OpenGLRenderer::issueIndexedQuadDraw(Vertex* mesh, GLsizei quadsCount) {
}
void OpenGLRenderer::clearLayerRegions() {
const size_t count = mLayers.size();
if (count == 0) return;
const size_t quadCount = mLayers.size();
if (quadCount == 0) return;
if (!mState.currentlyIgnored()) {
EVENT_LOGD("clearLayerRegions");
@@ -1212,10 +1212,10 @@ void OpenGLRenderer::clearLayerRegions() {
// is likely different so we need to disable clipping here
bool scissorChanged = mRenderState.scissor().setEnabled(false);
Vertex mesh[count * 4];
Vertex mesh[quadCount * 4];
Vertex* vertex = mesh;
for (uint32_t i = 0; i < count; i++) {
for (uint32_t i = 0; i < quadCount; i++) {
const Rect& bounds = mLayers[i];
Vertex::set(vertex++, bounds.left, bounds.top);
@@ -1228,18 +1228,30 @@ void OpenGLRenderer::clearLayerRegions() {
// the same thing again
mLayers.clear();
SkPaint clearPaint;
clearPaint.setXfermodeMode(SkXfermode::kClear_Mode);
if (USE_GLOPS) {
Glop glop;
GlopBuilder aBuilder(mRenderState, mCaches, &glop);
aBuilder.setMeshIndexedQuads(&mesh[0], quadCount)
.setFillClear()
.setTransformClip(currentSnapshot()->getOrthoMatrix(), Matrix4::identity(), false)
.setModelViewOffsetRect(0, 0, currentSnapshot()->getClipRect())
.setRoundRectClipState(currentSnapshot()->roundRectClipState)
.build();
renderGlop(glop);
} else {
SkPaint clearPaint;
clearPaint.setXfermodeMode(SkXfermode::kClear_Mode);
setupDraw(false);
setupDrawColor(0.0f, 0.0f, 0.0f, 1.0f);
setupDrawBlending(&clearPaint, true);
setupDrawProgram();
setupDrawPureColorUniforms();
setupDrawModelView(kModelViewMode_Translate, false,
0.0f, 0.0f, 0.0f, 0.0f, true);
setupDraw(false);
setupDrawColor(0.0f, 0.0f, 0.0f, 1.0f);
setupDrawBlending(&clearPaint, true);
setupDrawProgram();
setupDrawPureColorUniforms();
setupDrawModelView(kModelViewMode_Translate, false,
0.0f, 0.0f, 0.0f, 0.0f, true);
issueIndexedQuadDraw(&mesh[0], count);
issueIndexedQuadDraw(&mesh[0], quadCount);
}
if (scissorChanged) mRenderState.scissor().setEnabled(true);
} else {
@@ -1391,11 +1403,11 @@ static void handlePointNoTransform(std::vector<Vertex>& rectangleVertices, float
}
void OpenGLRenderer::drawRectangleList(const RectangleList& rectangleList) {
int count = rectangleList.getTransformedRectanglesCount();
std::vector<Vertex> rectangleVertices(count * 4);
int quadCount = rectangleList.getTransformedRectanglesCount();
std::vector<Vertex> rectangleVertices(quadCount * 4);
Rect scissorBox = rectangleList.calculateBounds();
scissorBox.snapToPixelBoundaries();
for (int i = 0; i < count; ++i) {
for (int i = 0; i < quadCount; ++i) {
const TransformedRectangle& tr(rectangleList.getTransformedRectangle(i));
const Matrix4& transform = tr.getTransform();
Rect bounds = tr.getBounds();
@@ -1420,6 +1432,19 @@ void OpenGLRenderer::drawRectangleList(const RectangleList& rectangleList) {
mRenderState.scissor().set(scissorBox.left, getViewportHeight() - scissorBox.bottom,
scissorBox.getWidth(), scissorBox.getHeight());
if (USE_GLOPS) {
Glop glop;
GlopBuilder aBuilder(mRenderState, mCaches, &glop);
aBuilder.setMeshIndexedQuads(&rectangleVertices[0], rectangleVertices.size() / 4)
.setFillBlack()
.setTransformClip(currentSnapshot()->getOrthoMatrix(), Matrix4::identity(), false)
.setModelViewOffsetRect(0, 0, scissorBox)
.setRoundRectClipState(currentSnapshot()->roundRectClipState)
.build();
renderGlop(glop);
return;
}
const SkPaint* paint = nullptr;
setupDraw();
setupDrawNoTexture();
@@ -2654,17 +2679,30 @@ void OpenGLRenderer::drawTextShadow(const SkPaint* paint, const char* text,
// NOTE: The drop shadow will not perform gamma correction
// if shader-based correction is enabled
mCaches.dropShadowCache.setFontRenderer(fontRenderer);
const ShadowTexture* shadow = mCaches.dropShadowCache.get(
ShadowTexture* texture = mCaches.dropShadowCache.get(
paint, text, bytesCount, count, textShadow.radius, positions);
// If the drop shadow exceeds the max texture size or couldn't be
// allocated, skip drawing
if (!shadow) return;
const AutoTexture autoCleanup(shadow);
if (!texture) return;
const AutoTexture autoCleanup(texture);
const float sx = x - shadow->left + textShadow.dx;
const float sy = y - shadow->top + textShadow.dy;
const float sx = x - texture->left + textShadow.dx;
const float sy = y - texture->top + textShadow.dy;
const int shadowAlpha = ((textShadow.color >> 24) & 0xFF) * writableSnapshot()->alpha;
if (USE_GLOPS) {
Glop glop;
GlopBuilder aBuilder(mRenderState, mCaches, &glop);
aBuilder.setMeshTexturedUnitQuad(nullptr, true)
.setFillShadowTexturePaint(*texture, textShadow.color, *paint, currentSnapshot()->alpha)
.setTransformClip(currentSnapshot()->getOrthoMatrix(), *currentTransform(), false)
.setModelViewMapUnitToRect(Rect(sx, sy, sx + texture->width, sy + texture->height))
.setRoundRectClipState(currentSnapshot()->roundRectClipState)
.build();
renderGlop(glop);
return;
}
const int shadowAlpha = ((textShadow.color >> 24) & 0xFF) * currentSnapshot()->alpha;
if (getShader(paint)) {
textShadow.color = SK_ColorWHITE;
}
@@ -2677,8 +2715,8 @@ void OpenGLRenderer::drawTextShadow(const SkPaint* paint, const char* text,
setupDrawBlending(paint, true);
setupDrawProgram();
setupDrawModelView(kModelViewMode_TranslateAndScale, false,
sx, sy, sx + shadow->width, sy + shadow->height);
setupDrawTexture(shadow->id);
sx, sy, sx + texture->width, sy + texture->height);
setupDrawTexture(texture->id);
setupDrawPureColorUniforms();
setupDrawColorFilterUniforms(getColorFilter(paint));
setupDrawShaderUniforms(getShader(paint));
@@ -3010,7 +3048,6 @@ void OpenGLRenderer::drawLayer(Layer* layer, float x, float y) {
DRAW_DOUBLE_STENCIL_IF(!layer->hasDrawnSinceUpdate,
composeLayerRect(layer, layer->regionRect));
} else if (layer->mesh) {
const float a = getLayerAlpha(layer);
setupDraw();
setupDrawWithTexture();
@@ -3093,8 +3130,8 @@ Texture* OpenGLRenderer::getTexture(const SkBitmap* bitmap) {
return texture;
}
void OpenGLRenderer::drawPathTexture(PathTexture* texture,
float x, float y, const SkPaint* paint) {
void OpenGLRenderer::drawPathTexture(PathTexture* texture, float x, float y,
const SkPaint* paint) {
if (quickRejectSetupScissor(x, y, x + texture->width, y + texture->height)) {
return;
}