Nikolay Sivov : dwrite: Add all installed font families to system font collection.
Alexandre Julliard
julliard at winehq.org
Mon Oct 22 13:42:45 CDT 2012
Module: wine
Branch: master
Commit: f0f1735495d79c474f50c0303718b719a4febe2d
URL: http://source.winehq.org/git/wine.git/?a=commit;h=f0f1735495d79c474f50c0303718b719a4febe2d
Author: Nikolay Sivov <nsivov at codeweavers.com>
Date: Sun Oct 21 00:24:35 2012 -0400
dwrite: Add all installed font families to system font collection.
---
dlls/dwrite/dwrite_private.h | 2 +-
dlls/dwrite/font.c | 57 +++++++++++++++++++++++++++++++++++++++--
dlls/dwrite/main.c | 8 ++++-
dlls/dwrite/tests/font.c | 34 ++++++++++++++++++++++++-
4 files changed, 94 insertions(+), 7 deletions(-)
diff --git a/dlls/dwrite/dwrite_private.h b/dlls/dwrite/dwrite_private.h
index 3135ade..4cb0e3b 100644
--- a/dlls/dwrite/dwrite_private.h
+++ b/dlls/dwrite/dwrite_private.h
@@ -68,10 +68,10 @@ static inline LPWSTR heap_strdupnW(const WCHAR *str, UINT32 len)
}
extern HRESULT create_font_from_logfont(const LOGFONTW*, IDWriteFont**) DECLSPEC_HIDDEN;
-extern HRESULT create_fontcollection(IDWriteFontCollection**) DECLSPEC_HIDDEN;
extern HRESULT create_textformat(const WCHAR*,DWRITE_FONT_WEIGHT,DWRITE_FONT_STYLE,DWRITE_FONT_STRETCH,
FLOAT,const WCHAR*,IDWriteTextFormat**) DECLSPEC_HIDDEN;
extern HRESULT create_textlayout(const WCHAR*,UINT32,IDWriteTextLayout**) DECLSPEC_HIDDEN;
extern HRESULT create_gdiinterop(IDWriteGdiInterop**) DECLSPEC_HIDDEN;
extern HRESULT create_localizedstrings(IDWriteLocalizedStrings**) DECLSPEC_HIDDEN;
extern HRESULT add_localizedstring(IDWriteLocalizedStrings*,const WCHAR*,const WCHAR*) DECLSPEC_HIDDEN;
+extern HRESULT create_system_fontcollection(IDWriteFontCollection**) DECLSPEC_HIDDEN;
diff --git a/dlls/dwrite/font.c b/dlls/dwrite/font.c
index d5346c9..689a330 100644
--- a/dlls/dwrite/font.c
+++ b/dlls/dwrite/font.c
@@ -130,6 +130,10 @@ typedef struct
struct dwrite_fontcollection {
IDWriteFontCollection IDWriteFontCollection_iface;
LONG ref;
+
+ WCHAR **families;
+ UINT32 count;
+ int alloc;
};
struct dwrite_fontfamily {
@@ -657,7 +661,14 @@ static ULONG WINAPI dwritefontcollection_Release(IDWriteFontCollection *iface)
TRACE("(%p)->(%d)\n", This, ref);
if (!ref)
+ {
+ int i;
+
+ for (i = 0; i < This->count; i++)
+ heap_free(This->families[i]);
+ heap_free(This->families);
heap_free(This);
+ }
return ref;
}
@@ -665,8 +676,8 @@ static ULONG WINAPI dwritefontcollection_Release(IDWriteFontCollection *iface)
static UINT32 WINAPI dwritefontcollection_GetFontFamilyCount(IDWriteFontCollection *iface)
{
struct dwrite_fontcollection *This = impl_from_IDWriteFontCollection(iface);
- FIXME("(%p): stub\n", This);
- return 0;
+ TRACE("(%p)\n", This);
+ return This->count;
}
static HRESULT WINAPI dwritefontcollection_GetFontFamily(IDWriteFontCollection *iface, UINT32 index, IDWriteFontFamily **family)
@@ -700,9 +711,35 @@ static const IDWriteFontCollectionVtbl fontcollectionvtbl = {
dwritefontcollection_GetFontFromFontFace
};
-HRESULT create_fontcollection(IDWriteFontCollection **collection)
+static HRESULT add_family_syscollection(struct dwrite_fontcollection *collection, const WCHAR *family)
+{
+ /* check for duplicate family name */
+ if (collection->count && !strcmpW(collection->families[collection->count-1], family)) return S_OK;
+
+ /* double array length */
+ if (collection->count == collection->alloc)
+ {
+ collection->alloc *= 2;
+ collection->families = heap_realloc(collection->families, collection->alloc*sizeof(WCHAR*));
+ }
+
+ collection->families[collection->count++] = heap_strdupW(family);
+ TRACE("family name %s\n", debugstr_w(family));
+
+ return S_OK;
+}
+
+static INT CALLBACK enum_font_families(const LOGFONTW *lf, const TEXTMETRICW *tm, DWORD type, LPARAM lParam)
+{
+ struct dwrite_fontcollection *collection = (struct dwrite_fontcollection*)lParam;
+ return add_family_syscollection(collection, lf->lfFaceName) == S_OK;
+}
+
+HRESULT create_system_fontcollection(IDWriteFontCollection **collection)
{
struct dwrite_fontcollection *This;
+ LOGFONTW lf;
+ HDC hdc;
*collection = NULL;
@@ -712,6 +749,20 @@ HRESULT create_fontcollection(IDWriteFontCollection **collection)
This->IDWriteFontCollection_iface.lpVtbl = &fontcollectionvtbl;
This->ref = 1;
+ This->alloc = 50;
+ This->count = 0;
+ This->families = heap_alloc(This->alloc*sizeof(WCHAR*));
+
+ TRACE("building system font collection:\n");
+
+ hdc = CreateCompatibleDC(0);
+ memset(&lf, 0, sizeof(lf));
+ lf.lfCharSet = DEFAULT_CHARSET;
+ lf.lfPitchAndFamily = DEFAULT_PITCH;
+ lf.lfFaceName[0] = 0;
+ EnumFontFamiliesExW(hdc, &lf, enum_font_families, (LPARAM)This, 0);
+ DeleteDC(hdc);
+
*collection = &This->IDWriteFontCollection_iface;
return S_OK;
diff --git a/dlls/dwrite/main.c b/dlls/dwrite/main.c
index 5f69723..4605008 100644
--- a/dlls/dwrite/main.c
+++ b/dlls/dwrite/main.c
@@ -384,8 +384,12 @@ static ULONG WINAPI dwritefactory_Release(IDWriteFactory *iface)
static HRESULT WINAPI dwritefactory_GetSystemFontCollection(IDWriteFactory *iface,
IDWriteFontCollection **collection, BOOL check_for_updates)
{
- FIXME("(%p %d): semi-stub\n", collection, check_for_updates);
- return create_fontcollection(collection);
+ TRACE("(%p %d)\n", collection, check_for_updates);
+
+ if (check_for_updates)
+ FIXME("checking for system font updates not implemented\n");
+
+ return create_system_fontcollection(collection);
}
static HRESULT WINAPI dwritefactory_CreateCustomFontCollection(IDWriteFactory *iface,
diff --git a/dlls/dwrite/tests/font.c b/dlls/dwrite/tests/font.c
index 594ccea..9dc59e0 100644
--- a/dlls/dwrite/tests/font.c
+++ b/dlls/dwrite/tests/font.c
@@ -41,11 +41,11 @@ static void _expect_ref(IUnknown* obj, ULONG ref, int line)
static IDWriteFactory *factory;
static const WCHAR tahomaW[] = {'T','a','h','o','m','a',0};
+static const WCHAR blahW[] = {'B','l','a','h','!',0};
static void test_CreateFontFromLOGFONT(void)
{
static const WCHAR tahomaspW[] = {'T','a','h','o','m','a',' ',0};
- static const WCHAR blahW[] = {'B','l','a','h','!',0};
IDWriteGdiInterop *interop;
DWRITE_FONT_WEIGHT weight;
DWRITE_FONT_STYLE style;
@@ -523,6 +523,37 @@ todo_wine
IDWriteGdiInterop_Release(interop);
}
+static void test_system_fontcollection(void)
+{
+ IDWriteFontCollection *collection;
+ HRESULT hr;
+ UINT32 i;
+ BOOL ret;
+
+ hr = IDWriteFactory_GetSystemFontCollection(factory, &collection, FALSE);
+ ok(hr == S_OK, "got 0x%08x\n", hr);
+
+ i = IDWriteFontCollection_GetFontFamilyCount(collection);
+ ok(i, "got %u\n", i);
+
+todo_wine {
+ ret = FALSE;
+ i = (UINT32)-1;
+ hr = IDWriteFontCollection_FindFamilyName(collection, tahomaW, &i, &ret);
+ ok(hr == S_OK, "got 0x%08x\n", hr);
+ ok(ret, "got %d\n", ret);
+ ok(i != (UINT32)-1, "got %u\n", i);
+
+ ret = TRUE;
+ i = 0;
+ hr = IDWriteFontCollection_FindFamilyName(collection, blahW, &i, &ret);
+ ok(hr == S_OK, "got 0x%08x\n", hr);
+ ok(!ret, "got %d\n", ret);
+ ok(i == (UINT32)-1, "got %u\n", i);
+}
+ IDWriteFontCollection_Release(collection);
+}
+
START_TEST(font)
{
HRESULT hr;
@@ -541,6 +572,7 @@ START_TEST(font)
test_GetFamilyNames();
test_CreateFontFace();
test_GetMetrics();
+ test_system_fontcollection();
IDWriteFactory_Release(factory);
}
More information about the wine-cvs
mailing list