Fixes eden* PLUS+MOSAIC.
Wine-Bug: https://bugs.winehq.org/show_bug.cgi?id=45400 Signed-off-by: Arkadiusz Hiler ahiler@codeweavers.com ---
Supersedes 193433
v4: * shorten commit message * shorten ok() messages * old compiler compatibility * fetch glyph 0x10003 metrics to a correct GLYPHMETRICS
v3:
* ReleaseDC instead of DeleteDC * test only with 0x10000 offset * test GGO_GLYPH_INDEX masking * don't print ret and GetLastError() in case of GetGlyphOutlineW failure we get GDI_ERROR and last error is not used * simplify comparing GLYPHMETRICS - memcmp
v2:
While investigating the failures with zh_CN locale I figured out that I did some mistakes in my font definition and that I can just reuse wine-test.ttf:
* It has .notdef with a distinct width * It has a few characters defined which are handy to test
The changes are: * use wine_test font, it's even better than what I had * make sure that our character is different than .notdef * test multiple characters * test multiple values in the higher bytes * make sure that no matter what we put past the two lower bytes we get the same character
dlls/gdi32/font.c | 2 ++ dlls/gdi32/tests/font.c | 52 +++++++++++++++++++++++++++++++++++++++++ 2 files changed, 54 insertions(+)
diff --git a/dlls/gdi32/font.c b/dlls/gdi32/font.c index a71b24423ac..3c5a6e9a231 100644 --- a/dlls/gdi32/font.c +++ b/dlls/gdi32/font.c @@ -2911,6 +2911,8 @@ DWORD WINAPI GetGlyphOutlineW( HDC hdc, UINT uChar, UINT fuFormat, dc = get_dc_ptr(hdc); if(!dc) return GDI_ERROR;
+ uChar &= 0xffff; + dev = GET_DC_PHYSDEV( dc, pGetGlyphOutline ); ret = dev->funcs->pGetGlyphOutline( dev, uChar, fuFormat, lpgm, cbBuffer, lpBuffer, lpmat2 ); release_dc_ptr( dc ); diff --git a/dlls/gdi32/tests/font.c b/dlls/gdi32/tests/font.c index 0ada22d95d5..4c8b1cbb91b 100644 --- a/dlls/gdi32/tests/font.c +++ b/dlls/gdi32/tests/font.c @@ -5823,6 +5823,57 @@ todo_wine ReleaseDC(NULL, hdc); }
+static void test_GetGlyphOutline_character(void) +{ + HFONT hfont, hfont_old; + LOGFONTA lf; + HDC hdc; + DWORD ret; + GLYPHMETRICS gm1, gm2, gmn; + char test_chars[] = { 'A', 'D', '!', '\0' }; + char *current_char; + + memset(&lf, 0, sizeof(lf)); + lf.lfHeight = 72; + lstrcpyA(lf.lfFaceName, "wine_test"); + + hfont = CreateFontIndirectA(&lf); + ok(hfont != 0, "CreateFontIndirectA error %u\n", GetLastError()); + + hdc = GetDC(NULL); + + hfont_old = SelectObject(hdc, hfont); + ok(hfont_old != NULL, "SelectObject failed\n"); + + ret = GetGlyphOutlineW(hdc, 'Z', GGO_METRICS, &gmn, 0, NULL, &mat); + ok(ret != GDI_ERROR, "GetGlyphOutlineW failed to default to .notdef for character 'Z'\n"); + + for (current_char = test_chars; *current_char != '\0'; current_char++) + { + ret = GetGlyphOutlineW(hdc, *current_char, GGO_METRICS, &gm1, 0, NULL, &mat); + ok(ret != GDI_ERROR, "GetGlyphOutlineW failed for '%c'\n", *current_char); + ok(memcmp(&gm1, &gmn, sizeof(gmn)) != 0, "the test character '%c' matches .notdef\n", *current_char); + + ret = GetGlyphOutlineW(hdc, 0x10000 + *current_char, GGO_METRICS, &gm2, 0, NULL, &mat); + ok(ret != GDI_ERROR, "GetGlyphOutlineW failed for 0x10000 + '%c'\n", *current_char); + ok(memcmp(&gm1, &gm2, sizeof(gmn)) == 0, "GetGlyphOutlineW returned wrong metrics for character 0x10000 + '%c'\n", *current_char); + } + + ret = GetGlyphOutlineW(hdc, 0x3, GGO_METRICS|GGO_GLYPH_INDEX, &gm1, 0, NULL, &mat); + ok(ret != GDI_ERROR, "GetGlyphOutlineW failed for glyph index 0x3\n"); + + ret = GetGlyphOutlineW(hdc, 0xFFFF, GGO_METRICS|GGO_GLYPH_INDEX, &gm2, 0, NULL, &mat); + ok(ret == GDI_ERROR, "GetGlyphOutlineW for nonexistent glyph index 0xFFFF has succeded\n"); + + ret = GetGlyphOutlineW(hdc, 0x10003, GGO_METRICS|GGO_GLYPH_INDEX, &gm2, 0, NULL, &mat); + ok(ret != GDI_ERROR, "GetGlyphOutlineW for index 0x10003 has failed\n"); + ok(memcmp(&gm1, &gm2, sizeof(gmn)) == 0, "GetGlyphOutlineW returned wrong metrics for glyph 0x10003\n"); + + SelectObject(hdc, hfont_old); + DeleteObject(hfont); + ReleaseDC(NULL, hdc); +} + static void test_fstype_fixup(void) { HDC hdc; @@ -5945,6 +5996,7 @@ static void test_CreateScalableFontResource(void)
test_GetGlyphOutline_empty_contour(); test_GetGlyphOutline_metric_clipping(); + test_GetGlyphOutline_character(); test_fstype_fixup();
ret = pRemoveFontResourceExA(fot_name, FR_PRIVATE, 0);