| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright 2014 Google Inc. | 2 * Copyright 2014 Google Inc. |
| 3 * | 3 * |
| 4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
| 5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
| 6 */ | 6 */ |
| 7 | 7 |
| 8 #include "GrStencilAndCoverTextContext.h" | 8 #include "GrStencilAndCoverTextContext.h" |
| 9 #include "GrAtlasTextContext.h" | 9 #include "GrAtlasTextContext.h" |
| 10 #include "GrContext.h" | 10 #include "GrContext.h" |
| (...skipping 217 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 228 GrPipelineBuilder pipelineBuilder(paint, dc->accessRenderTarget(), clip); | 228 GrPipelineBuilder pipelineBuilder(paint, dc->accessRenderTarget(), clip); |
| 229 | 229 |
| 230 TextBlob::Iter iter(blob); | 230 TextBlob::Iter iter(blob); |
| 231 for (TextRun* run = iter.get(); run; run = iter.next()) { | 231 for (TextRun* run = iter.get(); run; run = iter.next()) { |
| 232 run->draw(context, dc, &pipelineBuilder, paint.getColor(), viewMatrix, p
rops, x, y, | 232 run->draw(context, dc, &pipelineBuilder, paint.getColor(), viewMatrix, p
rops, x, y, |
| 233 clipBounds, fFallbackTextContext, skPaint); | 233 clipBounds, fFallbackTextContext, skPaint); |
| 234 run->releaseGlyphCache(); | 234 run->releaseGlyphCache(); |
| 235 } | 235 } |
| 236 } | 236 } |
| 237 | 237 |
| 238 static inline int style_key_cnt(const GrStyle& style) { |
| 239 int cnt = GrStyle::KeySize(style, GrStyle::Apply::kPathEffectAndStrokeRec); |
| 240 // We should be able to make a key because we filtered out arbitrary path ef
fects. |
| 241 SkASSERT(cnt > 0); |
| 242 return cnt; |
| 243 } |
| 244 |
| 245 static inline void write_style_key(uint32_t* dst, const GrStyle& style) { |
| 246 // Pass 1 for the scale since the GPU will apply the style not GrStyle::appl
yToPath(). |
| 247 GrStyle::WriteKey(dst, style, GrStyle::Apply::kPathEffectAndStrokeRec, SK_Sc
alar1); |
| 248 } |
| 249 |
| 238 const GrStencilAndCoverTextContext::TextBlob& | 250 const GrStencilAndCoverTextContext::TextBlob& |
| 239 GrStencilAndCoverTextContext::findOrCreateTextBlob(const SkTextBlob* skBlob, | 251 GrStencilAndCoverTextContext::findOrCreateTextBlob(const SkTextBlob* skBlob, |
| 240 const SkPaint& skPaint) { | 252 const SkPaint& skPaint) { |
| 241 // The font-related parameters are baked into the text blob and will overrid
e this skPaint, so | 253 // The font-related parameters are baked into the text blob and will overrid
e this skPaint, so |
| 242 // the only remaining properties that can affect a TextBlob are the ones rel
ated to stroke. | 254 // the only remaining properties that can affect a TextBlob are the ones rel
ated to stroke. |
| 243 if (SkPaint::kFill_Style == skPaint.getStyle()) { // Fast path. | 255 if (SkPaint::kFill_Style == skPaint.getStyle()) { // Fast path. |
| 244 if (TextBlob** found = fBlobIdCache.find(skBlob->uniqueID())) { | 256 if (TextBlob** found = fBlobIdCache.find(skBlob->uniqueID())) { |
| 245 fLRUList.remove(*found); | 257 fLRUList.remove(*found); |
| 246 fLRUList.addToTail(*found); | 258 fLRUList.addToTail(*found); |
| 247 return **found; | 259 return **found; |
| 248 } | 260 } |
| 249 TextBlob* blob = new TextBlob(skBlob->uniqueID(), skBlob, skPaint); | 261 TextBlob* blob = new TextBlob(skBlob->uniqueID(), skBlob, skPaint); |
| 250 this->purgeToFit(*blob); | 262 this->purgeToFit(*blob); |
| 251 fBlobIdCache.set(skBlob->uniqueID(), blob); | 263 fBlobIdCache.set(skBlob->uniqueID(), blob); |
| 252 fLRUList.addToTail(blob); | 264 fLRUList.addToTail(blob); |
| 253 fCacheSize += blob->cpuMemorySize(); | 265 fCacheSize += blob->cpuMemorySize(); |
| 254 return *blob; | 266 return *blob; |
| 255 } else { | 267 } else { |
| 256 GrStrokeInfo stroke(skPaint); | 268 GrStyle style(skPaint); |
| 257 SkSTArray<4, uint32_t, true> key; | 269 SkSTArray<4, uint32_t, true> key; |
| 258 key.reset(1 + stroke.computeUniqueKeyFragmentData32Cnt()); | 270 key.reset(1 + style_key_cnt(style)); |
| 259 key[0] = skBlob->uniqueID(); | 271 key[0] = skBlob->uniqueID(); |
| 260 stroke.asUniqueKeyFragment(&key[1]); | 272 write_style_key(&key[1], style); |
| 261 if (TextBlob** found = fBlobKeyCache.find(key)) { | 273 if (TextBlob** found = fBlobKeyCache.find(key)) { |
| 262 fLRUList.remove(*found); | 274 fLRUList.remove(*found); |
| 263 fLRUList.addToTail(*found); | 275 fLRUList.addToTail(*found); |
| 264 return **found; | 276 return **found; |
| 265 } | 277 } |
| 266 TextBlob* blob = new TextBlob(key, skBlob, skPaint); | 278 TextBlob* blob = new TextBlob(key, skBlob, skPaint); |
| 267 this->purgeToFit(*blob); | 279 this->purgeToFit(*blob); |
| 268 fBlobKeyCache.set(blob); | 280 fBlobKeyCache.set(blob); |
| 269 fLRUList.addToTail(blob); | 281 fLRUList.addToTail(blob); |
| 270 fCacheSize += blob->cpuMemorySize(); | 282 fCacheSize += blob->cpuMemorySize(); |
| (...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 346 SkPaint fFont; | 358 SkPaint fFont; |
| 347 int fBuffIdx; | 359 int fBuffIdx; |
| 348 int fCount; | 360 int fCount; |
| 349 uint16_t fGlyphIds[kWriteBufferSize]; | 361 uint16_t fGlyphIds[kWriteBufferSize]; |
| 350 SkPoint fPositions[kWriteBufferSize]; | 362 SkPoint fPositions[kWriteBufferSize]; |
| 351 }; | 363 }; |
| 352 | 364 |
| 353 ////////////////////////////////////////////////////////////////////////////////
//////////////////// | 365 ////////////////////////////////////////////////////////////////////////////////
//////////////////// |
| 354 | 366 |
| 355 GrStencilAndCoverTextContext::TextRun::TextRun(const SkPaint& fontAndStroke) | 367 GrStencilAndCoverTextContext::TextRun::TextRun(const SkPaint& fontAndStroke) |
| 356 : fStroke(fontAndStroke), | 368 : fStyle(fontAndStroke), |
| 357 fFont(fontAndStroke), | 369 fFont(fontAndStroke), |
| 358 fTotalGlyphCount(0), | 370 fTotalGlyphCount(0), |
| 359 fFallbackGlyphCount(0), | 371 fFallbackGlyphCount(0), |
| 360 fDetachedGlyphCache(nullptr), | 372 fDetachedGlyphCache(nullptr), |
| 361 fLastDrawnGlyphsID(SK_InvalidUniqueID) { | 373 fLastDrawnGlyphsID(SK_InvalidUniqueID) { |
| 362 SkASSERT(fFont.getTextSize() > 0); | 374 SkASSERT(fFont.getTextSize() > 0); |
| 363 SkASSERT(!fStroke.isHairlineStyle()); // Hairlines are not supported. | 375 SkASSERT(!fStyle.hasNonDashPathEffect()); // Arbitrary path effects not supp
orted. |
| 376 SkASSERT(!fStyle.isSimpleHairline()); // Hairlines are not supported. |
| 364 | 377 |
| 365 // Setting to "fill" ensures that no strokes get baked into font outlines. (
We use the GPU path | 378 // Setting to "fill" ensures that no strokes get baked into font outlines. (
We use the GPU path |
| 366 // rendering API for stroking). | 379 // rendering API for stroking). |
| 367 fFont.setStyle(SkPaint::kFill_Style); | 380 fFont.setStyle(SkPaint::kFill_Style); |
| 368 | 381 |
| 369 if (fFont.isFakeBoldText() && SkStrokeRec::kStroke_Style != fStroke.getStyle
()) { | 382 if (fFont.isFakeBoldText() && fStyle.isSimpleFill()) { |
| 383 const SkStrokeRec& stroke = fStyle.strokeRec(); |
| 370 // Instead of letting fake bold get baked into the glyph outlines, do it
with GPU stroke. | 384 // Instead of letting fake bold get baked into the glyph outlines, do it
with GPU stroke. |
| 371 SkScalar fakeBoldScale = SkScalarInterpFunc(fFont.getTextSize(), | 385 SkScalar fakeBoldScale = SkScalarInterpFunc(fFont.getTextSize(), |
| 372 kStdFakeBoldInterpKeys, | 386 kStdFakeBoldInterpKeys, |
| 373 kStdFakeBoldInterpValues, | 387 kStdFakeBoldInterpValues, |
| 374 kStdFakeBoldInterpLength); | 388 kStdFakeBoldInterpLength); |
| 375 SkScalar extra = SkScalarMul(fFont.getTextSize(), fakeBoldScale); | 389 SkScalar extra = SkScalarMul(fFont.getTextSize(), fakeBoldScale); |
| 376 fStroke.setStrokeStyle(fStroke.needToApply() ? fStroke.getWidth() + extr
a : extra, | |
| 377 true /*strokeAndFill*/); | |
| 378 | 390 |
| 391 SkStrokeRec strokeRec(SkStrokeRec::kFill_InitStyle); |
| 392 strokeRec.setStrokeStyle(stroke.needToApply() ? stroke.getWidth() + extr
a : extra, |
| 393 true /*strokeAndFill*/); |
| 394 fStyle = GrStyle(strokeRec, fStyle.pathEffect()); |
| 379 fFont.setFakeBoldText(false); | 395 fFont.setFakeBoldText(false); |
| 380 } | 396 } |
| 381 | 397 |
| 382 if (!fFont.getPathEffect() && !fStroke.isDashed()) { | 398 if (!fFont.getPathEffect() && !fStyle.isDashed()) { |
| 399 const SkStrokeRec& stroke = fStyle.strokeRec(); |
| 383 // We can draw the glyphs from canonically sized paths. | 400 // We can draw the glyphs from canonically sized paths. |
| 384 fTextRatio = fFont.getTextSize() / SkPaint::kCanonicalTextSizeForPaths; | 401 fTextRatio = fFont.getTextSize() / SkPaint::kCanonicalTextSizeForPaths; |
| 385 fTextInverseRatio = SkPaint::kCanonicalTextSizeForPaths / fFont.getTextS
ize(); | 402 fTextInverseRatio = SkPaint::kCanonicalTextSizeForPaths / fFont.getTextS
ize(); |
| 386 | 403 |
| 387 // Compensate for the glyphs being scaled by fTextRatio. | 404 // Compensate for the glyphs being scaled by fTextRatio. |
| 388 if (!fStroke.isFillStyle()) { | 405 if (!fStyle.isSimpleFill()) { |
| 389 fStroke.setStrokeStyle(fStroke.getWidth() / fTextRatio, | 406 SkStrokeRec strokeRec(SkStrokeRec::kFill_InitStyle); |
| 390 SkStrokeRec::kStrokeAndFill_Style == fStroke.
getStyle()); | 407 strokeRec.setStrokeStyle(stroke.getWidth() / fTextRatio, |
| 408 SkStrokeRec::kStrokeAndFill_Style == stroke
.getStyle()); |
| 409 fStyle = GrStyle(strokeRec, fStyle.pathEffect()); |
| 391 } | 410 } |
| 392 | 411 |
| 393 fFont.setLinearText(true); | 412 fFont.setLinearText(true); |
| 394 fFont.setLCDRenderText(false); | 413 fFont.setLCDRenderText(false); |
| 395 fFont.setAutohinted(false); | 414 fFont.setAutohinted(false); |
| 396 fFont.setHinting(SkPaint::kNo_Hinting); | 415 fFont.setHinting(SkPaint::kNo_Hinting); |
| 397 fFont.setSubpixelText(true); | 416 fFont.setSubpixelText(true); |
| 398 fFont.setTextSize(SkIntToScalar(SkPaint::kCanonicalTextSizeForPaths)); | 417 fFont.setTextSize(SkIntToScalar(SkPaint::kCanonicalTextSizeForPaths)); |
| 399 | 418 |
| 400 fUsingRawGlyphPaths = SK_Scalar1 == fFont.getTextScaleX() && | 419 fUsingRawGlyphPaths = SK_Scalar1 == fFont.getTextScaleX() && |
| 401 0 == fFont.getTextSkewX() && | 420 0 == fFont.getTextSkewX() && |
| 402 !fFont.isFakeBoldText() && | 421 !fFont.isFakeBoldText() && |
| 403 !fFont.isVerticalText(); | 422 !fFont.isVerticalText(); |
| 404 } else { | 423 } else { |
| 405 fTextRatio = fTextInverseRatio = 1.0f; | 424 fTextRatio = fTextInverseRatio = 1.0f; |
| 406 fUsingRawGlyphPaths = false; | 425 fUsingRawGlyphPaths = false; |
| 407 } | 426 } |
| 408 | 427 |
| 409 // Generate the key that will be used to cache the GPU glyph path objects. | 428 // Generate the key that will be used to cache the GPU glyph path objects. |
| 410 if (fUsingRawGlyphPaths && fStroke.isFillStyle()) { | 429 if (fUsingRawGlyphPaths && fStyle.isSimpleFill()) { |
| 411 static const GrUniqueKey::Domain kRawFillPathGlyphDomain = GrUniqueKey::
GenerateDomain(); | 430 static const GrUniqueKey::Domain kRawFillPathGlyphDomain = GrUniqueKey::
GenerateDomain(); |
| 412 | 431 |
| 413 const SkTypeface* typeface = fFont.getTypeface(); | 432 const SkTypeface* typeface = fFont.getTypeface(); |
| 414 GrUniqueKey::Builder builder(&fGlyphPathsKey, kRawFillPathGlyphDomain, 1
); | 433 GrUniqueKey::Builder builder(&fGlyphPathsKey, kRawFillPathGlyphDomain, 1
); |
| 415 reinterpret_cast<uint32_t&>(builder[0]) = typeface ? typeface->uniqueID(
) : 0; | 434 reinterpret_cast<uint32_t&>(builder[0]) = typeface ? typeface->uniqueID(
) : 0; |
| 416 } else { | 435 } else { |
| 417 static const GrUniqueKey::Domain kPathGlyphDomain = GrUniqueKey::Generat
eDomain(); | 436 static const GrUniqueKey::Domain kPathGlyphDomain = GrUniqueKey::Generat
eDomain(); |
| 418 | 437 |
| 419 int strokeDataCount = fStroke.computeUniqueKeyFragmentData32Cnt(); | 438 int styleDataCount = GrStyle::KeySize(fStyle, GrStyle::Apply::kPathEffec
tAndStrokeRec); |
| 439 // Key should be valid since we opted out of drawing arbitrary path effe
cts. |
| 440 SkASSERT(styleDataCount >= 0); |
| 420 if (fUsingRawGlyphPaths) { | 441 if (fUsingRawGlyphPaths) { |
| 421 const SkTypeface* typeface = fFont.getTypeface(); | 442 const SkTypeface* typeface = fFont.getTypeface(); |
| 422 GrUniqueKey::Builder builder(&fGlyphPathsKey, kPathGlyphDomain, 2 +
strokeDataCount); | 443 GrUniqueKey::Builder builder(&fGlyphPathsKey, kPathGlyphDomain, 2 +
styleDataCount); |
| 423 reinterpret_cast<uint32_t&>(builder[0]) = typeface ? typeface->uniqu
eID() : 0; | 444 reinterpret_cast<uint32_t&>(builder[0]) = typeface ? typeface->uniqu
eID() : 0; |
| 424 reinterpret_cast<uint32_t&>(builder[1]) = strokeDataCount; | 445 reinterpret_cast<uint32_t&>(builder[1]) = styleDataCount; |
| 425 fStroke.asUniqueKeyFragment(&builder[2]); | 446 if (styleDataCount) { |
| 447 write_style_key(&builder[2], fStyle); |
| 448 } |
| 426 } else { | 449 } else { |
| 427 SkGlyphCache* glyphCache = this->getGlyphCache(); | 450 SkGlyphCache* glyphCache = this->getGlyphCache(); |
| 428 const SkTypeface* typeface = glyphCache->getScalerContext()->getType
face(); | 451 const SkTypeface* typeface = glyphCache->getScalerContext()->getType
face(); |
| 429 const SkDescriptor* desc = &glyphCache->getDescriptor(); | 452 const SkDescriptor* desc = &glyphCache->getDescriptor(); |
| 430 int descDataCount = (desc->getLength() + 3) / 4; | 453 int descDataCount = (desc->getLength() + 3) / 4; |
| 431 GrUniqueKey::Builder builder(&fGlyphPathsKey, kPathGlyphDomain, | 454 GrUniqueKey::Builder builder(&fGlyphPathsKey, kPathGlyphDomain, |
| 432 2 + strokeDataCount + descDataCount); | 455 2 + styleDataCount + descDataCount); |
| 433 reinterpret_cast<uint32_t&>(builder[0]) = typeface ? typeface->uniqu
eID() : 0; | 456 reinterpret_cast<uint32_t&>(builder[0]) = typeface ? typeface->uniqu
eID() : 0; |
| 434 reinterpret_cast<uint32_t&>(builder[1]) = strokeDataCount | (descDat
aCount << 16); | 457 reinterpret_cast<uint32_t&>(builder[1]) = styleDataCount | (descData
Count << 16); |
| 435 fStroke.asUniqueKeyFragment(&builder[2]); | 458 if (styleDataCount) { |
| 436 memcpy(&builder[2 + strokeDataCount], desc, desc->getLength()); | 459 write_style_key(&builder[2], fStyle); |
| 460 } |
| 461 memcpy(&builder[2 + styleDataCount], desc, desc->getLength()); |
| 437 } | 462 } |
| 438 } | 463 } |
| 439 } | 464 } |
| 440 | 465 |
| 441 GrStencilAndCoverTextContext::TextRun::~TextRun() { | 466 GrStencilAndCoverTextContext::TextRun::~TextRun() { |
| 442 this->releaseGlyphCache(); | 467 this->releaseGlyphCache(); |
| 443 } | 468 } |
| 444 | 469 |
| 445 void GrStencilAndCoverTextContext::TextRun::setText(const char text[], size_t by
teLength, | 470 void GrStencilAndCoverTextContext::TextRun::setText(const char text[], size_t by
teLength, |
| 446 SkScalar x, SkScalar y) { | 471 SkScalar x, SkScalar y) { |
| (...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 534 fFallbackTextBlob.reset(fallback.buildIfNeeded(&fFallbackGlyphCount)); | 559 fFallbackTextBlob.reset(fallback.buildIfNeeded(&fFallbackGlyphCount)); |
| 535 } | 560 } |
| 536 | 561 |
| 537 GrPathRange* GrStencilAndCoverTextContext::TextRun::createGlyphs(GrContext* ctx)
const { | 562 GrPathRange* GrStencilAndCoverTextContext::TextRun::createGlyphs(GrContext* ctx)
const { |
| 538 GrPathRange* glyphs = static_cast<GrPathRange*>( | 563 GrPathRange* glyphs = static_cast<GrPathRange*>( |
| 539 ctx->resourceProvider()->findAndRefResourceByUniqueKey(fGlyphPathsKe
y)); | 564 ctx->resourceProvider()->findAndRefResourceByUniqueKey(fGlyphPathsKe
y)); |
| 540 if (nullptr == glyphs) { | 565 if (nullptr == glyphs) { |
| 541 if (fUsingRawGlyphPaths) { | 566 if (fUsingRawGlyphPaths) { |
| 542 SkScalerContextEffects noeffects; | 567 SkScalerContextEffects noeffects; |
| 543 glyphs = ctx->resourceProvider()->createGlyphs(fFont.getTypeface(),
noeffects, | 568 glyphs = ctx->resourceProvider()->createGlyphs(fFont.getTypeface(),
noeffects, |
| 544 nullptr, fStroke); | 569 nullptr, fStyle); |
| 545 } else { | 570 } else { |
| 546 SkGlyphCache* cache = this->getGlyphCache(); | 571 SkGlyphCache* cache = this->getGlyphCache(); |
| 547 glyphs = ctx->resourceProvider()->createGlyphs(cache->getScalerConte
xt()->getTypeface(), | 572 glyphs = ctx->resourceProvider()->createGlyphs(cache->getScalerConte
xt()->getTypeface(), |
| 548 cache->getScalerConte
xt()->getEffects(), | 573 cache->getScalerConte
xt()->getEffects(), |
| 549 &cache->getDescriptor
(), | 574 &cache->getDescriptor
(), |
| 550 fStroke); | 575 fStyle); |
| 551 } | 576 } |
| 552 ctx->resourceProvider()->assignUniqueKeyToResource(fGlyphPathsKey, glyph
s); | 577 ctx->resourceProvider()->assignUniqueKeyToResource(fGlyphPathsKey, glyph
s); |
| 553 } | 578 } |
| 554 return glyphs; | 579 return glyphs; |
| 555 } | 580 } |
| 556 | 581 |
| 557 inline void GrStencilAndCoverTextContext::TextRun::appendGlyph(const SkGlyph& gl
yph, | 582 inline void GrStencilAndCoverTextContext::TextRun::appendGlyph(const SkGlyph& gl
yph, |
| 558 const SkPoint& po
s, | 583 const SkPoint& po
s, |
| 559 FallbackBlobBuild
er* fallback) { | 584 FallbackBlobBuild
er* fallback) { |
| 560 // Stick the glyphs we can't draw into the fallback text blob. | 585 // Stick the glyphs we can't draw into the fallback text blob. |
| (...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 614 GrDrawPathRangeBatch::Create(viewMatrix, fTextRatio, fTextInverseRat
io * x, | 639 GrDrawPathRangeBatch::Create(viewMatrix, fTextRatio, fTextInverseRat
io * x, |
| 615 fTextInverseRatio * y, color, | 640 fTextInverseRatio * y, color, |
| 616 GrPathRendering::kWinding_FillType, gly
phs, fInstanceData, | 641 GrPathRendering::kWinding_FillType, gly
phs, fInstanceData, |
| 617 bounds)); | 642 bounds)); |
| 618 | 643 |
| 619 dc->drawPathBatch(*pipelineBuilder, batch); | 644 dc->drawPathBatch(*pipelineBuilder, batch); |
| 620 } | 645 } |
| 621 | 646 |
| 622 if (fFallbackTextBlob) { | 647 if (fFallbackTextBlob) { |
| 623 SkPaint fallbackSkPaint(originalSkPaint); | 648 SkPaint fallbackSkPaint(originalSkPaint); |
| 624 fStroke.applyToPaint(&fallbackSkPaint); | 649 fStyle.strokeRec().applyToPaint(&fallbackSkPaint); |
| 625 if (!fStroke.isFillStyle()) { | 650 if (!fStyle.isSimpleFill()) { |
| 626 fallbackSkPaint.setStrokeWidth(fStroke.getWidth() * fTextRatio); | 651 fallbackSkPaint.setStrokeWidth(fStyle.strokeRec().getWidth() * fText
Ratio); |
| 627 } | 652 } |
| 628 | 653 |
| 629 fallbackTextContext->drawTextBlob(ctx, dc, pipelineBuilder->clip(), fall
backSkPaint, | 654 fallbackTextContext->drawTextBlob(ctx, dc, pipelineBuilder->clip(), fall
backSkPaint, |
| 630 viewMatrix, props, fFallbackTextBlob,
x, y, nullptr, | 655 viewMatrix, props, fFallbackTextBlob,
x, y, nullptr, |
| 631 clipBounds); | 656 clipBounds); |
| 632 } | 657 } |
| 633 } | 658 } |
| 634 | 659 |
| 635 SkGlyphCache* GrStencilAndCoverTextContext::TextRun::getGlyphCache() const { | 660 SkGlyphCache* GrStencilAndCoverTextContext::TextRun::getGlyphCache() const { |
| 636 if (!fDetachedGlyphCache) { | 661 if (!fDetachedGlyphCache) { |
| (...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 703 } | 728 } |
| 704 | 729 |
| 705 const SkTextBlob* GrStencilAndCoverTextContext::FallbackBlobBuilder::buildIfNeed
ed(int *count) { | 730 const SkTextBlob* GrStencilAndCoverTextContext::FallbackBlobBuilder::buildIfNeed
ed(int *count) { |
| 706 *count = fCount; | 731 *count = fCount; |
| 707 if (fCount) { | 732 if (fCount) { |
| 708 this->flush(); | 733 this->flush(); |
| 709 return fBuilder->build(); | 734 return fBuilder->build(); |
| 710 } | 735 } |
| 711 return nullptr; | 736 return nullptr; |
| 712 } | 737 } |
| OLD | NEW |