with wayland scaling cairo is meddling with our font
so I see mixed large scaled and small unscaled letters in the writer header/footer
widget among other places
so don't give it our FreeType font face (FC_FT_FACE), keep that for ourselves,
but instead set the filename and face index and let it make a new one itself.
Change-Id: I2e5eceb7bf590ccfeb06123d0404120feacfff97
Reviewed-on: https://gerrit.libreoffice.org/31127
Tested-by: Jenkins <ci@libreoffice.org>
Reviewed-by: Caolán McNamara <caolanm@redhat.com>
Tested-by: Caolán McNamara <caolanm@redhat.com>
(cherry picked from commit 8c3e1465223bd8c824c4cecfd0e6fc387583e592)
Reviewed-on: https://gerrit.libreoffice.org/31153
diff --git a/vcl/inc/unx/fc_fontoptions.hxx b/vcl/inc/unx/fc_fontoptions.hxx
index e5dc491..3c34610 100644
--- a/vcl/inc/unx/fc_fontoptions.hxx
+++ b/vcl/inc/unx/fc_fontoptions.hxx
@@ -51,7 +51,9 @@ public:
bool DontUseEmbeddedBitmaps() const { return meEmbeddedBitmap == EMBEDDEDBITMAP_FALSE; }
bool DontUseAntiAlias() const { return meAntiAlias == ANTIALIAS_FALSE; }
bool DontUseHinting() const { return (meHinting == FontHinting::No) || (GetHintStyle() == FontHintStyle::NONE); }
void* GetPattern(void * /*pFace*/, bool /*bEmbolden*/) const;
void SyncPattern(const OString& rFileName, int nFontFace, bool bEmbolden);
FcPattern* GetPattern() const;
static void cairo_font_options_substitute(FcPattern* pPattern);
private:
FcPattern* mpPattern;
};
diff --git a/vcl/inc/unx/fontmanager.hxx b/vcl/inc/unx/fontmanager.hxx
index 057436a..7f0e057 100644
--- a/vcl/inc/unx/fontmanager.hxx
+++ b/vcl/inc/unx/fontmanager.hxx
@@ -492,7 +492,7 @@ public:
in different fonts in e.g. english and japanese
*/
void matchFont( FastPrintFontInfo& rInfo, const css::lang::Locale& rLocale );
static FontConfigFontOptions* getFontOptions( const FastPrintFontInfo&, int nSize, void (*subcallback)(void*));
static FontConfigFontOptions* getFontOptions( const FastPrintFontInfo&, int nSize);
void Substitute( FontSelectPattern &rPattern, OUString& rMissingCodes );
diff --git a/vcl/inc/unx/freetype_glyphcache.hxx b/vcl/inc/unx/freetype_glyphcache.hxx
index 304a090..119dcda 100644
--- a/vcl/inc/unx/freetype_glyphcache.hxx
+++ b/vcl/inc/unx/freetype_glyphcache.hxx
@@ -72,6 +72,7 @@ public:
void ReleaseFaceFT();
const OString& GetFontFileName() const { return mpFontFile->GetFileName(); }
int GetFontFaceIndex() const { return mnFaceNum; }
sal_IntPtr GetFontId() const { return mnFontId; }
bool IsSymbolFont() const { return maDevFontAttributes.IsSymbolFont(); }
const FontAttributes& GetFontAttributes() const { return maDevFontAttributes; }
diff --git a/vcl/inc/unx/glyphcache.hxx b/vcl/inc/unx/glyphcache.hxx
index e5852a0..8de5595 100644
--- a/vcl/inc/unx/glyphcache.hxx
+++ b/vcl/inc/unx/glyphcache.hxx
@@ -151,6 +151,7 @@ public:
~FreetypeFont();
const OString& GetFontFileName() const;
int GetFontFaceIndex() const;
bool TestFont() const { return mbFaceOk;}
FT_Face GetFtFace() const;
int GetLoadFlags() const { return (mnLoadFlags & ~FT_LOAD_IGNORE_TRANSFORM); }
@@ -231,7 +232,7 @@ private:
FT_FaceRec_* maFaceFT;
FT_SizeRec_* maSizeFT;
std::shared_ptr<FontConfigFontOptions> mxFontOptions;
mutable std::shared_ptr<FontConfigFontOptions> mxFontOptions;
bool mbFaceOk;
bool mbArtItalic;
@@ -253,13 +254,9 @@ public:
virtual ~FreetypeFontInstance() override;
void SetFreetypeFont(FreetypeFont* p);
void HandleFontOptions();
private:
FreetypeFont* mpFreetypeFont;
std::shared_ptr<FontConfigFontOptions> mxFontOptions;
bool mbGotFontOptions;
};
class VCL_DLLPUBLIC ServerFontLayout : public GenericSalLayout
diff --git a/vcl/unx/generic/fontmanager/fontconfig.cxx b/vcl/unx/generic/fontmanager/fontconfig.cxx
index a8731401..dd9d17b 100644
--- a/vcl/unx/generic/fontmanager/fontconfig.cxx
+++ b/vcl/unx/generic/fontmanager/fontconfig.cxx
@@ -1154,24 +1154,22 @@ FontConfigFontOptions::~FontConfigFontOptions()
FcPatternDestroy(mpPattern);
}
void *FontConfigFontOptions::GetPattern(void * face, bool bEmbolden) const
{
FcValue value;
value.type = FcTypeFTFace;
value.u.f = face;
FcPatternDel(mpPattern, FC_FT_FACE);
FcPatternAdd (mpPattern, FC_FT_FACE, value, FcTrue);
FcPatternDel(mpPattern, FC_EMBOLDEN);
FcPatternAddBool(mpPattern, FC_EMBOLDEN, bEmbolden ? FcTrue : FcFalse);
#if 0
FcPatternDel(mpPattern, FC_VERTICAL_LAYOUT);
FcPatternAddBool(mpPattern, FC_VERTICAL_LAYOUT, bVerticalLayout ? FcTrue : FcFalse);
#endif
return mpPattern;
}
FcPattern *FontConfigFontOptions::GetPattern() const
{
return mpPattern;
}
FontConfigFontOptions* PrintFontManager::getFontOptions(
const FastPrintFontInfo& rInfo, int nSize, void (*subcallback)(void*))
void FontConfigFontOptions::SyncPattern(const OString& rFileName, int nIndex, bool bEmbolden)
{
FcPatternDel(mpPattern, FC_FILE);
FcPatternAddString(mpPattern, FC_FILE, reinterpret_cast<FcChar8 const *>(rFileName.getStr()));
FcPatternDel(mpPattern, FC_INDEX);
FcPatternAddInteger(mpPattern, FC_INDEX, nIndex);
FcPatternDel(mpPattern, FC_EMBOLDEN);
FcPatternAddBool(mpPattern, FC_EMBOLDEN, bEmbolden ? FcTrue : FcFalse);
}
FontConfigFontOptions* PrintFontManager::getFontOptions(const FastPrintFontInfo& rInfo, int nSize)
{
FontCfgWrapper& rWrapper = FontCfgWrapper::get();
@@ -1194,8 +1192,7 @@ FontConfigFontOptions* PrintFontManager::getFontOptions(
int hintstyle = FC_HINT_FULL;
FcConfigSubstitute(pConfig, pPattern, FcMatchPattern);
if (subcallback)
subcallback(pPattern);
FontConfigFontOptions::cairo_font_options_substitute(pPattern);
FcDefaultSubstitute(pPattern);
FcResult eResult = FcResultNoMatch;
diff --git a/vcl/unx/generic/gdi/cairotextrender.cxx b/vcl/unx/generic/gdi/cairotextrender.cxx
index 3c571f7..eb941e2 100644
--- a/vcl/unx/generic/gdi/cairotextrender.cxx
+++ b/vcl/unx/generic/gdi/cairotextrender.cxx
@@ -64,7 +64,7 @@ public:
struct CacheId
{
FT_Face maFace;
const void *mpOptions;
const FontConfigFontOptions *mpOptions;
bool mbEmbolden;
bool mbVerticalMetrics;
bool operator ==(const CacheId& rOther) const
@@ -138,33 +138,12 @@ bool CairoTextRender::setFont( const FontSelectPattern *pEntry, int nFallbackLev
// register to use the font
mpFreetypeFont[ nFallbackLevel ] = pFreetypeFont;
// apply font specific-hint settings
FreetypeFontInstance* pSFE = static_cast<FreetypeFontInstance*>( pEntry->mpFontInstance );
pSFE->HandleFontOptions();
return true;
}
return false;
}
FontConfigFontOptions* GetFCFontOptions( const FontAttributes& rFontAttributes, int nSize);
void FreetypeFontInstance::HandleFontOptions()
{
if( !mpFreetypeFont )
return;
if( !mbGotFontOptions )
{
// get and cache the font options
mbGotFontOptions = true;
mxFontOptions.reset(GetFCFontOptions( *maFontSelData.mpFontData,
maFontSelData.mnHeight ));
}
// apply the font options
mpFreetypeFont->SetFontOptions(mxFontOptions);
}
void CairoFontsCache::CacheFont(void *pFont, const CairoFontsCache::CacheId &rId)
{
maLRUFonts.push_front( std::pair<void*, CairoFontsCache::CacheId>(pFont, rId) );
@@ -288,12 +267,9 @@ void CairoTextRender::DrawServerFontLayout( const GenericSalLayout& rLayout, con
cairo_font_face_t* font_face = static_cast<cairo_font_face_t*>(CairoFontsCache::FindCachedFont(aId));
if (!font_face)
{
const FontConfigFontOptions *pOptions = rFont.GetFontOptions().get();
void *pPattern = pOptions ? pOptions->GetPattern(aFace, aId.mbEmbolden) : nullptr;
if (pPattern)
font_face = cairo_ft_font_face_create_for_pattern(static_cast<FcPattern*>(pPattern));
if (!font_face)
font_face = cairo_ft_font_face_create_for_ft_face(reinterpret_cast<FT_Face>(aFace), rFont.GetLoadFlags());
const FontConfigFontOptions *pOptions = aId.mpOptions;
FcPattern *pPattern = pOptions->GetPattern();
font_face = cairo_ft_font_face_create_for_pattern(pPattern);
CairoFontsCache::CacheFont(font_face, aId);
}
cairo_set_font_face(cr, font_face);
@@ -466,29 +442,16 @@ void CairoTextRender::GetDevFontList( PhysicalFontCollection* pFontCollection )
ImplGetSVData()->maGDIData.mbNativeFontConfig = true;
}
void cairosubcallback(void* pPattern)
void FontConfigFontOptions::cairo_font_options_substitute(FcPattern* pPattern)
{
ImplSVData* pSVData = ImplGetSVData();
const cairo_font_options_t* pFontOptions = pSVData->mpDefInst->GetCairoFontOptions();
if( !pFontOptions )
return;
cairo_ft_font_options_substitute(pFontOptions, static_cast<FcPattern*>(pPattern));
cairo_ft_font_options_substitute(pFontOptions, pPattern);
}
FontConfigFontOptions* GetFCFontOptions( const FontAttributes& rFontAttributes, int nSize)
{
psp::FastPrintFontInfo aInfo;
aInfo.m_aFamilyName = rFontAttributes.GetFamilyName();
aInfo.m_eItalic = rFontAttributes.GetItalic();
aInfo.m_eWeight = rFontAttributes.GetWeight();
aInfo.m_eWidth = rFontAttributes.GetWidthType();
return psp::PrintFontManager::getFontOptions(aInfo, nSize, cairosubcallback);
}
void
CairoTextRender::GetFontMetric( ImplFontMetricDataRef& rxFontMetric, int nFallbackLevel )
void CairoTextRender::GetFontMetric( ImplFontMetricDataRef& rxFontMetric, int nFallbackLevel )
{
if( nFallbackLevel >= MAX_FALLBACK )
return;
diff --git a/vcl/unx/generic/glyphs/freetype_glyphcache.cxx b/vcl/unx/generic/glyphs/freetype_glyphcache.cxx
index 2102e4a..6df2bba 100644
--- a/vcl/unx/generic/glyphs/freetype_glyphcache.cxx
+++ b/vcl/unx/generic/glyphs/freetype_glyphcache.cxx
@@ -512,11 +512,7 @@ FreetypeFont::FreetypeFont( const FontSelectPattern& rFSD, FreetypeFontInfo* pFI
ApplyGSUB( rFSD );
// TODO: query GASP table for load flags
mnLoadFlags = FT_LOAD_DEFAULT;
#if 1 // #i97326# cairo sometimes uses FT_Set_Transform() on our FT_FACE
// we are not using FT_Set_Transform() yet, so just ignore it for now
mnLoadFlags |= FT_LOAD_IGNORE_TRANSFORM;
#endif
mnLoadFlags = FT_LOAD_DEFAULT | FT_LOAD_IGNORE_TRANSFORM;
mbArtItalic = (rFSD.GetItalic() != ITALIC_NONE && pFI->GetFontAttributes().GetItalic() == ITALIC_NONE);
mbArtBold = (rFSD.GetWeight() > WEIGHT_MEDIUM && pFI->GetFontAttributes().GetWeight() <= WEIGHT_MEDIUM);
@@ -592,8 +588,28 @@ void FreetypeFont::SetFontOptions(const std::shared_ptr<FontConfigFontOptions>&
mnLoadFlags |= FT_LOAD_NO_BITMAP;
}
namespace
{
FontConfigFontOptions* GetFCFontOptions( const FontAttributes& rFontAttributes, int nSize)
{
psp::FastPrintFontInfo aInfo;
aInfo.m_aFamilyName = rFontAttributes.GetFamilyName();
aInfo.m_eItalic = rFontAttributes.GetItalic();
aInfo.m_eWeight = rFontAttributes.GetWeight();
aInfo.m_eWidth = rFontAttributes.GetWidthType();
return psp::PrintFontManager::getFontOptions(aInfo, nSize);
}
}
const std::shared_ptr<FontConfigFontOptions>& FreetypeFont::GetFontOptions() const
{
if (!mxFontOptions)
{
mxFontOptions.reset(GetFCFontOptions(mpFontInfo->GetFontAttributes(), maFontSelData.mnHeight));
mxFontOptions->SyncPattern(GetFontFileName(), GetFontFaceIndex(), NeedsArtificialBold());
}
return mxFontOptions;
}
@@ -602,6 +618,10 @@ const OString& FreetypeFont::GetFontFileName() const
return mpFontInfo->GetFontFileName();
}
int FreetypeFont::GetFontFaceIndex() const
{
return mpFontInfo->GetFontFaceIndex();
}
FreetypeFont::~FreetypeFont()
{
diff --git a/vcl/unx/generic/glyphs/glyphcache.cxx b/vcl/unx/generic/glyphs/glyphcache.cxx
index c1b4a4e..a4ba09a 100644
--- a/vcl/unx/generic/glyphs/glyphcache.cxx
+++ b/vcl/unx/generic/glyphs/glyphcache.cxx
@@ -343,7 +343,6 @@ void FreetypeFont::GarbageCollect( long nMinLruIndex )
FreetypeFontInstance::FreetypeFontInstance( FontSelectPattern& rFSD )
: LogicalFontInstance( rFSD )
, mpFreetypeFont( nullptr )
, mbGotFontOptions( false )
{}
void FreetypeFontInstance::SetFreetypeFont(FreetypeFont* p)