[PATCH 1/5] dwrite: Accept platform 0 name records if there's nothing, else
Nikolay Sivov
bunglehead at gmail.com
Mon Feb 8 03:31:07 CST 2016
---
-------------- next part --------------
From 4c9989f5a64ff30ca654870183cb1d03491217a2 Mon Sep 17 00:00:00 2001
From: Nikolay Sivov <nsivov at codeweavers.com>
Date: Sat, 6 Feb 2016 02:59:39 +0300
Subject: [PATCH 1/5] dwrite: Accept platform 0 name records if there's nothing
else
Signed-off-by: Nikolay Sivov <nsivov at codeweavers.com>
---
dlls/dwrite/opentype.c | 111 +++++++++++++++++++++++++++++--------------------
1 file changed, 65 insertions(+), 46 deletions(-)
diff --git a/dlls/dwrite/opentype.c b/dlls/dwrite/opentype.c
index 99d24ea..0d3482d 100644
--- a/dlls/dwrite/opentype.c
+++ b/dlls/dwrite/opentype.c
@@ -1281,20 +1281,69 @@ static void get_name_record_locale(enum OPENTYPE_PLATFORM_ID platform, USHORT la
strcpyW(locale, enusW);
}
break;
+ case OPENTYPE_PLATFORM_UNICODE:
+ strcpyW(locale, enusW);
+ break;
default:
FIXME("unknown platform %d\n", platform);
}
}
+static BOOL opentype_decode_namerecord(const TT_NAME_V0 *header, BYTE *storage_area, USHORT recid, IDWriteLocalizedStrings *strings)
+{
+ const TT_NameRecord *record = &header->nameRecord[recid];
+ USHORT lang_id, length, offset, encoding, platform;
+ BOOL ret = FALSE;
+
+ platform = GET_BE_WORD(record->platformID);
+ lang_id = GET_BE_WORD(record->languageID);
+ length = GET_BE_WORD(record->length);
+ offset = GET_BE_WORD(record->offset);
+ encoding = GET_BE_WORD(record->encodingID);
+
+ if (lang_id < 0x8000) {
+ WCHAR locale[LOCALE_NAME_MAX_LENGTH];
+ WCHAR *name_string;
+ UINT codepage;
+
+ codepage = get_name_record_codepage(platform, encoding);
+ get_name_record_locale(platform, lang_id, locale, sizeof(locale)/sizeof(WCHAR));
+
+ if (codepage) {
+ DWORD len = MultiByteToWideChar(codepage, 0, (LPSTR)(storage_area + offset), length, NULL, 0);
+ name_string = heap_alloc(sizeof(WCHAR) * (len+1));
+ MultiByteToWideChar(codepage, 0, (LPSTR)(storage_area + offset), length, name_string, len);
+ name_string[len] = 0;
+ }
+ else {
+ int i;
+
+ length /= sizeof(WCHAR);
+ name_string = heap_strdupnW((LPWSTR)(storage_area + offset), length);
+ for (i = 0; i < length; i++)
+ name_string[i] = GET_BE_WORD(name_string[i]);
+ }
+
+ TRACE("string %s for locale %s found\n", debugstr_w(name_string), debugstr_w(locale));
+ add_localizedstring(strings, locale, name_string);
+ heap_free(name_string);
+ ret = TRUE;
+ }
+ else
+ FIXME("handle NAME format 1\n");
+
+ return ret;
+}
+
static HRESULT opentype_get_font_strings_from_id(const void *table_data, enum OPENTYPE_STRING_ID id, IDWriteLocalizedStrings **strings)
{
const TT_NAME_V0 *header;
BYTE *storage_area = 0;
USHORT count = 0;
+ int i, candidate;
WORD format;
BOOL exists;
HRESULT hr;
- int i;
if (!table_data)
return E_FAIL;
@@ -1313,20 +1362,18 @@ static HRESULT opentype_get_font_strings_from_id(const void *table_data, enum OP
FIXME("unsupported NAME format %d\n", format);
}
-
storage_area = (LPBYTE)table_data + GET_BE_WORD(header->stringOffset);
count = GET_BE_WORD(header->count);
exists = FALSE;
+ candidate = -1;
for (i = 0; i < count; i++) {
const TT_NameRecord *record = &header->nameRecord[i];
- USHORT lang_id, length, offset, encoding, platform;
+ USHORT platform;
if (GET_BE_WORD(record->nameID) != id)
continue;
- exists = TRUE;
-
/* Right now only accept unicode and windows encoded fonts */
platform = GET_BE_WORD(record->platformID);
if (platform != OPENTYPE_PLATFORM_UNICODE &&
@@ -1337,53 +1384,25 @@ static HRESULT opentype_get_font_strings_from_id(const void *table_data, enum OP
continue;
}
- /* Skip such entries for now, as it's not clear which locale is implied when
- unicode platform is used. Also fonts tend to duplicate those strings as
- WIN platform entries. */
- if (platform == OPENTYPE_PLATFORM_UNICODE)
+ /* Skip such entries for now, fonts tend to duplicate those strings as
+ WIN platform entries. If font does not have WIN or MAC entry for this id, we will
+ use this Unicode platform entry while assuming en-US locale. */
+ if (platform == OPENTYPE_PLATFORM_UNICODE) {
+ candidate = i;
continue;
-
- lang_id = GET_BE_WORD(record->languageID);
- length = GET_BE_WORD(record->length);
- offset = GET_BE_WORD(record->offset);
- encoding = GET_BE_WORD(record->encodingID);
-
- if (lang_id < 0x8000) {
- WCHAR locale[LOCALE_NAME_MAX_LENGTH];
- WCHAR *name_string;
- UINT codepage;
-
- codepage = get_name_record_codepage(platform, encoding);
- get_name_record_locale(platform, lang_id, locale, sizeof(locale)/sizeof(WCHAR));
-
- if (codepage) {
- DWORD len = MultiByteToWideChar(codepage, 0, (LPSTR)(storage_area + offset), length, NULL, 0);
- name_string = heap_alloc(sizeof(WCHAR) * (len+1));
- MultiByteToWideChar(codepage, 0, (LPSTR)(storage_area + offset), length, name_string, len);
- name_string[len] = 0;
- }
- else {
- int i;
-
- length /= sizeof(WCHAR);
- name_string = heap_strdupnW((LPWSTR)(storage_area + offset), length);
- for (i = 0; i < length; i++)
- name_string[i] = GET_BE_WORD(name_string[i]);
- }
-
- TRACE("string %s for locale %s found\n", debugstr_w(name_string), debugstr_w(locale));
- add_localizedstring(*strings, locale, name_string);
- heap_free(name_string);
}
- else {
- FIXME("handle NAME format 1\n");
+
+ if (!(exists = opentype_decode_namerecord(header, storage_area, i, *strings)))
continue;
- }
}
if (!exists) {
- IDWriteLocalizedStrings_Release(*strings);
- *strings = NULL;
+ if (candidate != -1)
+ exists = opentype_decode_namerecord(header, storage_area, candidate, *strings);
+ else {
+ IDWriteLocalizedStrings_Release(*strings);
+ *strings = NULL;
+ }
}
return exists ? S_OK : E_FAIL;
--
2.7.0
More information about the wine-patches
mailing list