diff options
author | Eskil Abrahamsen Blomfeldt <eskil.abrahamsen-blomfeldt@qt.io> | 2017-12-11 11:14:22 +0100 |
---|---|---|
committer | Eskil Abrahamsen Blomfeldt <eskil.abrahamsen-blomfeldt@qt.io> | 2017-12-13 14:42:50 +0000 |
commit | 9e99dba4a22bbf212b3e6d1e2607a16dbbd04d90 (patch) | |
tree | d3aa2bc2c5a8d48048c0686e0d8e697d4aa1249f /src/platformsupport | |
parent | e79efe94e3e77ee035ff7d046158a577759f8c7c (diff) |
Windows: Add font fallback for EUDC glyphs
EUDC, or "End-User Defined Characters", is a concept in Windows,
where the end-user can create a local fallback font of default
glyphs for the PUA (Private Use Area, a range of Unicode
not reserved to any writing system), and these glyphs will be
used when displaying the character using a font which does not
itself support the code point.
To support this in Qt we look up the default EUDC font in the registry
and add it to the fallback fonts if it is available. We use the
font for code page 1252. This has been tested on a couple of systems,
and appears to always be present. The font is added to the front of
all fallback lists, so that it will override other fallbacks,
such as Segoe UI Symbol, which happens to assign glyphs to the PUA.
If there is no end-user defined fallback, then Segoe UI Symbol will still
be used as before.
Note that this required a small change in the code to get canonical
font names. The EUDC font that Windows generates will only have a
name set for the current locale, and we expected all fonts to have
an English name. Instead, the code has now been changed to prefer
the English name if one is present, but accept any other name if
there is nothing in English.
[ChangeLog][Windows][Text] Added support for End-User Defined Characters
in Qt.
Task-number: QTBUG-44594
Change-Id: I83ae68b6d16e9b50e990dfb3ac3d294b7b2a5113
Reviewed-by: Lars Knoll <lars.knoll@qt.io>
Diffstat (limited to 'src/platformsupport')
-rw-r--r-- | src/platformsupport/fontdatabases/windows/qwindowsfontdatabase.cpp | 48 | ||||
-rw-r--r-- | src/platformsupport/fontdatabases/windows/qwindowsfontdatabase_p.h | 2 |
2 files changed, 47 insertions, 3 deletions
diff --git a/src/platformsupport/fontdatabases/windows/qwindowsfontdatabase.cpp b/src/platformsupport/fontdatabases/windows/qwindowsfontdatabase.cpp index def67c6199..9d86f461e9 100644 --- a/src/platformsupport/fontdatabases/windows/qwindowsfontdatabase.cpp +++ b/src/platformsupport/fontdatabases/windows/qwindowsfontdatabase.cpp @@ -872,8 +872,8 @@ FontNames qt_getCanonicalFontNames(const uchar *table, quint32 bytes) if ((platform_id == PlatformId_Microsoft && (encoding_id == 0 || encoding_id == 1)) - && (language_id & 0x3ff) == MS_LangIdEnglish - && *idType < Microsoft) { + && ((language_id & 0x3ff) == MS_LangIdEnglish + || *idType < Microsoft)) { *id = i; *idType = Microsoft; } @@ -1172,6 +1172,46 @@ static int QT_WIN_CALLBACK populateFontFamilies(const LOGFONT *logFont, const TE return 1; // continue } +void QWindowsFontDatabase::addDefaultEUDCFont() +{ + QString path; + { + HKEY key; + if (RegOpenKeyEx(HKEY_CURRENT_USER, + L"EUDC\\1252", + 0, + KEY_READ, + &key) != ERROR_SUCCESS) { + return; + } + + WCHAR value[MAX_PATH]; + DWORD bufferSize = sizeof(value); + ZeroMemory(value, bufferSize); + + if (RegQueryValueEx(key, + L"SystemDefaultEUDCFont", + nullptr, + nullptr, + reinterpret_cast<LPBYTE>(value), + &bufferSize) == ERROR_SUCCESS) { + path = QString::fromWCharArray(value); + } + + RegCloseKey(key); + } + + if (!path.isEmpty()) { + QFile file(path); + if (!file.open(QIODevice::ReadOnly)) { + qCWarning(lcQpaFonts) << "Unable to open default EUDC font:" << path; + return; + } + + m_eudcFonts = addApplicationFont(file.readAll(), path); + } +} + void QWindowsFontDatabase::populateFontDatabase() { removeApplicationFonts(); @@ -1186,6 +1226,7 @@ void QWindowsFontDatabase::populateFontDatabase() QString systemDefaultFamily = QWindowsFontDatabase::systemDefaultFont().family(); if (QPlatformFontDatabase::resolveFontFamilyAlias(systemDefaultFamily) == systemDefaultFamily) QPlatformFontDatabase::registerFontFamily(systemDefaultFamily); + addDefaultEUDCFont(); } typedef QSharedPointer<QWindowsFontEngineData> QWindowsFontEngineDataPtr; @@ -1583,6 +1624,7 @@ void QWindowsFontDatabase::removeApplicationFonts() } } m_applicationFonts.clear(); + m_eudcFonts.clear(); } void QWindowsFontDatabase::releaseHandle(void *handle) @@ -1842,7 +1884,7 @@ QString QWindowsFontDatabase::familyForStyleHint(QFont::StyleHint styleHint) QStringList QWindowsFontDatabase::fallbacksForFamily(const QString &family, QFont::Style style, QFont::StyleHint styleHint, QChar::Script script) const { - QStringList result; + QStringList result = m_eudcFonts; result.append(QWindowsFontDatabase::familyForStyleHint(styleHint)); result.append(QWindowsFontDatabase::extraTryFontsForFamily(family)); result.append(QPlatformFontDatabase::fallbacksForFamily(family, style, styleHint, script)); diff --git a/src/platformsupport/fontdatabases/windows/qwindowsfontdatabase_p.h b/src/platformsupport/fontdatabases/windows/qwindowsfontdatabase_p.h index bbdb90f70a..c01a03c7b4 100644 --- a/src/platformsupport/fontdatabases/windows/qwindowsfontdatabase_p.h +++ b/src/platformsupport/fontdatabases/windows/qwindowsfontdatabase_p.h @@ -134,6 +134,7 @@ public: private: void removeApplicationFonts(); + void addDefaultEUDCFont(); struct WinApplicationFont { HANDLE handle; @@ -150,6 +151,7 @@ private: QMap<QString, UniqueFontData> m_uniqueFontData; static unsigned m_fontOptions; + QStringList m_eudcFonts; }; #ifndef QT_NO_DEBUG_STREAM |