905 SkScalar SkPaint::measure_text(SkGlyphCache* cache,
906 const char* text, size_t byteLength,
907 int* count, SkRect* bounds) const {
908 SkASSERT(count);
909 if (byteLength == 0) {
910 *count = 0;
911 if (bounds) {
912 bounds->setEmpty();
913 }
914 return 0;
915 }
916
917 SkMeasureCacheProc glyphCacheProc;
918 glyphCacheProc = this->getMeasureCacheProc(kForward_TextBufferDirection,
919 NULL != bounds);
920
921 int xyIndex;
922 JoinBoundsProc joinBoundsProc;
923 if (this->isVerticalText()) {
924 xyIndex = 1;
925 joinBoundsProc = join_bounds_y;
926 } else {
927 xyIndex = 0;
928 joinBoundsProc = join_bounds_x;
929 }
930
931 int n = 1;
932 const char* stop = (const char*)text + byteLength;
933 const SkGlyph* g = &glyphCacheProc(cache, &text);
934
935
936
937 Sk48Dot16 x = advance(*g, xyIndex);
938
939 SkAutoKern autokern;
940
941 if (NULL == bounds) {
942 if (this->isDevKernText()) {
943 int rsb;
944 for (; text < stop; n++) {
945 rsb = g->fRsbDelta;
946 g = &glyphCacheProc(cache, &text); <==========
947 x += SkAutoKern_AdjustF(rsb, g->fLsbDelta) + advance(*g, xyIndex);
948 }
949 } else {
950 for (; text < stop; n++) {
951 x += advance(glyphCacheProc(cache, &text), xyIndex); <==========
952 }
953 }
954 } else {
955 set_bounds(*g, bounds);
956 if (this->isDevKernText()) {
957 int rsb;
958 for (; text < stop; n++) {
959 rsb = g->fRsbDelta;
960 g = &glyphCacheProc(cache, &text); <==========
961 x += SkAutoKern_AdjustF(rsb, g->fLsbDelta);
962 joinBoundsProc(*g, bounds, x);
963 x += advance(*g, xyIndex);
964 }
965 } else {
966 for (; text < stop; n++) {
967 g = &glyphCacheProc(cache, &text); <==========
968 joinBoundsProc(*g, bounds, x);
969 x += advance(*g, xyIndex);
970 }
971 }
972 }
973 SkASSERT(text == stop);
974
975 *count = n;
976 return Sk48Dot16ToScalar(x);
977 }
172 const SkGlyph& SkGlyphCache::getUnicharMetrics(SkUnichar charCode,
173 SkFixed x, SkFixed y) {
174 VALIDATE();
175 uint32_t id = SkGlyph::MakeID(charCode, x, y);
176 CharGlyphRec* rec = &fCharToGlyphHash[ID2HashIndex(id)];
177
178 if (rec->fID != id) {
179 RecordHashCollisionIf(rec->fGlyph != NULL);
180
181 rec->fID = id;
182
183 id = SkGlyph::MakeID(fScalerContext->charToGlyphID(charCode), x, y);
184 rec->fGlyph = this->lookupMetrics(id, kFull_MetricsType);
185 } else {
186 RecordHashSuccess();
187 if (rec->fGlyph->isJustAdvance()) {
188 fScalerContext->getMetrics(rec->fGlyph);
189 }
190 }
191 SkASSERT(rec->fGlyph->isFullMetrics());
192 return *rec->fGlyph;
193 }