summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/gui/text/qfontdatabase.cpp35
-rw-r--r--src/platformsupport/fontdatabases/mac/qcoretextfontdatabase.mm3
-rw-r--r--tests/auto/gui/text/qrawfont/tst_qrawfont.cpp35
3 files changed, 73 insertions, 0 deletions
diff --git a/src/gui/text/qfontdatabase.cpp b/src/gui/text/qfontdatabase.cpp
index 2cc071d67b..33dc27983a 100644
--- a/src/gui/text/qfontdatabase.cpp
+++ b/src/gui/text/qfontdatabase.cpp
@@ -2837,6 +2837,41 @@ QString QFontDatabase::resolveFontFamilyAlias(const QString &family)
return QGuiApplicationPrivate::platformIntegration()->fontDatabase()->resolveFontFamilyAlias(family);
}
+Q_GUI_EXPORT QStringList qt_sort_families_by_writing_system(QChar::Script script, const QStringList &families)
+{
+ size_t writingSystem = std::find(scriptForWritingSystem,
+ scriptForWritingSystem + QFontDatabase::WritingSystemsCount,
+ script) - scriptForWritingSystem;
+ if (writingSystem == QFontDatabase::Any
+ || writingSystem >= QFontDatabase::WritingSystemsCount) {
+ return families;
+ }
+
+ QFontDatabasePrivate *db = privateDb();
+ QMultiMap<uint, QString> supported;
+ for (int i = 0; i < families.size(); ++i) {
+ const QString &family = families.at(i);
+
+ QtFontFamily *testFamily = nullptr;
+ for (int x = 0; x < db->count; ++x) {
+ if (Q_UNLIKELY(matchFamilyName(family, db->families[x]))) {
+ testFamily = db->families[x];
+ testFamily->ensurePopulated();
+ break;
+ }
+ }
+
+ uint order = i;
+ if (testFamily == nullptr
+ || (testFamily->writingSystems[writingSystem] & QtFontFamily::Supported) == 0) {
+ order |= 1 << 31;
+ }
+
+ supported.insert(order, family);
+ }
+
+ return supported.values();
+}
QT_END_NAMESPACE
diff --git a/src/platformsupport/fontdatabases/mac/qcoretextfontdatabase.mm b/src/platformsupport/fontdatabases/mac/qcoretextfontdatabase.mm
index 237e8a89a5..7397312820 100644
--- a/src/platformsupport/fontdatabases/mac/qcoretextfontdatabase.mm
+++ b/src/platformsupport/fontdatabases/mac/qcoretextfontdatabase.mm
@@ -544,6 +544,9 @@ QStringList QCoreTextFontDatabase::fallbacksForFamily(const QString &family, QFo
fallbackList.append(QStringLiteral("Arial Unicode MS"));
#endif
+ extern QStringList qt_sort_families_by_writing_system(QChar::Script, const QStringList &);
+ fallbackList = qt_sort_families_by_writing_system(script, fallbackList);
+
return fallbackList;
}
}
diff --git a/tests/auto/gui/text/qrawfont/tst_qrawfont.cpp b/tests/auto/gui/text/qrawfont/tst_qrawfont.cpp
index ee775d4a31..37f94d0278 100644
--- a/tests/auto/gui/text/qrawfont/tst_qrawfont.cpp
+++ b/tests/auto/gui/text/qrawfont/tst_qrawfont.cpp
@@ -90,6 +90,9 @@ private slots:
void rawFontFromInvalidData();
void kernedAdvances();
+
+ void fallbackFontsOrder();
+
private:
QString testFont;
QString testFontBoldItalic;
@@ -1009,6 +1012,38 @@ void tst_QRawFont::kernedAdvances()
QVERIFY(FUZZY_LTEQ(qAbs(advances.at(0).x() - expectedAdvanceWidth), errorMargin));
}
+void tst_QRawFont::fallbackFontsOrder()
+{
+ QFontDatabase fontDatabase;
+ int id = fontDatabase.addApplicationFont(testFont);
+
+ QFont font("QtBidiTestFont");
+ font.setPixelSize(12.0);
+
+ QString arabicText = QFontDatabase::writingSystemSample(QFontDatabase::Arabic);
+
+ // If this fails, then the writing system sample has changed and we need to create
+ // a new text containing both a space and Arabic characters.
+ QVERIFY(arabicText.contains(QLatin1Char(' ')));
+
+ QTextLayout layout;
+ layout.setFont(font);
+ layout.setText(arabicText);
+ layout.setCacheEnabled(true);
+ layout.beginLayout();
+ layout.createLine();
+ layout.endLayout();
+
+ QList<QGlyphRun> glyphRuns = layout.glyphRuns();
+
+ // Since QtBidiTestFont does not support Arabic nor the space, both should map to
+ // the same font. If this fails, it is an indication that the list of fallbacks fonts
+ // is not sorted by writing system support.
+ QCOMPARE(glyphRuns.size(), 1);
+
+ fontDatabase.removeApplicationFont(id);
+}
+
#endif // QT_NO_RAWFONT
QTEST_MAIN(tst_QRawFont)