This shows that although Windows is only matching family names up to LF_FACESIZE chars, and that it doesn't match against the preferred / typographic family names and styles, it still keeps the faces separate when the full names don't match. Wine incorrectly discard one of them.
Signed-off-by: Rémi Bernon rbernon@codeweavers.com --- dlls/gdi32/tests/font.c | 71 ++++++++++++++++++++ dlls/gdi32/tests/resource.rc | 6 ++ dlls/gdi32/tests/wine_ttfnames.sfd | 85 ++++++++++++++++++++++++ dlls/gdi32/tests/wine_ttfnames.ttf | Bin 0 -> 2232 bytes dlls/gdi32/tests/wine_ttfnames_bold.sfd | 85 ++++++++++++++++++++++++ dlls/gdi32/tests/wine_ttfnames_bold.ttf | Bin 0 -> 2272 bytes 6 files changed, 247 insertions(+) create mode 100644 dlls/gdi32/tests/wine_ttfnames.sfd create mode 100644 dlls/gdi32/tests/wine_ttfnames.ttf create mode 100644 dlls/gdi32/tests/wine_ttfnames_bold.sfd create mode 100644 dlls/gdi32/tests/wine_ttfnames_bold.ttf
diff --git a/dlls/gdi32/tests/font.c b/dlls/gdi32/tests/font.c index ad894dfdcad..b1848a43743 100644 --- a/dlls/gdi32/tests/font.c +++ b/dlls/gdi32/tests/font.c @@ -6940,6 +6940,76 @@ static void test_long_names(void) ReleaseDC(NULL, dc); }
+static void test_ttf_names(void) +{ + struct enum_fullname_data efnd; + char ttf_name[MAX_PATH], ttf_name_bold[MAX_PATH]; + LOGFONTA font = {0}; + HFONT handle_font; + int ret; + HDC dc; + + if (!write_ttf_file("wine_ttfnames.ttf", ttf_name)) + { + skip("Failed to create ttf file for testing\n"); + return; + } + + if (!write_ttf_file("wine_ttfnames_bold.ttf", ttf_name_bold)) + { + skip("Failed to create ttf file for testing\n"); + DeleteFileA(ttf_name); + return; + } + + ret = AddFontResourceExA(ttf_name, FR_PRIVATE, 0); + ok(ret, "AddFontResourceEx() failed\n"); + + ret = AddFontResourceExA(ttf_name_bold, FR_PRIVATE, 0); + ok(ret, "AddFontResourceEx() failed\n"); + + dc = GetDC(NULL); + + strcpy(font.lfFaceName, "Wine_TTF_Names_Long_Family1_Con"); + memset(&efnd, 0, sizeof(efnd)); + EnumFontFamiliesExA(dc, &font, enum_fullname_data_proc, (LPARAM)&efnd, 0); + ok(efnd.total == 0, "EnumFontFamiliesExA must not find font.\n"); + + /* Windows doesn't match with Typographic/Preferred Family tags */ + strcpy(font.lfFaceName, "Wine TTF Names Long Family1"); + memset(&efnd, 0, sizeof(efnd)); + EnumFontFamiliesExA(dc, &font, enum_fullname_data_proc, (LPARAM)&efnd, 0); + ok(efnd.total == 0, "EnumFontFamiliesExA must not find font.\n"); + + strcpy(font.lfFaceName, "Wine TTF Names Long Family1 Ext"); + memset(&efnd, 0, sizeof(efnd)); + EnumFontFamiliesExA(dc, &font, enum_fullname_data_proc, (LPARAM)&efnd, 0); + todo_wine + ok(efnd.total == 2, "EnumFontFamiliesExA found %d fonts, expected 2.\n", efnd.total); + + strcpy(font.lfFaceName, "Wine TTF Names Long Family1 Con"); + memset(&efnd, 0, sizeof(efnd)); + EnumFontFamiliesExA(dc, &font, enum_fullname_data_proc, (LPARAM)&efnd, 0); + todo_wine + ok(efnd.total == 2, "EnumFontFamiliesExA found %d fonts, expected 2.\n", efnd.total); + + handle_font = CreateFontIndirectA(&font); + ok(handle_font != NULL, "CreateFontIndirectA failed\n"); + DeleteObject(handle_font); + + ret = RemoveFontResourceExA(ttf_name_bold, FR_PRIVATE, 0); + todo_wine + ok(ret, "RemoveFontResourceEx() failed\n"); + + DeleteFileA(ttf_name_bold); + + ret = RemoveFontResourceExA(ttf_name, FR_PRIVATE, 0); + ok(ret, "RemoveFontResourceEx() failed\n"); + + DeleteFileA(ttf_name); + ReleaseDC(NULL, dc); +} + typedef struct { USHORT majorVersion; @@ -7351,6 +7421,7 @@ START_TEST(font) test_bitmap_font_glyph_index(); test_GetCharWidthI(); test_long_names(); + test_ttf_names(); test_char_width();
/* These tests should be last test until RemoveFontResource diff --git a/dlls/gdi32/tests/resource.rc b/dlls/gdi32/tests/resource.rc index 6dcbd42ab52..b5a6107a987 100644 --- a/dlls/gdi32/tests/resource.rc +++ b/dlls/gdi32/tests/resource.rc @@ -31,3 +31,9 @@ vertical.ttf RCDATA vertical.ttf
/* @makedep: wine_longname.ttf */ wine_longname.ttf RCDATA wine_longname.ttf + +/* @makedep: wine_ttfnames.ttf */ +wine_ttfnames.ttf RCDATA wine_ttfnames.ttf + +/* @makedep: wine_ttfnames_bold.ttf */ +wine_ttfnames_bold.ttf RCDATA wine_ttfnames_bold.ttf diff --git a/dlls/gdi32/tests/wine_ttfnames.sfd b/dlls/gdi32/tests/wine_ttfnames.sfd new file mode 100644 index 00000000000..566749d19a7 --- /dev/null +++ b/dlls/gdi32/tests/wine_ttfnames.sfd @@ -0,0 +1,85 @@ +SplineFontDB: 3.2 +FontName: Wine_TTF_Names_Long_Family1_Cond_Regular +FamilyName: Wine_TTF_Names_Long_Family1_Cond +Weight: Regular +Copyright: Copyright (c) 2020, Remi Bernon for CodeWeavers +UComments: "2017-11-17: Created with FontForge (http://fontforge.org)" +Version: 001.000 +ItalicAngle: 0 +UnderlinePosition: -102 +UnderlineWidth: 51 +Ascent: 819 +Descent: 205 +InvalidEm: 0 +LayerCount: 2 +Layer: 0 0 "Back" 1 +Layer: 1 0 "Fore" 0 +XUID: [1021 48 28337276 3092883] +OS2Version: 0 +OS2_WeightWidthSlopeOnly: 0 +OS2_UseTypoMetrics: 1 +CreationTime: 1510948643 +ModificationTime: 1598865292 +OS2TypoAscent: 0 +OS2TypoAOffset: 1 +OS2TypoDescent: 0 +OS2TypoDOffset: 1 +OS2TypoLinegap: 0 +OS2WinAscent: 0 +OS2WinAOffset: 1 +OS2WinDescent: 0 +OS2WinDOffset: 1 +HheadAscent: 0 +HheadAOffset: 1 +HheadDescent: 0 +HheadDOffset: 1 +OS2Vendor: 'PfEd' +MarkAttachClasses: 1 +DEI: 91125 +LangName: 1033 \ + "" \ + "Wine TTF Names Long Family1 Cond" \ + "Regular" \ + "" \ + "Wine TTF Names Long Family1 Extremely Long Full Name Condensed" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "Wine TTF Names Long Family1" \ + "Condensed Regular" \ + +Encoding: ISO8859-1 +UnicodeInterp: none +NameList: AGL For New Fonts +DisplaySize: -48 +AntiAlias: 1 +FitToEm: 0 +WinInfo: 64 16 4 +BeginPrivate: 0 +EndPrivate +BeginChars: 256 1 + +StartChar: at +Encoding: 64 64 0 +Width: 1024 +VWidth: 0 +Flags: HW +LayerCount: 2 +Fore +SplineSet +259 332 m 29 + 468 664 l 29 + 514 332 l 29 + 259 332 l 29 +EndSplineSet +EndChar +EndChars +EndSplineFont diff --git a/dlls/gdi32/tests/wine_ttfnames.ttf b/dlls/gdi32/tests/wine_ttfnames.ttf new file mode 100644 index 0000000000000000000000000000000000000000..2eb2ad1f95e7bb384abe41bcf68f64da320fefb9 GIT binary patch literal 2232 zcmdT`O>7%Q6#iy+?W8oKb_J*AFt|aaC_ft;MWu?6mDHvOQ>qXpJyhK+$@)jKcdfM( zVhN-kdqAQW1eFk%-YVsgs22{1142S57eGR&px#j_Js>zi%{SwT?exH(xG>i2eDBSB zZ{FX|8UnzRxCR^R#p22<Z-00-0!BX|cl_n^g(9BDQ>3pc`qkHFv#SaJ4M0>$uWvN` zCQc;plm3=-abvqJk+H4=_Bi*Qir;E>yR?ka9nzzfdZ+x^-oDHIDbmeq;BTJ%;nphg zkDT*WG7`s}1Z_=_o~Sn3J7W;flKz}@svd3lcpWR$m!zL)_&ZHpz>D0!Kw5@=BY3zw z(d9n<cXpdmtKGeac^+Nj{_{|=a(=ygx$B)+_yxxuGJtPhcz8>#-^I-_WB|*uZj&5^ zrMMi_(VQzidCSt4dV9U6qd87rM`;Sp%VS21I25@7#%A5L4#;_@w~G77iDTp<!KWF@ z&;GbnE^M+sdF1U}H-{_Q6YW!9L_*Lrdd{fz6wJBGyPo65+XYg}@;HSgSBF1E=UF5D z?0#w_A(Ddwgo;JY;c>*n;f(=S$N$fV?q&9k`kiGgmddfnvH~_nFtaBxyRbjv;6ZjT znfQKT-?j*`XDfC>vG+%k;<tr;rtm>FmwqPwTrPb&BT_#d99Xx1U(Hx$niIAtvE$xX zIToi#emNsbqV(vFO5RD_JFE$2v2L(n{k}5T!U(I~tA~yA;$4FsykuQAIDwS)k-<q! z^6l)&r*O)C%iuK9_Q$G29My+cIeS<jj~fPCyeWP**v55n++YW9in|6UAg%WdPU4dF zg~2Jz+XaKu$k;crga}P^5Tk|)s%SH+No?Q@*DPE;r-+vkpg|dlMWPrX^+Hl*t}$0- zXOlZ?oIbX-Obb|wnw_{-skY_h#u=G)v+k5!4jMJN7{p-|%5oITrD!u)3;gXMrotM} z2&pZ3!>pjl^&;&x$Y~Lm^r;o1qUP36r|)y5)%hVkz*;Q~<jP7>UgSm8lBFoD$fDn< z)jM-MDWrr7rGhQ0`g9%3L1nA%6BM<Hwq9dOC?~SKI9#shI1gR(jBDPIYhK?q?=jcB zzH8oNC-<!8=>9Ytd%B-)6r-?RjN(clvoo$dCsjxuL-KS;o(jn`A$ck!&xAnH+}!lp zX_e-GpUDDt*ab1eS6Ns2J(_owxH@@<bs6M7U<F##`HLzPcG_{!2<jbEoUM9Y7fY8X z2wMU5S7|1uv6`-lWDQ*AN!3FABn8+lH8zmz&ds>4OU{2?9^FZQC+&ly|5?-iS*!BR zF%3OPYVRc+>ReTOoiDypriXcBn6E_l4sxUf=h5Mi6qGux*@EAl!IyN5|1;FSvY|A4 Q+WL9-*GHcyjp6U~A6<%D%m4rY
literal 0 HcmV?d00001
diff --git a/dlls/gdi32/tests/wine_ttfnames_bold.sfd b/dlls/gdi32/tests/wine_ttfnames_bold.sfd new file mode 100644 index 00000000000..b3bf4ddfe90 --- /dev/null +++ b/dlls/gdi32/tests/wine_ttfnames_bold.sfd @@ -0,0 +1,85 @@ +SplineFontDB: 3.2 +FontName: Wine_TTF_Names_Long_Family1_Cond_Regular +FamilyName: Wine_TTF_Names_Long_Family1_Cond +Weight: Regular +Copyright: Copyright (c) 2020, Remi Bernon for CodeWeavers +UComments: "2017-11-17: Created with FontForge (http://fontforge.org)" +Version: 001.000 +ItalicAngle: 0 +UnderlinePosition: -102 +UnderlineWidth: 51 +Ascent: 819 +Descent: 205 +InvalidEm: 0 +LayerCount: 2 +Layer: 0 0 "Back" 1 +Layer: 1 0 "Fore" 0 +XUID: [1021 48 28337276 3092883] +OS2Version: 0 +OS2_WeightWidthSlopeOnly: 0 +OS2_UseTypoMetrics: 1 +CreationTime: 1510948643 +ModificationTime: 1598865292 +OS2TypoAscent: 0 +OS2TypoAOffset: 1 +OS2TypoDescent: 0 +OS2TypoDOffset: 1 +OS2TypoLinegap: 0 +OS2WinAscent: 0 +OS2WinAOffset: 1 +OS2WinDescent: 0 +OS2WinDOffset: 1 +HheadAscent: 0 +HheadAOffset: 1 +HheadDescent: 0 +HheadDOffset: 1 +OS2Vendor: 'PfEd' +MarkAttachClasses: 1 +DEI: 91125 +LangName: 1033 \ + "" \ + "Wine TTF Names Long Family1 CondBold" \ + "Regular" \ + "" \ + "Wine TTF Names Long Family1 Extremely Long Full Name Condensed Bold" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "Wine TTF Names Long Family1" \ + "Condensed Bold Regular" \ + +Encoding: ISO8859-1 +UnicodeInterp: none +NameList: AGL For New Fonts +DisplaySize: -48 +AntiAlias: 1 +FitToEm: 0 +WinInfo: 64 16 4 +BeginPrivate: 0 +EndPrivate +BeginChars: 256 1 + +StartChar: at +Encoding: 64 64 0 +Width: 1024 +VWidth: 0 +Flags: HW +LayerCount: 2 +Fore +SplineSet +259 332 m 29 + 468 664 l 29 + 514 332 l 29 + 259 332 l 29 +EndSplineSet +EndChar +EndChars +EndSplineFont diff --git a/dlls/gdi32/tests/wine_ttfnames_bold.ttf b/dlls/gdi32/tests/wine_ttfnames_bold.ttf new file mode 100644 index 0000000000000000000000000000000000000000..919a5ea1310dd95904d882afb56b95aaf94dc9be GIT binary patch literal 2272 zcmdT`O>7%Q6#iy+?W7Qqq~hn$9ELQA6eZ5aMxj(bL`h?M2yGRj<WhCB#2eevde>Sz zA-)v}p&pRvjUpj_)C<ZjR_+`Ci9;?(2v9*iAc0i1g%g~h=9}@vPAY^7;=)+7?|X0F zn|Xh`V+a6`;R<Z56$;BQzxDp*80i0u(vg?WE)?(t9w+~?;xD{1m0d~suK}V=er>(# z*D#pAL;hRNx%I7v#He)@ut&J=l>B<F-R92d|B!rtDQs?hzT0xSK0&@#4*cTr+c#E- z?{dzRDM%f2Qrv5d{8+i#*dBm*hWr=ghr)Q>$E#STy(Irg)!(k+9A4!5Ir1{{tHC>& z*AuS4$K$`L#q~z}7G`*KgX_;h#mf1{&IcE~!Thgy)S&?Q`uSgODEeJe8^9=FS=J8O zeppJ%K^rZ()X}#ry;Enc^K`Vt>Dnkup=GnkXcdPl*TC4UcddO&-tJIw2RU(!Ql$7a zL;2Yq7dIA)xPn>C+PQWPm$WC^r>=^Gpl9@)QR^v~bCq{JM~t_5a%$%hDoIj@KgG|o zM*7+Q)M!Gadj|*=i<*bW5f2Y9^sqYqe?D|Cvv1VzG-I(;jzyLgu+fLiuE12j)#u<| zb~l~+KHst}LhRZ~oKoUeUt0X0Z!v}Uvbo`>ho8+2pBxoKKkx5bJAbT<S{vL>*kX|# zcU|RJoFMyUMl6cO`+F*R$8qbRCYZvS!2)BrX|RPpF=()jv*IIz9n4#i!6^(`Um2Xn zxc!2`LpWhyH+UFN+CQicaa12(=Img>H|(0h7QYngeO5X)u8OA&cJQY7$>0>E)iOAZ zi`I_@4`Ie$Gk6#i_8#UDqlP9DR8T@04R+-?)^Un73s=tx;w1#AQb%HrC_zNKh};Hg zLaO#Da%Gj%$ClQq1M_jMnN&*Uh8$l%C9`hUosdgGwIb(&B#I-s5hrp!E(WWCzZE1j zSmhZJttG!O%P5eZ=YCa6>cors)DlraODhQJ`!soVenb!ENJCPrR-!;IFBjx_evs;N zF^)>I;8!bQbDAec#kn}7mI|wcO`7-&14}_^GxP}xdb@_E2{n{MS$;%Z(leX~ZhFQ| z?~t2b*G=yMH@&W#-UBChcFi%ANjCXpH}xpQQKJwir9fsgt~?`ESRTXjbXcAW%QInl zDlE^0K-Jvz<mpM3@_(Pz1#Gh;5{9oTpmKe*1}bqOWd}9t)gfRt>a;0x^`UCAu-!<4 zY7jO}sW!t<mrfTei0VO6c1pIwT@&tI(It{BiOaO9(x{&VR@g`t_Ll2TXI$5%<iD<# zZmx%^LhtB**3W;}y?m)mum4q!J8$ZtmR3#COCMi8)8PlVNqY}DerE*d(V;FeL9LTo gEO<ZlZrlO>A5rV-MpBj?YyG_W+x<_J#o_z>Pvq`pzyJUM
literal 0 HcmV?d00001
And use them directly instead of get_family_names.
Signed-off-by: Rémi Bernon rbernon@codeweavers.com ---
v2: Drop the get_family_names helper that didn't really help much.
dlls/gdi32/freetype.c | 81 ++++++++++++++++++++++--------------------- 1 file changed, 41 insertions(+), 40 deletions(-)
diff --git a/dlls/gdi32/freetype.c b/dlls/gdi32/freetype.c index 38d59e3fd9b..af1473a62bd 100644 --- a/dlls/gdi32/freetype.c +++ b/dlls/gdi32/freetype.c @@ -1482,6 +1482,26 @@ static WCHAR *get_face_name(FT_Face ft_face, FT_UShort name_id, LANGID language_ return NULL; }
+static WCHAR *ft_face_get_family_name( FT_Face ft_face, LANGID langid ) +{ + WCHAR *family_name; + + if ((family_name = get_face_name( ft_face, TT_NAME_ID_FONT_FAMILY, langid ))) + return family_name; + + return towstr( CP_ACP, ft_face->family_name ); +} + +static WCHAR *ft_face_get_style_name( FT_Face ft_face, LANGID langid ) +{ + WCHAR *style_name; + + if ((style_name = get_face_name( ft_face, TT_NAME_ID_FONT_SUBFAMILY, langid ))) + return style_name; + + return towstr( CP_ACP, ft_face->style_name ); +} + static inline BOOL faces_equal( const Face *f1, const Face *f2 ) { if (strcmpiW( f1->StyleName, f2->StyleName )) return FALSE; @@ -1905,55 +1925,44 @@ static WCHAR *prepend_at(WCHAR *family) return str; }
-static void get_family_names( FT_Face ft_face, WCHAR **name, WCHAR **english, BOOL vertical ) +static Family *get_family( FT_Face ft_face, BOOL vertical ) { - *english = get_face_name( ft_face, TT_NAME_ID_FONT_FAMILY, MAKELANGID(LANG_ENGLISH,SUBLANG_DEFAULT) ); - if (!*english) *english = towstr( CP_ACP, ft_face->family_name ); + Family *family; + WCHAR *family_name, *english_name;
- *name = get_face_name( ft_face, TT_NAME_ID_FONT_FAMILY, GetSystemDefaultLCID() ); - if (!*name) - { - *name = *english; - *english = NULL; - } - else if (!strcmpiW( *name, *english )) + family_name = ft_face_get_family_name( ft_face, GetSystemDefaultLCID() ); + english_name = ft_face_get_family_name( ft_face, MAKELANGID(LANG_ENGLISH, SUBLANG_DEFAULT) ); + + if (!strcmpiW( family_name, english_name )) { - HeapFree( GetProcessHeap(), 0, *english ); - *english = NULL; + HeapFree( GetProcessHeap(), 0, english_name ); + english_name = NULL; }
if (vertical) { - *name = prepend_at( *name ); - *english = prepend_at( *english ); + family_name = prepend_at( family_name ); + english_name = prepend_at( english_name ); } -} - -static Family *get_family( FT_Face ft_face, BOOL vertical ) -{ - Family *family; - WCHAR *name, *english_name; - - get_family_names( ft_face, &name, &english_name, vertical );
- family = find_family_from_name( name ); + family = find_family_from_name( family_name );
if (!family) { - family = create_family( name, english_name ); + family = create_family( family_name, english_name ); if (english_name) { FontSubst *subst = HeapAlloc( GetProcessHeap(), 0, sizeof(*subst) ); subst->from.name = strdupW( english_name ); subst->from.charset = -1; - subst->to.name = strdupW( name ); + subst->to.name = strdupW( family_name ); subst->to.charset = -1; add_font_subst( &font_subst_list, subst, 0 ); } } else { - HeapFree( GetProcessHeap(), 0, name ); + HeapFree( GetProcessHeap(), 0, family_name ); HeapFree( GetProcessHeap(), 0, english_name ); family->refcount++; } @@ -2088,9 +2097,7 @@ static Face *create_face( FT_Face ft_face, FT_Long face_index, const char *file, Face *face = HeapAlloc( GetProcessHeap(), 0, sizeof(*face) );
face->refcount = 1; - face->StyleName = get_face_name( ft_face, TT_NAME_ID_FONT_SUBFAMILY, GetSystemDefaultLangID() ); - if (!face->StyleName) face->StyleName = towstr( CP_ACP, ft_face->style_name ); - + face->StyleName = ft_face_get_style_name( ft_face, GetSystemDefaultLangID() ); face->FullName = get_face_name( ft_face, TT_NAME_ID_FULL_NAME, GetSystemDefaultLangID() ); if (flags & ADDFONT_VERTICAL_FONT) face->FullName = prepend_at( face->FullName ); @@ -3498,20 +3505,19 @@ static BOOL get_fontdir( const char *unix_name, struct fontdir *fd ) { FT_Face ft_face = new_ft_face( unix_name, NULL, 0, 0, FALSE ); Face *face; - WCHAR *name, *english_name; + WCHAR *family_name; ENUMLOGFONTEXW elf; NEWTEXTMETRICEXW ntm; DWORD type;
if (!ft_face) return FALSE; face = create_face( ft_face, 0, unix_name, NULL, 0, 0 ); - get_family_names( ft_face, &name, &english_name, FALSE ); + family_name = ft_face_get_family_name( ft_face, GetSystemDefaultLCID() ); pFT_Done_Face( ft_face );
- GetEnumStructs( face, name, &elf, &ntm, &type ); + GetEnumStructs( face, family_name, &elf, &ntm, &type ); release_face( face ); - HeapFree( GetProcessHeap(), 0, name ); - HeapFree( GetProcessHeap(), 0, english_name ); + HeapFree( GetProcessHeap(), 0, family_name );
if ((type & TRUETYPE_FONTTYPE) == 0) return FALSE;
@@ -7955,12 +7961,7 @@ static BOOL get_outline_text_metrics(GdiFont *font) lenfam = (strlenW(font->name) + 1) * sizeof(WCHAR); family_nameW = strdupW(font->name);
- style_nameW = get_face_name( ft_face, TT_NAME_ID_FONT_SUBFAMILY, GetSystemDefaultLangID() ); - if (!style_nameW) - { - FIXME("failed to read style_nameW for font %s!\n", wine_dbgstr_w(font->name)); - style_nameW = towstr( CP_ACP, ft_face->style_name ); - } + style_nameW = ft_face_get_style_name( ft_face, GetSystemDefaultLangID() ); lensty = (strlenW(style_nameW) + 1) * sizeof(WCHAR);
face_nameW = get_face_name( ft_face, TT_NAME_ID_FULL_NAME, GetSystemDefaultLangID() );
Signed-off-by: Huw Davies huw@codeweavers.com
And only prepend '@'' if it's not already there.
Signed-off-by: Rémi Bernon rbernon@codeweavers.com --- dlls/gdi32/freetype.c | 32 +++++++++++++++----------------- 1 file changed, 15 insertions(+), 17 deletions(-)
diff --git a/dlls/gdi32/freetype.c b/dlls/gdi32/freetype.c index af1473a62bd..678196cc5d8 100644 --- a/dlls/gdi32/freetype.c +++ b/dlls/gdi32/freetype.c @@ -1911,18 +1911,17 @@ static void remove_face_from_cache( Face *face ) RegCloseKey(hkey_family); }
-static WCHAR *prepend_at(WCHAR *family) +static WCHAR *get_vertical_name( WCHAR *name ) { - WCHAR *str; + SIZE_T length; + if (!name) return NULL; + if (name[0] == '@') return name;
- if (!family) - return NULL; - - str = HeapAlloc(GetProcessHeap(), 0, sizeof (WCHAR) * (strlenW(family) + 2)); - str[0] = '@'; - strcpyW(str + 1, family); - HeapFree(GetProcessHeap(), 0, family); - return str; + length = strlenW( name ) + 1; + name = HeapReAlloc( GetProcessHeap(), 0, name, (length + 1) * sizeof(WCHAR) ); + memmove( name + 1, name, length * sizeof(WCHAR) ); + name[0] = '@'; + return name; }
static Family *get_family( FT_Face ft_face, BOOL vertical ) @@ -1941,8 +1940,8 @@ static Family *get_family( FT_Face ft_face, BOOL vertical )
if (vertical) { - family_name = prepend_at( family_name ); - english_name = prepend_at( english_name ); + family_name = get_vertical_name( family_name ); + english_name = get_vertical_name( english_name ); }
family = find_family_from_name( family_name ); @@ -2099,8 +2098,7 @@ static Face *create_face( FT_Face ft_face, FT_Long face_index, const char *file, face->refcount = 1; face->StyleName = ft_face_get_style_name( ft_face, GetSystemDefaultLangID() ); face->FullName = get_face_name( ft_face, TT_NAME_ID_FULL_NAME, GetSystemDefaultLangID() ); - if (flags & ADDFONT_VERTICAL_FONT) - face->FullName = prepend_at( face->FullName ); + if (flags & ADDFONT_VERTICAL_FONT) face->FullName = get_vertical_name( face->FullName );
face->dev = 0; face->ino = 0; @@ -2378,10 +2376,10 @@ static BOOL map_vertical_font_family(const WCHAR *orig, const WCHAR *repl, const if (!face || !(face->fs.fsCsb[0] & FS_DBCS_MASK)) return FALSE;
- at_orig = prepend_at(strdupW(orig)); + at_orig = get_vertical_name( strdupW( orig ) ); if (at_orig && !find_family_from_any_name(at_orig)) { - at_repl = prepend_at(strdupW(repl)); + at_repl = get_vertical_name( strdupW( repl ) ); if (at_repl) ret = map_font_family(at_orig, at_repl); } @@ -7970,7 +7968,7 @@ static BOOL get_outline_text_metrics(GdiFont *font) FIXME("failed to read face_nameW for font %s!\n", wine_dbgstr_w(font->name)); face_nameW = strdupW(font->name); } - if (font->name[0] == '@') face_nameW = prepend_at( face_nameW ); + if (font->name[0] == '@') face_nameW = get_vertical_name( face_nameW ); lenface = (strlenW(face_nameW) + 1) * sizeof(WCHAR);
full_nameW = get_face_name( ft_face, TT_NAME_ID_UNIQUE_ID, GetSystemDefaultLangID() );
Signed-off-by: Huw Davies huw@codeweavers.com
Also add full name in TRACE messages. The gdi32 family not always matches the real font family, as we match only LF_FACESIZE chars, so it could make traces confusing.
Signed-off-by: Rémi Bernon rbernon@codeweavers.com ---
v2: Fix an off-by-one error in the full name realloc length, it previously missed the strlen( space_w ).
Squash it with the TRACE messages patch.
dlls/gdi32/freetype.c | 108 ++++++++++++++++++++++-------------------- 1 file changed, 57 insertions(+), 51 deletions(-)
diff --git a/dlls/gdi32/freetype.c b/dlls/gdi32/freetype.c index 678196cc5d8..f0fd296c009 100644 --- a/dlls/gdi32/freetype.c +++ b/dlls/gdi32/freetype.c @@ -270,7 +270,7 @@ typedef struct tagFace { struct list entry; unsigned int refcount; WCHAR *StyleName; - WCHAR *FullName; + WCHAR *full_name; WCHAR *file; dev_t dev; ino_t ino; @@ -1502,6 +1502,29 @@ static WCHAR *ft_face_get_style_name( FT_Face ft_face, LANGID langid ) return towstr( CP_ACP, ft_face->style_name ); }
+static WCHAR *ft_face_get_full_name( FT_Face ft_face, LANGID langid ) +{ + static const WCHAR space_w[] = {' ',0}; + WCHAR *full_name, *style_name; + SIZE_T length; + + if ((full_name = get_face_name( ft_face, TT_NAME_ID_FULL_NAME, langid ))) + return full_name; + + full_name = ft_face_get_family_name( ft_face, langid ); + style_name = ft_face_get_style_name( ft_face, langid ); + + length = strlenW( full_name ) + strlenW( space_w ) + strlenW( style_name ) + 1; + full_name = HeapReAlloc( GetProcessHeap(), 0, full_name, length * sizeof(WCHAR) ); + + strcatW( full_name, space_w ); + strcatW( full_name, style_name ); + HeapFree( GetProcessHeap(), 0, style_name ); + + WARN( "full name not found, using %s instead\n", debugstr_w(full_name) ); + return full_name; +} + static inline BOOL faces_equal( const Face *f1, const Face *f2 ) { if (strcmpiW( f1->StyleName, f2->StyleName )) return FALSE; @@ -1531,7 +1554,7 @@ static void release_face( Face *face ) } HeapFree( GetProcessHeap(), 0, face->file ); HeapFree( GetProcessHeap(), 0, face->StyleName ); - HeapFree( GetProcessHeap(), 0, face->FullName ); + HeapFree( GetProcessHeap(), 0, face->full_name ); HeapFree( GetProcessHeap(), 0, face->cached_enum_data ); HeapFree( GetProcessHeap(), 0, face ); } @@ -1549,10 +1572,7 @@ static inline int style_order(const Face *face) case NTM_BOLD | NTM_ITALIC: return 3; default: - WARN("Don't know how to order font %s %s with flags 0x%08x\n", - debugstr_w(face->family->FamilyName), - debugstr_w(face->StyleName), - face->ntmFlags); + WARN( "Don't know how to order face %s with flags 0x%08x\n", debugstr_w(face->full_name), face->ntmFlags ); return 9999; } } @@ -1565,9 +1585,9 @@ static BOOL insert_face_in_family_list( Face *face, Family *family ) { if (faces_equal( face, cursor )) { - TRACE("Already loaded font %s %s original version is %lx, this version is %lx\n", - debugstr_w(family->FamilyName), debugstr_w(face->StyleName), - cursor->font_version, face->font_version); + TRACE( "Already loaded face %s in family %s, original version %lx, new version %lx\n", + debugstr_w(face->full_name), debugstr_w(family->FamilyName), + cursor->font_version, face->font_version );
if (face->file && face->dev == cursor->dev && face->ino == cursor->ino) { @@ -1598,7 +1618,8 @@ static BOOL insert_face_in_family_list( Face *face, Family *family ) if (style_order( face ) < style_order( cursor )) break; }
- TRACE("Adding new %s\n", debugstr_w(face->file)); + TRACE( "Adding face %s in family %s from %s\n", debugstr_w(face->full_name), + debugstr_w(family->FamilyName), debugstr_w(face->file) ); list_add_before( &cursor->entry, &face->entry ); face->family = family; family->refcount++; @@ -1677,10 +1698,14 @@ static void load_face(HKEY hkey_face, WCHAR *face_name, Family *family, void *bu face->StyleName = strdupW(face_name);
needed = buffer_size; - if(RegQueryValueExW(hkey_face, face_full_name_value, NULL, NULL, buffer, &needed) == ERROR_SUCCESS) - face->FullName = strdupW( buffer ); - else - face->FullName = NULL; + if (RegQueryValueExW( hkey_face, face_full_name_value, NULL, NULL, buffer, &needed ) != ERROR_SUCCESS) + { + ERR( "couldn't find full name for %s %s in cache\n", debugstr_w(family->FamilyName), + debugstr_w(face->StyleName) ); + release_face( face ); + return; + } + face->full_name = strdupW( buffer );
reg_load_ftlong(hkey_face, face_index_value, &face->face_index); reg_load_dword(hkey_face, face_ntmflags_value, &face->ntmFlags); @@ -1715,7 +1740,7 @@ static void load_face(HKEY hkey_face, WCHAR *face_name, Family *family, void *bu face->fs.fsUsb[2], face->fs.fsUsb[3]);
if (insert_face_in_family_list(face, family)) - TRACE("Added font %s %s\n", debugstr_w(family->FamilyName), debugstr_w(face->StyleName)); + TRACE( "Added face %s to family %s\n", debugstr_w(face->full_name), debugstr_w(family->FamilyName) );
release_face( face ); } @@ -1866,9 +1891,8 @@ static void add_face_to_cache(Face *face)
RegSetValueExW(hkey_face, face_file_name_value, 0, REG_SZ, (BYTE *)face->file, (strlenW(face->file) + 1) * sizeof(WCHAR)); - if (face->FullName) - RegSetValueExW(hkey_face, face_full_name_value, 0, REG_SZ, (BYTE*)face->FullName, - (strlenW(face->FullName) + 1) * sizeof(WCHAR)); + RegSetValueExW( hkey_face, face_full_name_value, 0, REG_SZ, (BYTE *)face->full_name, + (strlenW( face->full_name ) + 1) * sizeof(WCHAR) );
reg_save_dword(hkey_face, face_index_value, face->face_index); reg_save_dword(hkey_face, face_ntmflags_value, face->ntmFlags); @@ -2097,8 +2121,8 @@ static Face *create_face( FT_Face ft_face, FT_Long face_index, const char *file,
face->refcount = 1; face->StyleName = ft_face_get_style_name( ft_face, GetSystemDefaultLangID() ); - face->FullName = get_face_name( ft_face, TT_NAME_ID_FULL_NAME, GetSystemDefaultLangID() ); - if (flags & ADDFONT_VERTICAL_FONT) face->FullName = get_vertical_name( face->FullName ); + face->full_name = ft_face_get_full_name( ft_face, GetSystemDefaultLangID() ); + if (flags & ADDFONT_VERTICAL_FONT) face->full_name = get_vertical_name( face->full_name );
face->dev = 0; face->ino = 0; @@ -2162,9 +2186,7 @@ static void AddFaceToList(FT_Face ft_face, const char *file, void *font_data_ptr { if (flags & ADDFONT_ADD_TO_CACHE) add_face_to_cache( face ); - - TRACE("Added font %s %s\n", debugstr_w(family->FamilyName), - debugstr_w(face->StyleName)); + TRACE( "Added face %s to family %s\n", debugstr_w(face->full_name), debugstr_w(family->FamilyName) ); } release_face( face ); release_family( family ); @@ -2358,7 +2380,8 @@ static void DumpFontList(void) LIST_FOR_EACH_ENTRY( family, &font_list, Family, entry ) { TRACE("Family: %s\n", debugstr_w(family->FamilyName)); LIST_FOR_EACH_ENTRY( face, &family->faces, Face, entry ) { - TRACE("\t%s\t%08x", debugstr_w(face->StyleName), face->fs.fsCsb[0]); + TRACE( "\t%s\t%s\t%08x", debugstr_w(face->StyleName), debugstr_w(face->full_name), + face->fs.fsCsb[0] ); if(!face->scalable) TRACE(" %d", face->size.height); TRACE("\n"); @@ -3197,18 +3220,14 @@ static void update_reg_entries(void) LIST_FOR_EACH_ENTRY( family, &font_list, Family, entry ) { LIST_FOR_EACH_ENTRY( face, &family->faces, Face, entry ) { char *buffer; - WCHAR *name; - if (!(face->flags & ADDFONT_EXTERNAL_FONT)) continue;
- name = face->FullName ? face->FullName : family->FamilyName; - - len = strlenW(name) + 1; + len = strlenW( face->full_name ) + 1; if (face->scalable) len += ARRAY_SIZE(TrueType);
valueW = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR)); - strcpyW(valueW, name); + strcpyW( valueW, face->full_name );
if (face->scalable) strcatW(valueW, TrueType); @@ -5682,8 +5701,7 @@ static HFONT CDECL freetype_SelectFont( PHYSDEV dev, HFONT hfont, UINT *aa_flags LIST_FOR_EACH_ENTRY( family, &font_list, Family, entry ) { face_list = get_face_list_from_family(family); LIST_FOR_EACH_ENTRY( face, face_list, Face, entry ) { - if(face->FullName && !strncmpiW(face->FullName, FaceName, LF_FACESIZE - 1) && - (face->scalable || can_use_bitmap)) + if (!strncmpiW( face->full_name, FaceName, LF_FACESIZE - 1 ) && (face->scalable || can_use_bitmap)) { if (csi.fs.fsCsb[0] & face->fs.fsCsb[0] || !csi.fs.fsCsb[0]) goto found_face; @@ -5879,8 +5897,8 @@ found_face: else ret->charset = get_nearest_charset(family->FamilyName, face, &ret->codepage);
- TRACE("Chosen: %s %s (%s/%p:%ld)\n", debugstr_w(family->FamilyName), - debugstr_w(face->StyleName), debugstr_w(face->file), face->font_data_ptr, face->face_index); + TRACE( "Chosen: %s (%s/%p:%ld)\n", debugstr_w(face->full_name), debugstr_w(face->file), + face->font_data_ptr, face->face_index );
ret->aveWidth = height ? lf.lfWidth : 0;
@@ -6176,10 +6194,7 @@ static void GetEnumStructs(Face *face, const WCHAR *family_name, LPENUMLOGFONTEX pntm->ntmTm.ntmAvgWidth = pntm->ntmTm.tmAveCharWidth;
lstrcpynW(pelf->elfLogFont.lfFaceName, family_name, LF_FACESIZE); - if (face->FullName) - lstrcpynW(pelf->elfFullName, face->FullName, LF_FULLFACESIZE); - else - lstrcpynW(pelf->elfFullName, family_name, LF_FULLFACESIZE); + lstrcpynW( pelf->elfFullName, face->full_name, LF_FULLFACESIZE ); lstrcpynW(pelf->elfStyle, face->StyleName, LF_FACESIZE); }
@@ -6230,7 +6245,7 @@ static BOOL family_matches(Family *family, const WCHAR *face_name)
face_list = get_face_list_from_family(family); LIST_FOR_EACH_ENTRY(face, face_list, Face, entry) - if (face->FullName && !strncmpiW(face_name, face->FullName, LF_FACESIZE - 1)) return TRUE; + if (!strncmpiW( face_name, face->full_name, LF_FACESIZE - 1 )) return TRUE;
return FALSE; } @@ -6238,8 +6253,7 @@ static BOOL family_matches(Family *family, const WCHAR *face_name) static BOOL face_matches(const WCHAR *family_name, Face *face, const WCHAR *face_name) { if (!strncmpiW(face_name, family_name, LF_FACESIZE - 1)) return TRUE; - - return (face->FullName && !strncmpiW(face_name, face->FullName, LF_FACESIZE - 1)); + return !strncmpiW( face_name, face->full_name, LF_FACESIZE - 1 ); }
static BOOL enum_face_charsets(const Family *family, Face *face, struct enum_charset_list *list, @@ -6272,10 +6286,7 @@ static BOOL enum_face_charsets(const Family *family, Face *face, struct enum_cha if (family != face->family) { lstrcpynW(elf.elfLogFont.lfFaceName, family->FamilyName, LF_FACESIZE); - if (face->FullName) - lstrcpynW(elf.elfFullName, face->FullName, LF_FULLFACESIZE); - else - lstrcpynW(elf.elfFullName, family->FamilyName, LF_FULLFACESIZE); + lstrcpynW( elf.elfFullName, face->full_name, LF_FULLFACESIZE ); } if (subst) strcpyW(elf.elfLogFont.lfFaceName, subst); @@ -7962,12 +7973,7 @@ static BOOL get_outline_text_metrics(GdiFont *font) style_nameW = ft_face_get_style_name( ft_face, GetSystemDefaultLangID() ); lensty = (strlenW(style_nameW) + 1) * sizeof(WCHAR);
- face_nameW = get_face_name( ft_face, TT_NAME_ID_FULL_NAME, GetSystemDefaultLangID() ); - if (!face_nameW) - { - FIXME("failed to read face_nameW for font %s!\n", wine_dbgstr_w(font->name)); - face_nameW = strdupW(font->name); - } + face_nameW = ft_face_get_full_name( ft_face, GetSystemDefaultLangID() ); if (font->name[0] == '@') face_nameW = get_vertical_name( face_nameW ); lenface = (strlenW(face_nameW) + 1) * sizeof(WCHAR);
Signed-off-by: Huw Davies huw@codeweavers.com
Signed-off-by: Rémi Bernon rbernon@codeweavers.com --- dlls/gdi32/freetype.c | 29 ++++++++++++++--------------- 1 file changed, 14 insertions(+), 15 deletions(-)
diff --git a/dlls/gdi32/freetype.c b/dlls/gdi32/freetype.c index f0fd296c009..2b3f7b337e4 100644 --- a/dlls/gdi32/freetype.c +++ b/dlls/gdi32/freetype.c @@ -269,7 +269,7 @@ struct enum_data typedef struct tagFace { struct list entry; unsigned int refcount; - WCHAR *StyleName; + WCHAR *style_name; WCHAR *full_name; WCHAR *file; dev_t dev; @@ -1527,7 +1527,7 @@ static WCHAR *ft_face_get_full_name( FT_Face ft_face, LANGID langid )
static inline BOOL faces_equal( const Face *f1, const Face *f2 ) { - if (strcmpiW( f1->StyleName, f2->StyleName )) return FALSE; + if (strcmpiW( f1->style_name, f2->style_name )) return FALSE; if (f1->scalable) return TRUE; if (f1->size.y_ppem != f2->size.y_ppem) return FALSE; return !memcmp( &f1->fs, &f2->fs, sizeof(f1->fs) ); @@ -1553,7 +1553,7 @@ static void release_face( Face *face ) release_family( face->family ); } HeapFree( GetProcessHeap(), 0, face->file ); - HeapFree( GetProcessHeap(), 0, face->StyleName ); + HeapFree( GetProcessHeap(), 0, face->style_name ); HeapFree( GetProcessHeap(), 0, face->full_name ); HeapFree( GetProcessHeap(), 0, face->cached_enum_data ); HeapFree( GetProcessHeap(), 0, face ); @@ -1695,13 +1695,13 @@ static void load_face(HKEY hkey_face, WCHAR *face_name, Family *family, void *bu
face->refcount = 1; face->file = strdupW( buffer ); - face->StyleName = strdupW(face_name); + face->style_name = strdupW( face_name );
needed = buffer_size; if (RegQueryValueExW( hkey_face, face_full_name_value, NULL, NULL, buffer, &needed ) != ERROR_SUCCESS) { ERR( "couldn't find full name for %s %s in cache\n", debugstr_w(family->FamilyName), - debugstr_w(face->StyleName) ); + debugstr_w(face->style_name) ); release_face( face ); return; } @@ -1876,13 +1876,12 @@ static void add_face_to_cache(Face *face) RegSetValueExW(hkey_family, english_name_value, 0, REG_SZ, (BYTE*)face->family->EnglishName, (strlenW(face->family->EnglishName) + 1) * sizeof(WCHAR));
- if(face->scalable) - face_key_name = face->StyleName; + if (face->scalable) face_key_name = face->style_name; else { static const WCHAR fmtW[] = {'%','s','\','%','d',0}; - face_key_name = HeapAlloc(GetProcessHeap(), 0, (strlenW(face->StyleName) + 10) * sizeof(WCHAR)); - sprintfW(face_key_name, fmtW, face->StyleName, face->size.y_ppem); + face_key_name = HeapAlloc( GetProcessHeap(), 0, (strlenW( face->style_name ) + 10) * sizeof(WCHAR) ); + sprintfW( face_key_name, fmtW, face->style_name, face->size.y_ppem ); } RegCreateKeyExW(hkey_family, face_key_name, 0, NULL, REG_OPTION_VOLATILE, KEY_ALL_ACCESS, NULL, &hkey_face, NULL); @@ -1922,13 +1921,13 @@ static void remove_face_from_cache( Face *face )
if (face->scalable) { - RegDeleteKeyW( hkey_family, face->StyleName ); + RegDeleteKeyW( hkey_family, face->style_name ); } else { static const WCHAR fmtW[] = {'%','s','\','%','d',0}; - WCHAR *face_key_name = HeapAlloc(GetProcessHeap(), 0, (strlenW(face->StyleName) + 10) * sizeof(WCHAR)); - sprintfW(face_key_name, fmtW, face->StyleName, face->size.y_ppem); + WCHAR *face_key_name = HeapAlloc( GetProcessHeap(), 0, (strlenW( face->style_name ) + 10) * sizeof(WCHAR) ); + sprintfW( face_key_name, fmtW, face->style_name, face->size.y_ppem ); RegDeleteKeyW( hkey_family, face_key_name ); HeapFree(GetProcessHeap(), 0, face_key_name); } @@ -2120,7 +2119,7 @@ static Face *create_face( FT_Face ft_face, FT_Long face_index, const char *file, Face *face = HeapAlloc( GetProcessHeap(), 0, sizeof(*face) );
face->refcount = 1; - face->StyleName = ft_face_get_style_name( ft_face, GetSystemDefaultLangID() ); + face->style_name = ft_face_get_style_name( ft_face, GetSystemDefaultLangID() ); face->full_name = ft_face_get_full_name( ft_face, GetSystemDefaultLangID() ); if (flags & ADDFONT_VERTICAL_FONT) face->full_name = get_vertical_name( face->full_name );
@@ -2380,7 +2379,7 @@ static void DumpFontList(void) LIST_FOR_EACH_ENTRY( family, &font_list, Family, entry ) { TRACE("Family: %s\n", debugstr_w(family->FamilyName)); LIST_FOR_EACH_ENTRY( face, &family->faces, Face, entry ) { - TRACE( "\t%s\t%s\t%08x", debugstr_w(face->StyleName), debugstr_w(face->full_name), + TRACE( "\t%s\t%s\t%08x", debugstr_w(face->style_name), debugstr_w(face->full_name), face->fs.fsCsb[0] ); if(!face->scalable) TRACE(" %d", face->size.height); @@ -6195,7 +6194,7 @@ static void GetEnumStructs(Face *face, const WCHAR *family_name, LPENUMLOGFONTEX
lstrcpynW(pelf->elfLogFont.lfFaceName, family_name, LF_FACESIZE); lstrcpynW( pelf->elfFullName, face->full_name, LF_FULLFACESIZE ); - lstrcpynW(pelf->elfStyle, face->StyleName, LF_FACESIZE); + lstrcpynW( pelf->elfStyle, face->style_name, LF_FACESIZE ); }
pntm->ntmTm.ntmFlags = face->ntmFlags;
Signed-off-by: Huw Davies huw@codeweavers.com
This stops stealing pointer ownership, and will also make sure the TRACE messages contain the truncated family names, that are actually compared.
Also rename the fields to make them consistent with most Wine internal coding style.
Signed-off-by: Rémi Bernon rbernon@codeweavers.com ---
v2: Add this patch to TRACE truncated family names and clean up this part of the code a bit at the same time.
dlls/gdi32/freetype.c | 140 ++++++++++++++++++++---------------------- 1 file changed, 65 insertions(+), 75 deletions(-)
diff --git a/dlls/gdi32/freetype.c b/dlls/gdi32/freetype.c index 2b3f7b337e4..b40be5b92e3 100644 --- a/dlls/gdi32/freetype.c +++ b/dlls/gdi32/freetype.c @@ -300,8 +300,8 @@ typedef struct tagFace { typedef struct tagFamily { struct list entry; unsigned int refcount; - WCHAR *FamilyName; - WCHAR *EnglishName; + WCHAR family_name[LF_FACESIZE]; + WCHAR english_name[LF_FACESIZE]; struct list faces; struct list *replacement; } Family; @@ -1040,8 +1040,7 @@ static Face *find_face_from_filename(const WCHAR *file_name, const WCHAR *face_n LIST_FOR_EACH_ENTRY(family, &font_list, Family, entry) { const struct list *face_list; - if(face_name && strncmpiW(face_name, family->FamilyName, LF_FACESIZE - 1)) - continue; + if (face_name && strncmpiW( face_name, family->family_name, LF_FACESIZE - 1 )) continue; face_list = get_face_list_from_family(family); LIST_FOR_EACH_ENTRY(face, face_list, Face, entry) { @@ -1065,10 +1064,7 @@ static Family *find_family_from_name(const WCHAR *name) Family *family;
LIST_FOR_EACH_ENTRY(family, &font_list, Family, entry) - { - if(!strncmpiW(family->FamilyName, name, LF_FACESIZE -1)) - return family; - } + if (!strncmpiW( family->family_name, name, LF_FACESIZE - 1 )) return family;
return NULL; } @@ -1079,10 +1075,8 @@ static Family *find_family_from_any_name(const WCHAR *name)
LIST_FOR_EACH_ENTRY(family, &font_list, Family, entry) { - if(!strncmpiW(family->FamilyName, name, LF_FACESIZE - 1)) - return family; - if(family->EnglishName && !strncmpiW(family->EnglishName, name, LF_FACESIZE - 1)) - return family; + if (!strncmpiW( family->family_name, name, LF_FACESIZE - 1 )) return family; + if (!strncmpiW( family->english_name, name, LF_FACESIZE - 1 )) return family; }
return NULL; @@ -1538,8 +1532,6 @@ static void release_family( Family *family ) if (--family->refcount) return; assert( list_empty( &family->faces )); list_remove( &family->entry ); - HeapFree( GetProcessHeap(), 0, family->FamilyName ); - HeapFree( GetProcessHeap(), 0, family->EnglishName ); HeapFree( GetProcessHeap(), 0, family ); }
@@ -1586,7 +1578,7 @@ static BOOL insert_face_in_family_list( Face *face, Family *family ) if (faces_equal( face, cursor )) { TRACE( "Already loaded face %s in family %s, original version %lx, new version %lx\n", - debugstr_w(face->full_name), debugstr_w(family->FamilyName), + debugstr_w(face->full_name), debugstr_w(family->family_name), cursor->font_version, face->font_version );
if (face->file && face->dev == cursor->dev && face->ino == cursor->ino) @@ -1619,7 +1611,7 @@ static BOOL insert_face_in_family_list( Face *face, Family *family ) }
TRACE( "Adding face %s in family %s from %s\n", debugstr_w(face->full_name), - debugstr_w(family->FamilyName), debugstr_w(face->file) ); + debugstr_w(family->family_name), debugstr_w(face->file) ); list_add_before( &cursor->entry, &face->entry ); face->family = family; family->refcount++; @@ -1631,12 +1623,13 @@ static BOOL insert_face_in_family_list( Face *face, Family *family ) * NB This function stores the ptrs to the strings to save copying. * Don't free them after calling. */ -static Family *create_family( WCHAR *name, WCHAR *english_name ) +static Family *create_family( WCHAR *family_name, WCHAR *english_name ) { Family * const family = HeapAlloc( GetProcessHeap(), 0, sizeof(*family) ); family->refcount = 1; - family->FamilyName = name; - family->EnglishName = english_name; + lstrcpynW( family->family_name, family_name, LF_FACESIZE ); + if (english_name) lstrcpynW( family->english_name, english_name, LF_FACESIZE ); + else family->english_name[0] = 0; list_init( &family->faces ); family->replacement = &family->faces; list_add_tail( &font_list, &family->entry ); @@ -1700,7 +1693,7 @@ static void load_face(HKEY hkey_face, WCHAR *face_name, Family *family, void *bu needed = buffer_size; if (RegQueryValueExW( hkey_face, face_full_name_value, NULL, NULL, buffer, &needed ) != ERROR_SUCCESS) { - ERR( "couldn't find full name for %s %s in cache\n", debugstr_w(family->FamilyName), + ERR( "couldn't find full name for %s %s in cache\n", debugstr_w(family->family_name), debugstr_w(face->style_name) ); release_face( face ); return; @@ -1740,7 +1733,7 @@ static void load_face(HKEY hkey_face, WCHAR *face_name, Family *family, void *bu face->fs.fsUsb[2], face->fs.fsUsb[3]);
if (insert_face_in_family_list(face, family)) - TRACE( "Added face %s to family %s\n", debugstr_w(face->full_name), debugstr_w(family->FamilyName) ); + TRACE( "Added face %s to family %s\n", debugstr_w(face->full_name), debugstr_w(family->family_name) );
release_face( face ); } @@ -1769,7 +1762,7 @@ static void reorder_vertical_fonts(void)
LIST_FOR_EACH_ENTRY_SAFE( family, next, &font_list, Family, entry ) { - if (family->FamilyName[0] != '@') continue; + if (family->family_name[0] != '@') continue; list_remove( &family->entry ); list_add_tail( &vertical_families, &family->entry ); } @@ -1780,7 +1773,7 @@ static void reorder_vertical_fonts(void) { family = LIST_ENTRY( ptr, Family, entry ); vert_family = LIST_ENTRY( vptr, Family, entry ); - if (strcmpiW( family->FamilyName, vert_family->FamilyName + 1 ) > 0) + if (strcmpiW( family->family_name, vert_family->family_name + 1 ) > 0) { list_remove( vptr ); list_add_before( ptr, vptr ); @@ -1801,7 +1794,7 @@ static void load_font_list_from_cache(HKEY hkey_font_cache) size = sizeof(buffer); while (!RegEnumKeyExW(hkey_font_cache, family_index++, buffer, &size, NULL, NULL, NULL, NULL)) { - WCHAR *english_family = NULL; + WCHAR *english_name = NULL; WCHAR *family_name = strdupW( buffer ); DWORD face_index = 0;
@@ -1809,14 +1802,14 @@ static void load_font_list_from_cache(HKEY hkey_font_cache) TRACE("opened family key %s\n", debugstr_w(family_name)); size = sizeof(buffer); if (!RegQueryValueExW(hkey_family, english_name_value, NULL, NULL, (BYTE *)buffer, &size)) - english_family = strdupW( buffer ); + english_name = strdupW( buffer );
- family = create_family(family_name, english_family); + family = create_family( family_name, english_name );
- if(english_family) + if (english_name) { FontSubst *subst = HeapAlloc(GetProcessHeap(), 0, sizeof(*subst)); - subst->from.name = strdupW(english_family); + subst->from.name = strdupW( english_name ); subst->from.charset = -1; subst->to.name = strdupW(family_name); subst->to.charset = -1; @@ -1837,6 +1830,10 @@ static void load_font_list_from_cache(HKEY hkey_font_cache) HeapFree( GetProcessHeap(), 0, face_name ); size = sizeof(buffer); } + + HeapFree( GetProcessHeap(), 0, family_name ); + HeapFree( GetProcessHeap(), 0, english_name ); + RegCloseKey(hkey_family); release_family( family ); size = sizeof(buffer); @@ -1870,11 +1867,11 @@ static void add_face_to_cache(Face *face) HKEY hkey_family, hkey_face; WCHAR *face_key_name;
- RegCreateKeyExW(hkey_font_cache, face->family->FamilyName, 0, - NULL, REG_OPTION_VOLATILE, KEY_ALL_ACCESS, NULL, &hkey_family, NULL); - if(face->family->EnglishName) - RegSetValueExW(hkey_family, english_name_value, 0, REG_SZ, (BYTE*)face->family->EnglishName, - (strlenW(face->family->EnglishName) + 1) * sizeof(WCHAR)); + RegCreateKeyExW( hkey_font_cache, face->family->family_name, 0, NULL, REG_OPTION_VOLATILE, + KEY_ALL_ACCESS, NULL, &hkey_family, NULL ); + if (face->family->english_name[0]) + RegSetValueExW( hkey_family, english_name_value, 0, REG_SZ, (BYTE *)face->family->english_name, + (strlenW( face->family->english_name ) + 1) * sizeof(WCHAR) );
if (face->scalable) face_key_name = face->style_name; else @@ -1917,7 +1914,7 @@ static void remove_face_from_cache( Face *face ) { HKEY hkey_family;
- RegOpenKeyExW( hkey_font_cache, face->family->FamilyName, 0, KEY_ALL_ACCESS, &hkey_family ); + RegOpenKeyExW( hkey_font_cache, face->family->family_name, 0, KEY_ALL_ACCESS, &hkey_family );
if (face->scalable) { @@ -1967,28 +1964,20 @@ static Family *get_family( FT_Face ft_face, BOOL vertical ) english_name = get_vertical_name( english_name ); }
- family = find_family_from_name( family_name ); - - if (!family) + if ((family = find_family_from_name( family_name ))) family->refcount++; + else if ((family = create_family( family_name, english_name )) && english_name) { - family = create_family( family_name, english_name ); - if (english_name) - { - FontSubst *subst = HeapAlloc( GetProcessHeap(), 0, sizeof(*subst) ); - subst->from.name = strdupW( english_name ); - subst->from.charset = -1; - subst->to.name = strdupW( family_name ); - subst->to.charset = -1; - add_font_subst( &font_subst_list, subst, 0 ); - } - } - else - { - HeapFree( GetProcessHeap(), 0, family_name ); - HeapFree( GetProcessHeap(), 0, english_name ); - family->refcount++; + FontSubst *subst = HeapAlloc( GetProcessHeap(), 0, sizeof(*subst) ); + subst->from.name = strdupW( english_name ); + subst->from.charset = -1; + subst->to.name = strdupW( family_name ); + subst->to.charset = -1; + add_font_subst( &font_subst_list, subst, 0 ); }
+ HeapFree( GetProcessHeap(), 0, family_name ); + HeapFree( GetProcessHeap(), 0, english_name ); + return family; }
@@ -2185,7 +2174,7 @@ static void AddFaceToList(FT_Face ft_face, const char *file, void *font_data_ptr { if (flags & ADDFONT_ADD_TO_CACHE) add_face_to_cache( face ); - TRACE( "Added face %s to family %s\n", debugstr_w(face->full_name), debugstr_w(family->FamilyName) ); + TRACE( "Added face %s to family %s\n", debugstr_w(face->full_name), debugstr_w(family->family_name) ); } release_face( face ); release_family( family ); @@ -2377,7 +2366,7 @@ static void DumpFontList(void) Face *face;
LIST_FOR_EACH_ENTRY( family, &font_list, Family, entry ) { - TRACE("Family: %s\n", debugstr_w(family->FamilyName)); + TRACE( "Family: %s\n", debugstr_w(family->family_name) ); LIST_FOR_EACH_ENTRY( face, &family->faces, Face, entry ) { TRACE( "\t%s\t%s\t%08x", debugstr_w(face->style_name), debugstr_w(face->full_name), face->fs.fsCsb[0] ); @@ -2421,8 +2410,8 @@ static BOOL map_font_family(const WCHAR *orig, const WCHAR *repl) if (new_family != NULL) { TRACE("mapping %s to %s\n", debugstr_w(repl), debugstr_w(orig)); - new_family->FamilyName = strdupW(orig); - new_family->EnglishName = NULL; + lstrcpynW( new_family->family_name, orig, LF_FACESIZE ); + new_family->english_name[0] = 0; list_init(&new_family->faces); new_family->replacement = &family->faces; list_add_tail(&font_list, &new_family->entry); @@ -4387,7 +4376,7 @@ static BOOL move_to_front(const WCHAR *name) Family *family, *cursor2; LIST_FOR_EACH_ENTRY_SAFE(family, cursor2, &font_list, Family, entry) { - if(!strncmpiW(family->FamilyName, name, LF_FACESIZE - 1)) + if (!strncmpiW( family->family_name, name, LF_FACESIZE - 1 )) { list_remove(&family->entry); list_add_head(&font_list, &family->entry); @@ -5371,7 +5360,7 @@ static Family* get_fontconfig_family(DWORD pitch_and_family, const CHARSETINFO * family = find_family_from_any_name(nameW); if (!family) continue;
- font_link = find_font_link(family->FamilyName); + font_link = find_font_link( family->family_name ); face_list = get_face_list_from_family(family); LIST_FOR_EACH_ENTRY( face, face_list, Face, entry ) { if (!face->scalable) @@ -5677,10 +5666,10 @@ static HFONT CDECL freetype_SelectFont( PHYSDEV dev, HFONT hfont, UINT *aa_flags or if that's unavailable the first charset that the font supports. */ LIST_FOR_EACH_ENTRY( family, &font_list, Family, entry ) { - if (!strncmpiW(family->FamilyName, FaceName, LF_FACESIZE - 1) || - (psub && !strncmpiW(family->FamilyName, psub->to.name, LF_FACESIZE - 1))) + if (!strncmpiW( family->family_name, FaceName, LF_FACESIZE - 1 ) || + (psub && !strncmpiW( family->family_name, psub->to.name, LF_FACESIZE - 1 ))) { - font_link = find_font_link(family->FamilyName); + font_link = find_font_link( family->family_name ); face_list = get_face_list_from_family(family); LIST_FOR_EACH_ENTRY( face, face_list, Face, entry ) { if (!(face->scalable || can_use_bitmap)) @@ -5704,7 +5693,7 @@ static HFONT CDECL freetype_SelectFont( PHYSDEV dev, HFONT hfont, UINT *aa_flags { if (csi.fs.fsCsb[0] & face->fs.fsCsb[0] || !csi.fs.fsCsb[0]) goto found_face; - font_link = find_font_link(family->FamilyName); + font_link = find_font_link( family->family_name ); if (font_link != NULL && csi.fs.fsCsb[0] & font_link->fs.fsCsb[0]) goto found_face; @@ -5732,7 +5721,7 @@ static HFONT CDECL freetype_SelectFont( PHYSDEV dev, HFONT hfont, UINT *aa_flags family = face->family; if (csi.fs.fsCsb[0] & face->fs.fsCsb[0] || !csi.fs.fsCsb[0]) goto found; - links = find_font_link(family->FamilyName); + links = find_font_link( family->family_name ); if (links != NULL && csi.fs.fsCsb[0] & links->fs.fsCsb[0]) goto found; } @@ -5769,8 +5758,9 @@ static HFONT CDECL freetype_SelectFont( PHYSDEV dev, HFONT hfont, UINT *aa_flags else strcpyW(lf.lfFaceName, default_sans); LIST_FOR_EACH_ENTRY( family, &font_list, Family, entry ) { - if(!strncmpiW(family->FamilyName, lf.lfFaceName, LF_FACESIZE - 1)) { - font_link = find_font_link(family->FamilyName); + if (!strncmpiW( family->family_name, lf.lfFaceName, LF_FACESIZE - 1 )) + { + font_link = find_font_link( family->family_name ); face_list = get_face_list_from_family(family); LIST_FOR_EACH_ENTRY( face, face_list, Face, entry ) { if (!(face->scalable || can_use_bitmap)) @@ -5791,7 +5781,7 @@ static HFONT CDECL freetype_SelectFont( PHYSDEV dev, HFONT hfont, UINT *aa_flags
last_resort_family = NULL; LIST_FOR_EACH_ENTRY( family, &font_list, Family, entry ) { - font_link = find_font_link(family->FamilyName); + font_link = find_font_link( family->family_name ); face_list = get_face_list_from_family(family); LIST_FOR_EACH_ENTRY( face, face_list, Face, entry ) { if(!(face->flags & ADDFONT_VERTICAL_FONT) == !want_vertical && @@ -5841,7 +5831,7 @@ found: height = lf.lfHeight;
face = best = best_bitmap = NULL; - font_link = find_font_link(family->FamilyName); + font_link = find_font_link( family->family_name ); face_list = get_face_list_from_family(family); LIST_FOR_EACH_ENTRY(face, face_list, Face, entry) { @@ -5894,7 +5884,7 @@ found_face: ret->codepage = csi.ciACP; } else - ret->charset = get_nearest_charset(family->FamilyName, face, &ret->codepage); + ret->charset = get_nearest_charset( family->family_name, face, &ret->codepage );
TRACE( "Chosen: %s (%s/%p:%ld)\n", debugstr_w(face->full_name), debugstr_w(face->file), face->font_data_ptr, face->face_index ); @@ -5955,7 +5945,7 @@ found_face: pick_charmap( ret->ft_face, ret->charset );
ret->orientation = FT_IS_SCALABLE(ret->ft_face) ? lf.lfOrientation : 0; - ret->name = psub ? strdupW(psub->from.name) : strdupW(family->FamilyName); + ret->name = psub ? strdupW( psub->from.name ) : strdupW( family->family_name ); ret->underline = lf.lfUnderline ? 0xff : 0; ret->strikeout = lf.lfStrikeOut ? 0xff : 0; create_child_font_list(ret); @@ -6240,7 +6230,7 @@ static BOOL family_matches(Family *family, const WCHAR *face_name) Face *face; const struct list *face_list;
- if (!strncmpiW(face_name, family->FamilyName, LF_FACESIZE - 1)) return TRUE; + if (!strncmpiW( face_name, family->family_name, LF_FACESIZE - 1 )) return TRUE;
face_list = get_face_list_from_family(family); LIST_FOR_EACH_ENTRY(face, face_list, Face, entry) @@ -6263,7 +6253,7 @@ static BOOL enum_face_charsets(const Family *family, Face *face, struct enum_cha DWORD type = 0; DWORD i;
- GetEnumStructs(face, face->family->FamilyName, &elf, &ntm, &type); + GetEnumStructs( face, face->family->family_name, &elf, &ntm, &type ); for(i = 0; i < list->total; i++) { if(!face->scalable && face->fs.fsCsb[0] == 0) { /* OEM bitmap */ elf.elfLogFont.lfCharSet = ntm.ntmTm.tmCharSet = OEM_CHARSET; @@ -6284,7 +6274,7 @@ static BOOL enum_face_charsets(const Family *family, Face *face, struct enum_cha /* Font Replacement */ if (family != face->family) { - lstrcpynW(elf.elfLogFont.lfFaceName, family->FamilyName, LF_FACESIZE); + lstrcpynW( elf.elfLogFont.lfFaceName, family->family_name, LF_FACESIZE ); lstrcpynW( elf.elfFullName, face->full_name, LF_FULLFACESIZE ); } if (subst) @@ -6342,7 +6332,7 @@ static BOOL CDECL freetype_EnumFonts( PHYSDEV dev, LPLOGFONTW plf, FONTENUMPROCW if (!family_matches(family, face_name)) continue; face_list = get_face_list_from_family(family); LIST_FOR_EACH_ENTRY( face, face_list, Face, entry ) { - if (!face_matches(family->FamilyName, face, face_name)) continue; + if (!face_matches( family->family_name, face, face_name )) continue; if (!enum_face_charsets(family, face, &enum_charsets, proc, lparam, psub ? psub->from.name : NULL)) return FALSE; } } @@ -8383,7 +8373,7 @@ static BOOL load_child_font(GdiFont *font, CHILD_FONT *child) child->font->ntmFlags = child_face->ntmFlags; child->font->orientation = font->orientation; child->font->scale_y = font->scale_y; - child->font->name = strdupW( child_face->family->FamilyName ); + child->font->name = strdupW( child_face->family->family_name ); child->font->base_font = font; TRACE("created child font %p for base %p\n", child->font, font); return TRUE;
Signed-off-by: Huw Davies huw@codeweavers.com
Signed-off-by: Rémi Bernon rbernon@codeweavers.com --- dlls/gdi32/freetype.c | 2 +- dlls/gdi32/tests/font.c | 3 --- 2 files changed, 1 insertion(+), 4 deletions(-)
diff --git a/dlls/gdi32/freetype.c b/dlls/gdi32/freetype.c index b40be5b92e3..cf53f148ad1 100644 --- a/dlls/gdi32/freetype.c +++ b/dlls/gdi32/freetype.c @@ -1521,7 +1521,7 @@ static WCHAR *ft_face_get_full_name( FT_Face ft_face, LANGID langid )
static inline BOOL faces_equal( const Face *f1, const Face *f2 ) { - if (strcmpiW( f1->style_name, f2->style_name )) return FALSE; + if (strcmpiW( f1->full_name, f2->full_name )) return FALSE; if (f1->scalable) return TRUE; if (f1->size.y_ppem != f2->size.y_ppem) return FALSE; return !memcmp( &f1->fs, &f2->fs, sizeof(f1->fs) ); diff --git a/dlls/gdi32/tests/font.c b/dlls/gdi32/tests/font.c index b1848a43743..f5c8d4dac3b 100644 --- a/dlls/gdi32/tests/font.c +++ b/dlls/gdi32/tests/font.c @@ -6984,13 +6984,11 @@ static void test_ttf_names(void) strcpy(font.lfFaceName, "Wine TTF Names Long Family1 Ext"); memset(&efnd, 0, sizeof(efnd)); EnumFontFamiliesExA(dc, &font, enum_fullname_data_proc, (LPARAM)&efnd, 0); - todo_wine ok(efnd.total == 2, "EnumFontFamiliesExA found %d fonts, expected 2.\n", efnd.total);
strcpy(font.lfFaceName, "Wine TTF Names Long Family1 Con"); memset(&efnd, 0, sizeof(efnd)); EnumFontFamiliesExA(dc, &font, enum_fullname_data_proc, (LPARAM)&efnd, 0); - todo_wine ok(efnd.total == 2, "EnumFontFamiliesExA found %d fonts, expected 2.\n", efnd.total);
handle_font = CreateFontIndirectA(&font); @@ -6998,7 +6996,6 @@ static void test_ttf_names(void) DeleteObject(handle_font);
ret = RemoveFontResourceExA(ttf_name_bold, FR_PRIVATE, 0); - todo_wine ok(ret, "RemoveFontResourceEx() failed\n");
DeleteFileA(ttf_name_bold);
Signed-off-by: Huw Davies huw@codeweavers.com