18e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project/* 2db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block * Copyright (C) 2007, 2008, 2009, 2010 Apple Inc. All rights reserved. 38e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 48e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * This library is free software; you can redistribute it and/or 58e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * modify it under the terms of the GNU Library General Public 68e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * License as published by the Free Software Foundation; either 78e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * version 2 of the License, or (at your option) any later version. 88e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 98e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * This library is distributed in the hope that it will be useful, 108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * but WITHOUT ANY WARRANTY; without even the implied warranty of 118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * Library General Public License for more details. 138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * You should have received a copy of the GNU Library General Public License 158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * along with this library; see the file COPYING.LIB. If not, write to 168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, 178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * Boston, MA 02110-1301, USA. 188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project */ 208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "config.h" 228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "FontCustomPlatformData.h" 238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "Base64.h" 258e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "FontPlatformData.h" 268e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "OpenTypeUtilities.h" 278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "SharedBuffer.h" 288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "SoftLinking.h" 29db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block#include "WOFFFileFormat.h" 308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include <ApplicationServices/ApplicationServices.h> 31635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project#include <WebKitSystemInterface/WebKitSystemInterface.h> 328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include <wtf/RetainPtr.h> 338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project// From t2embapi.h, which is missing from the Microsoft Platform SDK. 358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projecttypedef unsigned long(WINAPIV *READEMBEDPROC) (void*, void*, unsigned long); 368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstruct TTLOADINFO; 378e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#define TTLOAD_PRIVATE 0x00000001 388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#define LICENSE_PREVIEWPRINT 0x0004 398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#define E_NONE 0x0000L 408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectnamespace WebCore { 428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectusing namespace std; 448e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 458e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source ProjectSOFT_LINK_LIBRARY(T2embed); 468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source ProjectSOFT_LINK(T2embed, TTLoadEmbeddedFont, LONG, __stdcall, (HANDLE* phFontReference, ULONG ulFlags, ULONG* pulPrivStatus, ULONG ulPrivs, ULONG* pulStatus, READEMBEDPROC lpfnReadFromStream, LPVOID lpvReadStream, LPWSTR szWinFamilyName, LPSTR szMacFamilyName, TTLOADINFO* pTTLoadInfo), (phFontReference, ulFlags,pulPrivStatus, ulPrivs, pulStatus, lpfnReadFromStream, lpvReadStream, szWinFamilyName, szMacFamilyName, pTTLoadInfo)); 478e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source ProjectSOFT_LINK(T2embed, TTGetNewFontName, LONG, __stdcall, (HANDLE* phFontReference, LPWSTR szWinFamilyName, long cchMaxWinName, LPSTR szMacFamilyName, long cchMaxMacName), (phFontReference, szWinFamilyName, cchMaxWinName, szMacFamilyName, cchMaxMacName)); 488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source ProjectSOFT_LINK(T2embed, TTDeleteEmbeddedFont, LONG, __stdcall, (HANDLE hFontReference, ULONG ulFlags, ULONG* pulStatus), (hFontReference, ulFlags, pulStatus)); 498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source ProjectFontCustomPlatformData::~FontCustomPlatformData() 518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (m_fontReference) { 538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (m_name.isNull()) { 548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(T2embedLibrary()); 558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ULONG status; 568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project TTDeleteEmbeddedFont(m_fontReference, 0, &status); 578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else 588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project RemoveFontMemResourceEx(m_fontReference); 598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 622bde8e466a4451c7319e3a072d118917957d6554Steve BlockFontPlatformData FontCustomPlatformData::fontPlatformData(int size, bool bold, bool italic, FontOrientation, TextOrientation, FontWidthVariant, FontRenderingMode renderingMode) 638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(m_fontReference); 658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(T2embedLibrary()); 668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 678f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian LOGFONT& logFont = *static_cast<LOGFONT*>(malloc(sizeof(LOGFONT))); 688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (m_name.isNull()) 698e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project TTGetNewFontName(&m_fontReference, logFont.lfFaceName, LF_FACESIZE, 0, 0); 708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project else 718e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project memcpy(logFont.lfFaceName, m_name.charactersWithNullTermination(), sizeof(logFont.lfFaceName[0]) * min(static_cast<size_t>(LF_FACESIZE), 1 + m_name.length())); 728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 738e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project logFont.lfHeight = -size; 748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (renderingMode == NormalRenderingMode) 758e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project logFont.lfHeight *= 32; 768e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project logFont.lfWidth = 0; 778e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project logFont.lfEscapement = 0; 788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project logFont.lfOrientation = 0; 798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project logFont.lfUnderline = false; 808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project logFont.lfStrikeOut = false; 818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project logFont.lfCharSet = DEFAULT_CHARSET; 828e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project logFont.lfOutPrecision = OUT_TT_ONLY_PRECIS; 838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project logFont.lfQuality = CLEARTYPE_QUALITY; 848e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project logFont.lfPitchAndFamily = DEFAULT_PITCH | FF_DONTCARE; 858e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project logFont.lfItalic = italic; 868e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project logFont.lfWeight = bold ? 700 : 400; 878e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 888e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project HFONT hfont = CreateFontIndirect(&logFont); 89d0825bca7fe65beaee391d30da42e937db621564Steve Block 90dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block RetainPtr<CGFontRef> cgFont(AdoptCF, CGFontCreateWithPlatformFont(&logFont)); 91dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block return FontPlatformData(hfont, cgFont.get(), size, bold, italic, renderingMode == AlternateRenderingMode); 928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project// Streams the concatenation of a header and font data. 958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectclass EOTStream { 968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectpublic: 975f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian EOTStream(const EOTHeader& eotHeader, const SharedBuffer* fontData, size_t overlayDst, size_t overlaySrc, size_t overlayLength) 988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project : m_eotHeader(eotHeader) 998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_fontData(fontData) 1008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_overlayDst(overlayDst) 1018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_overlaySrc(overlaySrc) 1028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_overlayLength(overlayLength) 1038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_offset(0) 1048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_inHeader(true) 1058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project { 1068e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 1078e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1088e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t read(void* buffer, size_t count); 1098e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectprivate: 1115f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian const EOTHeader& m_eotHeader; 1128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project const SharedBuffer* m_fontData; 1138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t m_overlayDst; 1148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t m_overlaySrc; 1158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t m_overlayLength; 1168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t m_offset; 1178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project bool m_inHeader; 1188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project}; 1198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectsize_t EOTStream::read(void* buffer, size_t count) 1218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 1228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t bytesToRead = count; 1238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (m_inHeader) { 1248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t bytesFromHeader = min(m_eotHeader.size() - m_offset, count); 1258e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project memcpy(buffer, m_eotHeader.data() + m_offset, bytesFromHeader); 1268e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_offset += bytesFromHeader; 1278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project bytesToRead -= bytesFromHeader; 1288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (m_offset == m_eotHeader.size()) { 1298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_inHeader = false; 1308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_offset = 0; 1318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 1328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 1338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (bytesToRead && !m_inHeader) { 1348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t bytesFromData = min(m_fontData->size() - m_offset, bytesToRead); 1358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project memcpy(buffer, m_fontData->data() + m_offset, bytesFromData); 1368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (m_offset < m_overlayDst + m_overlayLength && m_offset + bytesFromData >= m_overlayDst) { 1378e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t dstOffset = max<int>(m_overlayDst - m_offset, 0); 1388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t srcOffset = max<int>(0, m_offset - m_overlayDst); 1398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t bytesToCopy = min(bytesFromData - dstOffset, m_overlayLength - srcOffset); 1408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project memcpy(reinterpret_cast<char*>(buffer) + dstOffset, m_fontData->data() + m_overlaySrc + srcOffset, bytesToCopy); 1418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 1428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_offset += bytesFromData; 1438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project bytesToRead -= bytesFromData; 1448e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 1458e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return count - bytesToRead; 1468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1478e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic unsigned long WINAPIV readEmbedProc(void* stream, void* buffer, unsigned long length) 1498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 1508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return static_cast<EOTStream*>(stream)->read(buffer, length); 1518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project// Creates a unique and unpredictable font name, in order to avoid collisions and to 1548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project// not allow access from CSS. 1558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic String createUniqueFontName() 1568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 1572fc2651226baac27029e38c9d6ef883fa32084dbSteve Block GUID fontUuid; 1582fc2651226baac27029e38c9d6ef883fa32084dbSteve Block CoCreateGuid(&fontUuid); 1598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1602fc2651226baac27029e38c9d6ef883fa32084dbSteve Block String fontName = base64Encode(reinterpret_cast<char*>(&fontUuid), sizeof(fontUuid)); 1612fc2651226baac27029e38c9d6ef883fa32084dbSteve Block ASSERT(fontName.length() < LF_FACESIZE); 1622fc2651226baac27029e38c9d6ef883fa32084dbSteve Block return fontName; 1638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source ProjectFontCustomPlatformData* createFontCustomPlatformData(SharedBuffer* buffer) 1668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 1678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT_ARG(buffer, buffer); 1688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(T2embedLibrary()); 1698e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 170db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block RefPtr<SharedBuffer> sfntBuffer; 171db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block if (isWOFF(buffer)) { 172db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block Vector<char> sfnt; 173db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block if (!convertWOFFToSfnt(buffer, sfnt)) 174db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block return 0; 175db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block 176db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block sfntBuffer = SharedBuffer::adoptVector(sfnt); 177db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block buffer = sfntBuffer.get(); 178db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block } 179db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block 1808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Introduce the font to GDI. AddFontMemResourceEx cannot be used, because it will pollute the process's 1818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // font namespace (Windows has no API for creating an HFONT from data without exposing the font to the 1828e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // entire process first). TTLoadEmbeddedFont lets us override the font family name, so using a unique name 1838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // we avoid namespace collisions. 1848e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1858e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project String fontName = createUniqueFontName(); 1868e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1878e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // TTLoadEmbeddedFont works only with Embedded OpenType (.eot) data, so we need to create an EOT header 1888e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // and prepend it to the font data. 1895f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian EOTHeader eotHeader; 1908e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t overlayDst; 1918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t overlaySrc; 1928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t overlayLength; 193d0825bca7fe65beaee391d30da42e937db621564Steve Block if (!getEOTHeader(buffer, eotHeader, overlayDst, overlaySrc, overlayLength)) 1948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return 0; 1958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project HANDLE fontReference; 1978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ULONG privStatus; 1988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ULONG status; 1998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project EOTStream eotStream(eotHeader, buffer, overlayDst, overlaySrc, overlayLength); 2008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project LONG loadEmbeddedFontResult = TTLoadEmbeddedFont(&fontReference, TTLOAD_PRIVATE, &privStatus, LICENSE_PREVIEWPRINT, &status, readEmbedProc, &eotStream, const_cast<LPWSTR>(fontName.charactersWithNullTermination()), 0, 0); 2028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (loadEmbeddedFontResult == E_NONE) 2038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project fontName = String(); 2048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project else { 2058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project fontReference = renameAndActivateFont(buffer, fontName); 206d0825bca7fe65beaee391d30da42e937db621564Steve Block if (!fontReference) 2078e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return 0; 2088e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 2098e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 210dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block return new FontCustomPlatformData(fontReference, fontName); 2118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 2128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 213db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Blockbool FontCustomPlatformData::supportsFormat(const String& format) 214db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block{ 215db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block return equalIgnoringCase(format, "truetype") || equalIgnoringCase(format, "opentype") || equalIgnoringCase(format, "woff"); 216db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block} 217db14019a23d96bc8a444b6576a5da8bd1cfbc8b0Steve Block 2188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 219