aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/gpu
diff options
context:
space:
mode:
Diffstat (limited to 'src/gpu')
-rw-r--r--src/gpu/GrContext.cpp33
-rw-r--r--src/gpu/GrContextPriv.h14
-rw-r--r--src/gpu/GrDrawOpAtlas.cpp3
-rw-r--r--src/gpu/GrOpFlushState.cpp9
-rw-r--r--src/gpu/GrOpFlushState.h6
-rw-r--r--src/gpu/GrProxyProvider.h3
-rw-r--r--src/gpu/ops/GrAtlasTextOp.cpp35
-rw-r--r--src/gpu/ops/GrAtlasTextOp.h24
-rw-r--r--src/gpu/ops/GrMeshDrawOp.h5
-rw-r--r--src/gpu/text/GrAtlasGlyphCache.cpp (renamed from src/gpu/text/GrGlyphCache.cpp)191
-rw-r--r--src/gpu/text/GrAtlasGlyphCache.h270
-rw-r--r--src/gpu/text/GrAtlasManager.cpp222
-rw-r--r--src/gpu/text/GrAtlasManager.h155
-rw-r--r--src/gpu/text/GrAtlasTextBlob.cpp21
-rw-r--r--src/gpu/text/GrAtlasTextBlob.h24
-rw-r--r--src/gpu/text/GrAtlasTextBlobVertexRegenerator.cpp29
-rw-r--r--src/gpu/text/GrAtlasTextContext.cpp121
-rw-r--r--src/gpu/text/GrAtlasTextContext.h27
-rw-r--r--src/gpu/text/GrGlyphCache.h148
-rw-r--r--src/gpu/text/GrTextUtils.h2
20 files changed, 582 insertions, 760 deletions
diff --git a/src/gpu/GrContext.cpp b/src/gpu/GrContext.cpp
index 6fbc4fe04f..38e170b7a0 100644
--- a/src/gpu/GrContext.cpp
+++ b/src/gpu/GrContext.cpp
@@ -77,7 +77,6 @@ public:
GrDDLContext(GrContextThreadSafeProxy* proxy) : INHERITED(proxy) {}
protected:
- // DDL TODO: grab a GrRestrictedAtlasManager from the proxy
private:
typedef GrContext INHERITED;
@@ -219,8 +218,7 @@ GrContext::GrContext(GrBackend backend)
fResourceCache = nullptr;
fResourceProvider = nullptr;
fProxyProvider = nullptr;
- fGlyphCache = nullptr;
- fFullAtlasManager = nullptr;
+ fAtlasGlyphCache = nullptr;
}
GrContext::GrContext(GrContextThreadSafeProxy* proxy)
@@ -230,8 +228,7 @@ GrContext::GrContext(GrContextThreadSafeProxy* proxy)
fResourceCache = nullptr;
fResourceProvider = nullptr;
fProxyProvider = nullptr;
- fGlyphCache = nullptr;
- fFullAtlasManager = nullptr;
+ fAtlasGlyphCache = nullptr;
}
bool GrContext::init(const GrContextOptions& options) {
@@ -296,17 +293,9 @@ bool GrContext::init(const GrContextOptions& options) {
} else {
allowMultitexturing = GrDrawOpAtlas::AllowMultitexturing::kYes;
}
-
- fGlyphCache = new GrGlyphCache;
-
- // DDL TODO: in DDL-mode grab a GrRestrictedAtlasManager from the thread-proxy and
- // do not add an onFlushCB
- fFullAtlasManager = new GrAtlasManager(fProxyProvider, fGlyphCache,
- options.fGlyphCacheTextureMaximumBytes,
- allowMultitexturing);
- this->contextPriv().addOnFlushCallbackObject(fFullAtlasManager);
-
- fGlyphCache->setGlyphSizeLimit(fFullAtlasManager->getGlyphSizeLimit());
+ fAtlasGlyphCache = new GrAtlasGlyphCache(fProxyProvider, options.fGlyphCacheTextureMaximumBytes,
+ allowMultitexturing);
+ this->contextPriv().addOnFlushCallbackObject(fAtlasGlyphCache);
fTextBlobCache.reset(new GrTextBlobCache(TextBlobCacheOverBudgetCB,
this, this->uniqueID(), SkToBool(fGpu)));
@@ -338,8 +327,7 @@ GrContext::~GrContext() {
delete fResourceProvider;
delete fResourceCache;
delete fProxyProvider;
- delete fGlyphCache;
- delete fFullAtlasManager;
+ delete fAtlasGlyphCache;
}
sk_sp<GrContextThreadSafeProxy> GrContext::threadSafeProxy() {
@@ -398,8 +386,7 @@ void GrContext::abandonContext() {
fGpu->disconnect(GrGpu::DisconnectType::kAbandon);
- fGlyphCache->freeAll();
- fFullAtlasManager->freeAll();
+ fAtlasGlyphCache->freeAll();
fTextBlobCache->freeAll();
}
@@ -418,8 +405,7 @@ void GrContext::releaseResourcesAndAbandonContext() {
fGpu->disconnect(GrGpu::DisconnectType::kCleanup);
- fGlyphCache->freeAll();
- fFullAtlasManager->freeAll();
+ fAtlasGlyphCache->freeAll();
fTextBlobCache->freeAll();
}
@@ -433,8 +419,7 @@ void GrContext::freeGpuResources() {
this->flush();
- fGlyphCache->freeAll();
- fFullAtlasManager->freeAll();
+ fAtlasGlyphCache->freeAll();
fDrawingManager->freeGpuResources();
diff --git a/src/gpu/GrContextPriv.h b/src/gpu/GrContextPriv.h
index c2e525d9b9..a2a45b5007 100644
--- a/src/gpu/GrContextPriv.h
+++ b/src/gpu/GrContextPriv.h
@@ -10,7 +10,6 @@
#include "GrContext.h"
#include "GrSurfaceContext.h"
-#include "text/GrAtlasManager.h"
class GrBackendRenderTarget;
class GrOnFlushCallbackObject;
@@ -188,19 +187,8 @@ public:
GrGpu* getGpu() { return fContext->fGpu.get(); }
const GrGpu* getGpu() const { return fContext->fGpu.get(); }
- GrGlyphCache* getGlyphCache() { return fContext->fGlyphCache; }
+ GrAtlasGlyphCache* getAtlasGlyphCache() { return fContext->fAtlasGlyphCache; }
GrTextBlobCache* getTextBlobCache() { return fContext->fTextBlobCache.get(); }
- GrRestrictedAtlasManager* getRestrictedAtlasManager() { return fContext->fFullAtlasManager; }
-
- // This accessor should only ever be called by the GrOpFlushState.
- GrAtlasManager* getFullAtlasManager() {
- if (fContext->fResourceProvider) {
- // Disallow access to the full atlasManager when recording DDLs
- return fContext->fFullAtlasManager;
- }
-
- return nullptr;
- }
void moveOpListsToDDL(SkDeferredDisplayList*);
void copyOpListsFromDDL(const SkDeferredDisplayList*, GrRenderTargetProxy* newDest);
diff --git a/src/gpu/GrDrawOpAtlas.cpp b/src/gpu/GrDrawOpAtlas.cpp
index 56dfcef56d..3fd3110dcc 100644
--- a/src/gpu/GrDrawOpAtlas.cpp
+++ b/src/gpu/GrDrawOpAtlas.cpp
@@ -14,7 +14,6 @@
#include "GrRectanizer.h"
#include "GrProxyProvider.h"
#include "GrResourceProvider.h"
-#include "GrSurfaceProxyPriv.h"
#include "GrTexture.h"
#include "GrTracing.h"
@@ -337,8 +336,8 @@ bool GrDrawOpAtlas::addToAtlas(GrResourceProvider* resourceProvider,
// With c+14 we could move sk_sp into lambda to only ref once.
sk_sp<Plot> plotsp(SkRef(newPlot.get()));
+ SkASSERT(fProxies[pageIdx]->priv().isInstantiated());
GrTextureProxy* proxy = fProxies[pageIdx].get();
- SkASSERT(proxy->priv().isInstantiated());
GrDeferredUploadToken lastUploadToken = target->addInlineUpload(
[plotsp, proxy](GrDeferredTextureUploadWritePixelsFn& writePixels) {
diff --git a/src/gpu/GrOpFlushState.cpp b/src/gpu/GrOpFlushState.cpp
index 53986c5f6a..06a05c6bb3 100644
--- a/src/gpu/GrOpFlushState.cpp
+++ b/src/gpu/GrOpFlushState.cpp
@@ -7,7 +7,6 @@
#include "GrOpFlushState.h"
-#include "GrContextPriv.h"
#include "GrDrawOpAtlas.h"
#include "GrGpu.h"
#include "GrResourceProvider.h"
@@ -192,11 +191,3 @@ void GrOpFlushState::putBackVertices(int vertices, size_t vertexStride) {
GrAppliedClip GrOpFlushState::detachAppliedClip() {
return fOpArgs->fAppliedClip ? std::move(*fOpArgs->fAppliedClip) : GrAppliedClip();
}
-
-GrGlyphCache* GrOpFlushState::glyphCache() const {
- return fGpu->getContext()->contextPriv().getGlyphCache();
-}
-
-GrAtlasManager* GrOpFlushState::fullAtlasManager() const {
- return fGpu->getContext()->contextPriv().getFullAtlasManager();
-}
diff --git a/src/gpu/GrOpFlushState.h b/src/gpu/GrOpFlushState.h
index ad33a98e2d..1f77c25cb7 100644
--- a/src/gpu/GrOpFlushState.h
+++ b/src/gpu/GrOpFlushState.h
@@ -90,12 +90,6 @@ public:
const GrCaps& caps() const final;
GrResourceProvider* resourceProvider() const final { return fResourceProvider; }
- GrGlyphCache* glyphCache() const final;
-
- // At this point we know we're flushing so full access to the GrAtlasManager is required (and
- // permissible).
- GrAtlasManager* fullAtlasManager() const final;
-
private:
/** GrMeshDrawOp::Target override. */
SkArenaAlloc* pipelineArena() override { return &fArena; }
diff --git a/src/gpu/GrProxyProvider.h b/src/gpu/GrProxyProvider.h
index 254686a613..dfd06dfe80 100644
--- a/src/gpu/GrProxyProvider.h
+++ b/src/gpu/GrProxyProvider.h
@@ -8,13 +8,13 @@
#ifndef GrProxyProvider_DEFINED
#define GrProxyProvider_DEFINED
-#include "GrCaps.h"
#include "GrResourceKey.h"
#include "GrTextureProxy.h"
#include "GrTypes.h"
#include "SkRefCnt.h"
#include "SkTDynamicHash.h"
+class GrCaps;
class GrResourceProvider;
class GrSingleOwner;
class GrBackendRenderTarget;
@@ -207,7 +207,6 @@ public:
void processInvalidProxyUniqueKey(const GrUniqueKey&, GrTextureProxy*, bool invalidateSurface);
const GrCaps* caps() const { return fCaps.get(); }
- sk_sp<const GrCaps> refCaps() const { return fCaps; }
void abandon() {
fResourceCache = nullptr;
diff --git a/src/gpu/ops/GrAtlasTextOp.cpp b/src/gpu/ops/GrAtlasTextOp.cpp
index 8f0c555295..952b3ba5ad 100644
--- a/src/gpu/ops/GrAtlasTextOp.cpp
+++ b/src/gpu/ops/GrAtlasTextOp.cpp
@@ -16,8 +16,7 @@
#include "SkPoint3.h"
#include "effects/GrBitmapTextGeoProc.h"
#include "effects/GrDistanceFieldGeoProc.h"
-#include "text/GrAtlasManager.h"
-#include "text/GrGlyphCache.h"
+#include "text/GrAtlasGlyphCache.h"
///////////////////////////////////////////////////////////////////////////////////////////////////
@@ -54,12 +53,9 @@ void GrAtlasTextOp::init() {
void GrAtlasTextOp::visitProxies(const VisitProxyFunc& func) const {
fProcessors.visitProxies(func);
- // We need to visit the atlasManager's proxies because, although the atlasManager explicitly
- // manages their lifetimes, if they fail to allocate the draws that reference them need to
- // be dropped.
unsigned int numProxies;
- const sk_sp<GrTextureProxy>* proxies = fRestrictedAtlasManager->getProxies(
- this->maskFormat(), &numProxies);
+ const sk_sp<GrTextureProxy>* proxies = fFontCache->getProxies(this->maskFormat(),
+ &numProxies);
for (unsigned int i = 0; i < numProxies; ++i) {
if (proxies[i]) {
func(proxies[i].get());
@@ -236,15 +232,10 @@ void GrAtlasTextOp::onPrepareDraws(Target* target) {
return;
}
- GrAtlasManager* fullAtlasManager = target->fullAtlasManager();
- SkASSERT(fRestrictedAtlasManager == fullAtlasManager);
- GrGlyphCache* glyphCache = target->glyphCache();
-
GrMaskFormat maskFormat = this->maskFormat();
unsigned int atlasPageCount;
- const sk_sp<GrTextureProxy>* proxies = fullAtlasManager->getProxies(maskFormat,
- &atlasPageCount);
+ const sk_sp<GrTextureProxy>* proxies = fFontCache->getProxies(maskFormat, &atlasPageCount);
if (!proxies[0]) {
SkDebugf("Could not allocate backing texture for atlas\n");
return;
@@ -255,7 +246,7 @@ void GrAtlasTextOp::onPrepareDraws(Target* target) {
target->makePipeline(fSRGBFlags, std::move(fProcessors), target->detachAppliedClip());
SkDEBUGCODE(bool dfPerspective = false);
if (this->usesDistanceFields()) {
- flushInfo.fGeometryProcessor = this->setupDfProcessor(fullAtlasManager);
+ flushInfo.fGeometryProcessor = this->setupDfProcessor();
SkDEBUGCODE(dfPerspective = fGeoData[0].fViewMatrix.hasPerspective());
} else {
flushInfo.fGeometryProcessor = GrBitmapTextGeoProc::Make(
@@ -281,15 +272,14 @@ void GrAtlasTextOp::onPrepareDraws(Target* target) {
char* currVertex = reinterpret_cast<char*>(vertices);
- SkAutoGlyphCache autoGlyphCache;
+ SkAutoGlyphCache glyphCache;
// each of these is a SubRun
for (int i = 0; i < fGeoCount; i++) {
const Geometry& args = fGeoData[i];
Blob* blob = args.fBlob;
GrAtlasTextBlob::VertexRegenerator regenerator(
resourceProvider, blob, args.fRun, args.fSubRun, args.fViewMatrix, args.fX, args.fY,
- args.fColor, target->deferredUploadTarget(), glyphCache, fullAtlasManager,
- &autoGlyphCache);
+ args.fColor, target->deferredUploadTarget(), fFontCache, &glyphCache);
GrAtlasTextBlob::VertexRegenerator::Result result;
do {
result = regenerator.regenerate();
@@ -329,14 +319,11 @@ void GrAtlasTextOp::onPrepareDraws(Target* target) {
}
void GrAtlasTextOp::flush(GrMeshDrawOp::Target* target, FlushInfo* flushInfo) const {
- auto fullAtlasManager = target->fullAtlasManager();
- SkASSERT(fRestrictedAtlasManager == fullAtlasManager);
-
GrGeometryProcessor* gp = flushInfo->fGeometryProcessor.get();
GrMaskFormat maskFormat = this->maskFormat();
unsigned int numProxies;
- const sk_sp<GrTextureProxy>* proxies = fullAtlasManager->getProxies(maskFormat, &numProxies);
+ const sk_sp<GrTextureProxy>* proxies = fFontCache->getProxies(maskFormat, &numProxies);
if (gp->numTextureSamplers() != (int) numProxies) {
// During preparation the number of atlas pages has increased.
// Update the proxies used in the GP to match.
@@ -440,11 +427,9 @@ bool GrAtlasTextOp::onCombineIfPossible(GrOp* t, const GrCaps& caps) {
// TODO trying to figure out why lcd is so whack
// (see comments in GrAtlasTextContext::ComputeCanonicalColor)
-sk_sp<GrGeometryProcessor> GrAtlasTextOp::setupDfProcessor(
- GrRestrictedAtlasManager* restrictedAtlasManager) const {
+sk_sp<GrGeometryProcessor> GrAtlasTextOp::setupDfProcessor() const {
unsigned int numProxies;
- const sk_sp<GrTextureProxy>* p = restrictedAtlasManager->getProxies(this->maskFormat(),
- &numProxies);
+ const sk_sp<GrTextureProxy>* p = fFontCache->getProxies(this->maskFormat(), &numProxies);
bool isLCD = this->isLCD();
SkMatrix localMatrix = SkMatrix::I();
diff --git a/src/gpu/ops/GrAtlasTextOp.h b/src/gpu/ops/GrAtlasTextOp.h
index ae1c95b56e..dbdce387ec 100644
--- a/src/gpu/ops/GrAtlasTextOp.h
+++ b/src/gpu/ops/GrAtlasTextOp.h
@@ -11,7 +11,6 @@
#include "ops/GrMeshDrawOp.h"
#include "text/GrAtlasTextContext.h"
#include "text/GrDistanceFieldAdjustTable.h"
-#include "text/GrGlyphCache.h"
class SkAtlasTextTarget;
@@ -40,12 +39,11 @@ public:
GrColor fColor;
};
- static std::unique_ptr<GrAtlasTextOp> MakeBitmap(
- GrPaint&& paint, GrMaskFormat maskFormat,
- int glyphCount, GrRestrictedAtlasManager* restrictedAtlasManager) {
- std::unique_ptr<GrAtlasTextOp> op(new GrAtlasTextOp(restrictedAtlasManager,
- std::move(paint)));
+ static std::unique_ptr<GrAtlasTextOp> MakeBitmap(GrPaint&& paint, GrMaskFormat maskFormat,
+ int glyphCount, GrAtlasGlyphCache* fontCache) {
+ std::unique_ptr<GrAtlasTextOp> op(new GrAtlasTextOp(std::move(paint)));
+ op->fFontCache = fontCache;
switch (maskFormat) {
case kA8_GrMaskFormat:
op->fMaskType = kGrayscaleCoverageMask_MaskType;
@@ -60,17 +58,18 @@ public:
op->fNumGlyphs = glyphCount;
op->fGeoCount = 1;
op->fLuminanceColor = 0;
+ op->fFontCache = fontCache;
return op;
}
static std::unique_ptr<GrAtlasTextOp> MakeDistanceField(
- GrPaint&& paint, int glyphCount, GrRestrictedAtlasManager* restrictedAtlasManager,
+ GrPaint&& paint, int glyphCount, GrAtlasGlyphCache* fontCache,
const GrDistanceFieldAdjustTable* distanceAdjustTable,
bool useGammaCorrectDistanceTable, SkColor luminanceColor, bool isLCD, bool useBGR,
bool isAntiAliased) {
- std::unique_ptr<GrAtlasTextOp> op(new GrAtlasTextOp(restrictedAtlasManager,
- std::move(paint)));
+ std::unique_ptr<GrAtlasTextOp> op(new GrAtlasTextOp(std::move(paint)));
+ op->fFontCache = fontCache;
op->fMaskType = !isAntiAliased ? kAliasedDistanceField_MaskType
: isLCD ? (useBGR ? kLCDBGRDistanceField_MaskType
: kLCDDistanceField_MaskType)
@@ -121,9 +120,8 @@ private:
// The minimum number of Geometry we will try to allocate.
static constexpr auto kMinGeometryAllocated = 12;
- GrAtlasTextOp(GrRestrictedAtlasManager* restrictedAtlasManager, GrPaint&& paint)
+ GrAtlasTextOp(GrPaint&& paint)
: INHERITED(ClassID())
- , fRestrictedAtlasManager(restrictedAtlasManager)
, fGeoDataAllocSize(kMinGeometryAllocated)
, fSRGBFlags(GrPipeline::SRGBFlagsFromPaint(paint))
, fProcessors(std::move(paint)) {}
@@ -176,9 +174,8 @@ private:
bool onCombineIfPossible(GrOp* t, const GrCaps& caps) override;
- sk_sp<GrGeometryProcessor> setupDfProcessor(GrRestrictedAtlasManager*) const;
+ sk_sp<GrGeometryProcessor> setupDfProcessor() const;
- GrRestrictedAtlasManager* fRestrictedAtlasManager;
SkAutoSTMalloc<kMinGeometryAllocated, Geometry> fGeoData;
int fGeoDataAllocSize;
uint32_t fSRGBFlags;
@@ -188,6 +185,7 @@ private:
int fGeoCount;
int fNumGlyphs;
MaskType fMaskType;
+ GrAtlasGlyphCache* fFontCache;
// Distance field properties
sk_sp<const GrDistanceFieldAdjustTable> fDistanceAdjustTable;
SkColor fLuminanceColor;
diff --git a/src/gpu/ops/GrMeshDrawOp.h b/src/gpu/ops/GrMeshDrawOp.h
index 766fd23ce5..1b8831cfe8 100644
--- a/src/gpu/ops/GrMeshDrawOp.h
+++ b/src/gpu/ops/GrMeshDrawOp.h
@@ -15,9 +15,7 @@
#include "SkTLList.h"
-class GrAtlasManager;
class GrCaps;
-class GrGlyphCache;
class GrOpFlushState;
/**
@@ -154,9 +152,6 @@ public:
virtual GrResourceProvider* resourceProvider() const = 0;
- virtual GrGlyphCache* glyphCache() const = 0;
- virtual GrAtlasManager* fullAtlasManager() const = 0;
-
virtual const GrCaps& caps() const = 0;
virtual GrDeferredUploadTarget* deferredUploadTarget() = 0;
diff --git a/src/gpu/text/GrGlyphCache.cpp b/src/gpu/text/GrAtlasGlyphCache.cpp
index d4440897bc..f7b1e1269a 100644
--- a/src/gpu/text/GrGlyphCache.cpp
+++ b/src/gpu/text/GrAtlasGlyphCache.cpp
@@ -5,19 +5,81 @@
* found in the LICENSE file.
*/
-#include "GrAtlasManager.h"
+#include "GrAtlasGlyphCache.h"
+#include "GrContext.h"
#include "GrDistanceFieldGenFromVector.h"
-#include "GrGlyphCache.h"
+#include "GrGpu.h"
+#include "GrProxyProvider.h"
+#include "GrRectanizer.h"
#include "SkAutoMalloc.h"
#include "SkDistanceFieldGen.h"
+#include "SkMathPriv.h"
+#include "SkString.h"
+
+bool GrAtlasGlyphCache::initAtlas(GrMaskFormat format) {
+ int index = MaskFormatToAtlasIndex(format);
+ if (!fAtlases[index]) {
+ GrPixelConfig config = MaskFormatToPixelConfig(format, *fProxyProvider->caps());
+ int width = fAtlasConfigs[index].fWidth;
+ int height = fAtlasConfigs[index].fHeight;
+ int numPlotsX = fAtlasConfigs[index].numPlotsX();
+ int numPlotsY = fAtlasConfigs[index].numPlotsY();
+
+ fAtlases[index] = GrDrawOpAtlas::Make(fProxyProvider, config, width, height,
+ numPlotsX, numPlotsY, fAllowMultitexturing,
+ &GrAtlasGlyphCache::HandleEviction, (void*)this);
+ if (!fAtlases[index]) {
+ return false;
+ }
+ }
+ return true;
+}
-GrGlyphCache::GrGlyphCache()
- : fPreserveStrike(nullptr)
- , fGlyphSizeLimit(0) {
+GrAtlasGlyphCache::GrAtlasGlyphCache(GrProxyProvider* proxyProvider, float maxTextureBytes,
+ GrDrawOpAtlas::AllowMultitexturing allowMultitexturing)
+ : fProxyProvider(proxyProvider)
+ , fAllowMultitexturing(allowMultitexturing)
+ , fPreserveStrike(nullptr) {
+ // Calculate RGBA size. Must be between 512 x 256 and MaxTextureSize x MaxTextureSize / 2
+ int log2MaxTextureSize = SkPrevLog2(fProxyProvider->caps()->maxTextureSize());
+ int log2MaxDim = 9;
+ for (; log2MaxDim <= log2MaxTextureSize; ++log2MaxDim) {
+ int maxDim = 1 << log2MaxDim;
+ int minDim = 1 << (log2MaxDim - 1);
+
+ if (maxDim * minDim * 4 >= maxTextureBytes) break;
+ }
+
+ int log2MinDim = log2MaxDim - 1;
+ int maxDim = 1 << log2MaxDim;
+ int minDim = 1 << log2MinDim;
+ // Plots are either 256 or 512.
+ int maxPlot = SkTMin(512, SkTMax(256, 1 << (log2MaxDim - 2)));
+ int minPlot = SkTMin(512, SkTMax(256, 1 << (log2MaxDim - 3)));
+
+ // Setup default atlas configs. The A8 atlas uses maxDim for both width and height, as the A8
+ // format is already very compact.
+ fAtlasConfigs[kA8_GrMaskFormat].fWidth = maxDim;
+ fAtlasConfigs[kA8_GrMaskFormat].fHeight = maxDim;
+ fAtlasConfigs[kA8_GrMaskFormat].fPlotWidth = maxPlot;
+ fAtlasConfigs[kA8_GrMaskFormat].fPlotHeight = minPlot;
+
+ // A565 and ARGB use maxDim x minDim.
+ fAtlasConfigs[kA565_GrMaskFormat].fWidth = minDim;
+ fAtlasConfigs[kA565_GrMaskFormat].fHeight = maxDim;
+ fAtlasConfigs[kA565_GrMaskFormat].fPlotWidth = minPlot;
+ fAtlasConfigs[kA565_GrMaskFormat].fPlotHeight = minPlot;
+
+ fAtlasConfigs[kARGB_GrMaskFormat].fWidth = minDim;
+ fAtlasConfigs[kARGB_GrMaskFormat].fHeight = maxDim;
+ fAtlasConfigs[kARGB_GrMaskFormat].fPlotWidth = minPlot;
+ fAtlasConfigs[kARGB_GrMaskFormat].fPlotHeight = minPlot;
+
+ fGlyphSizeLimit = minPlot;
}
-GrGlyphCache::~GrGlyphCache() {
+GrAtlasGlyphCache::~GrAtlasGlyphCache() {
StrikeHash::Iter iter(&fCache);
while (!iter.done()) {
(*iter).fIsAbandoned = true;
@@ -26,7 +88,7 @@ GrGlyphCache::~GrGlyphCache() {
}
}
-void GrGlyphCache::freeAll() {
+void GrAtlasGlyphCache::freeAll() {
StrikeHash::Iter iter(&fCache);
while (!iter.done()) {
(*iter).fIsAbandoned = true;
@@ -34,26 +96,120 @@ void GrGlyphCache::freeAll() {
++iter;
}
fCache.rewind();
+ for (int i = 0; i < kMaskFormatCount; ++i) {
+ fAtlases[i] = nullptr;
+ }
}
-void GrGlyphCache::HandleEviction(GrDrawOpAtlas::AtlasID id, void* ptr) {
- GrGlyphCache* glyphCache = reinterpret_cast<GrGlyphCache*>(ptr);
+void GrAtlasGlyphCache::HandleEviction(GrDrawOpAtlas::AtlasID id, void* ptr) {
+ GrAtlasGlyphCache* fontCache = reinterpret_cast<GrAtlasGlyphCache*>(ptr);
- StrikeHash::Iter iter(&glyphCache->fCache);
+ StrikeHash::Iter iter(&fontCache->fCache);
for (; !iter.done(); ++iter) {
GrAtlasTextStrike* strike = &*iter;
strike->removeID(id);
// clear out any empty strikes. We will preserve the strike whose call to addToAtlas
// triggered the eviction
- if (strike != glyphCache->fPreserveStrike && 0 == strike->fAtlasedGlyphs) {
- glyphCache->fCache.remove(GrAtlasTextStrike::GetKey(*strike));
+ if (strike != fontCache->fPreserveStrike && 0 == strike->fAtlasedGlyphs) {
+ fontCache->fCache.remove(GrAtlasTextStrike::GetKey(*strike));
strike->fIsAbandoned = true;
strike->unref();
}
}
}
+#ifdef SK_DEBUG
+#include "GrContextPriv.h"
+#include "GrSurfaceProxy.h"
+#include "GrSurfaceContext.h"
+#include "GrTextureProxy.h"
+
+#include "SkBitmap.h"
+#include "SkImageEncoder.h"
+#include "SkStream.h"
+#include <stdio.h>
+
+/**
+ * Write the contents of the surface proxy to a PNG. Returns true if successful.
+ * @param filename Full path to desired file
+ */
+static bool save_pixels(GrContext* context, GrSurfaceProxy* sProxy, const char* filename) {
+ if (!sProxy) {
+ return false;
+ }
+
+ SkImageInfo ii = SkImageInfo::Make(sProxy->width(), sProxy->height(),
+ kRGBA_8888_SkColorType, kPremul_SkAlphaType);
+ SkBitmap bm;
+ if (!bm.tryAllocPixels(ii)) {
+ return false;
+ }
+
+ sk_sp<GrSurfaceContext> sContext(context->contextPriv().makeWrappedSurfaceContext(
+ sk_ref_sp(sProxy)));
+ if (!sContext || !sContext->asTextureProxy()) {
+ return false;
+ }
+
+ bool result = sContext->readPixels(ii, bm.getPixels(), bm.rowBytes(), 0, 0);
+ if (!result) {
+ SkDebugf("------ failed to read pixels for %s\n", filename);
+ return false;
+ }
+
+ // remove any previous version of this file
+ remove(filename);
+
+ SkFILEWStream file(filename);
+ if (!file.isValid()) {
+ SkDebugf("------ failed to create file: %s\n", filename);
+ remove(filename); // remove any partial file
+ return false;
+ }
+
+ if (!SkEncodeImage(&file, bm, SkEncodedImageFormat::kPNG, 100)) {
+ SkDebugf("------ failed to encode %s\n", filename);
+ remove(filename); // remove any partial file
+ return false;
+ }
+
+ return true;
+}
+
+void GrAtlasGlyphCache::dump(GrContext* context) const {
+ static int gDumpCount = 0;
+ for (int i = 0; i < kMaskFormatCount; ++i) {
+ if (fAtlases[i]) {
+ const sk_sp<GrTextureProxy>* proxies = fAtlases[i]->getProxies();
+ for (uint32_t pageIdx = 0; pageIdx < fAtlases[i]->numActivePages(); ++pageIdx) {
+ SkASSERT(proxies[pageIdx]);
+ SkString filename;
+#ifdef SK_BUILD_FOR_ANDROID
+ filename.printf("/sdcard/fontcache_%d%d%d.png", gDumpCount, i, pageIdx);
+#else
+ filename.printf("fontcache_%d%d%d.png", gDumpCount, i, pageIdx);
+#endif
+
+ save_pixels(context, proxies[pageIdx].get(), filename.c_str());
+ }
+ }
+ }
+ ++gDumpCount;
+}
+#endif
+
+void GrAtlasGlyphCache::setAtlasSizes_ForTesting(const GrDrawOpAtlasConfig configs[3]) {
+ // Delete any old atlases.
+ // This should be safe to do as long as we are not in the middle of a flush.
+ for (int i = 0; i < kMaskFormatCount; i++) {
+ fAtlases[i] = nullptr;
+ }
+ memcpy(fAtlasConfigs, configs, sizeof(fAtlasConfigs));
+}
+
+///////////////////////////////////////////////////////////////////////////////
+
static inline GrMaskFormat get_packed_glyph_mask_format(const SkGlyph& glyph) {
SkMask::Format format = static_cast<SkMask::Format>(glyph.fMaskFormat);
switch (format) {
@@ -294,8 +450,7 @@ void GrAtlasTextStrike::removeID(GrDrawOpAtlas::AtlasID id) {
bool GrAtlasTextStrike::addGlyphToAtlas(GrResourceProvider* resourceProvider,
GrDeferredUploadTarget* target,
- GrGlyphCache* glyphCache,
- GrAtlasManager* fullAtlasManager,
+ GrAtlasGlyphCache* atlasGlyphCache,
GrGlyph* glyph,
SkGlyphCache* cache,
GrMaskFormat expectedMaskFormat) {
@@ -322,10 +477,10 @@ bool GrAtlasTextStrike::addGlyphToAtlas(GrResourceProvider* resourceProvider,
}
}
- bool success = fullAtlasManager->addToAtlas(resourceProvider, glyphCache, this,
- &glyph->fID, target, expectedMaskFormat,
- glyph->width(), glyph->height(),
- storage.get(), &glyph->fAtlasLocation);
+ bool success = atlasGlyphCache->addToAtlas(resourceProvider, this, &glyph->fID, target,
+ expectedMaskFormat,
+ glyph->width(), glyph->height(),
+ storage.get(), &glyph->fAtlasLocation);
if (success) {
SkASSERT(GrDrawOpAtlas::kInvalidAtlasID != glyph->fID);
fAtlasedGlyphs++;
diff --git a/src/gpu/text/GrAtlasGlyphCache.h b/src/gpu/text/GrAtlasGlyphCache.h
new file mode 100644
index 0000000000..84b7d1b249
--- /dev/null
+++ b/src/gpu/text/GrAtlasGlyphCache.h
@@ -0,0 +1,270 @@
+/*
+ * Copyright 2015 Google Inc.
+ *
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ */
+
+#ifndef GrAtlasGlyphCache_DEFINED
+#define GrAtlasGlyphCache_DEFINED
+
+#include "GrCaps.h"
+#include "GrDrawOpAtlas.h"
+#include "GrGlyph.h"
+#include "GrOnFlushResourceProvider.h"
+#include "SkArenaAlloc.h"
+#include "SkGlyphCache.h"
+#include "SkTDynamicHash.h"
+
+class GrAtlasGlyphCache;
+class GrGpu;
+
+/**
+ * The GrAtlasTextStrike manages a pool of CPU backing memory for GrGlyphs. This backing memory
+ * is indexed by a PackedID and SkGlyphCache. The SkGlyphCache is what actually creates the mask.
+ * The GrAtlasTextStrike may outlive the generating SkGlyphCache. However, it retains a copy
+ * of it's SkDescriptor as a key to access (or regenerate) the SkGlyphCache. GrAtlasTextStrike are
+ * created by and owned by a GrAtlasGlyphCache.
+ */
+class GrAtlasTextStrike : public SkNVRefCnt<GrAtlasTextStrike> {
+public:
+ GrAtlasTextStrike(const SkDescriptor& fontScalerKey);
+ ~GrAtlasTextStrike();
+
+ inline GrGlyph* getGlyph(const SkGlyph& skGlyph, GrGlyph::PackedID packed,
+ SkGlyphCache* cache) {
+ GrGlyph* glyph = fCache.find(packed);
+ if (nullptr == glyph) {
+ glyph = this->generateGlyph(skGlyph, packed, cache);
+ }
+ return glyph;
+ }
+
+ // This variant of the above function is called by GrAtlasTextOp. At this point, it is possible
+ // that the maskformat of the glyph differs from what we expect. In these cases we will just
+ // draw a clear square.
+ // skbug:4143 crbug:510931
+ inline GrGlyph* getGlyph(GrGlyph::PackedID packed,
+ GrMaskFormat expectedMaskFormat,
+ SkGlyphCache* cache) {
+ GrGlyph* glyph = fCache.find(packed);
+ if (nullptr == glyph) {
+ // We could return this to the caller, but in practice it adds code complexity for
+ // potentially little benefit(ie, if the glyph is not in our font cache, then its not
+ // in the atlas and we're going to be doing a texture upload anyways).
+ const SkGlyph& skGlyph = GrToSkGlyph(cache, packed);
+ glyph = this->generateGlyph(skGlyph, packed, cache);
+ glyph->fMaskFormat = expectedMaskFormat;
+ }
+ return glyph;
+ }
+
+ // returns true if glyph successfully added to texture atlas, false otherwise. If the glyph's
+ // mask format has changed, then addGlyphToAtlas will draw a clear box. This will almost never
+ // happen.
+ // TODO we can handle some of these cases if we really want to, but the long term solution is to
+ // get the actual glyph image itself when we get the glyph metrics.
+ bool addGlyphToAtlas(GrResourceProvider*, GrDeferredUploadTarget*, GrAtlasGlyphCache*, GrGlyph*,
+ SkGlyphCache*, GrMaskFormat expectedMaskFormat);
+
+ // testing
+ int countGlyphs() const { return fCache.count(); }
+
+ // remove any references to this plot
+ void removeID(GrDrawOpAtlas::AtlasID);
+
+ // If a TextStrike is abandoned by the cache, then the caller must get a new strike
+ bool isAbandoned() const { return fIsAbandoned; }
+
+ static const SkDescriptor& GetKey(const GrAtlasTextStrike& ts) {
+ return *ts.fFontScalerKey.getDesc();
+ }
+
+ static uint32_t Hash(const SkDescriptor& desc) { return desc.getChecksum(); }
+
+private:
+ SkTDynamicHash<GrGlyph, GrGlyph::PackedID> fCache;
+ SkAutoDescriptor fFontScalerKey;
+ SkArenaAlloc fPool{512};
+
+ int fAtlasedGlyphs;
+ bool fIsAbandoned;
+
+ static const SkGlyph& GrToSkGlyph(SkGlyphCache* cache, GrGlyph::PackedID id) {
+ return cache->getGlyphIDMetrics(GrGlyph::UnpackID(id),
+ GrGlyph::UnpackFixedX(id),
+ GrGlyph::UnpackFixedY(id));
+ }
+
+ GrGlyph* generateGlyph(const SkGlyph&, GrGlyph::PackedID, SkGlyphCache*);
+
+ friend class GrAtlasGlyphCache;
+};
+
+/**
+ * GrAtlasGlyphCache manages strikes which are indexed by a SkGlyphCache. These strikes can then be
+ * used to generate individual Glyph Masks. The GrAtlasGlyphCache also manages GrDrawOpAtlases,
+ * though this is more or less transparent to the client(aside from atlasGeneration, described
+ * below).
+ */
+class GrAtlasGlyphCache : public GrOnFlushCallbackObject {
+public:
+ GrAtlasGlyphCache(GrProxyProvider*, float maxTextureBytes,
+ GrDrawOpAtlas::AllowMultitexturing);
+ ~GrAtlasGlyphCache() override;
+ // The user of the cache may hold a long-lived ref to the returned strike. However, actions by
+ // another client of the cache may cause the strike to be purged while it is still reffed.
+ // Therefore, the caller must check GrAtlasTextStrike::isAbandoned() if there are other
+ // interactions with the cache since the strike was received.
+ inline GrAtlasTextStrike* getStrike(const SkGlyphCache* cache) {
+ GrAtlasTextStrike* strike = fCache.find(cache->getDescriptor());
+ if (nullptr == strike) {
+ strike = this->generateStrike(cache);
+ }
+ return strike;
+ }
+
+ void freeAll();
+
+ // if getProxies returns nullptr, the client must not try to use other functions on the
+ // GrAtlasGlyphCache which use the atlas. This function *must* be called first, before other
+ // functions which use the atlas.
+ const sk_sp<GrTextureProxy>* getProxies(GrMaskFormat format, unsigned int* numProxies) {
+ SkASSERT(numProxies);
+
+ if (this->initAtlas(format)) {
+ *numProxies = this->getAtlas(format)->numActivePages();
+ return this->getAtlas(format)->getProxies();
+ }
+ *numProxies = 0;
+ return nullptr;
+ }
+
+ SkScalar getGlyphSizeLimit() const { return fGlyphSizeLimit; }
+
+ bool hasGlyph(GrGlyph* glyph) {
+ SkASSERT(glyph);
+ return this->getAtlas(glyph->fMaskFormat)->hasID(glyph->fID);
+ }
+
+ // To ensure the GrDrawOpAtlas does not evict the Glyph Mask from its texture backing store,
+ // the client must pass in the current op token along with the GrGlyph.
+ // A BulkUseTokenUpdater is used to manage bulk last use token updating in the Atlas.
+ // For convenience, this function will also set the use token for the current glyph if required
+ // NOTE: the bulk uploader is only valid if the subrun has a valid atlasGeneration
+ void addGlyphToBulkAndSetUseToken(GrDrawOpAtlas::BulkUseTokenUpdater* updater, GrGlyph* glyph,
+ GrDeferredUploadToken token) {
+ SkASSERT(glyph);
+ updater->add(glyph->fID);
+ this->getAtlas(glyph->fMaskFormat)->setLastUseToken(glyph->fID, token);
+ }
+
+ void setUseTokenBulk(const GrDrawOpAtlas::BulkUseTokenUpdater& updater,
+ GrDeferredUploadToken token,
+ GrMaskFormat format) {
+ this->getAtlas(format)->setLastUseTokenBulk(updater, token);
+ }
+
+ // add to texture atlas that matches this format
+ bool addToAtlas(GrResourceProvider* resourceProvider, GrAtlasTextStrike* strike,
+ GrDrawOpAtlas::AtlasID* id,
+ GrDeferredUploadTarget* target, GrMaskFormat format, int width, int height,
+ const void* image, SkIPoint16* loc) {
+ fPreserveStrike = strike;
+ return this->getAtlas(format)->addToAtlas(resourceProvider, id, target,
+ width, height, image, loc);
+ }
+
+ // Some clients may wish to verify the integrity of the texture backing store of the
+ // GrDrawOpAtlas. The atlasGeneration returned below is a monotonically increasing number which
+ // changes every time something is removed from the texture backing store.
+ uint64_t atlasGeneration(GrMaskFormat format) const {
+ return this->getAtlas(format)->atlasGeneration();
+ }
+
+ // GrOnFlushCallbackObject overrides
+
+ void preFlush(GrOnFlushResourceProvider* onFlushResourceProvider, const uint32_t*, int,
+ SkTArray<sk_sp<GrRenderTargetContext>>*) override {
+ for (int i = 0; i < kMaskFormatCount; ++i) {
+ if (fAtlases[i]) {
+ fAtlases[i]->instantiate(onFlushResourceProvider);
+ }
+ }
+ }
+
+ void postFlush(GrDeferredUploadToken startTokenForNextFlush, const uint32_t*, int) override {
+ for (int i = 0; i < kMaskFormatCount; ++i) {
+ if (fAtlases[i]) {
+ fAtlases[i]->compact(startTokenForNextFlush);
+ }
+ }
+ }
+
+ // The AtlasGlyph cache always survives freeGpuResources so we want it to remain in the active
+ // OnFlushCallbackObject list
+ bool retainOnFreeGpuResources() override { return true; }
+
+ ///////////////////////////////////////////////////////////////////////////
+ // Functions intended debug only
+#ifdef SK_DEBUG
+ void dump(GrContext*) const;
+#endif
+
+ void setAtlasSizes_ForTesting(const GrDrawOpAtlasConfig configs[3]);
+
+private:
+ static GrPixelConfig MaskFormatToPixelConfig(GrMaskFormat format, const GrCaps& caps) {
+ switch (format) {
+ case kA8_GrMaskFormat:
+ return kAlpha_8_GrPixelConfig;
+ case kA565_GrMaskFormat:
+ return kRGB_565_GrPixelConfig;
+ case kARGB_GrMaskFormat:
+ return caps.srgbSupport() ? kSRGBA_8888_GrPixelConfig : kRGBA_8888_GrPixelConfig;
+ default:
+ SkDEBUGFAIL("unsupported GrMaskFormat");
+ return kAlpha_8_GrPixelConfig;
+ }
+ }
+
+ // There is a 1:1 mapping between GrMaskFormats and atlas indices
+ static int MaskFormatToAtlasIndex(GrMaskFormat format) {
+ static const int sAtlasIndices[] = {
+ kA8_GrMaskFormat,
+ kA565_GrMaskFormat,
+ kARGB_GrMaskFormat,
+ };
+ static_assert(SK_ARRAY_COUNT(sAtlasIndices) == kMaskFormatCount, "array_size_mismatch");
+
+ SkASSERT(sAtlasIndices[format] < kMaskFormatCount);
+ return sAtlasIndices[format];
+ }
+
+ bool initAtlas(GrMaskFormat);
+
+ GrAtlasTextStrike* generateStrike(const SkGlyphCache* cache) {
+ GrAtlasTextStrike* strike = new GrAtlasTextStrike(cache->getDescriptor());
+ fCache.add(strike);
+ return strike;
+ }
+
+ GrDrawOpAtlas* getAtlas(GrMaskFormat format) const {
+ int atlasIndex = MaskFormatToAtlasIndex(format);
+ SkASSERT(fAtlases[atlasIndex]);
+ return fAtlases[atlasIndex].get();
+ }
+
+ static void HandleEviction(GrDrawOpAtlas::AtlasID, void*);
+
+ using StrikeHash = SkTDynamicHash<GrAtlasTextStrike, SkDescriptor>;
+ GrProxyProvider* fProxyProvider;
+ StrikeHash fCache;
+ GrDrawOpAtlas::AllowMultitexturing fAllowMultitexturing;
+ std::unique_ptr<GrDrawOpAtlas> fAtlases[kMaskFormatCount];
+ GrAtlasTextStrike* fPreserveStrike;
+ GrDrawOpAtlasConfig fAtlasConfigs[kMaskFormatCount];
+ SkScalar fGlyphSizeLimit;
+};
+
+#endif
diff --git a/src/gpu/text/GrAtlasManager.cpp b/src/gpu/text/GrAtlasManager.cpp
deleted file mode 100644
index 6e227a94a2..0000000000
--- a/src/gpu/text/GrAtlasManager.cpp
+++ /dev/null
@@ -1,222 +0,0 @@
-/*
- * Copyright 2018 Google Inc.
- *
- * Use of this source code is governed by a BSD-style license that can be
- * found in the LICENSE file.
- */
-
-#include "GrAtlasManager.h"
-
-#include "GrCaps.h"
-#include "GrGlyph.h"
-#include "GrGlyphCache.h"
-#include "GrProxyProvider.h"
-
-GrRestrictedAtlasManager::GrRestrictedAtlasManager(
- sk_sp<const GrCaps> caps,
- float maxTextureBytes,
- GrDrawOpAtlas::AllowMultitexturing allowMultitexturing)
- : fCaps(std::move(caps))
- , fAllowMultitexturing(allowMultitexturing) {
- // Calculate RGBA size. Must be between 512 x 256 and MaxTextureSize x MaxTextureSize / 2
- int log2MaxTextureSize = SkPrevLog2(fCaps->maxTextureSize());
- int log2MaxDim = 9;
- for (; log2MaxDim <= log2MaxTextureSize; ++log2MaxDim) {
- int maxDim = 1 << log2MaxDim;
- int minDim = 1 << (log2MaxDim - 1);
-
- if (maxDim * minDim * 4 >= maxTextureBytes) break;
- }
-
- int log2MinDim = log2MaxDim - 1;
- int maxDim = 1 << log2MaxDim;
- int minDim = 1 << log2MinDim;
- // Plots are either 256 or 512.
- int maxPlot = SkTMin(512, SkTMax(256, 1 << (log2MaxDim - 2)));
- int minPlot = SkTMin(512, SkTMax(256, 1 << (log2MaxDim - 3)));
-
- // Setup default atlas configs. The A8 atlas uses maxDim for both width and height, as the A8
- // format is already very compact.
- fAtlasConfigs[kA8_GrMaskFormat].fWidth = maxDim;
- fAtlasConfigs[kA8_GrMaskFormat].fHeight = maxDim;
- fAtlasConfigs[kA8_GrMaskFormat].fPlotWidth = maxPlot;
- fAtlasConfigs[kA8_GrMaskFormat].fPlotHeight = minPlot;
-
- // A565 and ARGB use maxDim x minDim.
- fAtlasConfigs[kA565_GrMaskFormat].fWidth = minDim;
- fAtlasConfigs[kA565_GrMaskFormat].fHeight = maxDim;
- fAtlasConfigs[kA565_GrMaskFormat].fPlotWidth = minPlot;
- fAtlasConfigs[kA565_GrMaskFormat].fPlotHeight = minPlot;
-
- fAtlasConfigs[kARGB_GrMaskFormat].fWidth = minDim;
- fAtlasConfigs[kARGB_GrMaskFormat].fHeight = maxDim;
- fAtlasConfigs[kARGB_GrMaskFormat].fPlotWidth = minPlot;
- fAtlasConfigs[kARGB_GrMaskFormat].fPlotHeight = minPlot;
-
- fGlyphSizeLimit = minPlot;
-}
-
-GrRestrictedAtlasManager::~GrRestrictedAtlasManager() {
-}
-
-static GrPixelConfig mask_format_to_pixel_config(GrMaskFormat format, const GrCaps& caps) {
- switch (format) {
- case kA8_GrMaskFormat:
- return kAlpha_8_GrPixelConfig;
- case kA565_GrMaskFormat:
- return kRGB_565_GrPixelConfig;
- case kARGB_GrMaskFormat:
- return caps.srgbSupport() ? kSRGBA_8888_GrPixelConfig : kRGBA_8888_GrPixelConfig;
- default:
- SkDEBUGFAIL("unsupported GrMaskFormat");
- return kAlpha_8_GrPixelConfig;
- }
-}
-
-//////////////////////////////////////////////////////////////////////////////////////////////////
-GrAtlasManager::GrAtlasManager(GrProxyProvider* proxyProvider, GrGlyphCache* glyphCache,
- float maxTextureBytes,
- GrDrawOpAtlas::AllowMultitexturing allowMultitexturing)
- : INHERITED(proxyProvider->refCaps(), maxTextureBytes, allowMultitexturing)
- , fProxyProvider(proxyProvider)
- , fGlyphCache(glyphCache) {
-}
-
-void GrAtlasManager::freeAll() {
- for (int i = 0; i < kMaskFormatCount; ++i) {
- fAtlases[i] = nullptr;
- }
-}
-
-bool GrAtlasManager::hasGlyph(GrGlyph* glyph) {
- SkASSERT(glyph);
- return this->getAtlas(glyph->fMaskFormat)->hasID(glyph->fID);
-}
-
-// add to texture atlas that matches this format
-bool GrAtlasManager::addToAtlas(GrResourceProvider* resourceProvider,
- GrGlyphCache* glyphCache,
- GrAtlasTextStrike* strike, GrDrawOpAtlas::AtlasID* id,
- GrDeferredUploadTarget* target, GrMaskFormat format,
- int width, int height, const void* image, SkIPoint16* loc) {
- glyphCache->setStrikeToPreserve(strike);
- return this->getAtlas(format)->addToAtlas(resourceProvider, id, target, width, height,
- image, loc);
-}
-
-void GrAtlasManager::addGlyphToBulkAndSetUseToken(GrDrawOpAtlas::BulkUseTokenUpdater* updater,
- GrGlyph* glyph,
- GrDeferredUploadToken token) {
- SkASSERT(glyph);
- updater->add(glyph->fID);
- this->getAtlas(glyph->fMaskFormat)->setLastUseToken(glyph->fID, token);
-}
-
-#ifdef SK_DEBUG
-#include "GrContextPriv.h"
-#include "GrSurfaceProxy.h"
-#include "GrSurfaceContext.h"
-#include "GrTextureProxy.h"
-
-#include "SkBitmap.h"
-#include "SkImageEncoder.h"
-#include "SkStream.h"
-#include <stdio.h>
-
-/**
- * Write the contents of the surface proxy to a PNG. Returns true if successful.
- * @param filename Full path to desired file
- */
-static bool save_pixels(GrContext* context, GrSurfaceProxy* sProxy, const char* filename) {
- if (!sProxy) {
- return false;
- }
-
- SkImageInfo ii = SkImageInfo::Make(sProxy->width(), sProxy->height(),
- kRGBA_8888_SkColorType, kPremul_SkAlphaType);
- SkBitmap bm;
- if (!bm.tryAllocPixels(ii)) {
- return false;
- }
-
- sk_sp<GrSurfaceContext> sContext(context->contextPriv().makeWrappedSurfaceContext(
- sk_ref_sp(sProxy)));
- if (!sContext || !sContext->asTextureProxy()) {
- return false;
- }
-
- bool result = sContext->readPixels(ii, bm.getPixels(), bm.rowBytes(), 0, 0);
- if (!result) {
- SkDebugf("------ failed to read pixels for %s\n", filename);
- return false;
- }
-
- // remove any previous version of this file
- remove(filename);
-
- SkFILEWStream file(filename);
- if (!file.isValid()) {
- SkDebugf("------ failed to create file: %s\n", filename);
- remove(filename); // remove any partial file
- return false;
- }
-
- if (!SkEncodeImage(&file, bm, SkEncodedImageFormat::kPNG, 100)) {
- SkDebugf("------ failed to encode %s\n", filename);
- remove(filename); // remove any partial file
- return false;
- }
-
- return true;
-}
-
-void GrAtlasManager::dump(GrContext* context) const {
- static int gDumpCount = 0;
- for (int i = 0; i < kMaskFormatCount; ++i) {
- if (fAtlases[i]) {
- const sk_sp<GrTextureProxy>* proxies = fAtlases[i]->getProxies();
- for (uint32_t pageIdx = 0; pageIdx < fAtlases[i]->numActivePages(); ++pageIdx) {
- SkASSERT(proxies[pageIdx]);
- SkString filename;
-#ifdef SK_BUILD_FOR_ANDROID
- filename.printf("/sdcard/fontcache_%d%d%d.png", gDumpCount, i, pageIdx);
-#else
- filename.printf("fontcache_%d%d%d.png", gDumpCount, i, pageIdx);
-#endif
-
- save_pixels(context, proxies[pageIdx].get(), filename.c_str());
- }
- }
- }
- ++gDumpCount;
-}
-#endif
-
-void GrAtlasManager::setAtlasSizes_ForTesting(const GrDrawOpAtlasConfig configs[3]) {
- // Delete any old atlases.
- // This should be safe to do as long as we are not in the middle of a flush.
- for (int i = 0; i < kMaskFormatCount; i++) {
- fAtlases[i] = nullptr;
- }
- memcpy(fAtlasConfigs, configs, sizeof(fAtlasConfigs));
-}
-
-bool GrAtlasManager::initAtlas(GrMaskFormat format) {
- int index = MaskFormatToAtlasIndex(format);
- if (!fAtlases[index]) {
- GrPixelConfig config = mask_format_to_pixel_config(format, *fCaps);
- int width = fAtlasConfigs[index].fWidth;
- int height = fAtlasConfigs[index].fHeight;
- int numPlotsX = fAtlasConfigs[index].numPlotsX();
- int numPlotsY = fAtlasConfigs[index].numPlotsY();
-
- fAtlases[index] = GrDrawOpAtlas::Make(fProxyProvider, config, width, height,
- numPlotsX, numPlotsY, fAllowMultitexturing,
- &GrGlyphCache::HandleEviction,
- fGlyphCache);
- if (!fAtlases[index]) {
- return false;
- }
- }
- return true;
-}
diff --git a/src/gpu/text/GrAtlasManager.h b/src/gpu/text/GrAtlasManager.h
deleted file mode 100644
index 4629cb173b..0000000000
--- a/src/gpu/text/GrAtlasManager.h
+++ /dev/null
@@ -1,155 +0,0 @@
-/*
- * Copyright 2018 Google Inc.
- *
- * Use of this source code is governed by a BSD-style license that can be
- * found in the LICENSE file.
- */
-
-#ifndef GrAtlasManager_DEFINED
-#define GrAtlasManager_DEFINED
-
-#include "GrDrawOpAtlas.h"
-#include "GrOnFlushResourceProvider.h"
-
-class GrAtlasGlypCache;
-class GrAtlasTextStrike;
-struct GrGlyph;
-
- /** The GrAtlasManager classes manage the lifetime of and access to GrDrawOpAtlases.
- * The restricted version is available at op creation time and only allows basic access
- * to the proxies (so the created ops can reference them). The full GrAtlasManager class
- * is only available at flush time and only via the GrOpFlushState.
- *
- * This organization implies that all of the advanced atlasManager functionality (i.e.,
- * adding glyphs to the atlas) are only available at flush time.
- */
-class GrRestrictedAtlasManager : public GrOnFlushCallbackObject {
-public:
- GrRestrictedAtlasManager(sk_sp<const GrCaps>, float maxTextureBytes,
- GrDrawOpAtlas::AllowMultitexturing);
- ~GrRestrictedAtlasManager() override;
-
- // if getProxies returns nullptr, the client must not try to use other functions on the
- // GrGlyphCache which use the atlas. This function *must* be called first, before other
- // functions which use the atlas.
- const sk_sp<GrTextureProxy>* getProxies(GrMaskFormat format, unsigned int* numProxies) {
- if (this->initAtlas(format)) {
- *numProxies = this->getAtlas(format)->numActivePages();
- return this->getAtlas(format)->getProxies();
- }
- *numProxies = 0;
- return nullptr;
- }
-
- SkScalar getGlyphSizeLimit() const { return fGlyphSizeLimit; }
-
-protected:
- // There is a 1:1 mapping between GrMaskFormats and atlas indices
- static int MaskFormatToAtlasIndex(GrMaskFormat format) {
- static const int sAtlasIndices[] = {
- kA8_GrMaskFormat,
- kA565_GrMaskFormat,
- kARGB_GrMaskFormat,
- };
- static_assert(SK_ARRAY_COUNT(sAtlasIndices) == kMaskFormatCount, "array_size_mismatch");
-
- SkASSERT(sAtlasIndices[format] < kMaskFormatCount);
- return sAtlasIndices[format];
- }
-
- GrDrawOpAtlas* getAtlas(GrMaskFormat format) const {
- int atlasIndex = MaskFormatToAtlasIndex(format);
- SkASSERT(fAtlases[atlasIndex]);
- return fAtlases[atlasIndex].get();
- }
-
- sk_sp<const GrCaps> fCaps;
- GrDrawOpAtlas::AllowMultitexturing fAllowMultitexturing;
- std::unique_ptr<GrDrawOpAtlas> fAtlases[kMaskFormatCount];
- GrDrawOpAtlasConfig fAtlasConfigs[kMaskFormatCount];
- SkScalar fGlyphSizeLimit;
-
-private:
- virtual bool initAtlas(GrMaskFormat) = 0;
-
- typedef GrOnFlushCallbackObject INHERITED;
-};
-
-//////////////////////////////////////////////////////////////////////////////////////////////////
-class GrAtlasManager : public GrRestrictedAtlasManager {
-public:
- GrAtlasManager(GrProxyProvider*, GrGlyphCache*,
- float maxTextureBytes, GrDrawOpAtlas::AllowMultitexturing);
-
- void freeAll();
-
- bool hasGlyph(GrGlyph* glyph);
-
- // To ensure the GrDrawOpAtlas does not evict the Glyph Mask from its texture backing store,
- // the client must pass in the current op token along with the GrGlyph.
- // A BulkUseTokenUpdater is used to manage bulk last use token updating in the Atlas.
- // For convenience, this function will also set the use token for the current glyph if required
- // NOTE: the bulk uploader is only valid if the subrun has a valid atlasGeneration
- void addGlyphToBulkAndSetUseToken(GrDrawOpAtlas::BulkUseTokenUpdater*, GrGlyph*,
- GrDeferredUploadToken);
-
- void setUseTokenBulk(const GrDrawOpAtlas::BulkUseTokenUpdater& updater,
- GrDeferredUploadToken token,
- GrMaskFormat format) {
- this->getAtlas(format)->setLastUseTokenBulk(updater, token);
- }
-
- // add to texture atlas that matches this format
- bool addToAtlas(GrResourceProvider*, GrGlyphCache*, GrAtlasTextStrike*,
- GrDrawOpAtlas::AtlasID*, GrDeferredUploadTarget*, GrMaskFormat,
- int width, int height, const void* image, SkIPoint16* loc);
-
- // Some clients may wish to verify the integrity of the texture backing store of the
- // GrDrawOpAtlas. The atlasGeneration returned below is a monotonically increasing number which
- // changes every time something is removed from the texture backing store.
- uint64_t atlasGeneration(GrMaskFormat format) const {
- return this->getAtlas(format)->atlasGeneration();
- }
-
- // GrOnFlushCallbackObject overrides
-
- void preFlush(GrOnFlushResourceProvider* onFlushResourceProvider, const uint32_t*, int,
- SkTArray<sk_sp<GrRenderTargetContext>>*) override {
- for (int i = 0; i < kMaskFormatCount; ++i) {
- if (fAtlases[i]) {
- fAtlases[i]->instantiate(onFlushResourceProvider);
- }
- }
- }
-
- void postFlush(GrDeferredUploadToken startTokenForNextFlush,
- const uint32_t* opListIDs, int numOpListIDs) override {
- for (int i = 0; i < kMaskFormatCount; ++i) {
- if (fAtlases[i]) {
- fAtlases[i]->compact(startTokenForNextFlush);
- }
- }
- }
-
- // The AtlasGlyph cache always survives freeGpuResources so we want it to remain in the active
- // OnFlushCallbackObject list
- bool retainOnFreeGpuResources() override { return true; }
-
- ///////////////////////////////////////////////////////////////////////////
- // Functions intended debug only
-#ifdef SK_DEBUG
- void dump(GrContext* context) const;
-#endif
-
- void setAtlasSizes_ForTesting(const GrDrawOpAtlasConfig configs[3]);
-
-private:
- bool initAtlas(GrMaskFormat) override;
-
- GrProxyProvider* fProxyProvider;
- GrGlyphCache* fGlyphCache;
-
- typedef GrRestrictedAtlasManager INHERITED;
-};
-
-#endif // GrAtlasManager_DEFINED
diff --git a/src/gpu/text/GrAtlasTextBlob.cpp b/src/gpu/text/GrAtlasTextBlob.cpp
index 35e783019f..90bcf5a224 100644
--- a/src/gpu/text/GrAtlasTextBlob.cpp
+++ b/src/gpu/text/GrAtlasTextBlob.cpp
@@ -250,8 +250,8 @@ inline std::unique_ptr<GrAtlasTextOp> GrAtlasTextBlob::makeOp(
const Run::SubRunInfo& info, int glyphCount, uint16_t run, uint16_t subRun,
const SkMatrix& viewMatrix, SkScalar x, SkScalar y, const SkIRect& clipRect,
const GrTextUtils::Paint& paint, const SkSurfaceProps& props,
- const GrDistanceFieldAdjustTable* distanceAdjustTable,
- GrRestrictedAtlasManager* restrictedAtlasManager, GrTextUtils::Target* target) {
+ const GrDistanceFieldAdjustTable* distanceAdjustTable, GrAtlasGlyphCache* cache,
+ GrTextUtils::Target* target) {
GrMaskFormat format = info.maskFormat();
GrPaint grPaint;
@@ -260,12 +260,11 @@ inline std::unique_ptr<GrAtlasTextOp> GrAtlasTextBlob::makeOp(
if (info.drawAsDistanceFields()) {
bool useBGR = SkPixelGeometryIsBGR(props.pixelGeometry());
op = GrAtlasTextOp::MakeDistanceField(
- std::move(grPaint), glyphCount, restrictedAtlasManager, distanceAdjustTable,
+ std::move(grPaint), glyphCount, cache, distanceAdjustTable,
target->colorSpaceInfo().isGammaCorrect(), paint.luminanceColor(),
info.hasUseLCDText(), useBGR, info.isAntiAliased());
} else {
- op = GrAtlasTextOp::MakeBitmap(std::move(grPaint), format,
- glyphCount, restrictedAtlasManager);
+ op = GrAtlasTextOp::MakeBitmap(std::move(grPaint), format, glyphCount, cache);
}
GrAtlasTextOp::Geometry& geometry = op->geometry();
geometry.fViewMatrix = viewMatrix;
@@ -301,8 +300,8 @@ static void calculate_translation(bool applyVM,
}
}
-void GrAtlasTextBlob::flush(GrRestrictedAtlasManager* restrictedAtlasManager,
- GrTextUtils::Target* target, const SkSurfaceProps& props,
+void GrAtlasTextBlob::flush(GrAtlasGlyphCache* atlasGlyphCache, GrTextUtils::Target* target,
+ const SkSurfaceProps& props,
const GrDistanceFieldAdjustTable* distanceAdjustTable,
const GrTextUtils::Paint& paint, const GrClip& clip,
const SkMatrix& viewMatrix, const SkIRect& clipBounds,
@@ -377,7 +376,7 @@ void GrAtlasTextBlob::flush(GrRestrictedAtlasManager* restrictedAtlasManager,
if (submitOp) {
auto op = this->makeOp(info, glyphCount, runIndex, subRun, viewMatrix, x, y,
clipRect, std::move(paint), props, distanceAdjustTable,
- restrictedAtlasManager, target);
+ atlasGlyphCache, target);
if (op) {
if (skipClip) {
target->addDrawOp(GrNoClip(), std::move(op));
@@ -395,12 +394,12 @@ void GrAtlasTextBlob::flush(GrRestrictedAtlasManager* restrictedAtlasManager,
std::unique_ptr<GrDrawOp> GrAtlasTextBlob::test_makeOp(
int glyphCount, uint16_t run, uint16_t subRun, const SkMatrix& viewMatrix,
SkScalar x, SkScalar y, const GrTextUtils::Paint& paint, const SkSurfaceProps& props,
- const GrDistanceFieldAdjustTable* distanceAdjustTable,
- GrRestrictedAtlasManager* restrictedAtlasManager, GrTextUtils::Target* target) {
+ const GrDistanceFieldAdjustTable* distanceAdjustTable, GrAtlasGlyphCache* cache,
+ GrTextUtils::Target* target) {
const GrAtlasTextBlob::Run::SubRunInfo& info = fRuns[run].fSubRunInfo[subRun];
SkIRect emptyRect = SkIRect::MakeEmpty();
return this->makeOp(info, glyphCount, run, subRun, viewMatrix, x, y, emptyRect, paint, props,
- distanceAdjustTable, restrictedAtlasManager, target);
+ distanceAdjustTable, cache, target);
}
void GrAtlasTextBlob::AssertEqual(const GrAtlasTextBlob& l, const GrAtlasTextBlob& r) {
diff --git a/src/gpu/text/GrAtlasTextBlob.h b/src/gpu/text/GrAtlasTextBlob.h
index 9f91cae957..0fae3cd8c7 100644
--- a/src/gpu/text/GrAtlasTextBlob.h
+++ b/src/gpu/text/GrAtlasTextBlob.h
@@ -8,9 +8,9 @@
#ifndef GrAtlasTextBlob_DEFINED
#define GrAtlasTextBlob_DEFINED
+#include "GrAtlasGlyphCache.h"
#include "GrColor.h"
#include "GrDrawOpAtlas.h"
-#include "GrGlyphCache.h"
#include "GrMemoryPool.h"
#include "GrTextUtils.h"
#include "SkDescriptor.h"
@@ -22,13 +22,8 @@
#include "SkSurfaceProps.h"
#include "SkTInternalLList.h"
-class GrAtlasManager;
struct GrDistanceFieldAdjustTable;
-struct GrGlyph;
-class GrGlyphCache;
class GrMemoryPool;
-class GrRestrictedAtlasManager;
-
class SkDrawFilter;
class SkTextBlob;
class SkTextBlobRunIterator;
@@ -206,7 +201,7 @@ public:
bool mustRegenerate(const GrTextUtils::Paint&, const SkMaskFilterBase::BlurRec& blurRec,
const SkMatrix& viewMatrix, SkScalar x, SkScalar y);
- void flush(GrRestrictedAtlasManager*, GrTextUtils::Target*, const SkSurfaceProps& props,
+ void flush(GrAtlasGlyphCache*, GrTextUtils::Target*, const SkSurfaceProps& props,
const GrDistanceFieldAdjustTable* distanceAdjustTable,
const GrTextUtils::Paint& paint, const GrClip& clip,
const SkMatrix& viewMatrix, const SkIRect& clipBounds, SkScalar x,
@@ -281,8 +276,8 @@ public:
std::unique_ptr<GrDrawOp> test_makeOp(int glyphCount, uint16_t run, uint16_t subRun,
const SkMatrix& viewMatrix, SkScalar x, SkScalar y,
const GrTextUtils::Paint&, const SkSurfaceProps&,
- const GrDistanceFieldAdjustTable*,
- GrRestrictedAtlasManager*, GrTextUtils::Target*);
+ const GrDistanceFieldAdjustTable*, GrAtlasGlyphCache*,
+ GrTextUtils::Target*);
private:
GrAtlasTextBlob()
@@ -511,8 +506,9 @@ private:
inline std::unique_ptr<GrAtlasTextOp> makeOp(
const Run::SubRunInfo& info, int glyphCount, uint16_t run, uint16_t subRun,
const SkMatrix& viewMatrix, SkScalar x, SkScalar y, const SkIRect& clipRect,
- const GrTextUtils::Paint&, const SkSurfaceProps&,
- const GrDistanceFieldAdjustTable*, GrRestrictedAtlasManager* , GrTextUtils::Target*);
+ const GrTextUtils::Paint& paint, const SkSurfaceProps& props,
+ const GrDistanceFieldAdjustTable* distanceAdjustTable, GrAtlasGlyphCache* cache,
+ GrTextUtils::Target*);
struct StrokeInfo {
SkScalar fFrameWidth;
@@ -566,8 +562,7 @@ public:
*/
VertexRegenerator(GrResourceProvider*, GrAtlasTextBlob*, int runIdx, int subRunIdx,
const SkMatrix& viewMatrix, SkScalar x, SkScalar y, GrColor color,
- GrDeferredUploadTarget*, GrGlyphCache*, GrAtlasManager*,
- SkAutoGlyphCache*);
+ GrDeferredUploadTarget*, GrAtlasGlyphCache*, SkAutoGlyphCache*);
struct Result {
/**
@@ -598,8 +593,7 @@ private:
const SkMatrix& fViewMatrix;
GrAtlasTextBlob* fBlob;
GrDeferredUploadTarget* fUploadTarget;
- GrGlyphCache* fGlyphCache;
- GrAtlasManager* fFullAtlasManager;
+ GrAtlasGlyphCache* fGlyphCache;
SkAutoGlyphCache* fLazyCache;
Run* fRun;
Run::SubRunInfo* fSubRun;
diff --git a/src/gpu/text/GrAtlasTextBlobVertexRegenerator.cpp b/src/gpu/text/GrAtlasTextBlobVertexRegenerator.cpp
index 54001c2628..500ae31703 100644
--- a/src/gpu/text/GrAtlasTextBlobVertexRegenerator.cpp
+++ b/src/gpu/text/GrAtlasTextBlobVertexRegenerator.cpp
@@ -5,7 +5,6 @@
* found in the LICENSE file.
*/
-#include "GrAtlasManager.h"
#include "GrAtlasTextBlob.h"
#include "GrTextUtils.h"
#include "SkDistanceFieldGen.h"
@@ -194,14 +193,13 @@ inline void regen_vertices(char* vertex, const GrGlyph* glyph, size_t vertexStri
Regenerator::VertexRegenerator(GrResourceProvider* resourceProvider, GrAtlasTextBlob* blob,
int runIdx, int subRunIdx,
const SkMatrix& viewMatrix, SkScalar x, SkScalar y, GrColor color,
- GrDeferredUploadTarget* uploadTarget, GrGlyphCache* glyphCache,
- GrAtlasManager* fullAtlasManager, SkAutoGlyphCache* lazyCache)
+ GrDeferredUploadTarget* uploadTarget, GrAtlasGlyphCache* glyphCache,
+ SkAutoGlyphCache* lazyCache)
: fResourceProvider(resourceProvider)
, fViewMatrix(viewMatrix)
, fBlob(blob)
, fUploadTarget(uploadTarget)
, fGlyphCache(glyphCache)
- , fFullAtlasManager(fullAtlasManager)
, fLazyCache(lazyCache)
, fRun(&blob->fRuns[runIdx])
, fSubRun(&blob->fRuns[runIdx].fSubRunInfo[subRunIdx])
@@ -209,7 +207,7 @@ Regenerator::VertexRegenerator(GrResourceProvider* resourceProvider, GrAtlasText
// Compute translation if any
fSubRun->computeTranslation(fViewMatrix, x, y, &fTransX, &fTransY);
- // Because the GrGlyphCache may evict the strike a blob depends on using for
+ // Because the GrAtlasGlyphCache may evict the strike a blob depends on using for
// generating its texture coords, we have to track whether or not the strike has
// been abandoned. If it hasn't been abandoned, then we can use the GrGlyph*s as is
// otherwise we have to get the new strike, and use that to get the correct glyphs.
@@ -277,17 +275,16 @@ Regenerator::Result Regenerator::doRegen() {
glyph = fBlob->fGlyphs[glyphOffset];
SkASSERT(glyph && glyph->fMaskFormat == fSubRun->maskFormat());
- if (!fFullAtlasManager->hasGlyph(glyph) &&
- !strike->addGlyphToAtlas(fResourceProvider, fUploadTarget, fGlyphCache,
- fFullAtlasManager, glyph,
+ if (!fGlyphCache->hasGlyph(glyph) &&
+ !strike->addGlyphToAtlas(fResourceProvider, fUploadTarget, fGlyphCache, glyph,
fLazyCache->get(), fSubRun->maskFormat())) {
fBrokenRun = glyphIdx > 0;
result.fFinished = false;
return result;
}
auto tokenTracker = fUploadTarget->tokenTracker();
- fFullAtlasManager->addGlyphToBulkAndSetUseToken(fSubRun->bulkUseToken(), glyph,
- tokenTracker->nextDrawToken());
+ fGlyphCache->addGlyphToBulkAndSetUseToken(fSubRun->bulkUseToken(), glyph,
+ tokenTracker->nextDrawToken());
}
regen_vertices<regenPos, regenCol, regenTexCoords>(currVertex, glyph, vertexStride,
@@ -305,14 +302,14 @@ Regenerator::Result Regenerator::doRegen() {
fSubRun->setStrike(strike);
}
fSubRun->setAtlasGeneration(fBrokenRun
- ? GrDrawOpAtlas::kInvalidAtlasGeneration
- : fFullAtlasManager->atlasGeneration(fSubRun->maskFormat()));
+ ? GrDrawOpAtlas::kInvalidAtlasGeneration
+ : fGlyphCache->atlasGeneration(fSubRun->maskFormat()));
}
return result;
}
Regenerator::Result Regenerator::regenerate() {
- uint64_t currentAtlasGen = fFullAtlasManager->atlasGeneration(fSubRun->maskFormat());
+ uint64_t currentAtlasGen = fGlyphCache->atlasGeneration(fSubRun->maskFormat());
// If regenerate() is called multiple times then the atlas gen may have changed. So we check
// this each time.
if (fSubRun->atlasGeneration() != currentAtlasGen) {
@@ -355,9 +352,9 @@ Regenerator::Result Regenerator::regenerate() {
// set use tokens for all of the glyphs in our subrun. This is only valid if we
// have a valid atlas generation
- fFullAtlasManager->setUseTokenBulk(*fSubRun->bulkUseToken(),
- fUploadTarget->tokenTracker()->nextDrawToken(),
- fSubRun->maskFormat());
+ fGlyphCache->setUseTokenBulk(*fSubRun->bulkUseToken(),
+ fUploadTarget->tokenTracker()->nextDrawToken(),
+ fSubRun->maskFormat());
return result;
}
}
diff --git a/src/gpu/text/GrAtlasTextContext.cpp b/src/gpu/text/GrAtlasTextContext.cpp
index aadc2dc0c1..06282e103e 100644
--- a/src/gpu/text/GrAtlasTextContext.cpp
+++ b/src/gpu/text/GrAtlasTextContext.cpp
@@ -118,8 +118,7 @@ void GrAtlasTextContext::drawTextBlob(GrContext* context, GrTextUtils::Target* t
drawFilter);
SkScalerContextFlags scalerContextFlags = ComputeScalerContextFlags(target->colorSpaceInfo());
- auto glyphCache = context->contextPriv().getGlyphCache();
- auto restrictedAtlasManager = context->contextPriv().getRestrictedAtlasManager();
+ auto atlasGlyphCache = context->contextPriv().getAtlasGlyphCache();
GrTextBlobCache* textBlobCache = context->contextPriv().getTextBlobCache();
if (canCache) {
@@ -152,7 +151,7 @@ void GrAtlasTextContext::drawTextBlob(GrContext* context, GrTextUtils::Target* t
// 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,
+ this->regenerateTextBlob(cacheBlob.get(), atlasGlyphCache,
*context->caps()->shaderCaps(), paint, scalerContextFlags,
viewMatrix, props, blob, x, y, drawFilter);
} else {
@@ -164,7 +163,7 @@ void GrAtlasTextContext::drawTextBlob(GrContext* context, GrTextUtils::Target* t
GrTextBlobCache::BlobGlyphCount(&glyphCount, &runCount, blob);
sk_sp<GrAtlasTextBlob> sanityBlob(textBlobCache->makeBlob(glyphCount, runCount));
sanityBlob->setupKey(key, blurRec, skPaint);
- this->regenerateTextBlob(sanityBlob.get(), glyphCache,
+ this->regenerateTextBlob(sanityBlob.get(), atlasGlyphCache,
*context->caps()->shaderCaps(), paint, scalerContextFlags,
viewMatrix, props, blob, x, y, drawFilter);
GrAtlasTextBlob::AssertEqual(*sanityBlob, *cacheBlob);
@@ -176,17 +175,17 @@ void GrAtlasTextContext::drawTextBlob(GrContext* context, GrTextUtils::Target* t
} else {
cacheBlob = textBlobCache->makeBlob(blob);
}
- this->regenerateTextBlob(cacheBlob.get(), glyphCache,
+ this->regenerateTextBlob(cacheBlob.get(), atlasGlyphCache,
*context->caps()->shaderCaps(), paint, scalerContextFlags,
viewMatrix, props, blob, x, y, drawFilter);
}
- cacheBlob->flush(restrictedAtlasManager, target, props, fDistanceAdjustTable.get(), paint,
+ cacheBlob->flush(atlasGlyphCache, target, props, fDistanceAdjustTable.get(), paint,
clip, viewMatrix, clipBounds, x, y);
}
void GrAtlasTextContext::regenerateTextBlob(GrAtlasTextBlob* cacheBlob,
- GrGlyphCache* glyphCache,
+ GrAtlasGlyphCache* fontCache,
const GrShaderCaps& shaderCaps,
const GrTextUtils::Paint& paint,
SkScalerContextFlags scalerContextFlags,
@@ -212,21 +211,21 @@ void GrAtlasTextContext::regenerateTextBlob(GrAtlasTextBlob* cacheBlob,
if (this->canDrawAsDistanceFields(runPaint, viewMatrix, props, shaderCaps)) {
switch (it.positioning()) {
case SkTextBlob::kDefault_Positioning: {
- this->drawDFText(cacheBlob, run, glyphCache, props, runPaint, scalerContextFlags,
+ this->drawDFText(cacheBlob, run, fontCache, props, runPaint, scalerContextFlags,
viewMatrix, (const char*)it.glyphs(), textLen, x + offset.x(),
y + offset.y());
break;
}
case SkTextBlob::kHorizontal_Positioning: {
SkPoint dfOffset = SkPoint::Make(x, y + offset.y());
- this->drawDFPosText(cacheBlob, run, glyphCache, props, runPaint,
+ this->drawDFPosText(cacheBlob, run, fontCache, 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,
+ this->drawDFPosText(cacheBlob, run, fontCache, props, runPaint,
scalerContextFlags, viewMatrix, (const char*)it.glyphs(),
textLen, it.pos(), 2, dfOffset);
break;
@@ -235,17 +234,17 @@ void GrAtlasTextContext::regenerateTextBlob(GrAtlasTextBlob* cacheBlob,
} else {
switch (it.positioning()) {
case SkTextBlob::kDefault_Positioning:
- DrawBmpText(cacheBlob, run, glyphCache, props, runPaint, scalerContextFlags,
+ DrawBmpText(cacheBlob, run, fontCache, props, runPaint, scalerContextFlags,
viewMatrix, (const char*)it.glyphs(), textLen, x + offset.x(),
y + offset.y());
break;
case SkTextBlob::kHorizontal_Positioning:
- DrawBmpPosText(cacheBlob, run, glyphCache, props, runPaint, scalerContextFlags,
+ DrawBmpPosText(cacheBlob, run, fontCache, 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,
+ DrawBmpPosText(cacheBlob, run, fontCache, props, runPaint, scalerContextFlags,
viewMatrix, (const char*)it.glyphs(), textLen, it.pos(), 2,
SkPoint::Make(x, y));
break;
@@ -256,7 +255,7 @@ void GrAtlasTextContext::regenerateTextBlob(GrAtlasTextBlob* cacheBlob,
inline sk_sp<GrAtlasTextBlob>
GrAtlasTextContext::makeDrawTextBlob(GrTextBlobCache* blobCache,
- GrGlyphCache* glyphCache,
+ GrAtlasGlyphCache* fontCache,
const GrShaderCaps& shaderCaps,
const GrTextUtils::Paint& paint,
SkScalerContextFlags scalerContextFlags,
@@ -273,10 +272,10 @@ GrAtlasTextContext::makeDrawTextBlob(GrTextBlobCache* blobCache,
blob->setRunPaintFlags(0, paint.skPaint().getFlags());
if (this->canDrawAsDistanceFields(paint, viewMatrix, props, shaderCaps)) {
- this->drawDFText(blob.get(), 0, glyphCache, props, paint, scalerContextFlags, viewMatrix,
+ this->drawDFText(blob.get(), 0, fontCache, props, paint, scalerContextFlags, viewMatrix,
text, byteLength, x, y);
} else {
- DrawBmpText(blob.get(), 0, glyphCache, props, paint, scalerContextFlags, viewMatrix, text,
+ DrawBmpText(blob.get(), 0, fontCache, props, paint, scalerContextFlags, viewMatrix, text,
byteLength, x, y);
}
return blob;
@@ -284,7 +283,7 @@ GrAtlasTextContext::makeDrawTextBlob(GrTextBlobCache* blobCache,
inline sk_sp<GrAtlasTextBlob>
GrAtlasTextContext::makeDrawPosTextBlob(GrTextBlobCache* blobCache,
- GrGlyphCache* glyphCache,
+ GrAtlasGlyphCache* fontCache,
const GrShaderCaps& shaderCaps,
const GrTextUtils::Paint& paint,
SkScalerContextFlags scalerContextFlags,
@@ -303,11 +302,11 @@ GrAtlasTextContext::makeDrawPosTextBlob(GrTextBlobCache* blobCache,
blob->setRunPaintFlags(0, paint.skPaint().getFlags());
if (this->canDrawAsDistanceFields(paint, viewMatrix, props, shaderCaps)) {
- this->drawDFPosText(blob.get(), 0, glyphCache, props, paint, scalerContextFlags, viewMatrix,
+ this->drawDFPosText(blob.get(), 0, fontCache, props, paint, scalerContextFlags, viewMatrix,
text, byteLength, pos, scalarsPerPosition, offset);
} else {
- DrawBmpPosText(blob.get(), 0, glyphCache, props, paint, scalerContextFlags, viewMatrix,
- text, byteLength, pos, scalarsPerPosition, offset);
+ DrawBmpPosText(blob.get(), 0, fontCache, props, paint, scalerContextFlags, viewMatrix, text,
+ byteLength, pos, scalarsPerPosition, offset);
}
return blob;
}
@@ -321,18 +320,17 @@ void GrAtlasTextContext::drawText(GrContext* context, GrTextUtils::Target* targe
return;
}
- auto glyphCache = context->contextPriv().getGlyphCache();
- auto restrictedAtlasManager = context->contextPriv().getRestrictedAtlasManager();
+ auto atlasGlyphCache = context->contextPriv().getAtlasGlyphCache();
auto textBlobCache = context->contextPriv().getTextBlobCache();
GrTextUtils::Paint paint(&skPaint, &target->colorSpaceInfo());
sk_sp<GrAtlasTextBlob> blob(
- this->makeDrawTextBlob(textBlobCache, glyphCache,
+ this->makeDrawTextBlob(textBlobCache, atlasGlyphCache,
*context->caps()->shaderCaps(), paint,
ComputeScalerContextFlags(target->colorSpaceInfo()),
viewMatrix, props, text, byteLength, x, y));
if (blob) {
- blob->flush(restrictedAtlasManager, target, props, fDistanceAdjustTable.get(), paint,
+ blob->flush(atlasGlyphCache, target, props, fDistanceAdjustTable.get(), paint,
clip, viewMatrix, regionClipBounds, x, y);
}
}
@@ -348,23 +346,22 @@ void GrAtlasTextContext::drawPosText(GrContext* context, GrTextUtils::Target* ta
return;
}
- auto glyphCache = context->contextPriv().getGlyphCache();
- auto restrictedAtlasManager = context->contextPriv().getRestrictedAtlasManager();
+ auto atlasGlyphCache = context->contextPriv().getAtlasGlyphCache();
auto textBlobCache = context->contextPriv().getTextBlobCache();
sk_sp<GrAtlasTextBlob> blob(this->makeDrawPosTextBlob(
- textBlobCache, glyphCache,
+ textBlobCache, atlasGlyphCache,
*context->caps()->shaderCaps(), paint,
ComputeScalerContextFlags(target->colorSpaceInfo()), viewMatrix, props, text,
byteLength, pos, scalarsPerPosition, offset));
if (blob) {
- blob->flush(restrictedAtlasManager, target, props, fDistanceAdjustTable.get(), paint,
+ blob->flush(atlasGlyphCache, target, props, fDistanceAdjustTable.get(), paint,
clip, viewMatrix, regionClipBounds, offset.fX, offset.fY);
}
}
void GrAtlasTextContext::DrawBmpText(GrAtlasTextBlob* blob, int runIndex,
- GrGlyphCache* glyphCache, const SkSurfaceProps& props,
+ GrAtlasGlyphCache* fontCache, const SkSurfaceProps& props,
const GrTextUtils::Paint& paint,
SkScalerContextFlags scalerContextFlags,
const SkMatrix& viewMatrix, const char text[],
@@ -380,7 +377,7 @@ void GrAtlasTextContext::DrawBmpText(GrAtlasTextBlob* blob, int runIndex,
blob->setHasBitmap();
if (SkDraw::ShouldDrawTextAsPaths(paint, viewMatrix)) {
- DrawBmpTextAsPaths(blob, runIndex, glyphCache, props, paint, scalerContextFlags, viewMatrix,
+ DrawBmpTextAsPaths(blob, runIndex, fontCache, props, paint, scalerContextFlags, viewMatrix,
text, byteLength, x, y);
return;
}
@@ -390,7 +387,7 @@ void GrAtlasTextContext::DrawBmpText(GrAtlasTextBlob* blob, int runIndex,
viewMatrix, paint.skPaint().getTextAlign(), cache,
[&](const SkGlyph& glyph, SkPoint position, SkPoint rounding) {
position += rounding;
- BmpAppendGlyph(blob, runIndex, glyphCache, &currStrike,
+ BmpAppendGlyph(blob, runIndex, fontCache, &currStrike,
glyph, SkScalarFloorToScalar(position.fX),
SkScalarFloorToScalar(position.fY),
paint.filteredPremulColor(), cache,
@@ -401,7 +398,7 @@ void GrAtlasTextContext::DrawBmpText(GrAtlasTextBlob* blob, int runIndex,
}
void GrAtlasTextContext::DrawBmpPosText(GrAtlasTextBlob* blob, int runIndex,
- GrGlyphCache* glyphCache, const SkSurfaceProps& props,
+ GrAtlasGlyphCache* fontCache, const SkSurfaceProps& props,
const GrTextUtils::Paint& paint,
SkScalerContextFlags scalerContextFlags,
const SkMatrix& viewMatrix,
@@ -419,7 +416,7 @@ void GrAtlasTextContext::DrawBmpPosText(GrAtlasTextBlob* blob, int runIndex,
blob->setHasBitmap();
if (SkDraw::ShouldDrawTextAsPaths(paint, viewMatrix)) {
- DrawBmpPosTextAsPaths(blob, runIndex, glyphCache, props, paint, scalerContextFlags,
+ DrawBmpPosTextAsPaths(blob, runIndex, fontCache, props, paint, scalerContextFlags,
viewMatrix, text, byteLength, pos, scalarsPerPosition, offset);
return;
}
@@ -432,7 +429,7 @@ void GrAtlasTextContext::DrawBmpPosText(GrAtlasTextBlob* blob, int runIndex,
scalarsPerPosition, paint.skPaint().getTextAlign(), cache,
[&](const SkGlyph& glyph, SkPoint position, SkPoint rounding) {
position += rounding;
- BmpAppendGlyph(blob, runIndex, glyphCache, &currStrike, glyph,
+ BmpAppendGlyph(blob, runIndex, fontCache, &currStrike, glyph,
SkScalarFloorToScalar(position.fX),
SkScalarFloorToScalar(position.fY),
paint.filteredPremulColor(), cache, SK_Scalar1);
@@ -442,7 +439,7 @@ void GrAtlasTextContext::DrawBmpPosText(GrAtlasTextBlob* blob, int runIndex,
}
void GrAtlasTextContext::DrawBmpTextAsPaths(GrAtlasTextBlob* blob, int runIndex,
- GrGlyphCache* glyphCache,
+ GrAtlasGlyphCache* fontCache,
const SkSurfaceProps& props,
const GrTextUtils::Paint& origPaint,
SkScalerContextFlags scalerContextFlags,
@@ -460,7 +457,7 @@ void GrAtlasTextContext::DrawBmpTextAsPaths(GrAtlasTextBlob* blob, int runIndex,
GrTextUtils::PathTextIter iter(text, byteLength, pathPaint, true);
FallbackTextHelper fallbackTextHelper(viewMatrix, pathPaint.getTextSize(),
- glyphCache->getGlyphSizeLimit(),
+ fontCache->getGlyphSizeLimit(),
iter.getPathScale());
const SkGlyph* iterGlyph;
@@ -477,11 +474,11 @@ void GrAtlasTextContext::DrawBmpTextAsPaths(GrAtlasTextBlob* blob, int runIndex,
lastText = iter.getText();
}
- fallbackTextHelper.drawText(blob, runIndex, glyphCache, props, origPaint, scalerContextFlags);
+ fallbackTextHelper.drawText(blob, runIndex, fontCache, props, origPaint, scalerContextFlags);
}
void GrAtlasTextContext::DrawBmpPosTextAsPaths(GrAtlasTextBlob* blob, int runIndex,
- GrGlyphCache* glyphCache,
+ GrAtlasGlyphCache* fontCache,
const SkSurfaceProps& props,
const GrTextUtils::Paint& origPaint,
SkScalerContextFlags scalerContextFlags,
@@ -500,7 +497,7 @@ void GrAtlasTextContext::DrawBmpPosTextAsPaths(GrAtlasTextBlob* blob, int runInd
SkPaint pathPaint(origPaint);
SkScalar matrixScale = pathPaint.setupForAsPaths();
FallbackTextHelper fallbackTextHelper(viewMatrix, pathPaint.getTextSize(), matrixScale,
- glyphCache->getGlyphSizeLimit());
+ fontCache->getGlyphSizeLimit());
// Temporarily jam in kFill, so we only ever ask for the raw outline from the cache.
pathPaint.setStyle(SkPaint::kFill_Style);
@@ -537,23 +534,23 @@ void GrAtlasTextContext::DrawBmpPosTextAsPaths(GrAtlasTextBlob* blob, int runInd
pos += scalarsPerPosition;
}
- fallbackTextHelper.drawText(blob, runIndex, glyphCache, props, origPaint, scalerContextFlags);
+ fallbackTextHelper.drawText(blob, runIndex, fontCache, props, origPaint, scalerContextFlags);
}
void GrAtlasTextContext::BmpAppendGlyph(GrAtlasTextBlob* blob, int runIndex,
- GrGlyphCache* grGlyphCache, GrAtlasTextStrike** strike,
+ GrAtlasGlyphCache* fontCache, GrAtlasTextStrike** strike,
const SkGlyph& skGlyph, SkScalar sx, SkScalar sy,
- GrColor color, SkGlyphCache* skGlyphCache,
+ GrColor color, SkGlyphCache* glyphCache,
SkScalar textRatio) {
if (!*strike) {
- *strike = grGlyphCache->getStrike(skGlyphCache);
+ *strike = fontCache->getStrike(glyphCache);
}
GrGlyph::PackedID id = GrGlyph::Pack(skGlyph.getGlyphID(),
skGlyph.getSubXFixed(),
skGlyph.getSubYFixed(),
GrGlyph::kCoverage_MaskStyle);
- GrGlyph* glyph = (*strike)->getGlyph(skGlyph, id, skGlyphCache);
+ GrGlyph* glyph = (*strike)->getGlyph(skGlyph, id, glyphCache);
if (!glyph) {
return;
}
@@ -573,7 +570,7 @@ void GrAtlasTextContext::BmpAppendGlyph(GrAtlasTextBlob* blob, int runIndex,
SkRect glyphRect = SkRect::MakeXYWH(sx + dx, sy + dy, width, height);
- blob->appendGlyph(runIndex, glyphRect, color, *strike, glyph, skGlyphCache, skGlyph, sx, sy,
+ blob->appendGlyph(runIndex, glyphRect, color, *strike, glyph, glyphCache, skGlyph, sx, sy,
textRatio, true);
}
@@ -673,7 +670,7 @@ void GrAtlasTextContext::initDistanceFieldPaint(GrAtlasTextBlob* blob,
}
void GrAtlasTextContext::drawDFText(GrAtlasTextBlob* blob, int runIndex,
- GrGlyphCache* glyphCache, const SkSurfaceProps& props,
+ GrAtlasGlyphCache* fontCache, const SkSurfaceProps& props,
const GrTextUtils::Paint& paint,
SkScalerContextFlags scalerContextFlags,
const SkMatrix& viewMatrix, const char text[],
@@ -743,12 +740,12 @@ void GrAtlasTextContext::drawDFText(GrAtlasTextBlob* blob, int runIndex,
y -= alignY;
SkPoint offset = SkPoint::Make(x, y);
- this->drawDFPosText(blob, runIndex, glyphCache, props, paint, scalerContextFlags, viewMatrix,
+ this->drawDFPosText(blob, runIndex, fontCache, props, paint, scalerContextFlags, viewMatrix,
text, byteLength, positions.begin(), 2, offset);
}
void GrAtlasTextContext::drawDFPosText(GrAtlasTextBlob* blob, int runIndex,
- GrGlyphCache* glyphCache, const SkSurfaceProps& props,
+ GrAtlasGlyphCache* fontCache, const SkSurfaceProps& props,
const GrTextUtils::Paint& paint,
SkScalerContextFlags scalerContextFlags,
const SkMatrix& viewMatrix, const char text[],
@@ -774,7 +771,7 @@ void GrAtlasTextContext::drawDFPosText(GrAtlasTextBlob* blob, int runIndex,
FallbackTextHelper fallbackTextHelper(viewMatrix,
paint.skPaint().getTextSize(),
- glyphCache->getGlyphSizeLimit(),
+ fontCache->getGlyphSizeLimit(),
textRatio);
GrAtlasTextStrike* currStrike = nullptr;
@@ -803,7 +800,7 @@ void GrAtlasTextContext::drawDFPosText(GrAtlasTextBlob* blob, int runIndex,
SkFloatToScalar(glyph.fAdvanceY) * alignMul * textRatio;
if (glyph.fMaskFormat != SkMask::kARGB32_Format) {
- DfAppendGlyph(blob, runIndex, glyphCache, &currStrike, glyph, glyphPos.fX,
+ DfAppendGlyph(blob, runIndex, fontCache, &currStrike, glyph, glyphPos.fX,
glyphPos.fY, paint.filteredPremulColor(), cache, textRatio);
} else {
// can't append color glyph to SDF batch, send to fallback
@@ -815,24 +812,25 @@ void GrAtlasTextContext::drawDFPosText(GrAtlasTextBlob* blob, int runIndex,
SkGlyphCache::AttachCache(cache);
- fallbackTextHelper.drawText(blob, runIndex, glyphCache, props, paint, scalerContextFlags);
+ fallbackTextHelper.drawText(blob, runIndex, fontCache, props, paint,
+ scalerContextFlags);
}
// TODO: merge with BmpAppendGlyph
void GrAtlasTextContext::DfAppendGlyph(GrAtlasTextBlob* blob, int runIndex,
- GrGlyphCache* grGlyphCache, GrAtlasTextStrike** strike,
+ GrAtlasGlyphCache* cache, GrAtlasTextStrike** strike,
const SkGlyph& skGlyph, SkScalar sx, SkScalar sy,
- GrColor color, SkGlyphCache* skGlyphCache,
+ GrColor color, SkGlyphCache* glyphCache,
SkScalar textRatio) {
if (!*strike) {
- *strike = grGlyphCache->getStrike(skGlyphCache);
+ *strike = cache->getStrike(glyphCache);
}
GrGlyph::PackedID id = GrGlyph::Pack(skGlyph.getGlyphID(),
skGlyph.getSubXFixed(),
skGlyph.getSubYFixed(),
GrGlyph::kDistance_MaskStyle);
- GrGlyph* glyph = (*strike)->getGlyph(skGlyph, id, skGlyphCache);
+ GrGlyph* glyph = (*strike)->getGlyph(skGlyph, id, glyphCache);
if (!glyph) {
return;
}
@@ -848,7 +846,7 @@ void GrAtlasTextContext::DfAppendGlyph(GrAtlasTextBlob* blob, int runIndex,
height *= textRatio;
SkRect glyphRect = SkRect::MakeXYWH(sx + dx, sy + dy, width, height);
- blob->appendGlyph(runIndex, glyphRect, color, *strike, glyph, skGlyphCache, skGlyph, sx, sy,
+ blob->appendGlyph(runIndex, glyphRect, color, *strike, glyph, glyphCache, skGlyph, sx, sy,
textRatio, false);
}
@@ -873,7 +871,7 @@ void GrAtlasTextContext::FallbackTextHelper::appendText(const SkGlyph& glyph, in
}
void GrAtlasTextContext::FallbackTextHelper::drawText(GrAtlasTextBlob* blob, int runIndex,
- GrGlyphCache* glyphCache,
+ GrAtlasGlyphCache* fontCache,
const SkSurfaceProps& props,
const GrTextUtils::Paint& paint,
SkScalerContextFlags scalerContextFlags) {
@@ -911,7 +909,7 @@ void GrAtlasTextContext::FallbackTextHelper::drawText(GrAtlasTextBlob* blob, int
SkPoint* glyphPos = fFallbackPos.begin();
while (text < stop) {
const SkGlyph& glyph = glyphCacheProc(cache, &text);
- GrAtlasTextContext::BmpAppendGlyph(blob, runIndex, glyphCache, &currStrike, glyph,
+ GrAtlasTextContext::BmpAppendGlyph(blob, runIndex, fontCache, &currStrike, glyph,
glyphPos->fX, glyphPos->fY, textColor,
cache, textRatio);
glyphPos++;
@@ -964,19 +962,18 @@ GR_DRAW_OP_TEST_DEFINE(GrAtlasTextOp) {
SkScalar x = SkIntToScalar(xInt);
SkScalar y = SkIntToScalar(yInt);
- auto glyphCache = context->contextPriv().getGlyphCache();
- auto restrictedAtlasManager = context->contextPriv().getRestrictedAtlasManager();
+ auto atlasGlyphCache = context->contextPriv().getAtlasGlyphCache();
// right now we don't handle textblobs, nor do we handle drawPosText. Since we only intend to
// test the text op with this unit test, that is okay.
sk_sp<GrAtlasTextBlob> blob(gTextContext->makeDrawTextBlob(
- context->contextPriv().getTextBlobCache(), glyphCache,
+ context->contextPriv().getTextBlobCache(), atlasGlyphCache,
*context->caps()->shaderCaps(), utilsPaint,
GrAtlasTextContext::kTextBlobOpScalerContextFlags, viewMatrix, gSurfaceProps, text,
static_cast<size_t>(textLen), x, y));
return blob->test_makeOp(textLen, 0, 0, viewMatrix, x, y, utilsPaint, gSurfaceProps,
- gTextContext->dfAdjustTable(), restrictedAtlasManager,
+ gTextContext->dfAdjustTable(), atlasGlyphCache,
rtc->textTarget());
}
diff --git a/src/gpu/text/GrAtlasTextContext.h b/src/gpu/text/GrAtlasTextContext.h
index 37b7de5357..207dd67206 100644
--- a/src/gpu/text/GrAtlasTextContext.h
+++ b/src/gpu/text/GrAtlasTextContext.h
@@ -74,8 +74,9 @@ private:
}
void appendText(const SkGlyph& glyph, int count, const char* text, SkPoint glyphPos);
- void drawText(GrAtlasTextBlob* blob, int runIndex, GrGlyphCache*, const SkSurfaceProps&,
- const GrTextUtils::Paint&, SkScalerContextFlags);
+ void drawText(GrAtlasTextBlob* blob, int runIndex,
+ GrAtlasGlyphCache* fontCache, const SkSurfaceProps& props,
+ const GrTextUtils::Paint& paint, SkScalerContextFlags scalerContextFlags);
private:
SkTDArray<char> fFallbackTxt;
@@ -95,7 +96,7 @@ private:
// Determines if we need to use fake gamma (and contrast boost):
static SkScalerContextFlags ComputeScalerContextFlags(const GrColorSpaceInfo&);
void regenerateTextBlob(GrAtlasTextBlob* bmp,
- GrGlyphCache*,
+ GrAtlasGlyphCache*,
const GrShaderCaps&,
const GrTextUtils::Paint&,
SkScalerContextFlags scalerContextFlags,
@@ -106,7 +107,7 @@ private:
static bool HasLCD(const SkTextBlob*);
- sk_sp<GrAtlasTextBlob> makeDrawTextBlob(GrTextBlobCache*, GrGlyphCache*,
+ sk_sp<GrAtlasTextBlob> makeDrawTextBlob(GrTextBlobCache*, GrAtlasGlyphCache*,
const GrShaderCaps&,
const GrTextUtils::Paint&,
SkScalerContextFlags scalerContextFlags,
@@ -115,7 +116,7 @@ private:
const char text[], size_t byteLength,
SkScalar x, SkScalar y) const;
- sk_sp<GrAtlasTextBlob> makeDrawPosTextBlob(GrTextBlobCache*, GrGlyphCache*,
+ sk_sp<GrAtlasTextBlob> makeDrawPosTextBlob(GrTextBlobCache*, GrAtlasGlyphCache*,
const GrShaderCaps&,
const GrTextUtils::Paint&,
SkScalerContextFlags scalerContextFlags,
@@ -127,24 +128,24 @@ private:
const SkPoint& offset) const;
// Functions for appending BMP text to GrAtlasTextBlob
- static void DrawBmpText(GrAtlasTextBlob*, int runIndex, GrGlyphCache*,
+ static void DrawBmpText(GrAtlasTextBlob*, int runIndex, GrAtlasGlyphCache*,
const SkSurfaceProps&, const GrTextUtils::Paint& paint,
SkScalerContextFlags scalerContextFlags, const SkMatrix& viewMatrix,
const char text[], size_t byteLength, SkScalar x, SkScalar y);
- static void DrawBmpPosText(GrAtlasTextBlob*, int runIndex, GrGlyphCache*,
+ static void DrawBmpPosText(GrAtlasTextBlob*, int runIndex, GrAtlasGlyphCache*,
const SkSurfaceProps&, const GrTextUtils::Paint& paint,
SkScalerContextFlags scalerContextFlags, const SkMatrix& viewMatrix,
const char text[], size_t byteLength, const SkScalar pos[],
int scalarsPerPosition, const SkPoint& offset);
- static void DrawBmpTextAsPaths(GrAtlasTextBlob*, int runIndex, GrGlyphCache*,
+ static void DrawBmpTextAsPaths(GrAtlasTextBlob*, int runIndex, GrAtlasGlyphCache*,
const SkSurfaceProps&, const GrTextUtils::Paint& paint,
SkScalerContextFlags scalerContextFlags,
const SkMatrix& viewMatrix, const char text[],
size_t byteLength, SkScalar x, SkScalar y);
- static void DrawBmpPosTextAsPaths(GrAtlasTextBlob*, int runIndex, GrGlyphCache*,
+ static void DrawBmpPosTextAsPaths(GrAtlasTextBlob*, int runIndex, GrAtlasGlyphCache*,
const SkSurfaceProps&, const GrTextUtils::Paint& paint,
SkScalerContextFlags scalerContextFlags,
const SkMatrix& viewMatrix,
@@ -156,12 +157,12 @@ private:
bool canDrawAsDistanceFields(const SkPaint& skPaint, const SkMatrix& viewMatrix,
const SkSurfaceProps& props, const GrShaderCaps& caps) const;
- void drawDFText(GrAtlasTextBlob* blob, int runIndex, GrGlyphCache*, const SkSurfaceProps&,
+ void drawDFText(GrAtlasTextBlob* blob, int runIndex, GrAtlasGlyphCache*, const SkSurfaceProps&,
const GrTextUtils::Paint& paint, SkScalerContextFlags scalerContextFlags,
const SkMatrix& viewMatrix, const char text[], size_t byteLength, SkScalar x,
SkScalar y) const;
- void drawDFPosText(GrAtlasTextBlob* blob, int runIndex, GrGlyphCache*,
+ void drawDFPosText(GrAtlasTextBlob* blob, int runIndex, GrAtlasGlyphCache*,
const SkSurfaceProps&, const GrTextUtils::Paint& paint,
SkScalerContextFlags scalerContextFlags,
const SkMatrix& viewMatrix, const char text[],
@@ -173,11 +174,11 @@ private:
SkScalar* textRatio,
const SkMatrix& viewMatrix) const;
- static void BmpAppendGlyph(GrAtlasTextBlob*, int runIndex, GrGlyphCache*,
+ static void BmpAppendGlyph(GrAtlasTextBlob*, int runIndex, GrAtlasGlyphCache*,
GrAtlasTextStrike**, const SkGlyph&, SkScalar sx, SkScalar sy,
GrColor color, SkGlyphCache*, SkScalar textRatio);
- static void DfAppendGlyph(GrAtlasTextBlob*, int runIndex, GrGlyphCache*,
+ static void DfAppendGlyph(GrAtlasTextBlob*, int runIndex, GrAtlasGlyphCache*,
GrAtlasTextStrike**, const SkGlyph&, SkScalar sx, SkScalar sy,
GrColor color, SkGlyphCache* cache, SkScalar textRatio);
diff --git a/src/gpu/text/GrGlyphCache.h b/src/gpu/text/GrGlyphCache.h
deleted file mode 100644
index 169e4b30a5..0000000000
--- a/src/gpu/text/GrGlyphCache.h
+++ /dev/null
@@ -1,148 +0,0 @@
-/*
- * Copyright 2015 Google Inc.
- *
- * Use of this source code is governed by a BSD-style license that can be
- * found in the LICENSE file.
- */
-
-#ifndef GrAtlasGlyphCache_DEFINED
-#define GrAtlasGlyphCache_DEFINED
-
-#include "GrDrawOpAtlas.h"
-#include "GrGlyph.h"
-#include "SkArenaAlloc.h"
-#include "SkGlyphCache.h"
-#include "SkTDynamicHash.h"
-
-class GrGlyphCache;
-class GrAtlasManager;
-class GrGpu;
-
-/**
- * The GrAtlasTextStrike manages a pool of CPU backing memory for GrGlyphs. This backing memory
- * is indexed by a PackedID and SkGlyphCache. The SkGlyphCache is what actually creates the mask.
- * The GrAtlasTextStrike may outlive the generating SkGlyphCache. However, it retains a copy
- * of it's SkDescriptor as a key to access (or regenerate) the SkGlyphCache. GrAtlasTextStrike are
- * created by and owned by a GrGlyphCache.
- */
-class GrAtlasTextStrike : public SkNVRefCnt<GrAtlasTextStrike> {
-public:
- GrAtlasTextStrike(const SkDescriptor& fontScalerKey);
- ~GrAtlasTextStrike();
-
- inline GrGlyph* getGlyph(const SkGlyph& skGlyph, GrGlyph::PackedID packed,
- SkGlyphCache* cache) {
- GrGlyph* glyph = fCache.find(packed);
- if (nullptr == glyph) {
- glyph = this->generateGlyph(skGlyph, packed, cache);
- }
- return glyph;
- }
-
- // This variant of the above function is called by GrAtlasTextOp. At this point, it is possible
- // that the maskformat of the glyph differs from what we expect. In these cases we will just
- // draw a clear square.
- // skbug:4143 crbug:510931
- inline GrGlyph* getGlyph(GrGlyph::PackedID packed,
- GrMaskFormat expectedMaskFormat,
- SkGlyphCache* cache) {
- GrGlyph* glyph = fCache.find(packed);
- if (nullptr == glyph) {
- // We could return this to the caller, but in practice it adds code complexity for
- // potentially little benefit(ie, if the glyph is not in our font cache, then its not
- // in the atlas and we're going to be doing a texture upload anyways).
- const SkGlyph& skGlyph = GrToSkGlyph(cache, packed);
- glyph = this->generateGlyph(skGlyph, packed, cache);
- glyph->fMaskFormat = expectedMaskFormat;
- }
- return glyph;
- }
-
- // returns true if glyph successfully added to texture atlas, false otherwise. If the glyph's
- // mask format has changed, then addGlyphToAtlas will draw a clear box. This will almost never
- // happen.
- // TODO we can handle some of these cases if we really want to, but the long term solution is to
- // get the actual glyph image itself when we get the glyph metrics.
- bool addGlyphToAtlas(GrResourceProvider*, GrDeferredUploadTarget*, GrGlyphCache*,
- GrAtlasManager*, GrGlyph*,
- SkGlyphCache*, GrMaskFormat expectedMaskFormat);
-
- // testing
- int countGlyphs() const { return fCache.count(); }
-
- // remove any references to this plot
- void removeID(GrDrawOpAtlas::AtlasID);
-
- // If a TextStrike is abandoned by the cache, then the caller must get a new strike
- bool isAbandoned() const { return fIsAbandoned; }
-
- static const SkDescriptor& GetKey(const GrAtlasTextStrike& ts) {
- return *ts.fFontScalerKey.getDesc();
- }
-
- static uint32_t Hash(const SkDescriptor& desc) { return desc.getChecksum(); }
-
-private:
- SkTDynamicHash<GrGlyph, GrGlyph::PackedID> fCache;
- SkAutoDescriptor fFontScalerKey;
- SkArenaAlloc fPool{512};
-
- int fAtlasedGlyphs;
- bool fIsAbandoned;
-
- static const SkGlyph& GrToSkGlyph(SkGlyphCache* cache, GrGlyph::PackedID id) {
- return cache->getGlyphIDMetrics(GrGlyph::UnpackID(id),
- GrGlyph::UnpackFixedX(id),
- GrGlyph::UnpackFixedY(id));
- }
-
- GrGlyph* generateGlyph(const SkGlyph&, GrGlyph::PackedID, SkGlyphCache*);
-
- friend class GrGlyphCache;
-};
-
-/**
- * GrGlyphCache manages strikes which are indexed by a SkGlyphCache. These strikes can then be
- * used to generate individual Glyph Masks.
- */
-class GrGlyphCache {
-public:
- GrGlyphCache();
- ~GrGlyphCache();
-
- void setGlyphSizeLimit(SkScalar sizeLimit) { fGlyphSizeLimit = sizeLimit; }
- SkScalar getGlyphSizeLimit() const { return fGlyphSizeLimit; }
-
- void setStrikeToPreserve(GrAtlasTextStrike* strike) { fPreserveStrike = strike; }
-
- // The user of the cache may hold a long-lived ref to the returned strike. However, actions by
- // another client of the cache may cause the strike to be purged while it is still reffed.
- // Therefore, the caller must check GrAtlasTextStrike::isAbandoned() if there are other
- // interactions with the cache since the strike was received.
- inline GrAtlasTextStrike* getStrike(const SkGlyphCache* cache) {
- GrAtlasTextStrike* strike = fCache.find(cache->getDescriptor());
- if (nullptr == strike) {
- strike = this->generateStrike(cache);
- }
- return strike;
- }
-
- void freeAll();
-
- static void HandleEviction(GrDrawOpAtlas::AtlasID, void*);
-
-private:
- GrAtlasTextStrike* generateStrike(const SkGlyphCache* cache) {
- GrAtlasTextStrike* strike = new GrAtlasTextStrike(cache->getDescriptor());
- fCache.add(strike);
- return strike;
- }
-
- using StrikeHash = SkTDynamicHash<GrAtlasTextStrike, SkDescriptor>;
-
- StrikeHash fCache;
- GrAtlasTextStrike* fPreserveStrike;
- SkScalar fGlyphSizeLimit;
-};
-
-#endif
diff --git a/src/gpu/text/GrTextUtils.h b/src/gpu/text/GrTextUtils.h
index 69421c2474..5fe38fe773 100644
--- a/src/gpu/text/GrTextUtils.h
+++ b/src/gpu/text/GrTextUtils.h
@@ -16,13 +16,13 @@
#include "SkTextToPathIter.h"
#include "SkTLazy.h"
+class GrAtlasGlyphCache;
class GrAtlasTextBlob;
class GrAtlasTextOp;
class GrAtlasTextStrike;
class GrClip;
class GrColorSpaceXform;
class GrContext;
-class GrGlyphCache;
class GrPaint;
class GrShaderCaps;
class SkColorSpace;