15#include FT_TYPE1_TABLES_H
16#include FT_TRUETYPE_TABLES_H
17#include FT_TRUETYPE_TAGS_H
18#include FT_TRIGONOMETRY_H
22#include FT_SFNT_NAMES_H
23#include FT_SYNTHESIS_H
24#include FT_TRUETYPE_IDS_H
26#ifndef FT_INTERNAL_INTERNAL_H
27 #define FT_INTERNAL_INTERNAL_H <freetype/internal/internal.h>
28 #include FT_INTERNAL_INTERNAL_H
30#include FT_INTERNAL_TRUETYPE_TYPES_H
63#define FONTLINK_DEFAULT_CHAR 0x30FB
72#define MAX_FONTLINK_CACHE 128
96 DWORD cbData, dwValue;
103 L"\\Registry\\Machine\\Software\\Microsoft\\Windows NT\\CurrentVersion\\FontLink",
108 cbData =
sizeof(dwValue);
130 L"\\Registry\\Machine\\SYSTEM\\CurrentControlSet\\Control\\FontAssoc\\Associated DefaultFonts",
135 cbData =
sizeof(szValue);
143 cbData =
sizeof(szValue);
168 L"\\Registry\\Machine\\SYSTEM\\CurrentControlSet\\Control\\FontAssoc\\Associated Charset",
173 cbData =
sizeof(szValue);
181 cbData =
sizeof(szValue);
189 cbData =
sizeof(szValue);
224 if (pChain->pszzFontLink)
264 ASSERT(pNewHead != pOldHead);
289 pCache->
LogFont = pChain->LogFont;
290 pCache->
Chain = *pChain;
329#define HIGH_SURROGATE_MIN 0xD800U
330#define HIGH_SURROGATE_MAX 0xDBFFU
331#define LOW_SURROGATE_MIN 0xDC00U
332#define LOW_SURROGATE_MAX 0xDFFFU
334#define IS_HIGH_SURROGATE(ch0) (HIGH_SURROGATE_MIN <= (ch0) && (ch0) <= HIGH_SURROGATE_MAX)
335#define IS_LOW_SURROGATE(ch1) (LOW_SURROGATE_MIN <= (ch1) && (ch1) <= LOW_SURROGATE_MAX)
344#ifndef _TMPF_VARIABLE_PITCH
345 #define _TMPF_VARIABLE_PITCH TMPF_FIXED_PITCH
349#define EMUBOLD_NEEDED(original, request) \
350 (((request) != FW_DONTCARE) && ((request) - (original) >= FW_BOLD - FW_MEDIUM))
358#define gmxWorldToDeviceDefault gmxWorldToPageDefault
364 RTL_CONSTANT_STRING(
L"\\REGISTRY\\Machine\\Software\\Microsoft\\Windows NT\\CurrentVersion\\Fonts");
374#define ASSERT_FREETYPE_LOCK_HELD() \
375 ASSERT(g_FreeTypeLock->Owner == KeGetCurrentThread())
377#define ASSERT_FREETYPE_LOCK_NOT_HELD() \
378 ASSERT(g_FreeTypeLock->Owner != KeGetCurrentThread())
380#define IntLockFreeType() \
382 ASSERT_FREETYPE_LOCK_NOT_HELD(); \
383 ExEnterCriticalRegionAndAcquireFastMutexUnsafe(g_FreeTypeLock); \
386#define IntUnLockFreeType() \
388 ASSERT_FREETYPE_LOCK_HELD(); \
389 ExReleaseFastMutexUnsafeAndLeaveCriticalRegion(g_FreeTypeLock); \
392#define MAX_FONT_CACHE 256
424#define MAXTCIINDEX 32
515 if (pFontLink->bIgnore)
518 if (pFontLink->SharedFace)
535 pFontLink->bIgnore =
TRUE;
539 pFontGDI =
ObjToGDI(pFontObj, FONT);
547 pFontLink->bIgnore =
TRUE;
568 Cache->OutlineRequiredSize = 0;
602 Ptr->IsMapping = IsMapping;
603 DPRINT(
"Creating SharedMem for %p (%i, %p)\n",
Buffer, IsMapping,
Ptr);
636 for (CurrentEntry = g_FontCacheListHead.
Flink;
637 CurrentEntry != &g_FontCacheListHead;
638 CurrentEntry = NextEntry)
641 NextEntry = CurrentEntry->
Flink;
655 if (
Ptr->RefCount <= 0)
659 if (
Ptr->RefCount == 0)
661 DPRINT(
"Releasing SharedMem for %p (%i, %p)\n",
Ptr->Buffer,
Ptr->IsMapping,
Ptr);
683 if (
Ptr->RefCount <= 0)
687 if (
Ptr->RefCount == 0)
689 DPRINT(
"Releasing SharedFace for %s\n",
Ptr->Face->family_name ?
Ptr->Face->family_name :
"<NULL>");
731 pt->x.fract = (
vec->
x & 0x3f) << 10;
732 pt->x.fract |= ((
pt->x.fract >> 6) | (
pt->x.fract >> 12));
734 pt->y.fract = (
vec->
y & 0x3f) << 10;
735 pt->y.fract |= ((
pt->y.fract >> 6) | (
pt->y.fract >> 12));
752 const char *style_name;
771 style_name =
"<invalid>";
774 DPRINT(
"family_name '%s', style_name '%s', FaceName '%wZ', StyleName '%wZ', FontGDI %p, "
775 "FontObj %p, iUnique %lu, SharedFace %p, Face %p, CharSet %u, Filename '%S'\n",
794 DPRINT(
"## DumpFontList(%p)\n", Head);
799 DumpFontEntry(CurrentEntry);
805 DPRINT(
"%wZ,%u -> %wZ,%u\n",
818 DPRINT(
"## DumpFontSubstList\n");
820 for (pListEntry = pHead->
Flink;
822 pListEntry = pListEntry->
Flink)
825 DumpFontSubstEntry(pSubstEntry);
829VOID DumpPrivateFontList(
BOOL bDoLock)
851VOID DumpGlobalFontList(
BOOL bDoLock)
856 DumpFontList(&g_FontListHead);
864 DumpGlobalFontList(bDoLock);
865 DumpPrivateFontList(bDoLock);
882 BYTE InfoBuffer[128];
891 L"Microsoft\\Windows NT\\CurrentVersion\\"
907 &KeyFullInfo,
sizeof(KeyFullInfo), &
Length);
920 InfoBuffer,
sizeof(InfoBuffer), &
Length);
934 DPRINT(
"RtlCreateUnicodeString failed\n");
940 InfoBuffer,
sizeof(InfoBuffer), &
Length);
956 DPRINT(
"RtlCreateUnicodeString failed\n");
998 DPRINT(
"ExAllocatePoolWithTag failed\n");
1037 DPRINT1(
"FT_Init_FreeType failed with error code 0x%x\n", ulError);
1043 DPRINT1(
"Fonts registry is empty.\n");
1074 pHead = &g_FontCacheListHead;
1083 pHead = &g_FontSubstListHead;
1092 pHead = &g_FontListHead;
1112 nTenthsOfDegrees %= 360 * 10;
1113 if (nTenthsOfDegrees >= 0)
1114 return nTenthsOfDegrees;
1115 return nTenthsOfDegrees + 360 * 10;
1124 pmat->
xx = vecAngle.
x;
1125 pmat->
xy = -vecAngle.
y;
1126 pmat->
yx = -pmat->
xy;
1127 pmat->
yy = pmat->
xx;
1163 BYTE RequestedCharSet,
1174 for (pListEntry = pHead->
Flink;
1175 pListEntry != pHead;
1176 pListEntry = pListEntry->
Flink)
1261 UINT RecurseCount = 5;
1272 while (RecurseCount-- > 0)
1275 &OutputNameW, &InputNameW,
1301 pChain->pBaseTextObj = pTextObj;
1302 pChain->pDefFace =
face;
1308 L"tahoma.ttf,Tahoma\0"
1309 L"msgothic.ttc,MS UI Gothic\0"
1310 L"mingliu.ttc,PMingLiU\0"
1311 L"simsun.ttc,SimSun\0"
1312 L"gulim.ttc,Gulim\0"
1316 L"cour.ttf,Courier New\0"
1317 L"msgothic.ttc,MS Gothic\0"
1318 L"mingliu.ttc,MingLiU\0"
1319 L"simsun.ttc,NSimSun\0"
1320 L"gulim.ttc,GulimChe\0"
1331 WCHAR szzFontLink[512];
1335 ASSERT(pLF->lfFaceName[0]);
1339 L"\\Registry\\Machine\\Software\\Microsoft\\Windows NT\\CurrentVersion\\FontLink\\SystemLink",
1345 cbData =
sizeof(szzFontLink);
1352 cbData =
sizeof(szzFontLink);
1359 if (cbData >= 2 *
sizeof(
WCHAR))
1361 FontLinkSize = cbData;
1372 pszzFontLink =
NULL;
1409 pChain->pszzFontLink = pszzFontLink;
1480 PTEXTOBJ pTextObj = pChain->pBaseTextObj;
1507 default: bFixCharSet =
TRUE;
break;
1517 *pChain = pLinkCache->
Chain;
1523 pChain->LogFont = lfBase;
1530 pszLink = pChain->pszzFontLink;
1533 DPRINT(
"pszLink: '%S'\n", pszLink);
1537 pszLink +=
wcslen(pszLink) + 1;
1546 DPRINT(
"szEntry: '%S'\n", szEntry);
1568 BYTE *DirInfoBuffer;
1610 if (DirInfoBuffer ==
NULL)
1628 Status = ZwQueryDirectoryFile(
1679 bRestartScan =
FALSE;
1695 if (CodePageRange1 == 0)
1700 for (BitIndex = 0; BitIndex <
MAXTCIINDEX; ++BitIndex)
1702 if (CodePageRange1 & (1 << BitIndex))
1705 if ((nIndex >= 0) && (nCount == (
UINT)nIndex))
1717#define PX2PT(pixels) FT_MulDiv((pixels), 72, 96)
1745 Face = SharedFace->
Face;
1892 if (pOS2 && os2_version >= 1)
1899 for (BitIndex = 0; BitIndex <
MAXTCIINDEX; ++BitIndex)
1901 if (os2_ulCodePageRange1 & (1 << BitIndex))
1906 if ((CharSetIndex == -1 && CharSetCount == 0) ||
1907 CharSetIndex == CharSetCount)
1932 DPRINT(
"Font loaded: %s (%s)\n",
1939 Entry->Font = FontGDI;
1940 Entry->NotEnum = (Characteristics & FR_NOT_ENUM);
1943 if (Characteristics & FR_PRIVATE)
1958 if (CharSetIndex == -1)
1963 if (
Entry->StyleName.Length)
1964 NameLength +=
Entry->StyleName.Length +
sizeof(
WCHAR);
1992 *pValueName = NewString;
1994 if (
Entry->StyleName.Length)
2000 for (
i = 1;
i < CharSetCount; ++
i)
2024 ((FontIndex == -1) ? 0 : FontIndex), &Face);
2027 if (
Error == FT_Err_Unknown_File_Format)
2028 DPRINT1(
"Unknown font file format\n");
2030 DPRINT1(
"Error reading font (error code: %d)\n",
Error);
2043 DPRINT1(
"SharedFace_Create failed\n");
2048 if (FontIndex == -1)
2085 default:
return L"Unknown";
2124 RtlInitEmptyUnicodeString(&PathName, pszBuffer,
Length);
2147 DPRINT1(
"Could not load font file: %wZ\n", &PathName);
2156 DPRINT1(
"ObReferenceObjectByHandle failed.\n");
2169 DPRINT1(
"Could not map file: %wZ\n", &PathName);
2180 DPRINT1(
"Could not map file: %wZ\n", &PathName);
2190 LoadFont.Characteristics = Characteristics;
2218 RtlInitEmptyUnicodeString(&NewString, pszBuffer,
Length);
2241 RtlInitEmptyUnicodeString(&NewString, pszBuffer,
Length);
2267 pFileName = PathName.
Buffer;
2302 if (!lpszPath || !*lpszPath)
2304 if (*lpszPath ==
L'\\' || (*lpszPath && lpszPath[1] ==
L':'))
2339 &KeyFullInfo,
sizeof(KeyFullInfo), &
Length);
2352 DPRINT1(
"ExAllocatePoolWithTag failed\n");
2358 for (
i = 0;
i < KeyFullInfo.
Values; ++
i)
2362 InfoBuffer, InfoSize, &
Length);
2371 DPRINT1(
"ExAllocatePoolWithTag failed\n");
2376 InfoBuffer, InfoSize, &
Length);
2391 DPRINT1(
"RtlCreateUnicodeString failed\n");
2397 InfoBuffer, InfoSize, &
Length);
2406 DPRINT1(
"ExAllocatePoolWithTag failed\n");
2411 InfoBuffer, InfoSize, &
Length);
2431 L"\\SystemRoot\\Fonts\\%s", pchPath);
2458 return (KeyFullInfo.
Values != 0 && nFontCount != 0);
2479 LoadFont.Characteristics = FR_PRIVATE | FR_NOT_ENUM;
2493 if (EntryCollection)
2503 Ret = EntryCollection->
Handle;
2565 if (CurrentEntry->
Handle == hMMFont)
2567 EntryCollection = CurrentEntry;
2575 if (EntryCollection)
2592 DPRINT(
"IntGdiCleanupPrivateFontsForProcess()\n");
2595 EntryCollection =
NULL;
2608 if (EntryCollection)
2686 if (lf->lfEscapement != lf->lfOrientation)
2780 int Ascent, Descent;
2837 - ((Ascent + Descent)
2839 YScale) + 32) >> 6);
3028 Names->OtmSize = OtmSize;
3108 if (
Size == 0 &&
Cache->OutlineRequiredSize > 0)
3111 return Cache->OutlineRequiredSize;
3126 return Cache->OutlineRequiredSize;
3131 if (Size < Cache->OutlineRequiredSize)
3133 DPRINT1(
"Size %u < OutlineRequiredSize %u\n",
Size,
3134 Cache->OutlineRequiredSize);
3153 DPRINT1(
"Can't find OS/2 table - not TT font?\n");
3162 DPRINT1(
"Can't find HHEA table - not TT font?\n");
3183#define SCALE_X(value) ((FT_MulFix((value), XScale) + 32) >> 6)
3184#define SCALE_Y(value) ((FT_MulFix((value), YScale) + 32) >> 6)
3233 return Cache->OutlineRequiredSize;
3300 INT i,
Count, BestIndex, Score, BestScore;
3341 if (
Name.name_id != NameID)
3354 (
Name.string[0] == 0 &&
Name.string[1] == 0))
3378 if (Score > BestScore)
3437 if (!
Cache->FontFamily.Buffer)
3443 if (!
Cache->FullName.Buffer)
3488 Lf = &
Info->EnumLogFontEx.elfLogFont;
3501 Ntm = &
Info->NewTextMetricEx.ntmTm;
3546 sizeof(
Info->EnumLogFontEx.elfFullName),
3550 StyleW.
Buffer =
Info->EnumLogFontEx.elfStyle;
3591 if (
fs.fsCsb[0] == 0)
3598 case FT_ENCODING_UNICODE:
3599 case FT_ENCODING_APPLE_ROMAN:
3602 case FT_ENCODING_MS_SYMBOL:
3614 if (
fs.fsCsb[0] & fs0)
3626 DPRINT1(
"Unknown elfscript for bit %u\n",
i);
3631 Info->NewTextMetricEx.ntmFontSig =
fs;
3651 FontGDI = CurrentEntry->
Font;
3778 const DWORD *pdw = pv;
3794 DWORD dwHash = pCache->dwHash;
3798 for (CurrentEntry = g_FontCacheListHead.
Flink;
3799 CurrentEntry != &g_FontCacheListHead;
3800 CurrentEntry = CurrentEntry->
Flink)
3803 if (FontEntry->
dwHash == dwHash &&
3805 FontEntry->
Hashed.
Face == pCache->Hashed.Face &&
3816 if (CurrentEntry == &g_FontCacheListHead)
3842 DPRINT1(
"Failure caching glyph.\n");
3850 DPRINT1(
"Failure rendering glyph.\n");
3857 DPRINT1(
"Alloc failure caching glyph.\n");
3864 if (FT_Bitmap_Convert_ReactOS_Hack(GlyphSlot->library, &BitmapGlyph->
bitmap,
3865 &AlignedBitmap, 4,
TRUE))
3867 DPRINT1(
"Conversion failed\n");
3875 BitmapGlyph->
bitmap = AlignedBitmap;
3896 int needed = 0,
point = 0, contour, first_pt;
3897 unsigned int pph_start, cpfx;
3900 for (contour = 0; contour <
outline->n_contours; contour++)
3917 needed +=
sizeof(*pph);
3919 while (point <= outline->contours[contour])
3931 }
while (point <= outline->contours[contour] &&
3943 else if (point <= outline->contours[contour] &&
3957 needed +=
sizeof(*ppc) + (cpfx - 1) *
sizeof(
POINTFX);
3960 pph->
cb = needed - pph_start;
3983 int contour,
point = 0, first_pt;
3988 unsigned int needed = 0;
3990 for (contour = 0; contour <
outline->n_contours; contour++)
4000 needed +=
sizeof(*pph);
4002 while (point <= outline->contours[contour])
4029 cubic_control[0].
x >>= 1;
4030 cubic_control[0].
y >>= 1;
4033 cubic_control[3] =
outline->points[first_pt];
4041 cubic_control[3].
x >>= 1;
4042 cubic_control[3].
y >>= 1;
4047 cubic_control[1].
x = (2 *
outline->points[
point].x + 1) / 3;
4048 cubic_control[1].
y = (2 *
outline->points[
point].y + 1) / 3;
4049 cubic_control[2] = cubic_control[1];
4050 cubic_control[1].
x += (cubic_control[0].
x + 1) / 3;
4051 cubic_control[1].
y += (cubic_control[0].
y + 1) / 3;
4052 cubic_control[2].
x += (cubic_control[3].
x + 1) / 3;
4053 cubic_control[2].
y += (cubic_control[3].
y + 1) / 3;
4063 }
while (point <= outline->contours[contour] &&
4069 if (point <= outline->contours[contour] &&
4081 needed +=
sizeof(*ppc) + (cpfx - 1) *
sizeof(
POINTFX);
4084 pph->
cb = needed - pph_start;
4098 LONG Ascent, Descent, Sum, EmHeight, Width64;
4100 lfWidth =
abs(lfWidth);
4105 DPRINT(
"lfHeight and lfWidth are zero.\n");
4128 if (!pOS2 || !pHori)
4133 DPRINT1(
"%s: Failed to request font size.\n",
face->family_name);
4157#define FM_SEL_USE_TYPO_METRICS 0x80
4166 Sum = Ascent + Descent;
4179 else if (lfHeight < 0)
4195#undef FM_SEL_USE_TYPO_METRICS
4202 EmHeight =
max(EmHeight, 1);
4215 Width64 = (
FT_MulDiv(lfWidth, 96 * 5, 72 * 3) << 6);
4221 req.
width = Width64;
4222 req.
height = (EmHeight << 6);
4246 DPRINT(
"WARNING: No charmap selected!\n");
4247 DPRINT(
"This font face has %d charmaps\n",
face->num_charmaps);
4250 for (
n = 0;
n <
face->num_charmaps;
n++)
4252 charmap =
face->charmaps[
n];
4253 if (charmap->
encoding == FT_ENCODING_UNICODE)
4261 for (
n = 0;
n <
face->num_charmaps;
n++)
4263 charmap =
face->charmaps[
n];
4273 for (
n = 0;
n <
face->num_charmaps;
n++)
4275 charmap =
face->charmaps[
n];
4276 if (charmap->
encoding == FT_ENCODING_MS_SYMBOL)
4283 if (!found &&
face->num_charmaps > 0)
4285 found =
face->charmaps[0];
4289 DPRINT1(
"WARNING: Could not find desired charmap!\n");
4297 DPRINT1(
"WARNING: Could not set the charmap!\n");
4323 if (glyph < 0x100) glyph += 0xf000;
4350 return (fCodeAsIndex ?
code :