diff --git a/src/gui/text/coretext/qcoretextfontdatabase.mm b/src/gui/text/coretext/qcoretextfontdatabase.mm index 574f57047e..e67a01fca9 100644 --- a/src/gui/text/coretext/qcoretextfontdatabase.mm +++ b/src/gui/text/coretext/qcoretextfontdatabase.mm @@ -128,11 +128,7 @@ void QCoreTextFontDatabase::populateFontDatabase() qCDebug(lcQpaFonts) << "Populating available families took" << elapsed.restart() << "ms"; - // Force creating the theme fonts to get the descriptors in m_systemFontDescriptors - if (m_themeFonts.isEmpty()) - (void)themeFonts(); - - qCDebug(lcQpaFonts) << "Resolving theme fonts took" << elapsed.restart() << "ms"; + populateThemeFonts(); for (CTFontDescriptorRef fontDesc : m_systemFontDescriptors) populateFromDescriptor(fontDesc); @@ -752,31 +748,43 @@ static CTFontDescriptorRef fontDescriptorFromTheme(QPlatformTheme::Font f) return descriptorForFontType(fontTypeFromTheme(f)); } -const QHash &QCoreTextFontDatabase::themeFonts() const +void QCoreTextFontDatabase::populateThemeFonts() { - if (m_themeFonts.isEmpty()) { - for (long f = QPlatformTheme::SystemFont; f < QPlatformTheme::NFonts; f++) { - QPlatformTheme::Font ft = static_cast(f); - m_themeFonts.insert(ft, themeFont(ft)); - } + if (!m_themeFonts.isEmpty()) + return; + + QElapsedTimer elapsed; + if (lcQpaFonts().isDebugEnabled()) + elapsed.start(); + + qCDebug(lcQpaFonts) << "Populating theme fonts..."; + + for (long f = QPlatformTheme::SystemFont; f < QPlatformTheme::NFonts; f++) { + QPlatformTheme::Font themeFont = static_cast(f); + CTFontDescriptorRef fontDescriptor = fontDescriptorFromTheme(themeFont); + FontDescription fd; + getFontDescription(fontDescriptor, &fd); + + if (!m_systemFontDescriptors.contains(fontDescriptor)) + m_systemFontDescriptors.insert(fontDescriptor); + else + CFRelease(fontDescriptor); + + QFont *font = new QFont(fd.familyName, fd.pointSize, fd.weight, fd.style == QFont::StyleItalic); + m_themeFonts.insert(themeFont, font); } - return m_themeFonts; + qCDebug(lcQpaFonts) << "Populating theme fonts took" << elapsed.restart() << "ms"; } QFont *QCoreTextFontDatabase::themeFont(QPlatformTheme::Font f) const { - CTFontDescriptorRef fontDesc = fontDescriptorFromTheme(f); - FontDescription fd; - getFontDescription(fontDesc, &fd); + // The code paths via QFontDatabase::systemFont() or QPlatformTheme::font() + // do not ensure that the font database has been populated, so we need to + // manually populate the theme fonts lazily here just in case. + const_cast(this)->populateThemeFonts(); - if (!m_systemFontDescriptors.contains(fontDesc)) - m_systemFontDescriptors.insert(fontDesc); - else - CFRelease(fontDesc); - - QFont *font = new QFont(fd.familyName, fd.pointSize, fd.weight, fd.style == QFont::StyleItalic); - return font; + return m_themeFonts.value(f, nullptr); } QFont QCoreTextFontDatabase::defaultFont() const diff --git a/src/gui/text/coretext/qcoretextfontdatabase_p.h b/src/gui/text/coretext/qcoretextfontdatabase_p.h index 971ac3cfde..a6f93dd14a 100644 --- a/src/gui/text/coretext/qcoretextfontdatabase_p.h +++ b/src/gui/text/coretext/qcoretextfontdatabase_p.h @@ -83,20 +83,20 @@ public: bool fontsAlwaysScalable() const override; QList standardSizes() const override; - // For iOS and OS X platform themes + // For iOS and macOS platform themes QFont *themeFont(QPlatformTheme::Font) const; - const QHash &themeFonts() const; protected: mutable QSet m_systemFontDescriptors; private: + void populateThemeFonts(); void populateFromDescriptor(CTFontDescriptorRef font, const QString &familyName = QString(), QFontDatabasePrivate::ApplicationFont *applicationFont = nullptr); static CFArrayRef fallbacksForFamily(const QString &family); mutable QString defaultFontName; - mutable QHash m_themeFonts; + QHash m_themeFonts; bool m_hasPopulatedAliases; }; diff --git a/src/plugins/platforms/cocoa/qcocoatheme.mm b/src/plugins/platforms/cocoa/qcocoatheme.mm index cbea578cf9..3f5802afbb 100644 --- a/src/plugins/platforms/cocoa/qcocoatheme.mm +++ b/src/plugins/platforms/cocoa/qcocoatheme.mm @@ -371,7 +371,7 @@ const QFont *QCocoaTheme::font(Font type) const { const auto *platformIntegration = QGuiApplicationPrivate::platformIntegration(); const auto *coreTextFontDatabase = static_cast(platformIntegration->fontDatabase()); - return coreTextFontDatabase->themeFonts().value(type, nullptr); + return coreTextFontDatabase->themeFont(type); } //! \internal diff --git a/src/plugins/platforms/ios/qiostheme.mm b/src/plugins/platforms/ios/qiostheme.mm index 045b4d45c9..69416ec24a 100644 --- a/src/plugins/platforms/ios/qiostheme.mm +++ b/src/plugins/platforms/ios/qiostheme.mm @@ -184,7 +184,7 @@ const QFont *QIOSTheme::font(Font type) const { const auto *platformIntegration = QGuiApplicationPrivate::platformIntegration(); const auto *coreTextFontDatabase = static_cast(platformIntegration->fontDatabase()); - return coreTextFontDatabase->themeFonts().value(type, nullptr); + return coreTextFontDatabase->themeFont(type); } QT_END_NAMESPACE