gdi32: Use ANSI character code as glyph index for bitmap fonts.

This commit is contained in:
Akihiro Sagawa 2013-12-11 21:11:17 +09:00 committed by Alexandre Julliard
parent 882398b0a9
commit a88a121059
2 changed files with 137 additions and 2 deletions

View File

@ -6216,8 +6216,14 @@ static DWORD get_glyph_outline(GdiFont *incoming_font, UINT glyph, UINT format,
font->font_desc.matrix.eM21, font->font_desc.matrix.eM22); font->font_desc.matrix.eM21, font->font_desc.matrix.eM22);
if(format & GGO_GLYPH_INDEX) { if(format & GGO_GLYPH_INDEX) {
if(font->ft_face->charmap->encoding == FT_ENCODING_NONE) {
/* Windows bitmap font, e.g. Small Fonts, uses ANSI character code
as glyph index. "Tresure Adventure Game" depends on this. */
glyph_index = pFT_Get_Char_Index(font->ft_face, glyph);
TRACE("translate glyph index %04x -> %04x\n", glyph, glyph_index);
} else
glyph_index = glyph; glyph_index = glyph;
original_index = glyph; original_index = glyph_index;
format &= ~GGO_GLYPH_INDEX; format &= ~GGO_GLYPH_INDEX;
/* TODO: Window also turns off tategaki for glyphs passed in by index /* TODO: Window also turns off tategaki for glyphs passed in by index
if their unicode code points fall outside of the range that is if their unicode code points fall outside of the range that is

View File

@ -5704,6 +5704,134 @@ static void test_fake_bold_font(void)
} }
static void test_bitmap_font_glyph_index(void)
{
const WCHAR text[] = {'#','!','/','b','i','n','/','s','h',0};
const struct {
LPCSTR face;
BYTE charset;
} bitmap_font_list[] = {
{ "Courier", ANSI_CHARSET },
{ "Small Fonts", ANSI_CHARSET },
{ "Fixedsys", DEFAULT_CHARSET },
{ "System", DEFAULT_CHARSET }
};
HDC hdc;
LOGFONTA lf;
HFONT hFont;
CHAR facename[LF_FACESIZE];
BITMAPINFO bmi;
HBITMAP hBmp[2];
void *pixels[2];
int i, j;
DWORD ret;
BITMAP bmp;
TEXTMETRICA tm;
CHARSETINFO ci;
BYTE chr = '\xA9';
hdc = CreateCompatibleDC(0);
ok(hdc != NULL, "CreateCompatibleDC failed\n");
memset(&bmi, 0, sizeof(bmi));
bmi.bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
bmi.bmiHeader.biBitCount = 32;
bmi.bmiHeader.biPlanes = 1;
bmi.bmiHeader.biWidth = 128;
bmi.bmiHeader.biHeight = 32;
bmi.bmiHeader.biCompression = BI_RGB;
for (i = 0; i < sizeof(bitmap_font_list)/sizeof(bitmap_font_list[0]); i++) {
memset(&lf, 0, sizeof(lf));
lf.lfCharSet = bitmap_font_list[i].charset;
strcpy(lf.lfFaceName, bitmap_font_list[i].face);
hFont = CreateFontIndirectA(&lf);
ok(hFont != NULL, "Can't create font (%s:%d)\n", lf.lfFaceName, lf.lfCharSet);
hFont = SelectObject(hdc, hFont);
ret = GetTextMetricsA(hdc, &tm);
ok(ret, "GetTextMetric failed\n");
ret = GetTextFaceA(hdc, sizeof(facename), facename);
ok(ret, "GetTextFace failed\n");
if (tm.tmPitchAndFamily & TMPF_TRUETYPE) {
skip("TrueType font (%s) was selected for \"%s\"\n", facename, bitmap_font_list[i].face);
continue;
}
if (lstrcmpiA(facename, lf.lfFaceName) != 0) {
skip("expected %s, got %s\n", lf.lfFaceName, facename);
continue;
}
for (j = 0; j < 2; j++) {
HBITMAP hBmpPrev;
hBmp[j] = CreateDIBSection(hdc, &bmi, DIB_RGB_COLORS, &pixels[j], NULL, 0);
ok(hBmp[j] != NULL, "Can't create DIB\n");
hBmpPrev = SelectObject(hdc, hBmp[j]);
switch (j) {
case 0:
ret = ExtTextOutW(hdc, 0, 0, 0, NULL, text, lstrlenW(text), NULL);
break;
case 1:
{
int len = lstrlenW(text);
LPWORD indices = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WORD));
ret = GetGlyphIndicesW(hdc, text, len, indices, 0);
ok(ret, "GetGlyphIndices failed\n");
ok(memcmp(indices, text, sizeof(WORD) * len) == 0,
"Glyph indices and text are different for %s:%d\n", lf.lfFaceName, tm.tmCharSet);
ret = ExtTextOutW(hdc, 0, 0, ETO_GLYPH_INDEX, NULL, indices, len, NULL);
HeapFree(GetProcessHeap(), 0, indices);
break;
}
}
ok(ret, "ExtTextOutW failed\n");
SelectObject(hdc, hBmpPrev);
}
GetObjectA(hBmp[0], sizeof(bmp), &bmp);
ok(memcmp(pixels[0], pixels[1], bmp.bmHeight * bmp.bmWidthBytes) == 0,
"Images are different (%s:%d)\n", lf.lfFaceName, tm.tmCharSet);
ret = TranslateCharsetInfo((LPDWORD)(DWORD_PTR)tm.tmCharSet, &ci, TCI_SRCCHARSET);
if (!ret) {
skip("Can't get charset info for (%s:%d)\n", lf.lfFaceName, tm.tmCharSet);
goto next;
}
if (IsDBCSLeadByteEx(ci.ciACP, chr)) {
skip("High-ascii character is not defined in codepage %d\n", ci.ciACP);
goto next;
}
for (j = 0; j < 2; j++) {
HBITMAP hBmpPrev;
WORD code;
hBmpPrev = SelectObject(hdc, hBmp[j]);
switch (j) {
case 0:
ret = ExtTextOutA(hdc, 100, 0, 0, NULL, (LPCSTR)&chr, 1, NULL);
break;
case 1:
ret = GetGlyphIndicesA(hdc, (LPCSTR)&chr, 1, &code, 0);
ok(ret, "GetGlyphIndices failed\n");
ok(code == chr, "expected %02x, got %02x (%s:%d)\n", chr, code, lf.lfFaceName, tm.tmCharSet);
ret = ExtTextOutA(hdc, 100, 0, ETO_GLYPH_INDEX, NULL, (LPCSTR)&code, 1, NULL);
break;
}
ok(ret, "ExtTextOutA failed\n");
SelectObject(hdc, hBmpPrev);
}
ok(memcmp(pixels[0], pixels[1], bmp.bmHeight * bmp.bmWidthBytes) == 0,
"Images are different (%s:%d)\n", lf.lfFaceName, tm.tmCharSet);
next:
for (j = 0; j < 2; j++)
DeleteObject(hBmp[j]);
hFont = SelectObject(hdc, hFont);
DeleteObject(hFont);
}
DeleteDC(hdc);
}
START_TEST(font) START_TEST(font)
{ {
init(); init();
@ -5764,6 +5892,7 @@ START_TEST(font)
test_vertical_order(); test_vertical_order();
test_GetCharWidth32(); test_GetCharWidth32();
test_fake_bold_font(); test_fake_bold_font();
test_bitmap_font_glyph_index();
/* These tests should be last test until RemoveFontResource /* These tests should be last test until RemoveFontResource
* is properly implemented. * is properly implemented.