aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/gpu/text/GrTextContext.cpp
diff options
context:
space:
mode:
authorGravatar Herb Derby <herb@google.com>2018-07-16 11:19:04 -0400
committerGravatar Skia Commit-Bot <skia-commit-bot@chromium.org>2018-07-19 16:25:55 +0000
commitcddab25218c52327ee1c527d726e69aa89540917 (patch)
tree91a8bd583444bed7903bc51953c35e4b6f02c92b /src/gpu/text/GrTextContext.cpp
parent297c3c8e85bdb7ed79aaa6a596f52874d79e7a25 (diff)
Use SkGlyphRunListIterator in gpu
Instead of using the text blob through the stack start using the glyph run list. This CL is similar to a portion of https://skia-review.googlesource.com/c/skia/+/137224 which was reverted. Change-Id: I1f0619bd2d13523f9af1a68ab27fb26abd086add Reviewed-on: https://skia-review.googlesource.com/141543 Commit-Queue: Herb Derby <herb@google.com> Reviewed-by: Jim Van Verth <jvanverth@google.com>
Diffstat (limited to 'src/gpu/text/GrTextContext.cpp')
-rw-r--r--src/gpu/text/GrTextContext.cpp158
1 files changed, 43 insertions, 115 deletions
diff --git a/src/gpu/text/GrTextContext.cpp b/src/gpu/text/GrTextContext.cpp
index a2ef40f16d..e68be09bfb 100644
--- a/src/gpu/text/GrTextContext.cpp
+++ b/src/gpu/text/GrTextContext.cpp
@@ -84,56 +84,48 @@ SkScalerContextFlags GrTextContext::ComputeScalerContextFlags(
}
}
-// TODO if this function ever shows up in profiling, then we can compute this value when the
-// textblob is being built and cache it. However, for the time being textblobs mostly only have 1
-// run so this is not a big deal to compute here.
-bool GrTextContext::HasLCD(const SkTextBlob* blob) {
- SkTextBlobRunIterator it(blob);
- for (; !it.done(); it.next()) {
- if (it.isLCD()) {
- return true;
- }
- }
- return false;
-}
+void GrTextContext::drawGlyphRunList(
+ GrContext* context, GrTextUtils::Target* target, const GrClip& clip,
+ const SkMatrix& viewMatrix, const SkSurfaceProps& props, SkGlyphRunList* glyphRunList,
+ const SkIRect& clipBounds) {
+ SkPoint origin = glyphRunList->origin();
+
+ // Get the first paint to use as the key paint.
+ const SkPaint& skPaint = glyphRunList->paint();
-void GrTextContext::drawTextBlob(GrContext* context, GrTextUtils::Target* target,
- const GrClip& clip, const SkPaint& skPaint,
- const SkMatrix& viewMatrix, const SkSurfaceProps& props,
- const SkTextBlob* blob, SkScalar x, SkScalar y,
- const SkIRect& clipBounds) {
// If we have been abandoned, then don't draw
if (context->abandoned()) {
return;
}
- sk_sp<GrTextBlob> cacheBlob;
SkMaskFilterBase::BlurRec blurRec;
- GrTextBlob::Key key;
// It might be worth caching these things, but its not clear at this time
// TODO for animated mask filters, this will fill up our cache. We need a safeguard here
const SkMaskFilter* mf = skPaint.getMaskFilter();
- bool canCache = !(skPaint.getPathEffect() || (mf && !as_MFB(mf)->asABlur(&blurRec)));
+ bool canCache = glyphRunList->canCache() && !(skPaint.getPathEffect() ||
+ (mf && !as_MFB(mf)->asABlur(&blurRec)));
SkScalerContextFlags scalerContextFlags = ComputeScalerContextFlags(target->colorSpaceInfo());
auto glyphCache = context->contextPriv().getGlyphCache();
GrTextBlobCache* textBlobCache = context->contextPriv().getTextBlobCache();
+ sk_sp<GrTextBlob> cacheBlob;
+ GrTextBlob::Key key;
if (canCache) {
- bool hasLCD = HasLCD(blob);
+ bool hasLCD = glyphRunList->anyRunsLCD();
// We canonicalize all non-lcd draws to use kUnknown_SkPixelGeometry
SkPixelGeometry pixelGeometry = hasLCD ? props.pixelGeometry() :
- kUnknown_SkPixelGeometry;
+ kUnknown_SkPixelGeometry;
// TODO we want to figure out a way to be able to use the canonical color on LCD text,
// see the note on ComputeCanonicalColor above. We pick a dummy value for LCD text to
// ensure we always match the same key
GrColor canonicalColor = hasLCD ? SK_ColorTRANSPARENT :
- ComputeCanonicalColor(skPaint, hasLCD);
+ ComputeCanonicalColor(skPaint, hasLCD);
key.fPixelGeometry = pixelGeometry;
- key.fUniqueID = blob->uniqueID();
+ key.fUniqueID = glyphRunList->uniqueID();
key.fStyle = skPaint.getStyle();
key.fHasBlur = SkToBool(mf);
key.fCanonicalColor = canonicalColor;
@@ -143,139 +135,77 @@ void GrTextContext::drawTextBlob(GrContext* context, GrTextUtils::Target* target
GrTextUtils::Paint paint(&skPaint, &target->colorSpaceInfo());
if (cacheBlob) {
- if (cacheBlob->mustRegenerate(paint, blurRec, viewMatrix, x, y)) {
+ if (cacheBlob->mustRegenerate(paint, blurRec, viewMatrix, origin.x(), origin.y())) {
// We have to remake the blob because changes may invalidate our masks.
// TODO we could probably get away reuse most of the time if the pointer is unique,
// but we'd have to clear the subrun information
textBlobCache->remove(cacheBlob.get());
- cacheBlob = textBlobCache->makeCachedBlob(blob, key, blurRec, skPaint);
- this->regenerateTextBlob(cacheBlob.get(), glyphCache,
+ cacheBlob = textBlobCache->makeCachedBlob(glyphRunList, key, blurRec, skPaint);
+ this->regenerateGlyphRunList(cacheBlob.get(), glyphCache,
*context->contextPriv().caps()->shaderCaps(), paint,
- scalerContextFlags, viewMatrix, props, blob, x, y);
+ scalerContextFlags, viewMatrix, props, glyphRunList);
} else {
textBlobCache->makeMRU(cacheBlob.get());
if (CACHE_SANITY_CHECK) {
- int glyphCount = 0;
- int runCount = 0;
- GrTextBlobCache::BlobGlyphCount(&glyphCount, &runCount, blob);
+ int glyphCount = glyphRunList->totalGlyphCount();
+ int runCount = glyphRunList->runCount();
sk_sp<GrTextBlob> sanityBlob(textBlobCache->makeBlob(glyphCount, runCount));
sanityBlob->setupKey(key, blurRec, skPaint);
- this->regenerateTextBlob(
+ this->regenerateGlyphRunList(
sanityBlob.get(), glyphCache, *context->contextPriv().caps()->shaderCaps(),
- paint, scalerContextFlags, viewMatrix, props, blob, x, y);
+ paint, scalerContextFlags, viewMatrix, props, glyphRunList);
GrTextBlob::AssertEqual(*sanityBlob, *cacheBlob);
}
}
} else {
if (canCache) {
- cacheBlob = textBlobCache->makeCachedBlob(blob, key, blurRec, skPaint);
+ cacheBlob = textBlobCache->makeCachedBlob(glyphRunList, key, blurRec, skPaint);
} else {
- cacheBlob = textBlobCache->makeBlob(blob);
+ cacheBlob = textBlobCache->makeBlob(glyphRunList);
}
- this->regenerateTextBlob(cacheBlob.get(), glyphCache,
+ this->regenerateGlyphRunList(cacheBlob.get(), glyphCache,
*context->contextPriv().caps()->shaderCaps(), paint,
- scalerContextFlags, viewMatrix, props, blob, x, y);
+ scalerContextFlags, viewMatrix, props, glyphRunList);
}
cacheBlob->flush(target, props, fDistanceAdjustTable.get(), paint,
- clip, viewMatrix, clipBounds, x, y);
+ clip, viewMatrix, clipBounds, origin.x(), origin.y());
}
-void GrTextContext::regenerateTextBlob(GrTextBlob* cacheBlob,
+void GrTextContext::regenerateGlyphRunList(GrTextBlob* cacheBlob,
GrGlyphCache* glyphCache,
const GrShaderCaps& shaderCaps,
const GrTextUtils::Paint& paint,
SkScalerContextFlags scalerContextFlags,
const SkMatrix& viewMatrix,
- const SkSurfaceProps& props, const SkTextBlob* blob,
- SkScalar x, SkScalar y) const {
- cacheBlob->initReusableBlob(paint.luminanceColor(), viewMatrix, x, y);
+ const SkSurfaceProps& props,
+ SkGlyphRunList* glyphRunList) const {
+ SkPoint origin = glyphRunList->origin();
+ cacheBlob->initReusableBlob(paint.luminanceColor(), viewMatrix, origin.x(), origin.y());
// Regenerate textblob
- SkTextBlobRunIterator it(blob);
+ SkGlyphRunListIterator it(glyphRunList);
GrTextUtils::RunPaint runPaint(&paint);
for (int run = 0; !it.done(); it.next(), run++) {
int glyphCount = it.glyphCount();
size_t textLen = glyphCount * sizeof(uint16_t);
- const SkPoint& offset = it.offset();
cacheBlob->push_back_run(run);
if (!runPaint.modifyForRun([it](SkPaint* p) { it.applyFontToPaint(p); })) {
continue;
}
cacheBlob->setRunPaintFlags(run, runPaint.skPaint().getFlags());
+ SkASSERT(it.positioning() == SkTextBlob::kFull_Positioning);
if (CanDrawAsDistanceFields(runPaint, viewMatrix, props,
shaderCaps.supportsDistanceFieldText(), fOptions)) {
- switch (it.positioning()) {
- case SkTextBlob::kDefault_Positioning: {
- auto origin = SkPoint::Make(x + offset.x(), y + offset.y());
- SkGlyphRunBuilder builder;
- builder.drawText(runPaint.skPaint(),
- (const char*) it.glyphs(), textLen, origin);
-
- auto glyphRunList = builder.useGlyphRunList();
- if (!glyphRunList->empty()) {
- auto glyphRun = (*glyphRunList)[0];
- glyphRun.temporaryShuntToCallback(
- [&](size_t runSize, const char* glyphIDs, const SkScalar* pos) {
- this->drawDFPosText(
- cacheBlob, run, glyphCache, props, runPaint,
- scalerContextFlags, viewMatrix, glyphIDs, 2 * runSize,
- pos, 2, SkPoint::Make(0, 0));
- });
- }
- break;
- }
-
- case SkTextBlob::kHorizontal_Positioning: {
- SkPoint dfOffset = SkPoint::Make(x, y + offset.y());
- this->drawDFPosText(cacheBlob, run, glyphCache, props, runPaint,
- scalerContextFlags, viewMatrix, (const char*)it.glyphs(),
- textLen, it.pos(), 1, dfOffset);
- break;
- }
- case SkTextBlob::kFull_Positioning: {
- SkPoint dfOffset = SkPoint::Make(x, y);
- this->drawDFPosText(cacheBlob, run, glyphCache, props, runPaint,
- scalerContextFlags, viewMatrix, (const char*)it.glyphs(),
- textLen, it.pos(), 2, dfOffset);
- break;
- }
- }
+ this->drawDFPosText(cacheBlob, run, glyphCache, props, runPaint,
+ scalerContextFlags, viewMatrix, (const char*)it.glyphs(),
+ textLen, it.pos(), 2, origin);
} else {
- switch (it.positioning()) {
- case SkTextBlob::kDefault_Positioning: {
- auto origin = SkPoint::Make(x + offset.x(), y + offset.y());
- SkGlyphRunBuilder builder;
- builder.drawText(runPaint.skPaint(),
- (const char*) it.glyphs(), textLen, origin);
-
- auto glyphRunList = builder.useGlyphRunList();
- if (!glyphRunList->empty()) {
- auto glyphRun = (*glyphRunList)[0];
-
- glyphRun.temporaryShuntToCallback(
- [&](size_t runSize, const char* glyphIDs, const SkScalar* pos) {
- this->DrawBmpPosText(
- cacheBlob, run, glyphCache, props, runPaint,
- scalerContextFlags, viewMatrix, glyphIDs, 2 * runSize,
- pos, 2, SkPoint::Make(0, 0));
- });
- }
- break;
- }
- case SkTextBlob::kHorizontal_Positioning:
- DrawBmpPosText(cacheBlob, run, glyphCache, props, runPaint, scalerContextFlags,
- viewMatrix, (const char*)it.glyphs(), textLen, it.pos(), 1,
- SkPoint::Make(x, y + offset.y()));
- break;
- case SkTextBlob::kFull_Positioning:
- DrawBmpPosText(cacheBlob, run, glyphCache, props, runPaint, scalerContextFlags,
- viewMatrix, (const char*)it.glyphs(), textLen, it.pos(), 2,
- SkPoint::Make(x, y));
- break;
- }
+ DrawBmpPosText(cacheBlob, run, glyphCache, props, runPaint, scalerContextFlags,
+ viewMatrix, (const char*)it.glyphs(), textLen, it.pos(), 2,
+ origin);
}
}
}
@@ -335,7 +265,6 @@ void GrTextContext::drawPosText(GrContext* context, GrTextUtils::Target* target,
}
}
-
void GrTextContext::DrawBmpPosText(GrTextBlob* blob, int runIndex,
GrGlyphCache* glyphCache, const SkSurfaceProps& props,
const GrTextUtils::Paint& paint,
@@ -798,8 +727,7 @@ std::unique_ptr<GrDrawOp> GrTextContext::createOp_TestingOnly(GrContext* context
context->contextPriv().getTextBlobCache(), glyphCache,
*context->contextPriv().caps()->shaderCaps(), utilsPaint,
GrTextContext::kTextBlobOpScalerContextFlags, viewMatrix, surfaceProps,
- text,
- textLen, pos, 2, origin);
+ text, textLen, pos, 2, origin);
});
}