gdiplus: Fix generic string formats behavior.

Signed-off-by: Nikolay Sivov <nsivov@codeweavers.com>
Signed-off-by: Vincent Povirk <vincent@codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
Nikolay Sivov 2017-04-28 01:20:31 +03:00 committed by Alexandre Julliard
parent 8b649fe2f4
commit 69b41e7cf3
5 changed files with 104 additions and 36 deletions

View File

@ -63,11 +63,13 @@ BOOL WINAPI DllMain(HINSTANCE hinst, DWORD reason, LPVOID reserved)
{
case DLL_PROCESS_ATTACH:
DisableThreadLibraryCalls( hinst );
init_generic_string_formats();
break;
case DLL_PROCESS_DETACH:
if (reserved) break;
free_installed_fonts();
free_generic_string_formats();
break;
}
return TRUE;

View File

@ -441,6 +441,8 @@ struct GpFont{
Unit unit;
};
extern const struct GpStringFormat default_drawstring_format DECLSPEC_HIDDEN;
struct GpStringFormat{
INT attr;
LANGID lang;
@ -458,6 +460,9 @@ struct GpStringFormat{
BOOL generic_typographic;
};
extern void init_generic_string_formats(void) DECLSPEC_HIDDEN;
extern void free_generic_string_formats(void) DECLSPEC_HIDDEN;
struct GpFontCollection{
GpFontFamily **FontFamilies;
INT count;

View File

@ -4909,7 +4909,6 @@ GpStatus gdip_format_string(HDC hdc,
INT hotkeyprefix_count=0;
INT hotkeyprefix_pos=0, hotkeyprefix_end_pos=0;
BOOL seen_prefix = FALSE;
GpStringFormat *dyn_format=NULL;
if(length == -1) length = lstrlenW(string);
@ -4917,15 +4916,7 @@ GpStatus gdip_format_string(HDC hdc,
if(!stringdup) return OutOfMemory;
if (!format)
{
stat = GdipStringFormatGetGenericDefault(&dyn_format);
if (stat != Ok)
{
heap_free(stringdup);
return stat;
}
format = dyn_format;
}
format = &default_drawstring_format;
nwidth = rect->Width;
nheight = rect->Height;
@ -5075,7 +5066,6 @@ GpStatus gdip_format_string(HDC hdc,
heap_free(stringdup);
heap_free(hotkeyprefix_offsets);
GdipDeleteStringFormat(dyn_format);
return stat;
}

View File

@ -32,6 +32,47 @@
WINE_DEFAULT_DEBUG_CHANNEL(gdiplus);
const GpStringFormat default_drawstring_format =
{
0,
LANG_NEUTRAL,
LANG_NEUTRAL,
StringAlignmentNear,
StringTrimmingCharacter,
HotkeyPrefixNone,
StringAlignmentNear,
StringDigitSubstituteUser,
0,
0.0,
NULL,
NULL,
0,
FALSE
};
static GpStringFormat generic_default_format;
static GpStringFormat generic_typographic_format;
void init_generic_string_formats(void)
{
memcpy(&generic_default_format, &default_drawstring_format, sizeof(generic_default_format));
memcpy(&generic_typographic_format, &default_drawstring_format, sizeof(generic_typographic_format));
generic_typographic_format.attr = StringFormatFlagsNoFitBlackBox | StringFormatFlagsLineLimit |
StringFormatFlagsNoClip;
generic_typographic_format.trimming = StringTrimmingNone;
generic_typographic_format.generic_typographic = TRUE;
}
void free_generic_string_formats(void)
{
heap_free(generic_default_format.character_ranges);
heap_free(generic_default_format.tabs);
heap_free(generic_typographic_format.character_ranges);
heap_free(generic_typographic_format.tabs);
}
GpStatus WINGDIPAPI GdipCreateStringFormat(INT attr, LANGID lang,
GpStringFormat **format)
{
@ -66,6 +107,9 @@ GpStatus WINGDIPAPI GdipDeleteStringFormat(GpStringFormat *format)
if(!format)
return InvalidParameter;
if (format == &generic_default_format || format == &generic_typographic_format)
return Ok;
heap_free(format->character_ranges);
heap_free(format->tabs);
heap_free(format);
@ -75,17 +119,10 @@ GpStatus WINGDIPAPI GdipDeleteStringFormat(GpStringFormat *format)
GpStatus WINGDIPAPI GdipStringFormatGetGenericDefault(GpStringFormat **format)
{
GpStatus stat;
if (!format)
return InvalidParameter;
stat = GdipCreateStringFormat(0, LANG_NEUTRAL, format);
if(stat != Ok)
return stat;
(*format)->align = StringAlignmentNear;
(*format)->vertalign = StringAlignmentNear;
*format = &generic_default_format;
return Ok;
}
@ -370,24 +407,10 @@ GpStatus WINGDIPAPI GdipCloneStringFormat(GDIPCONST GpStringFormat *format, GpSt
GpStatus WINGDIPAPI GdipStringFormatGetGenericTypographic(GpStringFormat **format)
{
GpStatus stat;
if(!format)
return InvalidParameter;
stat = GdipCreateStringFormat(StringFormatFlagsNoFitBlackBox |
StringFormatFlagsLineLimit |
StringFormatFlagsNoClip, LANG_NEUTRAL, format);
if(stat != Ok)
return stat;
(*format)->digitlang = LANG_NEUTRAL;
(*format)->digitsub = StringDigitSubstituteUser;
(*format)->trimming = StringTrimmingNone;
(*format)->hkprefix = HotkeyPrefixNone;
(*format)->align = StringAlignmentNear;
(*format)->vertalign = StringAlignmentNear;
(*format)->generic_typographic = TRUE;
*format = &generic_typographic_format;
TRACE("%p => %p\n", format, *format);

View File

@ -140,7 +140,7 @@ static void test_digitsubstitution(void)
static void test_getgenerictypographic(void)
{
GpStringFormat *format;
GpStringFormat *format, *format2;
GpStatus stat;
INT flags;
INT n;
@ -157,6 +157,12 @@ static void test_getgenerictypographic(void)
stat = GdipStringFormatGetGenericTypographic(&format);
expect(Ok, stat);
stat = GdipStringFormatGetGenericTypographic(&format2);
expect(Ok, stat);
ok(format == format2, "expected same format object\n");
stat = GdipDeleteStringFormat(format2);
expect(Ok, stat);
GdipGetStringFormatFlags(format, &flags);
GdipGetStringFormatAlign(format, &align);
GdipGetStringFormatLineAlign(format, &line_align);
@ -175,6 +181,24 @@ static void test_getgenerictypographic(void)
expect(LANG_NEUTRAL, digitlang);
expect(0, tabcount);
/* Change format parameters, release, get format object again. */
stat = GdipSetStringFormatFlags(format, StringFormatFlagsNoWrap);
expect(Ok, stat);
stat = GdipGetStringFormatFlags(format, &flags);
expect(Ok, stat);
expect(StringFormatFlagsNoWrap, flags);
stat = GdipDeleteStringFormat(format);
expect(Ok, stat);
stat = GdipStringFormatGetGenericTypographic(&format);
expect(Ok, stat);
stat = GdipGetStringFormatFlags(format, &flags);
expect(Ok, stat);
expect(StringFormatFlagsNoWrap, flags);
stat = GdipDeleteStringFormat(format);
expect(Ok, stat);
}
@ -286,7 +310,7 @@ static void test_tabstops(void)
static void test_getgenericdefault(void)
{
GpStringFormat *format;
GpStringFormat *format, *format2;
GpStatus stat;
INT flags;
@ -304,6 +328,12 @@ static void test_getgenericdefault(void)
stat = GdipStringFormatGetGenericDefault(&format);
expect(Ok, stat);
stat = GdipStringFormatGetGenericDefault(&format2);
expect(Ok, stat);
ok(format == format2, "expected same format object\n");
stat = GdipDeleteStringFormat(format2);
expect(Ok, stat);
GdipGetStringFormatFlags(format, &flags);
GdipGetStringFormatAlign(format, &align);
GdipGetStringFormatLineAlign(format, &line_align);
@ -321,6 +351,24 @@ static void test_getgenericdefault(void)
expect(LANG_NEUTRAL, digitlang);
expect(0, tabcount);
/* Change default format parameters, release, get format object again. */
stat = GdipSetStringFormatFlags(format, StringFormatFlagsNoWrap);
expect(Ok, stat);
stat = GdipGetStringFormatFlags(format, &flags);
expect(Ok, stat);
expect(StringFormatFlagsNoWrap, flags);
stat = GdipDeleteStringFormat(format);
expect(Ok, stat);
stat = GdipStringFormatGetGenericDefault(&format);
expect(Ok, stat);
stat = GdipGetStringFormatFlags(format, &flags);
expect(Ok, stat);
expect(StringFormatFlagsNoWrap, flags);
stat = GdipDeleteStringFormat(format);
expect(Ok, stat);
}