summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorMårten Nordheim <marten.nordheim@qt.io>2018-11-09 17:56:08 +0100
committerMårten Nordheim <marten.nordheim@qt.io>2018-11-30 16:15:03 +0000
commit17ced070fd1e55948659bc37c421f98074910599 (patch)
tree2cc19157f873a7732ad4f470f8d6a872f5c42b5a /src
parentd23d146175d6fab2ede50818777afe248ca0be23 (diff)
Read font selection flags and use them when querying for metrics
Certain fonts with multiple styles have the same family name. When loading these as application fonts we were not specific enough when querying for the text metrics. This meant that e.g. the bold version in a font family would get the metrics of the regular one. Fixes: QTBUG-67273 Change-Id: Ic988d62cddde0a1f77ddcaf2891cadc21c9b31e6 Reviewed-by: Mårten Nordheim <marten.nordheim@qt.io> Reviewed-by: Eskil Abrahamsen Blomfeldt <eskil.abrahamsen-blomfeldt@qt.io>
Diffstat (limited to 'src')
-rw-r--r--src/platformsupport/fontdatabases/windows/qwindowsfontdatabase.cpp39
-rw-r--r--src/platformsupport/fontdatabases/windows/qwindowsfontdatabase_p.h8
2 files changed, 41 insertions, 6 deletions
diff --git a/src/platformsupport/fontdatabases/windows/qwindowsfontdatabase.cpp b/src/platformsupport/fontdatabases/windows/qwindowsfontdatabase.cpp
index c70d507b99..9ff50bdf05 100644
--- a/src/platformsupport/fontdatabases/windows/qwindowsfontdatabase.cpp
+++ b/src/platformsupport/fontdatabases/windows/qwindowsfontdatabase.cpp
@@ -1490,7 +1490,8 @@ static void getFontTable(const uchar *fileBegin, const uchar *data, quint32 tag,
static void getFamiliesAndSignatures(const QByteArray &fontData,
QList<QFontNames> *families,
- QVector<FONTSIGNATURE> *signatures)
+ QVector<FONTSIGNATURE> *signatures,
+ QVector<QFontValues> *values)
{
const uchar *data = reinterpret_cast<const uchar *>(fontData.constData());
@@ -1511,9 +1512,25 @@ static void getFamiliesAndSignatures(const QByteArray &fontData,
families->append(qMove(names));
+ if (values || signatures)
+ getFontTable(data, font, MAKE_TAG('O', 'S', '/', '2'), &table, &length);
+
+ if (values) {
+ QFontValues fontValues;
+ if (table && length >= 64) {
+ // Read in some details about the font, offset calculated based on the specification
+ fontValues.weight = qFromBigEndian<quint16>(table + 4);
+
+ quint16 fsSelection = qFromBigEndian<quint16>(table + 62);
+ fontValues.isItalic = (fsSelection & 1) != 0;
+ fontValues.isUnderlined = (fsSelection & (1 << 1)) != 0;
+ fontValues.isOverstruck = (fsSelection & (1 << 4)) != 0;
+ }
+ values->append(std::move(fontValues));
+ }
+
if (signatures) {
FONTSIGNATURE signature;
- getFontTable(data, font, MAKE_TAG('O', 'S', '/', '2'), &table, &length);
if (table && length >= 86) {
// Offsets taken from OS/2 table in the TrueType spec
signature.fsUsb[0] = qFromBigEndian<quint32>(table + 42);
@@ -1536,11 +1553,12 @@ QStringList QWindowsFontDatabase::addApplicationFont(const QByteArray &fontData,
WinApplicationFont font;
font.fileName = fileName;
QVector<FONTSIGNATURE> signatures;
+ QVector<QFontValues> fontValues;
QList<QFontNames> families;
QStringList familyNames;
if (!fontData.isEmpty()) {
- getFamiliesAndSignatures(fontData, &families, &signatures);
+ getFamiliesAndSignatures(fontData, &families, &signatures, &fontValues);
if (families.isEmpty())
return familyNames;
@@ -1553,14 +1571,23 @@ QStringList QWindowsFontDatabase::addApplicationFont(const QByteArray &fontData,
// Memory fonts won't show up in enumeration, so do add them the hard way.
for (int j = 0; j < families.count(); ++j) {
- const QString familyName = families.at(j).name;
- const QString styleName = families.at(j).style;
+ const auto &family = families.at(j);
+ const QString &familyName = family.name;
+ const QString &styleName = family.style;
familyNames << familyName;
HDC hdc = GetDC(0);
LOGFONT lf;
memset(&lf, 0, sizeof(LOGFONT));
memcpy(lf.lfFaceName, familyName.utf16(), sizeof(wchar_t) * qMin(LF_FACESIZE - 1, familyName.size()));
lf.lfCharSet = DEFAULT_CHARSET;
+ const QFontValues &values = fontValues.at(j);
+ lf.lfWeight = values.weight;
+ if (values.isItalic)
+ lf.lfItalic = TRUE;
+ if (values.isOverstruck)
+ lf.lfStrikeOut = TRUE;
+ if (values.isUnderlined)
+ lf.lfUnderline = TRUE;
HFONT hfont = CreateFontIndirect(&lf);
HGDIOBJ oldobj = SelectObject(hdc, hfont);
@@ -1581,7 +1608,7 @@ QStringList QWindowsFontDatabase::addApplicationFont(const QByteArray &fontData,
QByteArray data = f.readAll();
f.close();
- getFamiliesAndSignatures(data, &families, 0);
+ getFamiliesAndSignatures(data, &families, nullptr, nullptr);
if (families.isEmpty())
return QStringList();
diff --git a/src/platformsupport/fontdatabases/windows/qwindowsfontdatabase_p.h b/src/platformsupport/fontdatabases/windows/qwindowsfontdatabase_p.h
index ab6d6307c7..9d0aa7f723 100644
--- a/src/platformsupport/fontdatabases/windows/qwindowsfontdatabase_p.h
+++ b/src/platformsupport/fontdatabases/windows/qwindowsfontdatabase_p.h
@@ -177,6 +177,14 @@ struct QFontNames
QString preferredStyle; // e.g. "Condensed Italic"
};
+struct QFontValues
+{
+ quint16 weight = 0;
+ bool isItalic = false;
+ bool isOverstruck = false;
+ bool isUnderlined = false;
+};
+
bool qt_localizedName(const QString &name);
QString qt_getEnglishName(const QString &familyName, bool includeStyle = false);
QFontNames qt_getCanonicalFontNames(const LOGFONT &lf);