QFontEngine *QBasicFontDatabase::fontEngine(const QFontDef &fontDef, QChar::Script script, void *usrPtr) { QFontEngineFT *engine; FontFile *fontfile = static_cast<FontFile *> (usrPtr); QFontEngine::FaceId fid; fid.filename = QFile::encodeName(fontfile->fileName); fid.index = fontfile->indexValue; engine = new QFontEngineFT(fontDef); bool antialias = !(fontDef.styleStrategy & QFont::NoAntialias); QFontEngineFT::GlyphFormat format = antialias? QFontEngineFT::Format_A8 : QFontEngineFT::Format_Mono; if (!engine->init(fid,antialias,format)) { delete engine; engine = 0; return engine; } if (engine->invalid()) { delete engine; engine = 0; } else if (scriptRequiresOpenType(script)) { if (!engine->supportsScript(script)) { delete engine; engine = 0; } } return engine; }
QFontEngine *QFontconfigDatabase::fontEngine(const QFontDef &f, QChar::Script script, void *usrPtr) { if (!usrPtr) return 0; QFontDef fontDef = f; QFontEngineFT *engine; FontFile *fontfile = static_cast<FontFile *> (usrPtr); QFontEngine::FaceId fid; fid.filename = QFile::encodeName(fontfile->fileName); fid.index = fontfile->indexValue; bool antialias = !(fontDef.styleStrategy & QFont::NoAntialias); engine = new QFontEngineFT(fontDef); QFontEngineFT::GlyphFormat format; // try and get the pattern FcPattern *pattern = FcPatternCreate(); FcValue value; value.type = FcTypeString; QByteArray cs = fontDef.family.toUtf8(); value.u.s = (const FcChar8 *)cs.data(); FcPatternAdd(pattern,FC_FAMILY,value,true); value.u.s = (const FcChar8 *)fid.filename.data(); FcPatternAdd(pattern,FC_FILE,value,true); value.type = FcTypeInteger; value.u.i = fid.index; FcPatternAdd(pattern,FC_INDEX,value,true); FcResult result; FcPattern *match = FcFontMatch(0, pattern, &result); if (match) { QFontEngineFT::HintStyle default_hint_style; if (f.hintingPreference != QFont::PreferDefaultHinting) { switch (f.hintingPreference) { case QFont::PreferNoHinting: default_hint_style = QFontEngineFT::HintNone; break; case QFont::PreferVerticalHinting: default_hint_style = QFontEngineFT::HintLight; break; case QFont::PreferFullHinting: default: default_hint_style = QFontEngineFT::HintFull; break; } } else { int hint_style = 0; if (FcPatternGetInteger (match, FC_HINT_STYLE, 0, &hint_style) == FcResultNoMatch) hint_style = QFontEngineFT::HintFull; switch (hint_style) { case FC_HINT_NONE: default_hint_style = QFontEngineFT::HintNone; break; case FC_HINT_SLIGHT: default_hint_style = QFontEngineFT::HintLight; break; case FC_HINT_MEDIUM: default_hint_style = QFontEngineFT::HintMedium; break; default: default_hint_style = QFontEngineFT::HintFull; break; } } if (antialias) { // If antialiasing is not fully disabled, fontconfig may still disable it on a font match basis. FcBool fc_antialias; if (FcPatternGetBool(match, FC_ANTIALIAS,0, &fc_antialias) != FcResultMatch) fc_antialias = true; antialias = fc_antialias; } if (f.hintingPreference == QFont::PreferDefaultHinting) { const QPlatformServices *services = QGuiApplicationPrivate::platformIntegration()->services(); if (services && (services->desktopEnvironment() == "GNOME" || services->desktopEnvironment() == "UNITY")) { void *hintStyleResource = QGuiApplication::platformNativeInterface()->nativeResourceForScreen("hintstyle", QGuiApplication::primaryScreen()); int hintStyle = int(reinterpret_cast<qintptr>(hintStyleResource)); if (hintStyle > 0) default_hint_style = QFontEngine::HintStyle(hintStyle - 1); } } engine->setDefaultHintStyle(default_hint_style); if (antialias) { QFontEngineFT::SubpixelAntialiasingType subpixelType = QFontEngineFT::Subpixel_None; int subpixel = FC_RGBA_NONE; FcPatternGetInteger(match, FC_RGBA, 0, &subpixel); if (subpixel == FC_RGBA_UNKNOWN) subpixel = FC_RGBA_NONE; switch (subpixel) { case FC_RGBA_NONE: subpixelType = QFontEngineFT::Subpixel_None; break; case FC_RGBA_RGB: subpixelType = QFontEngineFT::Subpixel_RGB; break; case FC_RGBA_BGR: subpixelType = QFontEngineFT::Subpixel_BGR; break; case FC_RGBA_VRGB: subpixelType = QFontEngineFT::Subpixel_VRGB; break; case FC_RGBA_VBGR: subpixelType = QFontEngineFT::Subpixel_VBGR; break; default: break; } format = subpixelType == QFontEngineFT::Subpixel_None ? QFontEngineFT::Format_A8 : QFontEngineFT::Format_A32; engine->subpixelType = subpixelType; } else format = QFontEngineFT::Format_Mono; FcPatternDestroy(match); } else format = antialias ? QFontEngineFT::Format_A8 : QFontEngineFT::Format_Mono; FcPatternDestroy(pattern); if (!engine->init(fid,antialias,format)) { delete engine; engine = 0; return engine; } if (engine->invalid()) { delete engine; engine = 0; } else if (!engine->supportsScript(script)) { qWarning(" OpenType support missing for script %d", int(script)); delete engine; engine = 0; } return engine; }