diff options
Diffstat (limited to 'src/plugins/platforms/windows/qwindowsfontdatabase.cpp')
-rw-r--r-- | src/plugins/platforms/windows/qwindowsfontdatabase.cpp | 56 |
1 files changed, 23 insertions, 33 deletions
diff --git a/src/plugins/platforms/windows/qwindowsfontdatabase.cpp b/src/plugins/platforms/windows/qwindowsfontdatabase.cpp index f15783490e..46b05de4ae 100644 --- a/src/plugins/platforms/windows/qwindowsfontdatabase.cpp +++ b/src/plugins/platforms/windows/qwindowsfontdatabase.cpp @@ -618,20 +618,6 @@ QDebug operator<<(QDebug d, const QFontDef &def) return d; } -// convert 0 ~ 1000 integer to QFont::Weight -static inline QFont::Weight weightFromInteger(long weight) -{ - if (weight < 400) - return QFont::Light; - if (weight < 600) - return QFont::Normal; - if (weight < 700) - return QFont::DemiBold; - if (weight < 800) - return QFont::Bold; - return QFont::Black; -} - static inline QFontDatabase::WritingSystem writingSystemFromCharSet(uchar charSet) { switch (charSet) { @@ -808,7 +794,7 @@ QString getEnglishName(const QString &familyName) HDC hdc = GetDC( 0 ); LOGFONT lf; memset(&lf, 0, sizeof(LOGFONT)); - memcpy(lf.lfFaceName, familyName.utf16(), qMin(LF_FACESIZE, familyName.length()) * sizeof(wchar_t)); + memcpy(lf.lfFaceName, familyName.utf16(), qMin(familyName.length(), LF_FACESIZE - 1) * sizeof(wchar_t)); lf.lfCharSet = DEFAULT_CHARSET; HFONT hfont = CreateFontIndirect(&lf); @@ -865,7 +851,7 @@ static bool addFontToDatabase(const QString &familyName, uchar charSet, const int size = scalable ? SMOOTH_SCALABLE : tm->tmHeight; const QFont::Style style = tm->tmItalic ? QFont::StyleItalic : QFont::StyleNormal; const bool antialias = false; - const QFont::Weight weight = weightFromInteger(tm->tmWeight); + const QFont::Weight weight = QPlatformFontDatabase::weightFromInteger(tm->tmWeight); const QFont::Stretch stretch = QFont::Unstretched; #ifndef QT_NO_DEBUG_OUTPUT @@ -972,14 +958,9 @@ static int QT_WIN_CALLBACK storeFontSub(ENUMLOGFONTEX* f, NEWTEXTMETRICEX *textm HDC dummy = GetDC(0); LOGFONT lf; + memset(&lf, 0, sizeof(LOGFONT)); lf.lfCharSet = DEFAULT_CHARSET; - if (wcslen(f->elfLogFont.lfFaceName) >= LF_FACESIZE) { - qWarning("%s: Unable to enumerate family '%s'.", - __FUNCTION__, qPrintable(QString::fromWCharArray(f->elfLogFont.lfFaceName))); - return 1; - } - wmemcpy(lf.lfFaceName, f->elfLogFont.lfFaceName, - wcslen(f->elfLogFont.lfFaceName) + 1); + memcpy(lf.lfFaceName, f->elfLogFont.lfFaceName, LF_FACESIZE * sizeof(wchar_t)); lf.lfPitchAndFamily = 0; EnumFontFamiliesEx(dummy, &lf, (FONTENUMPROC)storeFont, (LPARAM)namesSetIn, 0); @@ -1015,20 +996,21 @@ void QWindowsFontDatabase::populate(const QString &family) HDC dummy = GetDC(0); LOGFONT lf; + memset(&lf, 0, sizeof(LOGFONT)); lf.lfCharSet = DEFAULT_CHARSET; if (family.size() >= LF_FACESIZE) { qWarning("%s: Unable to enumerate family '%s'.", __FUNCTION__, qPrintable(family)); return; } - wmemcpy(lf.lfFaceName, reinterpret_cast<const wchar_t*>(family.utf16()), - family.size() + 1); + lf.lfPitchAndFamily = 0; if (family.isEmpty()) { EnumFontFamiliesEx(dummy, &lf, (FONTENUMPROC)storeFontSub, (LPARAM)&m_families, 0); } else { + memcpy(lf.lfFaceName, family.utf16(), family.size() * sizeof(wchar_t)); EnumFontFamiliesEx(dummy, &lf, (FONTENUMPROC)storeFont, (LPARAM)&m_families, 0); } @@ -1093,7 +1075,7 @@ QFontEngineMulti *QWindowsFontDatabase::fontEngineMulti(QFontEngine *fontEngine, if (script == QChar::Script_Common) return new QWindowsMultiFontEngine(fontEngine, script); // ### as long as fallbacksForFamily() does not take script parameter into account, - // prefer QFontEngineMultiBasicImpl's loadEngine() implementation for complex scripts + // prefer QFontEngineMulti's loadEngine() implementation for complex scripts return QPlatformFontDatabase::fontEngineMulti(fontEngine, script); } @@ -1253,7 +1235,7 @@ QFontEngine *QWindowsFontDatabase::fontEngine(const QByteArray &fontData, qreal else fontEngine->fontDef.style = QFont::StyleNormal; - fontEngine->fontDef.weight = weightFromInteger(qFromBigEndian<quint16>(os2Table->weightClass)); + fontEngine->fontDef.weight = QPlatformFontDatabase::weightFromInteger(qFromBigEndian<quint16>(os2Table->weightClass)); } } @@ -1364,7 +1346,7 @@ QStringList QWindowsFontDatabase::addApplicationFont(const QByteArray &fontData, HDC hdc = GetDC(0); LOGFONT lf; memset(&lf, 0, sizeof(LOGFONT)); - memcpy(lf.lfFaceName, familyName.utf16(), sizeof(wchar_t) * qMin(LF_FACESIZE, familyName.size())); + memcpy(lf.lfFaceName, familyName.utf16(), sizeof(wchar_t) * qMin(LF_FACESIZE - 1, familyName.size())); lf.lfCharSet = DEFAULT_CHARSET; HFONT hfont = CreateFontIndirect(&lf); HGDIOBJ oldobj = SelectObject(hdc, hfont); @@ -1589,6 +1571,10 @@ LOGFONT QWindowsFontDatabase::fontDefToLOGFONT(const QFontDef &request) lf.lfPitchAndFamily = DEFAULT_PITCH | hint; QString fam = request.family; + if (fam.size() >= LF_FACESIZE) { + qCritical("%s: Family name '%s' is too long.", __FUNCTION__, qPrintable(fam)); + fam.truncate(LF_FACESIZE - 1); + } if (fam.isEmpty()) fam = QStringLiteral("MS Sans Serif"); @@ -1600,7 +1586,7 @@ LOGFONT QWindowsFontDatabase::fontDefToLOGFONT(const QFontDef &request) if (fam == QLatin1String("Courier") && !(request.styleStrategy & QFont::PreferBitmap)) fam = QStringLiteral("Courier New"); - memcpy(lf.lfFaceName, fam.utf16(), sizeof(wchar_t) * qMin(fam.length() + 1, 32)); // 32 = Windows hard-coded + memcpy(lf.lfFaceName, fam.utf16(), fam.size() * sizeof(wchar_t)); return lf; } @@ -1781,9 +1767,13 @@ QFontEngine *QWindowsFontDatabase::createEngine(const QFontDef &request, // turns out okay) useDirectWrite = false; if (initDirectWrite(data.data())) { - const QString nameSubstitute = QWindowsFontEngineDirectWrite::fontNameSubstitute(QString::fromWCharArray(lf.lfFaceName)); - memcpy(lf.lfFaceName, nameSubstitute.utf16(), - sizeof(wchar_t) * qMin(nameSubstitute.length() + 1, LF_FACESIZE)); + const QString fam = QString::fromWCharArray(lf.lfFaceName); + const QString nameSubstitute = QWindowsFontEngineDirectWrite::fontNameSubstitute(fam); + if (nameSubstitute != fam) { + const int nameSubstituteLength = qMin(nameSubstitute.length(), LF_FACESIZE - 1); + memcpy(lf.lfFaceName, nameSubstitute.utf16(), nameSubstituteLength * sizeof(wchar_t)); + lf.lfFaceName[nameSubstituteLength] = 0; + } HRESULT hr = data->directWriteGdiInterop->CreateFontFromLOGFONT( &lf, @@ -1854,7 +1844,7 @@ QFont QWindowsFontDatabase::LOGFONT_to_QFont(const LOGFONT& logFont, int vertica QFont qFont(QString::fromWCharArray(logFont.lfFaceName)); qFont.setItalic(logFont.lfItalic); if (logFont.lfWeight != FW_DONTCARE) - qFont.setWeight(weightFromInteger(logFont.lfWeight)); + qFont.setWeight(QPlatformFontDatabase::weightFromInteger(logFont.lfWeight)); const qreal logFontHeight = qAbs(logFont.lfHeight); qFont.setPointSizeF(logFontHeight * 72.0 / qreal(verticalDPI_In)); qFont.setUnderline(logFont.lfUnderline); |