Skip to content

Commit 2421439

Browse files
chethaaseAndroid (Google) Code Review
authored andcommitted
Merge "Remove CacheTextureLine structure from FontRenderer" into jb-mr1-dev
2 parents 3f1e8b9 + 378e919 commit 2421439

File tree

2 files changed

+103
-205
lines changed

2 files changed

+103
-205
lines changed

libs/hwui/FontRenderer.cpp

Lines changed: 73 additions & 147 deletions
Original file line numberDiff line numberDiff line change
@@ -109,11 +109,11 @@ CacheBlock* CacheBlock::removeBlock(CacheBlock* head, CacheBlock *blockToRemove)
109109
}
110110

111111
///////////////////////////////////////////////////////////////////////////////
112-
// CacheTextureLine
112+
// CacheTexture
113113
///////////////////////////////////////////////////////////////////////////////
114114

115-
bool CacheTextureLine::fitBitmap(const SkGlyph& glyph, uint32_t *retOriginX, uint32_t *retOriginY) {
116-
if (glyph.fHeight + TEXTURE_BORDER_SIZE > mMaxHeight) {
115+
bool CacheTexture::fitBitmap(const SkGlyph& glyph, uint32_t *retOriginX, uint32_t *retOriginY) {
116+
if (glyph.fHeight + TEXTURE_BORDER_SIZE > mHeight) {
117117
return false;
118118
}
119119

@@ -138,18 +138,18 @@ bool CacheTextureLine::fitBitmap(const SkGlyph& glyph, uint32_t *retOriginX, uin
138138
roundedUpW = glyphW;
139139
}
140140
*retOriginX = cacheBlock->mX;
141-
*retOriginY = mCurrentRow + cacheBlock->mY;
141+
*retOriginY = cacheBlock->mY;
142142
// If this is the remainder space, create a new cache block for this column. Otherwise,
143143
// adjust the info about this column.
144144
if (cacheBlock->mY == TEXTURE_BORDER_SIZE) {
145145
uint16_t oldX = cacheBlock->mX;
146146
// Adjust remainder space dimensions
147147
cacheBlock->mWidth -= roundedUpW;
148148
cacheBlock->mX += roundedUpW;
149-
if (mMaxHeight - glyphH >= glyphH) {
149+
if (mHeight - glyphH >= glyphH) {
150150
// There's enough height left over to create a new CacheBlock
151151
CacheBlock *newBlock = new CacheBlock(oldX, glyphH, roundedUpW,
152-
mMaxHeight - glyphH);
152+
mHeight - glyphH);
153153
#if DEBUG_FONT_RENDERER
154154
ALOGD("fitBitmap: Created new block: this, x, y, w, h = %p, %d, %d, %d, %d",
155155
newBlock, newBlock->mX, newBlock->mY,
@@ -213,10 +213,10 @@ Font::~Font() {
213213
}
214214
}
215215

216-
void Font::invalidateTextureCache(CacheTextureLine *cacheLine) {
216+
void Font::invalidateTextureCache(CacheTexture *cacheTexture) {
217217
for (uint32_t i = 0; i < mCachedGlyphs.size(); i++) {
218218
CachedGlyphInfo* cachedGlyph = mCachedGlyphs.valueAt(i);
219-
if (cacheLine == NULL || cachedGlyph->mCachedTextureLine == cacheLine) {
219+
if (cacheTexture == NULL || cachedGlyph->mCacheTexture == cacheTexture) {
220220
cachedGlyph->mIsValid = false;
221221
}
222222
}
@@ -260,7 +260,7 @@ void Font::drawCachedGlyph(CachedGlyphInfo* glyph, int x, int y,
260260
mState->appendMeshQuad(nPenX, nPenY, u1, v2,
261261
nPenX + width, nPenY, u2, v2,
262262
nPenX + width, nPenY - height, u2, v1,
263-
nPenX, nPenY - height, u1, v1, glyph->mCachedTextureLine->mCacheTexture);
263+
nPenX, nPenY - height, u1, v1, glyph->mCacheTexture);
264264
}
265265

266266
void Font::drawCachedGlyphBitmap(CachedGlyphInfo* glyph, int x, int y,
@@ -271,7 +271,7 @@ void Font::drawCachedGlyphBitmap(CachedGlyphInfo* glyph, int x, int y,
271271
uint32_t endX = glyph->mStartX + glyph->mBitmapWidth;
272272
uint32_t endY = glyph->mStartY + glyph->mBitmapHeight;
273273

274-
CacheTexture *cacheTexture = glyph->mCachedTextureLine->mCacheTexture;
274+
CacheTexture *cacheTexture = glyph->mCacheTexture;
275275
uint32_t cacheWidth = cacheTexture->mWidth;
276276
const uint8_t* cacheBuffer = cacheTexture->mTexture;
277277

@@ -325,7 +325,7 @@ void Font::drawCachedGlyph(CachedGlyphInfo* glyph, float x, float hOffset, float
325325
position->fY + destination[2].fY, u2, v1,
326326
position->fX + destination[3].fX,
327327
position->fY + destination[3].fY, u1, v1,
328-
glyph->mCachedTextureLine->mCacheTexture);
328+
glyph->mCacheTexture);
329329
}
330330

331331
CachedGlyphInfo* Font::getCachedGlyph(SkPaint* paint, glyph_t textUnit) {
@@ -556,8 +556,8 @@ void Font::updateGlyphCache(SkPaint* paint, const SkGlyph& skiaGlyph, CachedGlyp
556556
glyph->mBitmapWidth = skiaGlyph.fWidth;
557557
glyph->mBitmapHeight = skiaGlyph.fHeight;
558558

559-
uint32_t cacheWidth = glyph->mCachedTextureLine->mCacheTexture->mWidth;
560-
uint32_t cacheHeight = glyph->mCachedTextureLine->mCacheTexture->mHeight;
559+
uint32_t cacheWidth = glyph->mCacheTexture->mWidth;
560+
uint32_t cacheHeight = glyph->mCacheTexture->mHeight;
561561

562562
glyph->mBitmapMinU = startX / (float) cacheWidth;
563563
glyph->mBitmapMinV = startY / (float) cacheHeight;
@@ -620,10 +620,6 @@ FontRenderer::FontRenderer() {
620620
mTextMeshPtr = NULL;
621621
mCurrentCacheTexture = NULL;
622622
mLastCacheTexture = NULL;
623-
mCacheTextureSmall = NULL;
624-
mCacheTexture128 = NULL;
625-
mCacheTexture256 = NULL;
626-
mCacheTexture512 = NULL;
627623

628624
mLinearFiltering = false;
629625

@@ -659,21 +655,17 @@ FontRenderer::FontRenderer() {
659655
}
660656

661657
FontRenderer::~FontRenderer() {
662-
for (uint32_t i = 0; i < mCacheLines.size(); i++) {
663-
delete mCacheLines[i];
658+
for (uint32_t i = 0; i < mCacheTextures.size(); i++) {
659+
delete mCacheTextures[i];
664660
}
665-
mCacheLines.clear();
661+
mCacheTextures.clear();
666662

667663
if (mInitialized) {
668664
// Unbinding the buffer shouldn't be necessary but it crashes with some drivers
669665
Caches::getInstance().unbindIndicesBuffer();
670666
glDeleteBuffers(1, &mIndexBufferID);
671667

672668
delete[] mTextMeshPtr;
673-
delete mCacheTextureSmall;
674-
delete mCacheTexture128;
675-
delete mCacheTexture256;
676-
delete mCacheTexture512;
677669
}
678670

679671
Vector<Font*> fontsToDereference = mActiveFonts;
@@ -692,29 +684,19 @@ void FontRenderer::flushAllAndInvalidate() {
692684
mActiveFonts[i]->invalidateTextureCache();
693685
}
694686

695-
uint16_t totalGlyphs = 0;
696-
for (uint32_t i = 0; i < mCacheLines.size(); i++) {
697-
totalGlyphs += mCacheLines[i]->mNumGlyphs;
698-
mCacheLines[i]->init();
687+
for (uint32_t i = 0; i < mCacheTextures.size(); i++) {
688+
mCacheTextures[i]->init();
699689
}
700690

701-
#if DEBUG_FONT_RENDERER
702-
// Erase caches, just as a debugging facility
703-
if (mCacheTextureSmall && mCacheTextureSmall->mTexture) {
704-
memset(mCacheTextureSmall->mTexture, 0,
705-
mCacheTextureSmall->mWidth * mCacheTextureSmall->mHeight);
706-
}
707-
if (mCacheTexture128 && mCacheTexture128->mTexture) {
708-
memset(mCacheTexture128->mTexture, 0,
709-
mCacheTexture128->mWidth * mCacheTexture128->mHeight);
710-
}
711-
if (mCacheTexture256 && mCacheTexture256->mTexture) {
712-
memset(mCacheTexture256->mTexture, 0,
713-
mCacheTexture256->mWidth * mCacheTexture256->mHeight);
714-
}
715-
if (mCacheTexture512 && mCacheTexture512->mTexture) {
716-
memset(mCacheTexture512->mTexture, 0,
717-
mCacheTexture512->mWidth * mCacheTexture512->mHeight);
691+
#if DEBUG_FONT_RENDERER
692+
uint16_t totalGlyphs = 0;
693+
for (uint32_t i = 0; i < mCacheTextures.size(); i++) {
694+
totalGlyphs += mCacheTextures[i]->mNumGlyphs;
695+
// Erase caches, just as a debugging facility
696+
if (mCacheTextures[i]->mTexture) {
697+
memset(mCacheTextures[i]->mTexture, 0,
698+
mCacheTextures[i]->mWidth * mCacheTextures[i]->mHeight);
699+
}
718700
}
719701
ALOGD("Flushing caches: glyphs cached = %d", totalGlyphs);
720702
#endif
@@ -730,38 +712,17 @@ void FontRenderer::deallocateTextureMemory(CacheTexture *cacheTexture) {
730712
}
731713

732714
void FontRenderer::flushLargeCaches() {
733-
if ((!mCacheTexture128 || !mCacheTexture128->mTexture) &&
734-
(!mCacheTexture256 || !mCacheTexture256->mTexture) &&
735-
(!mCacheTexture512 || !mCacheTexture512->mTexture)) {
736-
// Typical case; no large glyph caches allocated
737-
return;
738-
}
739-
740-
for (uint32_t i = 0; i < mCacheLines.size(); i++) {
741-
CacheTextureLine* cacheLine = mCacheLines[i];
742-
if ((cacheLine->mCacheTexture == mCacheTexture128 ||
743-
cacheLine->mCacheTexture == mCacheTexture256 ||
744-
cacheLine->mCacheTexture == mCacheTexture512) &&
745-
cacheLine->mCacheTexture->mTexture != NULL) {
746-
#if DEBUG_FONT_RENDERER
747-
if (cacheLine->mCacheTexture == mCacheTexture128) {
748-
ALOGD("flushing cacheTexture128");
749-
} else if (cacheLine->mCacheTexture == mCacheTexture256) {
750-
ALOGD("flushing cacheTexture256");
751-
} else {
752-
ALOGD("flushing cacheTexture512");
753-
}
754-
#endif
755-
cacheLine->init();
756-
for (uint32_t i = 0; i < mActiveFonts.size(); i++) {
757-
mActiveFonts[i]->invalidateTextureCache(cacheLine);
715+
// Start from 1; don't deallocate smallest/default texture
716+
for (uint32_t i = 1; i < mCacheTextures.size(); i++) {
717+
CacheTexture* cacheTexture = mCacheTextures[i];
718+
if (cacheTexture->mTexture != NULL) {
719+
cacheTexture->init();
720+
for (uint32_t j = 0; j < mActiveFonts.size(); j++) {
721+
mActiveFonts[j]->invalidateTextureCache(cacheTexture);
758722
}
723+
deallocateTextureMemory(cacheTexture);
759724
}
760725
}
761-
762-
deallocateTextureMemory(mCacheTexture128);
763-
deallocateTextureMemory(mCacheTexture256);
764-
deallocateTextureMemory(mCacheTexture512);
765726
}
766727

767728
void FontRenderer::allocateTextureMemory(CacheTexture* cacheTexture) {
@@ -789,12 +750,24 @@ void FontRenderer::allocateTextureMemory(CacheTexture* cacheTexture) {
789750
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
790751
}
791752

753+
CacheTexture* FontRenderer::cacheBitmapInTexture(const SkGlyph& glyph,
754+
uint32_t* startX, uint32_t* startY) {
755+
for (uint32_t i = 0; i < mCacheTextures.size(); i++) {
756+
if (mCacheTextures[i]->fitBitmap(glyph, startX, startY)) {
757+
return mCacheTextures[i];
758+
}
759+
}
760+
// Could not fit glyph into current cache textures
761+
return NULL;
762+
}
763+
792764
void FontRenderer::cacheBitmap(const SkGlyph& glyph, CachedGlyphInfo* cachedGlyph,
793765
uint32_t* retOriginX, uint32_t* retOriginY) {
794766
checkInit();
795767
cachedGlyph->mIsValid = false;
796768
// If the glyph is too tall, don't cache it
797-
if (glyph.fHeight + TEXTURE_BORDER_SIZE * 2 > mCacheLines[mCacheLines.size() - 1]->mMaxHeight) {
769+
if (glyph.fHeight + TEXTURE_BORDER_SIZE * 2 >
770+
mCacheTextures[mCacheTextures.size() - 1]->mHeight) {
798771
ALOGE("Font size too large to fit in cache. width, height = %i, %i",
799772
(int) glyph.fWidth, (int) glyph.fHeight);
800773
return;
@@ -804,46 +777,31 @@ void FontRenderer::cacheBitmap(const SkGlyph& glyph, CachedGlyphInfo* cachedGlyp
804777
uint32_t startX = 0;
805778
uint32_t startY = 0;
806779

807-
bool bitmapFit = false;
808-
CacheTextureLine *cacheLine;
809-
for (uint32_t i = 0; i < mCacheLines.size(); i++) {
810-
bitmapFit = mCacheLines[i]->fitBitmap(glyph, &startX, &startY);
811-
if (bitmapFit) {
812-
cacheLine = mCacheLines[i];
813-
break;
814-
}
815-
}
780+
CacheTexture* cacheTexture = cacheBitmapInTexture(glyph, &startX, &startY);
816781

817782
// If the new glyph didn't fit, flush the state so far and invalidate everything
818-
if (!bitmapFit) {
783+
if (!cacheTexture) {
819784
flushAllAndInvalidate();
820785

821786
// Try to fit it again
822-
for (uint32_t i = 0; i < mCacheLines.size(); i++) {
823-
bitmapFit = mCacheLines[i]->fitBitmap(glyph, &startX, &startY);
824-
if (bitmapFit) {
825-
cacheLine = mCacheLines[i];
826-
break;
827-
}
828-
}
787+
cacheTexture = cacheBitmapInTexture(glyph, &startX, &startY);
829788

830789
// if we still don't fit, something is wrong and we shouldn't draw
831-
if (!bitmapFit) {
790+
if (!cacheTexture) {
832791
return;
833792
}
834793
}
835794

836-
cachedGlyph->mCachedTextureLine = cacheLine;
795+
cachedGlyph->mCacheTexture = cacheTexture;
837796

838797
*retOriginX = startX;
839798
*retOriginY = startY;
840799

841800
uint32_t endX = startX + glyph.fWidth;
842801
uint32_t endY = startY + glyph.fHeight;
843802

844-
uint32_t cacheWidth = cacheLine->mMaxWidth;
803+
uint32_t cacheWidth = cacheTexture->mWidth;
845804

846-
CacheTexture* cacheTexture = cacheLine->mCacheTexture;
847805
if (!cacheTexture->mTexture) {
848806
// Large-glyph texture memory is allocated only as needed
849807
allocateTextureMemory(cacheTexture);
@@ -896,17 +854,10 @@ CacheTexture* FontRenderer::createCacheTexture(int width, int height, bool alloc
896854
}
897855

898856
void FontRenderer::initTextTexture() {
899-
for (uint32_t i = 0; i < mCacheLines.size(); i++) {
900-
delete mCacheLines[i];
901-
}
902-
mCacheLines.clear();
903-
904-
if (mCacheTextureSmall) {
905-
delete mCacheTextureSmall;
906-
delete mCacheTexture128;
907-
delete mCacheTexture256;
908-
delete mCacheTexture512;
857+
for (uint32_t i = 0; i < mCacheTextures.size(); i++) {
858+
delete mCacheTextures[i];
909859
}
860+
mCacheTextures.clear();
910861

911862
// Next, use other, separate caches for large glyphs.
912863
uint16_t maxWidth = 0;
@@ -918,35 +869,12 @@ void FontRenderer::initTextTexture() {
918869
maxWidth = MAX_TEXT_CACHE_WIDTH;
919870
}
920871

921-
mCacheTextureSmall = createCacheTexture(mSmallCacheWidth, mSmallCacheHeight, true);
922-
mCacheTexture128 = createCacheTexture(maxWidth, 256, false);
923-
mCacheTexture256 = createCacheTexture(maxWidth, 256, false);
924-
mCacheTexture512 = createCacheTexture(maxWidth, 512, false);
925-
mCurrentCacheTexture = mCacheTextureSmall;
926-
927872
mUploadTexture = false;
928-
// Split up our default cache texture into lines of certain widths
929-
int nextLine = 0;
930-
mCacheLines.push(new CacheTextureLine(mSmallCacheWidth, 18, nextLine, mCacheTextureSmall));
931-
nextLine += mCacheLines.top()->mMaxHeight;
932-
mCacheLines.push(new CacheTextureLine(mSmallCacheWidth, 26, nextLine, mCacheTextureSmall));
933-
nextLine += mCacheLines.top()->mMaxHeight;
934-
mCacheLines.push(new CacheTextureLine(mSmallCacheWidth, 26, nextLine, mCacheTextureSmall));
935-
nextLine += mCacheLines.top()->mMaxHeight;
936-
mCacheLines.push(new CacheTextureLine(mSmallCacheWidth, 34, nextLine, mCacheTextureSmall));
937-
nextLine += mCacheLines.top()->mMaxHeight;
938-
mCacheLines.push(new CacheTextureLine(mSmallCacheWidth, 34, nextLine, mCacheTextureSmall));
939-
nextLine += mCacheLines.top()->mMaxHeight;
940-
mCacheLines.push(new CacheTextureLine(mSmallCacheWidth, 42, nextLine, mCacheTextureSmall));
941-
nextLine += mCacheLines.top()->mMaxHeight;
942-
mCacheLines.push(new CacheTextureLine(mSmallCacheWidth, mSmallCacheHeight - nextLine,
943-
nextLine, mCacheTextureSmall));
944-
945-
// The first cache is split into 2 lines of height 128, the rest have just one cache line.
946-
mCacheLines.push(new CacheTextureLine(maxWidth, 128, 0, mCacheTexture128));
947-
mCacheLines.push(new CacheTextureLine(maxWidth, 128, 128, mCacheTexture128));
948-
mCacheLines.push(new CacheTextureLine(maxWidth, 256, 0, mCacheTexture256));
949-
mCacheLines.push(new CacheTextureLine(maxWidth, 512, 0, mCacheTexture512));
873+
mCacheTextures.push(createCacheTexture(mSmallCacheWidth, mSmallCacheHeight, true));
874+
mCacheTextures.push(createCacheTexture(maxWidth, 256, false));
875+
mCacheTextures.push(createCacheTexture(maxWidth, 256, false));
876+
mCacheTextures.push(createCacheTexture(maxWidth, 512, false));
877+
mCurrentCacheTexture = mCacheTextures[0];
950878
}
951879

952880
// Avoid having to reallocate memory and render quad by quad
@@ -1001,30 +929,28 @@ void FontRenderer::checkTextureUpdate() {
1001929

1002930
Caches& caches = Caches::getInstance();
1003931
GLuint lastTextureId = 0;
1004-
// Iterate over all the cache lines and see which ones need to be updated
1005-
for (uint32_t i = 0; i < mCacheLines.size(); i++) {
1006-
CacheTextureLine* cl = mCacheLines[i];
1007-
if (cl->mDirty && cl->mCacheTexture->mTexture != NULL) {
1008-
CacheTexture* cacheTexture = cl->mCacheTexture;
932+
// Iterate over all the cache textures and see which ones need to be updated
933+
for (uint32_t i = 0; i < mCacheTextures.size(); i++) {
934+
CacheTexture* cacheTexture = mCacheTextures[i];
935+
if (cacheTexture->mDirty && cacheTexture->mTexture != NULL) {
1009936
uint32_t xOffset = 0;
1010-
uint32_t yOffset = cl->mCurrentRow;
1011-
uint32_t width = cl->mMaxWidth;
1012-
uint32_t height = cl->mMaxHeight;
1013-
void* textureData = cacheTexture->mTexture + (yOffset * width);
937+
uint32_t width = cacheTexture->mWidth;
938+
uint32_t height = cacheTexture->mHeight;
939+
void* textureData = cacheTexture->mTexture;
1014940

1015941
if (cacheTexture->mTextureId != lastTextureId) {
1016942
caches.activeTexture(0);
1017943
glBindTexture(GL_TEXTURE_2D, cacheTexture->mTextureId);
1018944
lastTextureId = cacheTexture->mTextureId;
1019945
}
1020946
#if DEBUG_FONT_RENDERER
1021-
ALOGD("glTextSubimage for cacheLine %d: xOff, yOff, width height = %d, %d, %d, %d", i,
1022-
xOffset, yOffset, width, height);
947+
ALOGD("glTextSubimage for cacheTexture %d: xOff, width height = %d, %d, %d",
948+
i, xOffset, width, height);
1023949
#endif
1024-
glTexSubImage2D(GL_TEXTURE_2D, 0, xOffset, yOffset, width, height,
950+
glTexSubImage2D(GL_TEXTURE_2D, 0, xOffset, 0, width, height,
1025951
GL_ALPHA, GL_UNSIGNED_BYTE, textureData);
1026952

1027-
cl->mDirty = false;
953+
cacheTexture->mDirty = false;
1028954
}
1029955
}
1030956

0 commit comments

Comments
 (0)