Chromium Code Reviews| Index: third_party/WebKit/Source/platform/fonts/FontCache.cpp |
| diff --git a/third_party/WebKit/Source/platform/fonts/FontCache.cpp b/third_party/WebKit/Source/platform/fonts/FontCache.cpp |
| index 29b184198ae71ce804bb47a3fdb79ec82ced6062..22cbe053356bb690238979c32b47b878a2a3844a 100644 |
| --- a/third_party/WebKit/Source/platform/fonts/FontCache.cpp |
| +++ b/third_party/WebKit/Source/platform/fonts/FontCache.cpp |
| @@ -67,7 +67,8 @@ FontCache::FontCache() |
| } |
| #endif // !OS(WIN) && !OS(LINUX) |
| -typedef HashMap<FontCacheKey, OwnPtr<FontPlatformData>, FontCacheKeyHash, FontCacheKeyTraits> FontPlatformDataCache; |
| +typedef HashMap<unsigned, OwnPtr<FontPlatformData>> SizedFontPlatformDataSet; |
|
eae
2016/05/17 14:42:55
Long term we should probably try to divorce the si
|
| +typedef HashMap<FontCacheKey, SizedFontPlatformDataSet, FontCacheKeyHash, FontCacheKeyTraits> FontPlatformDataCache; |
| typedef HashMap<FallbackListCompositeKey, OwnPtr<ShapeCache>, FallbackListCompositeKeyHash, FallbackListCompositeKeyTraits> FallbackListShaperCache; |
| static FontPlatformDataCache* gFontPlatformDataCache = nullptr; |
| @@ -96,17 +97,32 @@ FontPlatformData* FontCache::getFontPlatformData(const FontDescription& fontDesc |
| platformInit(); |
| } |
| + float size = fontDescription.effectiveFontSize(); |
| FontCacheKey key = fontDescription.cacheKey(creationParams); |
| + |
| + // Remove the font size from the cache key, and handle the font size separately in the inner |
| + // HashMap. So that different size of FontPlatformData can share underlying SkTypeface. |
| + key.clearFontSize(); |
| + |
| FontPlatformData* result; |
| bool foundResult; |
| + |
| { |
| // addResult's scope must end before we recurse for alternate family names below, |
| // to avoid trigering its dtor hash-changed asserts. |
| - auto addResult = gFontPlatformDataCache->add(key, nullptr); |
| - if (addResult.isNewEntry) |
| - addResult.storedValue->value = createFontPlatformData(fontDescription, creationParams, fontDescription.effectiveFontSize()); |
| + SizedFontPlatformDataSet* sizedFonts = &gFontPlatformDataCache->add(key, SizedFontPlatformDataSet()).storedValue->value; |
| + bool wasEmpty = sizedFonts->isEmpty(); |
| + FontPlatformData* anotherSize = wasEmpty ? nullptr : sizedFonts->begin()->value.get(); |
| + auto addResult = sizedFonts->add(size ? size * FontCacheKey::precisionMultiplier() : -2, nullptr); |
|
eae
2016/05/17 14:42:55
-2?
tzik
2016/05/17 14:56:19
Added a comment here. 0 and -1 are reserved for Ha
|
| + OwnPtr<FontPlatformData>* found = &addResult.storedValue->value; |
| + if (addResult.isNewEntry) { |
| + if (wasEmpty) |
| + *found = createFontPlatformData(fontDescription, creationParams, size); |
| + else |
|
eae
2016/05/17 14:42:55
How about using sizedFonts->begin()->value.get() d
tzik
2016/05/17 14:56:19
Hmm, since we are adding new entry into sizedFonts
|
| + *found = scaleFontPlatformData(anotherSize, fontDescription, creationParams, size); |
| + } |
| - result = addResult.storedValue->value.get(); |
| + result = found->get(); |
| foundResult = result || !addResult.isNewEntry; |
| } |
| @@ -118,13 +134,27 @@ FontPlatformData* FontCache::getFontPlatformData(const FontDescription& fontDesc |
| FontFaceCreationParams createByAlternateFamily(alternateName); |
| result = getFontPlatformData(fontDescription, createByAlternateFamily, true); |
| } |
| - if (result) |
| - gFontPlatformDataCache->set(key, adoptPtr(new FontPlatformData(*result))); // Cache the result under the old name. |
| + if (result) { |
| + // Cache the result under the old name. |
| + auto adding = &gFontPlatformDataCache->add(key, SizedFontPlatformDataSet()).storedValue->value; |
| + adding->set(size, adoptPtr(new FontPlatformData(*result))); |
| + } |
| } |
| return result; |
| } |
| +PassOwnPtr<FontPlatformData> FontCache::scaleFontPlatformData(const FontPlatformData* fontPlatformData, const FontDescription& fontDescription, const FontFaceCreationParams& creationParams, float fontSize) |
| +{ |
| +#if OS(MACOSX) |
| + return createFontPlatformData(fontDescription, creationParams, fontSize); |
| +#else |
| + if (!fontPlatformData) |
| + return nullptr; |
|
eae
2016/05/17 14:42:55
When would this be null?
tzik
2016/05/17 14:56:19
This can be null if the first createFontPlatformDa
|
| + return adoptPtr(new FontPlatformData(*fontPlatformData, fontSize)); |
| +#endif |
| +} |
| + |
| ShapeCache* FontCache::getShapeCache(const FallbackListCompositeKey& key) |
| { |
| if (!gFallbackListShaperCache) |
| @@ -226,10 +256,16 @@ static inline void purgePlatformFontDataCache() |
| Vector<FontCacheKey> keysToRemove; |
| keysToRemove.reserveInitialCapacity(gFontPlatformDataCache->size()); |
| - FontPlatformDataCache::iterator platformDataEnd = gFontPlatformDataCache->end(); |
| - for (FontPlatformDataCache::iterator platformData = gFontPlatformDataCache->begin(); platformData != platformDataEnd; ++platformData) { |
| - if (platformData->value && !gFontDataCache->contains(platformData->value.get())) |
| - keysToRemove.append(platformData->key); |
| + for (auto& sizedFonts : *gFontPlatformDataCache) { |
| + Vector<float> sizesToRemove; |
| + sizesToRemove.reserveInitialCapacity(sizedFonts.value.size()); |
| + for (const auto& platformData : sizedFonts.value) { |
| + if (platformData.value && !gFontDataCache->contains(platformData.value.get())) |
| + sizesToRemove.append(platformData.key); |
| + } |
| + sizedFonts.value.removeAll(sizesToRemove); |
| + if (sizedFonts.value.isEmpty()) |
| + keysToRemove.append(sizedFonts.key); |
| } |
| gFontPlatformDataCache->removeAll(keysToRemove); |
| } |