Nikolay Sivov : dwrite: Store font family name in IDWriteFontFamily implementation.

Alexandre Julliard julliard at winehq.org
Mon Oct 8 13:39:55 CDT 2012


Module: wine
Branch: master
Commit: 89561b9247c0f2a91667dfddb04c0e57d7628e33
URL:    http://source.winehq.org/git/wine.git/?a=commit;h=89561b9247c0f2a91667dfddb04c0e57d7628e33

Author: Nikolay Sivov <nsivov at codeweavers.com>
Date:   Sun Oct  7 12:29:39 2012 -0400

dwrite: Store font family name in IDWriteFontFamily implementation.

---

 dlls/dwrite/dwrite_private.h |   17 +++++++++++++++++
 dlls/dwrite/font.c           |   34 ++++++++++++++++++++++++++++++++--
 dlls/dwrite/tests/font.c     |   27 +++++++++++++++++++++++++--
 3 files changed, 74 insertions(+), 4 deletions(-)

diff --git a/dlls/dwrite/dwrite_private.h b/dlls/dwrite/dwrite_private.h
index 5c82453..d3af015 100644
--- a/dlls/dwrite/dwrite_private.h
+++ b/dlls/dwrite/dwrite_private.h
@@ -16,6 +16,8 @@
  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
  */
 
+#include "wine/unicode.h"
+
 static inline void *heap_alloc(size_t len)
 {
     return HeapAlloc(GetProcessHeap(), 0, len);
@@ -26,6 +28,21 @@ static inline BOOL heap_free(void *mem)
     return HeapFree(GetProcessHeap(), 0, mem);
 }
 
+static inline LPWSTR heap_strdupW(LPCWSTR str)
+{
+    LPWSTR ret = NULL;
+
+    if(str) {
+        DWORD size;
+
+        size = (strlenW(str)+1)*sizeof(WCHAR);
+        ret = heap_alloc(size);
+        memcpy(ret, str, size);
+    }
+
+    return ret;
+}
+
 extern HRESULT create_font_from_logfont(const LOGFONTW*, IDWriteFont**) DECLSPEC_HIDDEN;
 extern HRESULT create_textlayout(IDWriteTextLayout**) DECLSPEC_HIDDEN;
 extern HRESULT create_gdiinterop(IDWriteGdiInterop**) DECLSPEC_HIDDEN;
diff --git a/dlls/dwrite/font.c b/dlls/dwrite/font.c
index 892ee72..15e9d14 100644
--- a/dlls/dwrite/font.c
+++ b/dlls/dwrite/font.c
@@ -30,6 +30,8 @@ WINE_DEFAULT_DEBUG_CHANNEL(dwrite);
 struct dwrite_fontfamily {
     IDWriteFontFamily IDWriteFontFamily_iface;
     LONG ref;
+
+    WCHAR *familyname;
 };
 
 struct dwrite_font {
@@ -222,7 +224,10 @@ static ULONG WINAPI dwritefontfamily_Release(IDWriteFontFamily *iface)
     TRACE("(%p)->(%d)\n", This, ref);
 
     if (!ref)
+    {
+        heap_free(This->familyname);
         heap_free(This);
+    }
 
     return S_OK;
 }
@@ -283,7 +288,7 @@ static const IDWriteFontFamilyVtbl fontfamilyvtbl = {
     dwritefontfamily_GetMatchingFonts
 };
 
-static HRESULT create_fontfamily(IDWriteFontFamily **family)
+static HRESULT create_fontfamily(const WCHAR *familyname, IDWriteFontFamily **family)
 {
     struct dwrite_fontfamily *This;
 
@@ -294,6 +299,7 @@ static HRESULT create_fontfamily(IDWriteFontFamily **family)
 
     This->IDWriteFontFamily_iface.lpVtbl = &fontfamilyvtbl;
     This->ref = 1;
+    This->familyname = heap_strdupW(familyname);
 
     *family = &This->IDWriteFontFamily_iface;
 
@@ -302,13 +308,37 @@ static HRESULT create_fontfamily(IDWriteFontFamily **family)
 
 HRESULT create_font_from_logfont(const LOGFONTW *logfont, IDWriteFont **font)
 {
+    const WCHAR* facename, *familyname;
     struct dwrite_font *This;
     IDWriteFontFamily *family;
+    OUTLINETEXTMETRICW *otm;
     HRESULT hr;
+    HFONT hfont;
+    HDC hdc;
+    int ret;
 
     *font = NULL;
 
-    hr = create_fontfamily(&family);
+    hfont = CreateFontIndirectW(logfont);
+    if (!hfont) return DWRITE_E_NOFONT;
+
+    hdc = CreateCompatibleDC(0);
+    SelectObject(hdc, hfont);
+
+    ret = GetOutlineTextMetricsW(hdc, 0, NULL);
+    otm = heap_alloc(ret);
+    otm->otmSize = ret;
+    ret = GetOutlineTextMetricsW(hdc, otm->otmSize, otm);
+
+    DeleteDC(hdc);
+    DeleteObject(hfont);
+
+    facename = (WCHAR*)((char*)otm + (ptrdiff_t)otm->otmpFaceName);
+    familyname = (WCHAR*)((char*)otm + (ptrdiff_t)otm->otmpFamilyName);
+    TRACE("facename=%s, familyname=%s\n", debugstr_w(facename), debugstr_w(familyname));
+
+    hr = create_fontfamily(familyname, &family);
+    heap_free(otm);
     if (hr != S_OK) return hr;
 
     This = heap_alloc(sizeof(struct dwrite_font));
diff --git a/dlls/dwrite/tests/font.c b/dlls/dwrite/tests/font.c
index 64fe390..229e2f7 100644
--- a/dlls/dwrite/tests/font.c
+++ b/dlls/dwrite/tests/font.c
@@ -43,6 +43,7 @@ static IDWriteFactory *factory;
 static void test_CreateFontFromLOGFONT(void)
 {
     static const WCHAR arialW[] = {'A','r','i','a','l',0};
+    static const WCHAR arialspW[] = {'A','r','i','a','l',' ',0};
     static const WCHAR blahW[]  = {'B','l','a','h','!',0};
     IDWriteGdiInterop *interop;
     DWRITE_FONT_WEIGHT weight;
@@ -143,18 +144,40 @@ todo_wine
     logfont.lfWeight = FW_NORMAL;
     lstrcpyW(logfont.lfFaceName, blahW);
 
+    font = (void*)0xdeadbeef;
     hr = IDWriteGdiInterop_CreateFontFromLOGFONT(interop, &logfont, &font);
-todo_wine
+todo_wine {
     EXPECT_HR(hr, DWRITE_E_NOFONT);
+    ok(font == NULL, "got %p\n", font);
+    if(font) IDWriteFont_Release(font);
+}
 
     memset(&logfont, 0, sizeof(logfont));
     logfont.lfHeight = 12;
     logfont.lfWidth  = 12;
     logfont.lfWeight = FW_NORMAL;
+    lstrcpyW(logfont.lfFaceName, arialspW);
 
+    font = (void*)0xdeadbeef;
     hr = IDWriteGdiInterop_CreateFontFromLOGFONT(interop, &logfont, &font);
-todo_wine
+todo_wine {
     EXPECT_HR(hr, DWRITE_E_NOFONT);
+    ok(font == NULL, "got %p\n", font);
+    if(font) IDWriteFont_Release(font);
+}
+
+    memset(&logfont, 0, sizeof(logfont));
+    logfont.lfHeight = 12;
+    logfont.lfWidth  = 12;
+    logfont.lfWeight = FW_NORMAL;
+
+    font = (void*)0xdeadbeef;
+    hr = IDWriteGdiInterop_CreateFontFromLOGFONT(interop, &logfont, &font);
+todo_wine {
+    EXPECT_HR(hr, DWRITE_E_NOFONT);
+    ok(font == NULL, "got %p\n", font);
+    if(font) IDWriteFont_Release(font);
+}
 
     IDWriteGdiInterop_Release(interop);
 }




More information about the wine-cvs mailing list