1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
20 #ifndef INCLUDED_VCL_INC_FONTMANAGER_HXX
21 #define INCLUDED_VCL_INC_FONTMANAGER_HXX
23 #include <vcl/dllapi.h>
24 #include <unx/helper.hxx>
25 #include <vcl/timer.hxx>
26 #include <vcl/vclenum.hxx>
27 #include <com/sun/star/lang/Locale.hpp>
28 #include "salglyphid.hxx"
29 #include "unx/fc_fontoptions.hxx"
36 #include <unordered_map>
38 #include "config_dbus.h"
41 * some words on metrics: every length returned by PrintFontManager and
42 * friends are PostScript afm style, that is they are 1/1000 font height
46 class FontConfigFontOptions
;
47 class FontSelectPattern
;
55 * the difference between FastPrintFontInfo and PrintFontInfo
56 * is that the information in FastPrintFontInfo can usually
57 * be gathered without opening either the font file, they are
58 * gathered from fonts.dir alone.
59 * if only FastPrintFontInfo is gathered and PrintFontInfo
60 * on demand and for less fonts, then performance in startup
61 * increases considerably
64 struct FastPrintFontInfo
66 fontID m_nID
; // FontID
69 OUString m_aFamilyName
;
70 OUString m_aStyleName
;
71 std::list
< OUString
> m_aAliases
;
72 FontFamily m_eFamilyStyle
;
77 rtl_TextEncoding m_aEncoding
;
82 , m_eFamilyStyle(FAMILY_DONTKNOW
)
83 , m_eItalic(ITALIC_DONTKNOW
)
84 , m_eWidth(WIDTH_DONTKNOW
)
85 , m_eWeight(WEIGHT_DONTKNOW
)
86 , m_ePitch(PITCH_DONTKNOW
)
87 , m_aEncoding(RTL_TEXTENCODING_DONTKNOW
)
88 , m_bSubsettable(false)
92 struct PrintFontInfo
: public FastPrintFontInfo
108 // the values are per thousand of the font size
109 // note: width, height contain advances, not bounding box
110 struct CharacterMetric
112 short int width
, height
;
114 CharacterMetric() : width( 0 ), height( 0 ) {}
115 bool operator!=( const CharacterMetric
& rOther
) const
116 { return rOther
.width
!= width
|| rOther
.height
!= height
; }
119 // a class to manage printable fonts
121 class VCL_PLUGIN_PUBLIC PrintFontManager
124 friend struct PrintFont
;
129 OUString m_aFamilyName
;
130 std::vector
<OUString
> m_aAliases
;
132 OUString m_aStyleName
;
133 FontFamily m_eFamilyStyle
;
134 FontItalic m_eItalic
;
136 FontWeight m_eWeight
;
138 rtl_TextEncoding m_aEncoding
;
139 CharacterMetric m_aGlobalMetricX
;
140 CharacterMetric m_aGlobalMetricY
;
144 int m_nXMin
; // font bounding box
149 int m_nDirectory
; // atom containing system dependent path
150 OString m_aFontFile
; // relative to directory
151 int m_nCollectionEntry
; // 0 for regular fonts, 0 to ... for fonts stemming from collections
152 unsigned int m_nTypeFlags
; // copyright bits and PS-OpenType flag
154 explicit PrintFont();
157 fontID m_nNextFontID
;
158 std::unordered_map
< fontID
, PrintFont
* > m_aFonts
;
159 // for speeding up findFontFileID
160 std::unordered_map
< OString
, std::set
< fontID
>, OStringHash
>
163 std::unordered_map
< OString
, int, OStringHash
>
165 std::unordered_map
< int, OString
> m_aAtomToDir
;
168 OString
getFontFile(const PrintFont
* pFont
) const;
170 bool analyzeFontFile(int nDirID
, const OString
& rFileName
, std::list
<std::unique_ptr
<PrintFont
>>& rNewFonts
, const char *pFormat
=nullptr) const;
171 static OUString
convertSfntName( void* pNameRecord
); // actually a NameRecord* format font subsetting code
172 static void analyzeSfntFamilyName( void* pTTFont
, std::list
< OUString
>& rnames
); // actually a TrueTypeFont* from font subsetting code
173 bool analyzeSfntFile(PrintFont
* pFont
) const;
174 // finds the font id for the nFaceIndex face in this font file
175 // There may be multiple font ids for font collections
176 fontID
findFontFileID( int nDirID
, const OString
& rFile
, int nFaceIndex
) const;
178 // There may be multiple font ids for font collections
179 std::vector
<fontID
> findFontFileIDs( int nDirID
, const OString
& rFile
) const;
181 static FontFamily
matchFamilyName( const OUString
& rFamily
);
183 PrintFont
* getFont( fontID nID
) const
185 std::unordered_map
< fontID
, PrintFont
* >::const_iterator it
;
186 it
= m_aFonts
.find( nID
);
187 return it
== m_aFonts
.end() ? nullptr : it
->second
;
189 static void fillPrintFontInfo(PrintFont
* pFont
, FastPrintFontInfo
& rInfo
);
190 void fillPrintFontInfo( PrintFont
* pFont
, PrintFontInfo
& rInfo
) const;
192 OString
getDirectory( int nAtom
) const;
193 int getDirectoryAtom( const OString
& rDirectory
, bool bCreate
= false );
195 /* try to initialize fonts from libfontconfig
197 called from <code>initialize()</code>
199 static void initFontconfig();
200 void countFontconfigFonts( std::unordered_map
<OString
, int, OStringHash
>& o_rVisitedPaths
);
201 /* deinitialize fontconfig
203 static void deinitFontconfig();
205 /* register an application specific font directory for libfontconfig
207 since fontconfig is asked for font substitutes before OOo will check for font availability
208 and fontconfig will happily substitute fonts it doesn't know (e.g. "Arial Narrow" -> "DejaVu Sans Book"!)
209 it becomes necessary to tell the library about all the hidden font treasures
211 static void addFontconfigDir(const OString
& rDirectory
);
213 std::set
<OString
> m_aPreviousLangSupportRequests
;
215 std::vector
<OString
> m_aCurrentRequests
;
217 Timer m_aFontInstallerTimer
;
220 DECL_LINK( autoInstallFontLangSupport
, Timer
*, void );
225 static PrintFontManager
& get(); // one instance only
227 // There may be multiple font ids for font collections
228 std::vector
<fontID
> addFontFile( const OString
& rFileName
);
232 // returns the ids of all managed fonts.
233 void getFontList( std::list
< fontID
>& rFontIDs
);
235 // get font info for a specific font
236 bool getFontInfo( fontID nFontID
, PrintFontInfo
& rInfo
) const;
237 // get fast font info for a specific font
238 bool getFontFastInfo( fontID nFontID
, FastPrintFontInfo
& rInfo
) const;
240 // routines to get font info in small pieces
242 // get a specific fonts PSName name
243 OUString
getPSName( fontID nFontID
) const;
245 // get a specific fonts italic type
246 FontItalic
getFontItalic( fontID nFontID
) const
248 PrintFont
* pFont
= getFont( nFontID
);
249 return pFont
? pFont
->m_eItalic
: ITALIC_DONTKNOW
;
252 // get a specific fonts weight type
253 FontWeight
getFontWeight( fontID nFontID
) const
255 PrintFont
* pFont
= getFont( nFontID
);
256 return pFont
? pFont
->m_eWeight
: WEIGHT_DONTKNOW
;
259 // get a specific fonts encoding
260 rtl_TextEncoding
getFontEncoding( fontID nFontID
) const
262 PrintFont
* pFont
= getFont( nFontID
);
263 return pFont
? pFont
->m_aEncoding
: RTL_TEXTENCODING_DONTKNOW
;
266 // get a specific fonts system dependent filename
267 OString
getFontFileSysPath( fontID nFontID
) const
269 return getFontFile( getFont( nFontID
) );
272 // get the ttc face number
273 int getFontFaceNumber( fontID nFontID
) const;
275 // get a specific fonts ascend
276 int getFontAscend( fontID nFontID
) const;
278 // get a specific fonts descent
279 int getFontDescend( fontID nFontID
) const;
281 // get a fonts glyph bounding box
282 void getFontBoundingBox( fontID nFont
, int& xMin
, int& yMin
, int& xMax
, int& yMax
);
284 // creates a new font subset of an existing SFNT font
285 // returns true in case of success, else false
286 // nFont: the font to be subsetted
287 // rOutFile: the file to put the new subset into;
288 // must be a valid osl file URL
289 // pGlyphIDs: input array of glyph ids for new font
290 // pNewEncoding: the corresponding encoding in the new font
291 // pWidths: output array of widths of requested glyphs
292 // nGlyphs: number of glyphs in arrays
293 // pCapHeight:: capital height of the produced font
294 // pXMin, pYMin, pXMax, pYMax: outgoing font bounding box
295 // TODO: callers of this method should use its FontSubsetInfo counterpart directly
296 bool createFontSubset( FontSubsetInfo
&,
298 const OUString
& rOutFile
,
299 const sal_GlyphId
* pGlyphIDs
,
300 const sal_uInt8
* pNewEncoding
,
304 void getGlyphWidths( fontID nFont
,
306 std::vector
< sal_Int32
>& rWidths
,
307 std::map
< sal_Unicode
, sal_uInt32
>& rUnicodeEnc
);
309 // font administration functions
311 /* system dependent font matching
314 <code>matchFont</code> matches a pattern of font characteristics
315 and returns the closest match if possibe. If a match was found
316 the <code>FastPrintFontInfo</code> passed in as parameter
317 will be update to the found matching font.
320 implementation note: currently the function is only implemented
325 out of the FastPrintFontInfo structure the following
326 fields will be used for the match:
336 if <code>rLocal</code> contains non empty strings the corresponding
337 locale will be used for font matching also; e.g. "Sans" can result
338 in different fonts in e.g. english and japanese
340 void matchFont( FastPrintFontInfo
& rInfo
, const css::lang::Locale
& rLocale
);
341 static FontConfigFontOptions
* getFontOptions( const FastPrintFontInfo
&, int nSize
);
343 void Substitute( FontSelectPattern
&rPattern
, OUString
& rMissingCodes
);
349 #endif // INCLUDED_VCL_INC_FONTMANAGER_HXX
351 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */