Convert the CPU mask case to use prepareForDrawing

Change-Id: I3a36084544e12730f4815dbf5b6c78a1cd719f1b
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/207761
Reviewed-by: Ben Wagner <bungeman@google.com>
Commit-Queue: Herb Derby <herb@google.com>
This commit is contained in:
Herb Derby 2019-04-11 15:22:38 -04:00 committed by Skia Commit-Bot
parent 81fd86c1ca
commit c48879ed40
3 changed files with 41 additions and 36 deletions

View File

@ -20,6 +20,22 @@ void SkGlyph::toMask(SkMask* mask) const {
mask->fFormat = static_cast<SkMask::Format>(fMaskFormat); mask->fFormat = static_cast<SkMask::Format>(fMaskFormat);
} }
SkMask SkGlyph::mask(SkPoint position) const {
// findImage had to be called.
SkASSERT(fImage != nullptr);
// getMetrics had to be called.
SkASSERT(fMaskFormat != MASK_FORMAT_UNKNOWN);
SkMask mask;
mask.fImage = (uint8_t*)fImage;
mask.fBounds.set(fLeft, fTop, fLeft + fWidth, fTop + fHeight);
mask.fBounds.offset(SkScalarFloorToInt(position.x()), SkScalarFloorToInt(position.y()));
mask.fRowBytes = this->rowBytes();
mask.fFormat = static_cast<SkMask::Format>(fMaskFormat);
return mask;
}
void SkGlyph::zeroMetrics() { void SkGlyph::zeroMetrics() {
fAdvanceX = 0; fAdvanceX = 0;
fAdvanceY = 0; fAdvanceY = 0;
@ -119,4 +135,3 @@ SkPath* SkGlyph::addPath(SkScalerContext* scalerContext, SkArenaAlloc* alloc) {
} }
return this->path(); return this->path();
} }

View File

@ -152,6 +152,8 @@ public:
void toMask(SkMask* mask) const; void toMask(SkMask* mask) const;
SkMask mask(SkPoint position) const;
SkPath* addPath(SkScalerContext*, SkArenaAlloc*); SkPath* addPath(SkScalerContext*, SkArenaAlloc*);
SkPath* path() const { SkPath* path() const {

View File

@ -138,27 +138,6 @@ static bool check_glyph_position(SkPoint position) {
lt(position.fY, INT_MIN - (INT16_MIN + 0 /*UINT16_MIN*/))); lt(position.fY, INT_MIN - (INT16_MIN + 0 /*UINT16_MIN*/)));
} }
static SkMask create_mask(const SkGlyph& glyph, SkPoint position, const void* image) {
SkMask mask;
int left = SkScalarFloorToInt(position.fX);
int top = SkScalarFloorToInt(position.fY);
left += glyph.fLeft;
top += glyph.fTop;
int right = left + glyph.fWidth;
int bottom = top + glyph.fHeight;
mask.fBounds.set(left, top, right, bottom);
SkASSERT(!mask.fBounds.isEmpty());
mask.fImage = (uint8_t*)image;
mask.fRowBytes = glyph.rowBytes();
mask.fFormat = static_cast<SkMask::Format>(glyph.fMaskFormat);
return mask;
}
void SkGlyphRunListPainter::drawForBitmapDevice( void SkGlyphRunListPainter::drawForBitmapDevice(
const SkGlyphRunList& glyphRunList, const SkMatrix& deviceMatrix, const SkGlyphRunList& glyphRunList, const SkMatrix& deviceMatrix,
const BitmapDevicePainter* bitmapDevice) { const BitmapDevicePainter* bitmapDevice) {
@ -216,30 +195,39 @@ void SkGlyphRunListPainter::drawForBitmapDevice(
SkSpan<const SkPathPos>{pathsAndPositions.begin(), pathsAndPositions.size()}, SkSpan<const SkPathPos>{pathsAndPositions.begin(), pathsAndPositions.size()},
textScale, pathPaint); textScale, pathPaint);
} else { } else {
auto cache = SkStrikeCache::FindOrCreateStrikeExclusive( SkAutoDescriptor ad;
runFont, runPaint, props, SkScalerContextEffects effects;
fScalerContextFlags, deviceMatrix);
SkScalerContext::CreateDescriptorAndEffectsUsingPaint(
runFont, runPaint, props, fScalerContextFlags, deviceMatrix, &ad,
&effects);
SkTypeface* typeface = runFont.getTypefaceOrDefault();
SkScopedStrike strike =
fStrikeCache->findOrCreateScopedStrike(*ad.getDesc(), effects, *typeface);
// Add rounding and origin. // Add rounding and origin.
SkMatrix matrix = deviceMatrix; SkMatrix matrix = deviceMatrix;
matrix.preTranslate(origin.x(), origin.y()); matrix.preTranslate(origin.x(), origin.y());
SkPoint rounding = cache->rounding(); SkPoint rounding = strike->rounding();
matrix.postTranslate(rounding.x(), rounding.y()); matrix.postTranslate(rounding.x(), rounding.y());
matrix.mapPoints(fPositions, glyphRun.positions().data(), runSize); matrix.mapPoints(fPositions, glyphRun.positions().data(), runSize);
SkSpan<const SkGlyphPos> glyphPosSpan = strike->prepareForDrawing(
glyphRun.glyphsIDs().data(), fPositions, glyphRun.runSize(),
std::numeric_limits<int>::max(), fGlyphPos);
SkTDArray<SkMask> masks; SkTDArray<SkMask> masks;
masks.setReserve(runSize); masks.setReserve(glyphPosSpan.size());
const SkPoint* positionCursor = fPositions;
for (auto glyphID : glyphRun.glyphsIDs()) { for (const SkGlyphPos& glyphPos : glyphPosSpan) {
auto position = *positionCursor++; const SkGlyph& glyph = *glyphPos.glyph;
if (check_glyph_position(position)) { SkPoint position = glyphPos.position;
const SkGlyph& glyph = cache->getGlyphMetrics(glyphID, position); if (check_glyph_position(position) && !glyph.isEmpty()) {
const void* image; masks.push_back(glyph.mask(position));
if (!glyph.isEmpty() && (image = cache->findImage(glyph))) {
masks.push_back(create_mask(glyph, position, image));
}
} }
} }
bitmapDevice->paintMasks(SkSpan<const SkMask>{masks.begin(), masks.size()}, runPaint); bitmapDevice->paintMasks(SkSpan<const SkMask>{masks.begin(), masks.size()}, runPaint);
} }
} }