1/****************************************************************************
2**
3** Copyright (C) 2020 The Qt Company Ltd.
4** Contact: https://www.qt.io/licensing/
5**
6** This file is part of the QtGui module of the Qt Toolkit.
7**
8** $QT_BEGIN_LICENSE:LGPL$
9** Commercial License Usage
10** Licensees holding valid commercial Qt licenses may use this file in
11** accordance with the commercial license agreement provided with the
12** Software or, alternatively, in accordance with the terms contained in
13** a written agreement between you and The Qt Company. For licensing terms
14** and conditions see https://www.qt.io/terms-conditions. For further
15** information use the contact form at https://www.qt.io/contact-us.
16**
17** GNU Lesser General Public License Usage
18** Alternatively, this file may be used under the terms of the GNU Lesser
19** General Public License version 3 as published by the Free Software
20** Foundation and appearing in the file LICENSE.LGPL3 included in the
21** packaging of this file. Please review the following information to
22** ensure the GNU Lesser General Public License version 3 requirements
23** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
24**
25** GNU General Public License Usage
26** Alternatively, this file may be used under the terms of the GNU
27** General Public License version 2.0 or (at your option) the GNU General
28** Public license version 3 or any later version approved by the KDE Free
29** Qt Foundation. The licenses are as published by the Free Software
30** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
31** included in the packaging of this file. Please review the following
32** information to ensure the GNU General Public License requirements will
33** be met: https://www.gnu.org/licenses/gpl-2.0.html and
34** https://www.gnu.org/licenses/gpl-3.0.html.
35**
36** $QT_END_LICENSE$
37**
38****************************************************************************/
39
40#ifndef QFONTDATABASE_P_H
41#define QFONTDATABASE_P_H
42
43//
44// W A R N I N G
45// -------------
46//
47// This file is not part of the Qt API. It exists for the convenience
48// of internal files. This header file may change from version to version
49// without notice, or even be removed.
50//
51// We mean it.
52//
53
54#include <QtCore/qcache.h>
55
56#include <QtGui/qfontdatabase.h>
57
58QT_BEGIN_NAMESPACE
59
60struct QtFontFallbacksCacheKey
61{
62 QString family;
63 QFont::Style style;
64 QFont::StyleHint styleHint;
65 QChar::Script script;
66};
67
68inline bool operator==(const QtFontFallbacksCacheKey &lhs, const QtFontFallbacksCacheKey &rhs) noexcept
69{
70 return lhs.script == rhs.script &&
71 lhs.styleHint == rhs.styleHint &&
72 lhs.style == rhs.style &&
73 lhs.family == rhs.family;
74}
75
76inline bool operator!=(const QtFontFallbacksCacheKey &lhs, const QtFontFallbacksCacheKey &rhs) noexcept
77{
78 return !operator==(lhs, rhs);
79}
80
81inline size_t qHash(const QtFontFallbacksCacheKey &key, size_t seed = 0) noexcept
82{
83 QtPrivate::QHashCombine hash;
84 seed = hash(seed, key.family);
85 seed = hash(seed, int(key.style));
86 seed = hash(seed, int(key.styleHint));
87 seed = hash(seed, int(key.script));
88 return seed;
89}
90
91struct Q_GUI_EXPORT QtFontSize
92{
93 void *handle;
94 unsigned short pixelSize : 16;
95};
96
97struct Q_GUI_EXPORT QtFontStyle
98{
99 struct Key
100 {
101 Key(const QString &styleString);
102
103 Key()
104 : style(QFont::StyleNormal)
105 , weight(QFont::Normal)
106 , stretch(0)
107 {}
108
109 Key(const Key &o)
110 : style(o.style)
111 , weight(o.weight)
112 , stretch(o.stretch)
113 {}
114
115 uint style : 2;
116 uint weight : 10;
117 signed int stretch : 12;
118
119 bool operator==(const Key &other) const noexcept
120 {
121 return (style == other.style && weight == other.weight &&
122 (stretch == 0 || other.stretch == 0 || stretch == other.stretch));
123 }
124
125 bool operator!=(const Key &other) const noexcept
126 {
127 return !operator==(other);
128 }
129 };
130
131 QtFontStyle(const Key &k)
132 : key(k)
133 , bitmapScalable(false)
134 , smoothScalable(false)
135 , count(0)
136 , pixelSizes(nullptr)
137 {
138 }
139
140 ~QtFontStyle();
141
142 QtFontSize *pixelSize(unsigned short size, bool = false);
143
144 Key key;
145 bool bitmapScalable : 1;
146 bool smoothScalable : 1;
147 signed int count : 30;
148 QtFontSize *pixelSizes;
149 QString styleName;
150 bool antialiased;
151};
152
153struct Q_GUI_EXPORT QtFontFoundry
154{
155 QtFontFoundry(const QString &n)
156 : name(n)
157 , count(0)
158 , styles(nullptr)
159 {}
160
161 ~QtFontFoundry()
162 {
163 while (count--)
164 delete styles[count];
165 free(styles);
166 }
167
168 QString name;
169 int count;
170 QtFontStyle **styles;
171 QtFontStyle *style(const QtFontStyle::Key &, const QString & = QString(), bool = false);
172};
173
174struct Q_GUI_EXPORT QtFontFamily
175{
176 enum WritingSystemStatus {
177 Unknown = 0,
178 Supported = 1,
179 UnsupportedFT = 2,
180 Unsupported = UnsupportedFT
181 };
182
183 QtFontFamily(const QString &n)
184 :
185 populated(false),
186 fixedPitch(false),
187 name(n), count(0), foundries(nullptr)
188 {
189 memset(writingSystems, 0, sizeof(writingSystems));
190 }
191 ~QtFontFamily() {
192 while (count--)
193 delete foundries[count];
194 free(foundries);
195 }
196
197 bool populated : 1;
198 bool fixedPitch : 1;
199
200 QString name;
201 QStringList aliases;
202 int count;
203 QtFontFoundry **foundries;
204
205 unsigned char writingSystems[QFontDatabase::WritingSystemsCount];
206
207 bool matchesFamilyName(const QString &familyName) const;
208 QtFontFoundry *foundry(const QString &f, bool = false);
209
210 void ensurePopulated();
211};
212
213class Q_GUI_EXPORT QFontDatabasePrivate
214{
215public:
216 QFontDatabasePrivate()
217 : count(0)
218 , families(nullptr)
219 , fallbacksCache(64)
220 { }
221
222 ~QFontDatabasePrivate() {
223 free();
224 }
225
226 enum FamilyRequestFlags {
227 RequestFamily = 0,
228 EnsureCreated,
229 EnsurePopulated
230 };
231
232 QtFontFamily *family(const QString &f, FamilyRequestFlags flags = EnsurePopulated);
233 void free() {
234 while (count--)
235 delete families[count];
236 ::free(families);
237 families = nullptr;
238 count = 0;
239 // don't clear the memory fonts!
240 }
241
242 int count;
243 QtFontFamily **families;
244
245 QCache<QtFontFallbacksCacheKey, QStringList> fallbacksCache;
246 struct ApplicationFont {
247 QString fileName;
248 QByteArray data;
249
250 struct Properties {
251 QString familyName;
252 QString styleName;
253 int weight = 0;
254 QFont::Style style = QFont::StyleNormal;
255 int stretch = QFont::Unstretched;
256 };
257
258 QList<Properties> properties;
259 };
260 QList<ApplicationFont> applicationFonts;
261 int addAppFont(const QByteArray &fontData, const QString &fileName);
262 bool isApplicationFont(const QString &fileName);
263
264 static QFontDatabasePrivate *instance();
265
266 void invalidate();
267};
268Q_DECLARE_TYPEINFO(QFontDatabasePrivate::ApplicationFont, Q_MOVABLE_TYPE);
269
270QT_END_NAMESPACE
271
272#endif // QFONTDATABASE_P_H
273