Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*
3 : * This file is part of the LibreOffice project.
4 : *
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/.
8 : *
9 : * This file incorporates work covered by the following license notice:
10 : *
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 .
18 : */
19 :
20 : #ifndef _SV_GLYPHCACHE_HXX
21 : #define _SV_GLYPHCACHE_HXX
22 :
23 : #include <vcl/dllapi.h>
24 :
25 : class GlyphCache;
26 : class GlyphMetric;
27 : class GlyphData;
28 : class ServerFont;
29 : class GlyphCachePeer;
30 : class ServerFontLayoutEngine;
31 : class ServerFontLayout;
32 : class ExtraKernInfo;
33 : struct ImplKernPairData;
34 : class ImplFontOptions;
35 :
36 : #include <tools/gen.hxx>
37 : #include <boost/unordered_map.hpp>
38 : #include <boost/unordered_set.hpp>
39 : #include <boost/shared_ptr.hpp>
40 :
41 : namespace basegfx { class B2DPolyPolygon; }
42 :
43 : class RawBitmap;
44 :
45 : #include <outfont.hxx>
46 : #include <impfont.hxx>
47 :
48 : class ServerFontLayout;
49 : #include <sallayout.hxx>
50 :
51 : #ifdef ENABLE_GRAPHITE
52 : class GraphiteFaceWrapper;
53 : #endif
54 :
55 : #include <ft2build.h>
56 : #include FT_FREETYPE_H
57 : #include FT_GLYPH_H
58 :
59 : namespace vcl
60 : {
61 : struct FontCapabilities;
62 : }
63 :
64 : // =======================================================================
65 :
66 : class VCL_DLLPUBLIC GlyphCache
67 : {
68 : public:
69 : explicit GlyphCache( GlyphCachePeer& );
70 : /*virtual*/ ~GlyphCache();
71 :
72 : static GlyphCache& GetInstance();
73 :
74 : void AddFontFile( const rtl::OString& rNormalizedName,
75 : int nFaceNum, sal_IntPtr nFontId, const ImplDevFontAttributes&,
76 : const ExtraKernInfo* = NULL );
77 : void AnnounceFonts( ImplDevFontList* ) const;
78 :
79 : ServerFont* CacheFont( const FontSelectPattern& );
80 : void UncacheFont( ServerFont& );
81 : void ClearFontCache();
82 : void InvalidateAllGlyphs();
83 :
84 : protected:
85 : GlyphCachePeer& mrPeer;
86 :
87 : private:
88 : friend class ServerFont;
89 : // used by ServerFont class only
90 : void AddedGlyph( ServerFont&, GlyphData& );
91 : void RemovingGlyph( ServerFont&, GlyphData&, int nGlyphIndex );
92 : void UsingGlyph( ServerFont&, GlyphData& );
93 : void GrowNotify();
94 :
95 : private:
96 : void GarbageCollect();
97 :
98 : // the GlyphCache's FontList matches a font request to a serverfont instance
99 : // the FontList key's mpFontData member is reinterpreted as integer font id
100 : struct IFSD_Equal{ bool operator()( const FontSelectPattern&, const FontSelectPattern& ) const; };
101 : struct IFSD_Hash{ size_t operator()( const FontSelectPattern& ) const; };
102 : typedef ::boost::unordered_map<FontSelectPattern,ServerFont*,IFSD_Hash,IFSD_Equal > FontList;
103 : FontList maFontList;
104 : sal_uLong mnMaxSize; // max overall cache size in bytes
105 : mutable sal_uLong mnBytesUsed;
106 : mutable long mnLruIndex;
107 : mutable int mnGlyphCount;
108 : ServerFont* mpCurrentGCFont;
109 :
110 : class FreetypeManager* mpFtManager;
111 : };
112 :
113 : // =======================================================================
114 :
115 18461 : class GlyphMetric
116 : {
117 : public:
118 56548 : Point GetOffset() const { return maOffset; }
119 : Point GetDelta() const { return maDelta; }
120 56548 : Size GetSize() const { return maSize; }
121 1425466 : long GetCharWidth() const { return mnAdvanceWidth; }
122 :
123 : protected:
124 : friend class GlyphData;
125 18461 : void SetOffset( int nX, int nY ) { maOffset = Point( nX, nY); }
126 18461 : void SetDelta( int nX, int nY ) { maDelta = Point( nX, nY); }
127 18461 : void SetSize( const Size& s ) { maSize = s; }
128 18461 : void SetCharWidth( long nW ) { mnAdvanceWidth = nW; }
129 :
130 : private:
131 : long mnAdvanceWidth;
132 : Point maDelta;
133 : Point maOffset;
134 : Size maSize;
135 : };
136 :
137 : // -----------------------------------------------------------------------
138 :
139 : // the glyph specific data needed by a GlyphCachePeer is usually trivial,
140 : // not attaching it to the corresponding GlyphData would be overkill
141 : struct ExtGlyphData
142 : {
143 : int meInfo;
144 : void* mpData;
145 :
146 18461 : ExtGlyphData() : meInfo(0), mpData(NULL) {}
147 : };
148 :
149 : // -----------------------------------------------------------------------
150 :
151 18461 : class GlyphData
152 : {
153 : public:
154 1482014 : const GlyphMetric& GetMetric() const { return maMetric; }
155 : Size GetSize() const { return maMetric.GetSize(); }
156 :
157 18461 : void SetSize( const Size& s) { maMetric.SetSize( s ); }
158 18461 : void SetOffset( int nX, int nY ) { maMetric.SetOffset( nX, nY ); }
159 18461 : void SetDelta( int nX, int nY ) { maMetric.SetDelta( nX, nY ); }
160 18461 : void SetCharWidth( long nW ) { maMetric.SetCharWidth( nW ); }
161 :
162 1525490 : void SetLruValue( int n ) const { mnLruValue = n; }
163 0 : long GetLruValue() const { return mnLruValue;}
164 :
165 132171 : ExtGlyphData& ExtDataRef() { return maExtData; }
166 : const ExtGlyphData& ExtDataRef() const { return maExtData; }
167 :
168 : private:
169 : GlyphMetric maMetric;
170 : ExtGlyphData maExtData;
171 :
172 : // used by GlyphCache for cache LRU algorithm
173 : mutable long mnLruValue;
174 : };
175 :
176 : // =======================================================================
177 :
178 : class FtFontInfo;
179 :
180 : class VCL_DLLPUBLIC ServerFont
181 : {
182 : public:
183 : ServerFont( const FontSelectPattern&, FtFontInfo* );
184 : virtual ~ServerFont();
185 :
186 : const ::rtl::OString* GetFontFileName() const;
187 : bool TestFont() const;
188 : FT_Face GetFtFace() const;
189 0 : int GetLoadFlags() const { return (mnLoadFlags & ~FT_LOAD_IGNORE_TRANSFORM); }
190 : void SetFontOptions( boost::shared_ptr<ImplFontOptions> );
191 : boost::shared_ptr<ImplFontOptions> GetFontOptions() const;
192 0 : bool NeedsArtificialBold() const { return mbArtBold; }
193 0 : bool NeedsArtificialItalic() const { return mbArtItalic; }
194 :
195 2643814 : const FontSelectPattern& GetFontSelData() const { return maFontSelData; }
196 :
197 : void FetchFontMetric( ImplFontMetricData&, long& rFactor ) const;
198 : sal_uLong GetKernPairs( ImplKernPairData** ) const;
199 : const unsigned char* GetTable( const char* pName, sal_uLong* pLength );
200 : int GetEmUnits() const;
201 0 : const FT_Size_Metrics& GetMetricsFT() const { return maSizeFT->metrics; }
202 : const ImplFontCharMap* GetImplFontCharMap() const;
203 : bool GetFontCapabilities(vcl::FontCapabilities &) const;
204 :
205 : GlyphData& GetGlyphData( int nGlyphIndex );
206 1481433 : const GlyphMetric& GetGlyphMetric( int nGlyphIndex )
207 1481433 : { return GetGlyphData( nGlyphIndex ).GetMetric(); }
208 : #ifdef ENABLE_GRAPHITE
209 : virtual GraphiteFaceWrapper* GetGraphiteFace() const;
210 : #endif
211 :
212 : int GetGlyphIndex( sal_UCS4 ) const;
213 : int GetRawGlyphIndex( sal_UCS4 ) const;
214 : int FixupGlyphIndex( int nGlyphIndex, sal_UCS4 ) const;
215 : bool GetGlyphOutline( int nGlyphIndex, ::basegfx::B2DPolyPolygon& ) const;
216 : bool GetAntialiasAdvice( void ) const;
217 : bool GetGlyphBitmap1( int nGlyphIndex, RawBitmap& ) const;
218 : bool GetGlyphBitmap8( int nGlyphIndex, RawBitmap& ) const;
219 :
220 : void SetExtended( int nInfo, void* ppVoid );
221 : int GetExtInfo() { return mnExtInfo; }
222 : void* GetExtPointer() { return mpExtData; }
223 :
224 : private:
225 : friend class GlyphCache;
226 : friend class ServerFontLayout;
227 : friend class X11SalGraphics;
228 :
229 39733 : void AddRef() const { ++mnRefCount; }
230 0 : long GetRefCount() const { return mnRefCount; }
231 : long Release() const;
232 2249 : sal_uLong GetByteCount() const { return mnBytesUsed; }
233 :
234 : void InitGlyphData( int nGlyphIndex, GlyphData& ) const;
235 : void GarbageCollect( long );
236 : void ReleaseFromGarbageCollect();
237 :
238 : int ApplyGlyphTransform( int nGlyphFlags, FT_GlyphRec_*, bool ) const;
239 : bool ApplyGSUB( const FontSelectPattern& );
240 :
241 : ServerFontLayoutEngine* GetLayoutEngine();
242 :
243 : typedef ::boost::unordered_map<int,GlyphData> GlyphList;
244 : mutable GlyphList maGlyphList;
245 :
246 : const FontSelectPattern maFontSelData;
247 :
248 : // info for GlyphcachePeer
249 : int mnExtInfo;
250 : void* mpExtData;
251 :
252 : // used by GlyphCache for cache LRU algorithm
253 : mutable long mnRefCount;
254 : mutable sal_uLong mnBytesUsed;
255 :
256 : ServerFont* mpPrevGCFont;
257 : ServerFont* mpNextGCFont;
258 :
259 : // 16.16 fixed point values used for a rotated font
260 : long mnCos;
261 : long mnSin;
262 :
263 : int mnZWJ;
264 : int mnZWNJ;
265 : bool mbCollectedZW;
266 :
267 : int mnWidth;
268 : int mnPrioEmbedded;
269 : int mnPrioAntiAlias;
270 : int mnPrioAutoHint;
271 : FtFontInfo* mpFontInfo;
272 : FT_Int mnLoadFlags;
273 : double mfStretch;
274 : FT_FaceRec_* maFaceFT;
275 : FT_SizeRec_* maSizeFT;
276 :
277 : boost::shared_ptr<ImplFontOptions> mpFontOptions;
278 :
279 : bool mbFaceOk;
280 : bool mbArtItalic;
281 : bool mbArtBold;
282 : bool mbUseGamma;
283 :
284 : typedef ::boost::unordered_map<int,int> GlyphSubstitution;
285 : GlyphSubstitution maGlyphSubstitution;
286 : rtl_UnicodeToTextConverter maRecodeConverter;
287 :
288 : ServerFontLayoutEngine* mpLayoutEngine;
289 : };
290 :
291 : // =======================================================================
292 :
293 : // a class for cache entries for physical font instances that are based on serverfonts
294 : class VCL_DLLPUBLIC ImplServerFontEntry : public ImplFontEntry
295 : {
296 : private:
297 : ServerFont* mpServerFont;
298 : boost::shared_ptr<ImplFontOptions> mpFontOptions;
299 : bool mbGotFontOptions;
300 :
301 : public:
302 : ImplServerFontEntry( FontSelectPattern& );
303 : virtual ~ImplServerFontEntry();
304 2249 : void SetServerFont( ServerFont* p) { mpServerFont = p; }
305 : void HandleFontOptions();
306 : };
307 :
308 : // =======================================================================
309 :
310 246054 : class VCL_DLLPUBLIC ServerFontLayout : public GenericSalLayout
311 : {
312 : private:
313 : ServerFont& mrServerFont;
314 :
315 : // enforce proper copy semantic
316 : SAL_DLLPRIVATE ServerFontLayout( const ServerFontLayout& );
317 : SAL_DLLPRIVATE ServerFontLayout& operator=( const ServerFontLayout& );
318 :
319 : public:
320 : ServerFontLayout( ServerFont& );
321 : virtual bool LayoutText( ImplLayoutArgs& );
322 : virtual void AdjustLayout( ImplLayoutArgs& );
323 : virtual void DrawText( SalGraphics& ) const;
324 123027 : ServerFont& GetServerFont() const { return mrServerFont; }
325 : };
326 :
327 : // =======================================================================
328 :
329 1866 : class ServerFontLayoutEngine
330 : {
331 : public:
332 1866 : virtual ~ServerFontLayoutEngine() {}
333 : virtual bool layout(ServerFontLayout&, ImplLayoutArgs&) = 0;
334 : };
335 :
336 : // =======================================================================
337 :
338 : class GlyphCachePeer
339 : {
340 : protected:
341 74 : GlyphCachePeer() : mnBytesUsed(0) {}
342 74 : virtual ~GlyphCachePeer() {}
343 :
344 : public:
345 49513 : sal_Int32 GetByteCount() const { return mnBytesUsed; }
346 0 : virtual void RemovingFont( ServerFont& ) {}
347 0 : virtual void RemovingGlyph( ServerFont&, GlyphData&, int ) {}
348 :
349 : protected:
350 : sal_Int32 mnBytesUsed;
351 : };
352 :
353 : // =======================================================================
354 :
355 : class VCL_DLLPUBLIC RawBitmap
356 : {
357 : public:
358 : RawBitmap();
359 : ~RawBitmap();
360 : bool Rotate( int nAngle );
361 :
362 : public:
363 : unsigned char* mpBits;
364 : sal_uLong mnAllocated;
365 :
366 : sal_uLong mnWidth;
367 : sal_uLong mnHeight;
368 :
369 : sal_uLong mnScanlineSize;
370 : sal_uLong mnBitCount;
371 :
372 : int mnXOffset;
373 : int mnYOffset;
374 : };
375 :
376 : // =======================================================================
377 :
378 43359 : inline void ServerFont::SetExtended( int nInfo, void* pVoid )
379 : {
380 43359 : mnExtInfo = nInfo;
381 43359 : mpExtData = pVoid;
382 43359 : }
383 :
384 : // =======================================================================
385 :
386 : // ExtraKernInfo allows an on-demand query of extra kerning info #i29881#
387 : // The kerning values have to be scaled to match the font size before use
388 : class VCL_DLLPUBLIC ExtraKernInfo
389 : {
390 : public:
391 : ExtraKernInfo( sal_IntPtr nFontId );
392 2590 : virtual ~ExtraKernInfo() {}
393 :
394 : int GetUnscaledKernPairs( ImplKernPairData** ) const;
395 :
396 : protected:
397 : mutable bool mbInitialized;
398 : virtual void Initialize() const = 0;
399 :
400 : protected:
401 : sal_IntPtr mnFontId;
402 :
403 : // container to map a unicode pair to an unscaled kerning value
404 0 : struct PairEqual{ int operator()(const ImplKernPairData& rA, const ImplKernPairData& rB) const
405 0 : { return (rA.mnChar1 == rB.mnChar1) && (rA.mnChar2 == rB.mnChar2); } };
406 0 : struct PairHash{ int operator()(const ImplKernPairData& rA) const
407 0 : { return (rA.mnChar1) * 256 ^ rA.mnChar2; } };
408 : typedef boost::unordered_set< ImplKernPairData, PairHash, PairEqual > UnicodeKernPairs;
409 : mutable UnicodeKernPairs maUnicodeKernPairs;
410 : };
411 :
412 : // =======================================================================
413 :
414 : #endif // _SV_GLYPHCACHE_HXX
415 :
416 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|