void SkScalerContext::getMetrics(SkGlyph* glyph) { this->getGlyphContext(*glyph)->generateMetrics(glyph); // for now we have separate cache entries for devkerning on and off // in the future we might share caches, but make our measure/draw // code make the distinction. Thus we zap the values if the caller // has not asked for them. if ((fRec.fFlags & SkScalerContext::kDevKernText_Flag) == 0) { // no devkern, so zap the fields glyph->fLsbDelta = glyph->fRsbDelta = 0; } // if either dimension is empty, zap the image bounds of the glyph if (0 == glyph->fWidth || 0 == glyph->fHeight) { glyph->fWidth = 0; glyph->fHeight = 0; glyph->fTop = 0; glyph->fLeft = 0; glyph->fMaskFormat = 0; return; } if (fRec.fFrameWidth > 0 || fPathEffect != NULL || fRasterizer != NULL) { SkPath devPath, fillPath; SkMatrix fillToDevMatrix; this->internalGetPath(*glyph, &fillPath, &devPath, &fillToDevMatrix); if (fRasterizer) { SkMask mask; if (fRasterizer->rasterize(fillPath, fillToDevMatrix, NULL, fMaskFilter, &mask, SkMask::kJustComputeBounds_CreateMode)) { glyph->fLeft = mask.fBounds.fLeft; glyph->fTop = mask.fBounds.fTop; glyph->fWidth = SkToU16(mask.fBounds.width()); glyph->fHeight = SkToU16(mask.fBounds.height()); } else { goto SK_ERROR; } } else { // just use devPath SkIRect ir; devPath.getBounds().roundOut(&ir); if (ir.isEmpty() || !ir.is16Bit()) { goto SK_ERROR; } glyph->fLeft = ir.fLeft; glyph->fTop = ir.fTop; glyph->fWidth = SkToU16(ir.width()); glyph->fHeight = SkToU16(ir.height()); } } if (SkMask::kARGB32_Format != glyph->fMaskFormat) { glyph->fMaskFormat = fRec.fMaskFormat; } if (fMaskFilter) { SkMask src, dst; SkMatrix matrix; glyph->toMask(&src); fRec.getMatrixFrom2x2(&matrix); src.fImage = NULL; // only want the bounds from the filter if (fMaskFilter->filterMask(&dst, src, matrix, NULL)) { SkASSERT(dst.fImage == NULL); glyph->fLeft = dst.fBounds.fLeft; glyph->fTop = dst.fBounds.fTop; glyph->fWidth = SkToU16(dst.fBounds.width()); glyph->fHeight = SkToU16(dst.fBounds.height()); glyph->fMaskFormat = dst.fFormat; } } return; SK_ERROR: // draw nothing 'cause we failed glyph->fLeft = 0; glyph->fTop = 0; glyph->fWidth = 0; glyph->fHeight = 0; // put a valid value here, in case it was earlier set to // MASK_FORMAT_JUST_ADVANCE glyph->fMaskFormat = fRec.fMaskFormat; }