51bool QFontIconEngine::isNull()
53 const QString text = string();
54 if (!text.isEmpty()) {
55 const QChar c0 = text.at(0);
56 const QFontMetrics fontMetrics(m_iconFont);
57 if (c0.isHighSurrogate() && text.size() > 1)
58 return !fontMetrics.inFontUcs4(QChar::surrogateToUcs4(c0, text.at(1)));
59 return !fontMetrics.inFont(c0);
65QList<QSize> QFontIconEngine::availableSizes(QIcon::Mode, QIcon::State)
67 return {{16, 16}, {24, 24}, {48, 48}, {128, 128}};
70QSize QFontIconEngine::actualSize(
const QSize &size, QIcon::Mode mode, QIcon::State state)
73 return QIconEngine::actualSize(size, mode, state);
75 QFont renderFont(m_iconFont);
76 renderFont.setPixelSize(size.height());
78 if (
const glyph_t glyphIndex = glyph()) {
79 QFontEngine *engine = QFontPrivate::get(renderFont)->engineForScript(QChar::Script_Common);
81 const glyph_metrics_t gm = engine->boundingBox(glyphIndex);
82 const qreal glyph_x = gm.x.toReal();
83 const qreal glyph_y = gm.y.toReal();
84 const qreal glyph_width = (gm.x + gm.width).toReal() - glyph_x;
85 const qreal glyph_height = (gm.y + gm.height).toReal() - glyph_y;
87 if (glyph_width > .0 && glyph_height > .0)
88 result = {glyph_width, glyph_height};
89 }
else if (
const QString text = string(); !text.isEmpty()) {
90 const QFontMetricsF fm(renderFont);
91 result = {fm.horizontalAdvance(text), fm.tightBoundingRect(text).height()};
93 if (!result.isValid())
94 return QIconEngine::actualSize(size, mode, state);
96 return result.scaled(size, Qt::KeepAspectRatio).toSize();
99QPixmap QFontIconEngine::pixmap(
const QSize &size, QIcon::Mode mode, QIcon::State state)
101 return scaledPixmap(size, mode, state, 1.0);
104QPixmap QFontIconEngine::scaledPixmap(
const QSize &size, QIcon::Mode mode, QIcon::State state, qreal scale)
106 const quint64 cacheKey = calculateCacheKey(mode, state);
107 const QSize fittingSize = actualSize(size, mode, state);
108 if (cacheKey != m_pixmapCacheKey || m_pixmap.deviceIndependentSize() != fittingSize
109 || m_pixmap.devicePixelRatio() != scale) {
110 m_pixmap = QPixmap(fittingSize * scale);
111 m_pixmap.fill(Qt::transparent);
112 m_pixmap.setDevicePixelRatio(scale);
114 if (!m_pixmap.isNull()) {
115 QPainter painter(&m_pixmap);
116 paint(&painter, QRect(QPoint(), fittingSize), mode, state);
119 m_pixmapCacheKey = cacheKey;
125void QFontIconEngine::paint(QPainter *painter,
const QRect &rect, QIcon::Mode mode, QIcon::State state)
130 QFont renderFont(m_iconFont);
131 renderFont.setPixelSize(rect.height());
133 QColor color = Qt::black;
137 color = palette.color(QPalette::Active, QPalette::Text);
140 color = palette.color(QPalette::Active, QPalette::Text);
142 case QIcon::Disabled:
143 color = palette.color(QPalette::Disabled, QPalette::Text);
145 case QIcon::Selected:
146 color = palette.color(QPalette::Active, QPalette::HighlightedText);
150 if (glyph_t glyphIndex = glyph()) {
151 QFontEngine *engine = QFontPrivate::get(renderFont)->engineForScript(QChar::Script_Common);
153 const glyph_metrics_t gm = engine->boundingBox(glyphIndex);
154 const int glyph_x = qFloor(gm.x.toReal());
155 const int glyph_y = qFloor(gm.y.toReal());
156 const int glyph_width = qCeil((gm.x + gm.width).toReal()) - glyph_x;
157 const int glyph_height = qCeil((gm.y + gm.height).toReal()) - glyph_y;
159 if (glyph_width > 0 && glyph_height > 0) {
160 QFixedPoint pt(QFixed(-glyph_x), QFixed(-glyph_y));
162 path.setFillRule(Qt::WindingFill);
163 engine->addGlyphsToPath(&glyphIndex, &pt, 1, &path, {});
165 const QRectF pathBoundingRect = path.boundingRect();
167 const QPointF topLeft = rect.topLeft() - pathBoundingRect.topLeft()
168 + (QPointF(rect.width(), rect.height())
169 - QPointF(pathBoundingRect.width(), pathBoundingRect.height())) / 2;
170 painter->translate(topLeft);
172 painter->setRenderHint(QPainter::Antialiasing);
173 painter->setPen(Qt::NoPen);
174 painter->setBrush(color);
175 painter->drawPath(path);
177 }
else if (
const QString text = string(); !text.isEmpty()) {
178 painter->setFont(renderFont);
179 painter->setPen(color);
180 painter->drawText(rect, Qt::AlignCenter, text);
190glyph_t QFontIconEngine::glyph()
const
192 if (m_glyph == uninitializedGlyph) {
193 QFontEngine *engine = QFontPrivate::get(m_iconFont)->engineForScript(QChar::Script_Common);
195 m_glyph = engine->findGlyph(QLatin1StringView(m_iconName.toLatin1()));
199 QTextLayout layout(m_iconName, m_iconFont);
200 layout.beginLayout();
203 const auto glyphRuns = layout.glyphRuns();
204 if (glyphRuns.size() == 1) {
205 const auto glyphIndexes = glyphRuns.first().glyphIndexes();
206 if (glyphIndexes.size() == 1)
207 m_glyph = glyphIndexes.first();