1 // Copyright 2016 PDFium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 // Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com 6 7 #include "core/fxge/cfx_fontcache.h" 8 9 #include <memory> 10 #include <utility> 11 12 #include "core/fxge/cfx_facecache.h" 13 #include "core/fxge/fx_font.h" 14 #include "core/fxge/fx_freetype.h" 15 CountedFaceCache()16CFX_FontCache::CountedFaceCache::CountedFaceCache() {} 17 ~CountedFaceCache()18CFX_FontCache::CountedFaceCache::~CountedFaceCache() {} 19 CFX_FontCache()20CFX_FontCache::CFX_FontCache() {} 21 ~CFX_FontCache()22CFX_FontCache::~CFX_FontCache() { 23 ASSERT(m_ExtFaceMap.empty()); 24 ASSERT(m_FTFaceMap.empty()); 25 } 26 GetCachedFace(const CFX_Font * pFont)27CFX_FaceCache* CFX_FontCache::GetCachedFace(const CFX_Font* pFont) { 28 FXFT_Face face = pFont->GetFace(); 29 const bool bExternal = !face; 30 CFX_FTCacheMap& map = bExternal ? m_ExtFaceMap : m_FTFaceMap; 31 auto it = map.find(face); 32 if (it != map.end()) { 33 CountedFaceCache* counted_face_cache = it->second.get(); 34 counted_face_cache->m_nCount++; 35 return counted_face_cache->m_Obj.get(); 36 } 37 38 std::unique_ptr<CountedFaceCache> counted_face_cache(new CountedFaceCache); 39 counted_face_cache->m_nCount = 2; 40 CFX_FaceCache* face_cache = new CFX_FaceCache(bExternal ? nullptr : face); 41 counted_face_cache->m_Obj.reset(face_cache); 42 map[face] = std::move(counted_face_cache); 43 return face_cache; 44 } 45 46 #ifdef _SKIA_SUPPORT_ GetDeviceCache(const CFX_Font * pFont)47CFX_TypeFace* CFX_FontCache::GetDeviceCache(const CFX_Font* pFont) { 48 return GetCachedFace(pFont)->GetDeviceCache(pFont); 49 } 50 #endif 51 ReleaseCachedFace(const CFX_Font * pFont)52void CFX_FontCache::ReleaseCachedFace(const CFX_Font* pFont) { 53 FXFT_Face face = pFont->GetFace(); 54 const bool bExternal = !face; 55 CFX_FTCacheMap& map = bExternal ? m_ExtFaceMap : m_FTFaceMap; 56 57 auto it = map.find(face); 58 if (it == map.end()) 59 return; 60 61 CountedFaceCache* counted_face_cache = it->second.get(); 62 if (counted_face_cache->m_nCount > 2) { 63 counted_face_cache->m_nCount--; 64 } else { 65 map.erase(it); 66 } 67 } 68