dwrite: Fix lfItalic flag as returned by ConvertFontToLOGFONT().
Signed-off-by: Nikolay Sivov <nsivov@codeweavers.com> Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
parent
3316f90418
commit
a7fd13c244
|
@ -200,6 +200,7 @@ extern HRESULT create_fontfacereference(IDWriteFactory4*,IDWriteFontFile*,UINT32
|
|||
extern HRESULT factory_get_cached_fontface(IDWriteFactory4*,IDWriteFontFile*const*,UINT32,DWRITE_FONT_SIMULATIONS,IDWriteFontFace**,
|
||||
struct list**) DECLSPEC_HIDDEN;
|
||||
extern void factory_cache_fontface(struct list*,IDWriteFontFace4*) DECLSPEC_HIDDEN;
|
||||
extern void get_logfont_from_font(IDWriteFont*,LOGFONTW*) DECLSPEC_HIDDEN;
|
||||
|
||||
/* Opentype font table functions */
|
||||
struct dwrite_font_props {
|
||||
|
@ -207,6 +208,7 @@ struct dwrite_font_props {
|
|||
DWRITE_FONT_STRETCH stretch;
|
||||
DWRITE_FONT_WEIGHT weight;
|
||||
DWRITE_PANOSE panose;
|
||||
LOGFONTW lf;
|
||||
};
|
||||
|
||||
struct file_stream_desc {
|
||||
|
|
|
@ -19,6 +19,8 @@
|
|||
* License along with this library; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
*/
|
||||
|
||||
#include <assert.h>
|
||||
#include <math.h>
|
||||
|
||||
#define COBJMACROS
|
||||
|
@ -90,6 +92,8 @@ struct dwrite_font_data {
|
|||
|
||||
USHORT simulations;
|
||||
|
||||
LOGFONTW lf;
|
||||
|
||||
/* used to mark font as tested when scanning for simulation candidate */
|
||||
BOOL bold_sim_tested : 1;
|
||||
BOOL oblique_sim_tested : 1;
|
||||
|
@ -1673,6 +1677,20 @@ static const IDWriteFont3Vtbl dwritefontvtbl = {
|
|||
dwritefont3_GetLocality
|
||||
};
|
||||
|
||||
static struct dwrite_font *unsafe_impl_from_IDWriteFont(IDWriteFont *iface)
|
||||
{
|
||||
if (!iface)
|
||||
return NULL;
|
||||
assert(iface->lpVtbl == (IDWriteFontVtbl*)&dwritefontvtbl);
|
||||
return CONTAINING_RECORD(iface, struct dwrite_font, IDWriteFont3_iface);
|
||||
}
|
||||
|
||||
void get_logfont_from_font(IDWriteFont *iface, LOGFONTW *lf)
|
||||
{
|
||||
struct dwrite_font *font = unsafe_impl_from_IDWriteFont(iface);
|
||||
*lf = font->data->lf;
|
||||
}
|
||||
|
||||
static HRESULT create_font(struct dwrite_font_data *data, IDWriteFontFamily1 *family, IDWriteFont3 **font)
|
||||
{
|
||||
struct dwrite_font *This;
|
||||
|
@ -3244,6 +3262,7 @@ static HRESULT init_font_data(const struct fontface_desc *desc, IDWriteLocalized
|
|||
data->stretch = props.stretch;
|
||||
data->weight = props.weight;
|
||||
data->panose = props.panose;
|
||||
data->lf = props.lf;
|
||||
|
||||
fontstrings_get_en_string(*family_name, familyW, sizeof(familyW)/sizeof(WCHAR));
|
||||
fontstrings_get_en_string(data->names, faceW, sizeof(faceW)/sizeof(WCHAR));
|
||||
|
@ -3446,6 +3465,7 @@ static void fontfamily_add_oblique_simulated_face(struct dwrite_fontfamily_data
|
|||
|
||||
if (init_font_data_from_font(family->fonts[regular], DWRITE_FONT_SIMULATIONS_OBLIQUE, facenameW, &obliqueface) == S_OK) {
|
||||
obliqueface->oblique_sim_tested = 1;
|
||||
obliqueface->lf.lfItalic = 1;
|
||||
fontfamily_add_font(family, obliqueface);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -624,11 +624,9 @@ static HRESULT WINAPI gdiinterop_ConvertFontToLOGFONT(IDWriteGdiInterop1 *iface,
|
|||
{
|
||||
struct gdiinterop *This = impl_from_IDWriteGdiInterop1(iface);
|
||||
static const WCHAR enusW[] = {'e','n','-','u','s',0};
|
||||
DWRITE_FONT_SIMULATIONS simulations;
|
||||
IDWriteFontCollection *collection;
|
||||
IDWriteLocalizedStrings *name;
|
||||
IDWriteFontFamily *family;
|
||||
DWRITE_FONT_STYLE style;
|
||||
UINT32 index;
|
||||
BOOL exists;
|
||||
HRESULT hr;
|
||||
|
@ -654,12 +652,9 @@ static HRESULT WINAPI gdiinterop_ConvertFontToLOGFONT(IDWriteGdiInterop1 *iface,
|
|||
*is_systemfont = is_system_collection(collection);
|
||||
IDWriteFontCollection_Release(collection);
|
||||
|
||||
simulations = IDWriteFont_GetSimulations(font);
|
||||
style = IDWriteFont_GetStyle(font);
|
||||
|
||||
get_logfont_from_font(font, logfont);
|
||||
logfont->lfCharSet = DEFAULT_CHARSET;
|
||||
logfont->lfWeight = IDWriteFont_GetWeight(font);
|
||||
logfont->lfItalic = style == DWRITE_FONT_STYLE_ITALIC || (simulations & DWRITE_FONT_SIMULATIONS_OBLIQUE);
|
||||
logfont->lfOutPrecision = OUT_OUTLINE_PRECIS;
|
||||
logfont->lfFaceName[0] = 0;
|
||||
|
||||
|
|
|
@ -1285,6 +1285,7 @@ void opentype_get_font_properties(struct file_stream_desc *stream_desc, struct d
|
|||
props->weight = DWRITE_FONT_WEIGHT_NORMAL;
|
||||
props->style = DWRITE_FONT_STYLE_NORMAL;
|
||||
memset(&props->panose, 0, sizeof(props->panose));
|
||||
memset(&props->lf, 0, sizeof(props->lf));
|
||||
|
||||
/* DWRITE_FONT_STRETCH enumeration values directly match font data values */
|
||||
if (tt_os2) {
|
||||
|
@ -1306,8 +1307,10 @@ void opentype_get_font_properties(struct file_stream_desc *stream_desc, struct d
|
|||
|
||||
if (version >= 4 && (fsSelection & OS2_FSSELECTION_OBLIQUE))
|
||||
props->style = DWRITE_FONT_STYLE_OBLIQUE;
|
||||
else if (fsSelection & OS2_FSSELECTION_ITALIC)
|
||||
else if (fsSelection & OS2_FSSELECTION_ITALIC) {
|
||||
props->style = DWRITE_FONT_STYLE_ITALIC;
|
||||
props->lf.lfItalic = 1;
|
||||
}
|
||||
memcpy(&props->panose, &tt_os2->panose, sizeof(props->panose));
|
||||
}
|
||||
else if (tt_head) {
|
||||
|
@ -1321,8 +1324,10 @@ void opentype_get_font_properties(struct file_stream_desc *stream_desc, struct d
|
|||
if (macStyle & TT_HEAD_MACSTYLE_BOLD)
|
||||
props->weight = DWRITE_FONT_WEIGHT_BOLD;
|
||||
|
||||
if (macStyle & TT_HEAD_MACSTYLE_ITALIC)
|
||||
if (macStyle & TT_HEAD_MACSTYLE_ITALIC) {
|
||||
props->style = DWRITE_FONT_STYLE_ITALIC;
|
||||
props->lf.lfItalic = 1;
|
||||
}
|
||||
}
|
||||
|
||||
TRACE("stretch=%d, weight=%d, style %d\n", props->stretch, props->weight, props->style);
|
||||
|
|
|
@ -132,6 +132,17 @@ typedef struct
|
|||
SHORT glyphdata_format;
|
||||
} TT_HEAD;
|
||||
|
||||
enum TT_HEAD_MACSTYLE
|
||||
{
|
||||
TT_HEAD_MACSTYLE_BOLD = 1 << 0,
|
||||
TT_HEAD_MACSTYLE_ITALIC = 1 << 1,
|
||||
TT_HEAD_MACSTYLE_UNDERLINE = 1 << 2,
|
||||
TT_HEAD_MACSTYLE_OUTLINE = 1 << 3,
|
||||
TT_HEAD_MACSTYLE_SHADOW = 1 << 4,
|
||||
TT_HEAD_MACSTYLE_CONDENSED = 1 << 5,
|
||||
TT_HEAD_MACSTYLE_EXTENDED = 1 << 6,
|
||||
};
|
||||
|
||||
typedef struct
|
||||
{
|
||||
USHORT version;
|
||||
|
@ -3445,6 +3456,61 @@ static void test_TryGetFontTable(void)
|
|||
DELETE_FONTFILE(path);
|
||||
}
|
||||
|
||||
static void get_logfont_from_font(IDWriteFont *font, LOGFONTW *logfont)
|
||||
{
|
||||
DWRITE_FONT_STYLE style;
|
||||
|
||||
/* These are rendering time properties. */
|
||||
logfont->lfHeight = 0;
|
||||
logfont->lfWidth = 0;
|
||||
logfont->lfEscapement = 0;
|
||||
logfont->lfOrientation = 0;
|
||||
logfont->lfUnderline = 0;
|
||||
logfont->lfStrikeOut = 0;
|
||||
|
||||
logfont->lfItalic = 0;
|
||||
|
||||
if (IDWriteFont_GetSimulations(font) & DWRITE_FONT_SIMULATIONS_OBLIQUE)
|
||||
logfont->lfItalic = 1;
|
||||
|
||||
style = IDWriteFont_GetStyle(font);
|
||||
if (!logfont->lfItalic && ((style == DWRITE_FONT_STYLE_ITALIC) || (style == DWRITE_FONT_STYLE_OBLIQUE))) {
|
||||
void *os2_context, *head_context;
|
||||
IDWriteFontFace *fontface;
|
||||
const TT_OS2_V2 *tt_os2;
|
||||
const TT_HEAD *tt_head;
|
||||
UINT32 size;
|
||||
BOOL exists;
|
||||
HRESULT hr;
|
||||
|
||||
hr = IDWriteFont_CreateFontFace(font, &fontface);
|
||||
ok(hr == S_OK, "Failed to create font face, %#x\n", hr);
|
||||
|
||||
hr = IDWriteFontFace_TryGetFontTable(fontface, MS_0S2_TAG, (const void **)&tt_os2, &size,
|
||||
&os2_context, &exists);
|
||||
ok(hr == S_OK, "Failed to get OS/2 table, %#x\n", hr);
|
||||
|
||||
hr = IDWriteFontFace_TryGetFontTable(fontface, MS_HEAD_TAG, (const void **)&tt_head, &size,
|
||||
&head_context, &exists);
|
||||
ok(hr == S_OK, "Failed to get head table, %#x\n", hr);
|
||||
|
||||
if (tt_os2) {
|
||||
USHORT fsSelection = GET_BE_WORD(tt_os2->fsSelection);
|
||||
logfont->lfItalic = !!(fsSelection & OS2_FSSELECTION_ITALIC);
|
||||
}
|
||||
else if (tt_head) {
|
||||
USHORT macStyle = GET_BE_WORD(tt_head->macStyle);
|
||||
logfont->lfItalic = !!(macStyle & TT_HEAD_MACSTYLE_ITALIC);
|
||||
}
|
||||
|
||||
if (tt_os2)
|
||||
IDWriteFontFace_ReleaseFontTable(fontface, os2_context);
|
||||
if (tt_head)
|
||||
IDWriteFontFace_ReleaseFontTable(fontface, head_context);
|
||||
IDWriteFontFace_Release(fontface);
|
||||
}
|
||||
}
|
||||
|
||||
static void test_ConvertFontToLOGFONT(void)
|
||||
{
|
||||
IDWriteFactory *factory, *factory2;
|
||||
|
@ -3453,6 +3519,7 @@ static void test_ConvertFontToLOGFONT(void)
|
|||
IDWriteFontFamily *family;
|
||||
IDWriteFont *font;
|
||||
LOGFONTW logfont;
|
||||
UINT32 i, count;
|
||||
BOOL system;
|
||||
HRESULT hr;
|
||||
|
||||
|
@ -3486,41 +3553,67 @@ if (0) { /* crashes on native */
|
|||
ok(!system, "got %d\n", system);
|
||||
ok(logfont.lfFaceName[0] == 0, "got face name %s\n", wine_dbgstr_w(logfont.lfFaceName));
|
||||
|
||||
system = FALSE;
|
||||
count = IDWriteFontCollection_GetFontFamilyCount(collection);
|
||||
for (i = 0; i < count; i++) {
|
||||
WCHAR nameW[128], familynameW[64], facenameW[64];
|
||||
IDWriteLocalizedStrings *names;
|
||||
DWRITE_FONT_SIMULATIONS sim;
|
||||
IDWriteFontFamily *family;
|
||||
UINT32 font_count, j;
|
||||
IDWriteFont *font;
|
||||
LOGFONTW lf;
|
||||
|
||||
logfont.lfHeight = 10;
|
||||
logfont.lfWidth = 11;
|
||||
logfont.lfEscapement = 10;
|
||||
logfont.lfOrientation = 10;
|
||||
logfont.lfWeight = 0;
|
||||
logfont.lfItalic = 1;
|
||||
logfont.lfUnderline = 1;
|
||||
logfont.lfStrikeOut = 1;
|
||||
logfont.lfCharSet = 0;
|
||||
logfont.lfOutPrecision = 0;
|
||||
logfont.lfClipPrecision = 0;
|
||||
logfont.lfQuality = 0;
|
||||
logfont.lfPitchAndFamily = 0;
|
||||
logfont.lfFaceName[0] = 0;
|
||||
hr = IDWriteFontCollection_GetFontFamily(collection, i, &family);
|
||||
ok(hr == S_OK, "got 0x%08x\n", hr);
|
||||
|
||||
hr = IDWriteGdiInterop_ConvertFontToLOGFONT(interop, font, &logfont, &system);
|
||||
ok(hr == S_OK, "got 0x%08x\n", hr);
|
||||
ok(system, "got %d\n", system);
|
||||
hr = IDWriteFontFamily_GetFamilyNames(family, &names);
|
||||
ok(hr == S_OK, "got 0x%08x\n", hr);
|
||||
|
||||
ok(logfont.lfHeight == 0, "got %d\n", logfont.lfHeight);
|
||||
ok(logfont.lfWidth == 0, "got %d\n", logfont.lfWidth);
|
||||
ok(logfont.lfEscapement == 0, "got %d\n", logfont.lfEscapement);
|
||||
ok(logfont.lfOrientation == 0, "got %d\n", logfont.lfOrientation);
|
||||
ok(logfont.lfWeight > 0, "got %d\n", logfont.lfWeight);
|
||||
ok(logfont.lfItalic == 0, "got %d\n", logfont.lfItalic);
|
||||
ok(logfont.lfUnderline == 0, "got %d\n", logfont.lfUnderline);
|
||||
ok(logfont.lfStrikeOut == 0, "got %d\n", logfont.lfStrikeOut);
|
||||
ok(logfont.lfCharSet == DEFAULT_CHARSET, "got %d\n", logfont.lfCharSet);
|
||||
ok(logfont.lfOutPrecision == OUT_OUTLINE_PRECIS, "got %d\n", logfont.lfOutPrecision);
|
||||
ok(logfont.lfClipPrecision == 0, "got %d\n", logfont.lfClipPrecision);
|
||||
ok(logfont.lfQuality == 0, "got %d\n", logfont.lfQuality);
|
||||
ok(logfont.lfPitchAndFamily == 0, "got %d\n", logfont.lfPitchAndFamily);
|
||||
ok(logfont.lfFaceName[0] != 0, "got face name %s\n", wine_dbgstr_w(logfont.lfFaceName));
|
||||
get_enus_string(names, familynameW, sizeof(familynameW)/sizeof(familynameW[0]));
|
||||
IDWriteLocalizedStrings_Release(names);
|
||||
|
||||
font_count = IDWriteFontFamily_GetFontCount(family);
|
||||
|
||||
for (j = 0; j < font_count; j++) {
|
||||
static const WCHAR spaceW[] = {' ', 0};
|
||||
|
||||
hr = IDWriteFontFamily_GetFont(family, j, &font);
|
||||
ok(hr == S_OK, "got 0x%08x\n", hr);
|
||||
|
||||
hr = IDWriteFont_GetFaceNames(font, &names);
|
||||
ok(hr == S_OK, "got 0x%08x\n", hr);
|
||||
|
||||
get_enus_string(names, facenameW, sizeof(facenameW)/sizeof(facenameW[0]));
|
||||
IDWriteLocalizedStrings_Release(names);
|
||||
|
||||
lstrcpyW(nameW, familynameW);
|
||||
lstrcatW(nameW, spaceW);
|
||||
lstrcatW(nameW, facenameW);
|
||||
|
||||
system = FALSE;
|
||||
memset(&logfont, 0xcc, sizeof(logfont));
|
||||
hr = IDWriteGdiInterop_ConvertFontToLOGFONT(interop, font, &logfont, &system);
|
||||
ok(hr == S_OK, "got 0x%08x\n", hr);
|
||||
ok(system, "got %d\n", system);
|
||||
|
||||
sim = IDWriteFont_GetSimulations(font);
|
||||
|
||||
get_logfont_from_font(font, &lf);
|
||||
ok(logfont.lfItalic == lf.lfItalic, "%s: unexpected italic flag %d, oblique simulation %s\n",
|
||||
wine_dbgstr_w(nameW), logfont.lfItalic, sim & DWRITE_FONT_SIMULATIONS_OBLIQUE ? "yes" : "no");
|
||||
|
||||
ok(logfont.lfWeight > 0, "got %d\n", logfont.lfWeight);
|
||||
ok(logfont.lfOutPrecision == OUT_OUTLINE_PRECIS, "got %d\n", logfont.lfOutPrecision);
|
||||
ok(logfont.lfClipPrecision == 0, "got %d\n", logfont.lfClipPrecision);
|
||||
ok(logfont.lfQuality == 0, "got %d\n", logfont.lfQuality);
|
||||
ok(logfont.lfPitchAndFamily == 0, "got %d\n", logfont.lfPitchAndFamily);
|
||||
ok(logfont.lfFaceName[0] != 0, "got face name %s\n", wine_dbgstr_w(logfont.lfFaceName));
|
||||
|
||||
IDWriteFont_Release(font);
|
||||
}
|
||||
|
||||
IDWriteFontFamily_Release(family);
|
||||
}
|
||||
|
||||
IDWriteFactory_Release(factory2);
|
||||
|
||||
|
|
Loading…
Reference in New Issue