Kirigami2

platformtheme.h
1/*
2 * SPDX-FileCopyrightText: 2017 Marco Martin <mart@kde.org>
3 *
4 * SPDX-License-Identifier: LGPL-2.0-or-later
5 */
6
7#ifndef KIRIGAMI_PLATFORMTHEME_H
8#define KIRIGAMI_PLATFORMTHEME_H
9
10#include <QColor>
11#include <QIcon>
12#include <QObject>
13#include <QPalette>
14#include <QQuickItem>
15#include <qqmlregistration.h>
16
17#include "kirigamiplatform_export.h"
18
19namespace Kirigami
20{
21namespace Platform
22{
23class PlatformThemeData;
24class PlatformThemePrivate;
25
26/**
27 * @class PlatformTheme platformtheme.h <Kirigami/PlatformTheme>
28 *
29 * This class is the base for color management in Kirigami,
30 * different platforms can reimplement this class to integrate with
31 * system platform colors of a given platform
32 */
33class KIRIGAMIPLATFORM_EXPORT PlatformTheme : public QObject
34{
35 Q_OBJECT
36 QML_NAMED_ELEMENT(Theme)
38 QML_UNCREATABLE("Attached Property")
39
40 /**
41 * This enumeration describes the color set for which a color is being selected.
42 *
43 * Color sets define a color "environment", suitable for drawing all parts of a
44 * given region. Colors from different sets should not be combined.
45 */
46 Q_PROPERTY(ColorSet colorSet READ colorSet WRITE setColorSet NOTIFY colorSetChanged FINAL)
47
48 /**
49 * This enumeration describes the color group used to generate the colors.
50 * The enum value is based upon QPalette::ColorGroup and has the same values.
51 * It's redefined here in order to make it work with QML.
52 * @since 4.43
53 */
54 Q_PROPERTY(ColorGroup colorGroup READ colorGroup WRITE setColorGroup NOTIFY colorGroupChanged FINAL)
55
56 /**
57 * If true, the colorSet will be inherited from the colorset of a theme of one
58 * of the ancestor items
59 * default: true
60 */
61 Q_PROPERTY(bool inherit READ inherit WRITE setInherit NOTIFY inheritChanged FINAL)
62
63 // foreground colors
64 /**
65 * Color for normal foregrounds, usually text, but not limited to it,
66 * anything that should be painted with a clear contrast should use this color
67 */
68 Q_PROPERTY(QColor textColor READ textColor WRITE setCustomTextColor RESET setCustomTextColor NOTIFY colorsChanged FINAL)
69
70 /**
71 * Foreground color for disabled areas, usually a mid-gray
72 * @note Depending on the implementation, the color used for this property may not be
73 * based on the disabled palette. For example, for the Plasma implementation,
74 * "Inactive Text Color" of the active palette is used.
75 */
76 Q_PROPERTY(QColor disabledTextColor READ disabledTextColor WRITE setCustomDisabledTextColor RESET setCustomDisabledTextColor NOTIFY colorsChanged FINAL)
77
78 /**
79 * Color for text that has been highlighted, often is a light color while normal text is dark
80 */
81 Q_PROPERTY(
82 QColor highlightedTextColor READ highlightedTextColor WRITE setCustomHighlightedTextColor RESET setCustomHighlightedTextColor NOTIFY colorsChanged)
83
84 /**
85 * Foreground for areas that are active or requesting attention
86 */
87 Q_PROPERTY(QColor activeTextColor READ activeTextColor WRITE setCustomActiveTextColor RESET setCustomActiveTextColor NOTIFY colorsChanged FINAL)
88
89 /**
90 * Color for links
91 */
92 Q_PROPERTY(QColor linkColor READ linkColor WRITE setCustomLinkColor RESET setCustomLinkColor NOTIFY colorsChanged FINAL)
93
94 /**
95 * Color for visited links, usually a bit darker than linkColor
96 */
97 Q_PROPERTY(QColor visitedLinkColor READ visitedLinkColor WRITE setCustomVisitedLinkColor RESET setCustomVisitedLinkColor NOTIFY colorsChanged FINAL)
98
99 /**
100 * Foreground color for negative areas, such as critical error text
101 */
102 Q_PROPERTY(QColor negativeTextColor READ negativeTextColor WRITE setCustomNegativeTextColor RESET setCustomNegativeTextColor NOTIFY colorsChanged FINAL)
103
104 /**
105 * Foreground color for neutral areas, such as warning texts (but not critical)
106 */
107 Q_PROPERTY(QColor neutralTextColor READ neutralTextColor WRITE setCustomNeutralTextColor RESET setCustomNeutralTextColor NOTIFY colorsChanged FINAL)
108
109 /**
110 * Success messages, trusted content
111 */
112 Q_PROPERTY(QColor positiveTextColor READ positiveTextColor WRITE setCustomPositiveTextColor RESET setCustomPositiveTextColor NOTIFY colorsChanged FINAL)
113
114 // background colors
115 /**
116 * The generic background color
117 */
118 Q_PROPERTY(QColor backgroundColor READ backgroundColor WRITE setCustomBackgroundColor RESET setCustomBackgroundColor NOTIFY colorsChanged FINAL)
119
120 /**
121 * The generic background color
122 * Alternate background; for example, for use in lists.
123 * This color may be the same as BackgroundNormal,
124 * especially in sets other than View and Window.
125 */
126 Q_PROPERTY(QColor alternateBackgroundColor READ alternateBackgroundColor WRITE setCustomAlternateBackgroundColor RESET setCustomAlternateBackgroundColor
127 NOTIFY colorsChanged)
128
129 /**
130 * The background color for selected areas
131 */
132 Q_PROPERTY(QColor highlightColor READ highlightColor WRITE setCustomHighlightColor RESET setCustomHighlightColor NOTIFY colorsChanged FINAL)
133
134 /**
135 * Background for areas that are active or requesting attention
136 */
137 Q_PROPERTY(
138 QColor activeBackgroundColor READ activeBackgroundColor WRITE setCustomActiveBackgroundColor RESET setCustomActiveBackgroundColor NOTIFY colorsChanged)
139
140 /**
141 * Background color for links
142 */
143 Q_PROPERTY(
144 QColor linkBackgroundColor READ linkBackgroundColor WRITE setCustomLinkBackgroundColor RESET setCustomLinkBackgroundColor NOTIFY colorsChanged FINAL)
145
146 /**
147 * Background color for visited links, usually a bit darker than linkBackgroundColor
148 */
149 Q_PROPERTY(QColor visitedLinkBackgroundColor READ visitedLinkBackgroundColor WRITE setCustomVisitedLinkBackgroundColor RESET
150 setCustomVisitedLinkBackgroundColor NOTIFY colorsChanged)
151
152 /**
153 * Background color for negative areas, such as critical errors and destructive actions
154 */
155 Q_PROPERTY(QColor negativeBackgroundColor READ negativeBackgroundColor WRITE setCustomNegativeBackgroundColor RESET setCustomNegativeBackgroundColor NOTIFY
156 colorsChanged)
157
158 /**
159 * Background color for neutral areas, such as warnings (but not critical)
160 */
161 Q_PROPERTY(QColor neutralBackgroundColor READ neutralBackgroundColor WRITE setCustomNeutralBackgroundColor RESET setCustomNeutralBackgroundColor NOTIFY
162 colorsChanged)
163
164 /**
165 * Background color for positive areas, such as success messages and trusted content
166 */
167 Q_PROPERTY(QColor positiveBackgroundColor READ positiveBackgroundColor WRITE setCustomPositiveBackgroundColor RESET setCustomPositiveBackgroundColor NOTIFY
168 colorsChanged)
169
170 // decoration colors
171 /**
172 * A decoration color that indicates active focus
173 */
174 Q_PROPERTY(QColor focusColor READ focusColor WRITE setCustomFocusColor RESET setCustomFocusColor NOTIFY colorsChanged FINAL)
175
176 /**
177 * A decoration color that indicates mouse hovering
178 */
179 Q_PROPERTY(QColor hoverColor READ hoverColor WRITE setCustomHoverColor RESET setCustomHoverColor NOTIFY colorsChanged FINAL)
180
181 /**
182 * Hint for item views to actually make use of the alternate background color feature
183 */
184 Q_PROPERTY(
185 bool useAlternateBackgroundColor READ useAlternateBackgroundColor WRITE setUseAlternateBackgroundColor NOTIFY useAlternateBackgroundColorChanged FINAL)
186
187 // font and palette
188 Q_PROPERTY(QFont defaultFont READ defaultFont NOTIFY defaultFontChanged FINAL)
189
190 // small font
191 Q_PROPERTY(QFont smallFont READ smallFont NOTIFY smallFontChanged FINAL)
192
193 // Active palette
194 Q_PROPERTY(QPalette palette READ palette NOTIFY paletteChanged FINAL)
195
196 // Frame contrast value, usually used for separators and outlines
197 // Value is between 0.0 and 1.0
198 Q_PROPERTY(qreal frameContrast READ frameContrast CONSTANT FINAL)
199
200 // Returns half of the frameContrast value; used by Separator.Weight.Light
201 // Value is between 0.0 and 1.0
202 Q_PROPERTY(qreal lightFrameContrast READ lightFrameContrast CONSTANT FINAL)
203
204public:
205 enum ColorSet {
206 /** Color set for item views, usually the lightest of all */
207 View = 0,
208 /** Default Color set for windows and "chrome" areas */
210 /** Color set used by buttons */
212 /** Color set used by selected areas */
214 /** Color set used by tooltips */
216 /** Color set meant to be complementary to Window: usually is a dark theme for light themes */
218 /** Color set to be used by heading areas of applications, such as toolbars */
220 // Number of items in this enum, this should always be the last item.
221 ColorSetCount,
222 };
223 Q_ENUM(ColorSet)
224
225 enum ColorGroup {
226 Disabled = QPalette::Disabled,
227 Active = QPalette::Active,
228 Inactive = QPalette::Inactive,
229 Normal = QPalette::Normal,
230
231 ColorGroupCount, // Number of items in this enum, this should always be the last item.
232 };
233 Q_ENUM(ColorGroup)
234
235 explicit PlatformTheme(QObject *parent = nullptr);
236 ~PlatformTheme() override;
237
238 void setColorSet(PlatformTheme::ColorSet);
239 PlatformTheme::ColorSet colorSet() const;
240
241 void setColorGroup(PlatformTheme::ColorGroup);
242 PlatformTheme::ColorGroup colorGroup() const;
243
244 bool inherit() const;
245 void setInherit(bool inherit);
246
247 // foreground colors
248 QColor textColor() const;
249 QColor disabledTextColor() const;
250 QColor highlightedTextColor() const;
251 QColor activeTextColor() const;
252 QColor linkColor() const;
253 QColor visitedLinkColor() const;
254 QColor negativeTextColor() const;
255 QColor neutralTextColor() const;
256 QColor positiveTextColor() const;
257
258 // background colors
259 QColor backgroundColor() const;
260 QColor alternateBackgroundColor() const;
261 QColor highlightColor() const;
262 QColor activeBackgroundColor() const;
263 QColor linkBackgroundColor() const;
264 QColor visitedLinkBackgroundColor() const;
265 QColor negativeBackgroundColor() const;
266 QColor neutralBackgroundColor() const;
267 QColor positiveBackgroundColor() const;
268
269 // decoration colors
270 QColor focusColor() const;
271 QColor hoverColor() const;
272
273 QFont defaultFont() const;
274 QFont smallFont() const;
275
276 // this may is used by the desktop QQC2 to set the styleoption palettes
277 QPalette palette() const;
278
279 qreal frameContrast() const;
280 qreal lightFrameContrast() const;
281
282 // this will be used by desktopicon to fetch icons with KIconLoader
283 virtual Q_INVOKABLE QIcon iconFromTheme(const QString &name, const QColor &customColor = Qt::transparent);
284
285 bool supportsIconColoring() const;
286
287 // foreground colors
288 void setCustomTextColor(const QColor &color = QColor());
289 void setCustomDisabledTextColor(const QColor &color = QColor());
290 void setCustomHighlightedTextColor(const QColor &color = QColor());
291 void setCustomActiveTextColor(const QColor &color = QColor());
292 void setCustomLinkColor(const QColor &color = QColor());
293 void setCustomVisitedLinkColor(const QColor &color = QColor());
294 void setCustomNegativeTextColor(const QColor &color = QColor());
295 void setCustomNeutralTextColor(const QColor &color = QColor());
296 void setCustomPositiveTextColor(const QColor &color = QColor());
297 // background colors
298 void setCustomBackgroundColor(const QColor &color = QColor());
299 void setCustomAlternateBackgroundColor(const QColor &color = QColor());
300 void setCustomHighlightColor(const QColor &color = QColor());
301 void setCustomActiveBackgroundColor(const QColor &color = QColor());
302 void setCustomLinkBackgroundColor(const QColor &color = QColor());
303 void setCustomVisitedLinkBackgroundColor(const QColor &color = QColor());
304 void setCustomNegativeBackgroundColor(const QColor &color = QColor());
305 void setCustomNeutralBackgroundColor(const QColor &color = QColor());
306 void setCustomPositiveBackgroundColor(const QColor &color = QColor());
307 // decoration colors
308 void setCustomFocusColor(const QColor &color = QColor());
309 void setCustomHoverColor(const QColor &color = QColor());
310
311 bool useAlternateBackgroundColor() const;
312 void setUseAlternateBackgroundColor(bool alternate);
313
314 // QML attached property
315 static PlatformTheme *qmlAttachedProperties(QObject *object);
316
317Q_SIGNALS:
318 void colorsChanged();
319 void defaultFontChanged(const QFont &font);
320 void smallFontChanged(const QFont &font);
321 void colorSetChanged(Kirigami::Platform::PlatformTheme::ColorSet colorSet);
322 void colorGroupChanged(Kirigami::Platform::PlatformTheme::ColorGroup colorGroup);
323 void paletteChanged(const QPalette &pal);
324 void inheritChanged(bool inherit);
325 void useAlternateBackgroundColorChanged(bool alternate);
326
327protected:
328 // Setters, not accessible from QML but from implementations
329 void setSupportsIconColoring(bool support);
330
331 // foreground colors
332 void setTextColor(const QColor &color);
333 void setDisabledTextColor(const QColor &color);
334 void setHighlightedTextColor(const QColor &color);
335 void setActiveTextColor(const QColor &color);
336 void setLinkColor(const QColor &color);
337 void setVisitedLinkColor(const QColor &color);
338 void setNegativeTextColor(const QColor &color);
339 void setNeutralTextColor(const QColor &color);
340 void setPositiveTextColor(const QColor &color);
341
342 // background colors
343 void setBackgroundColor(const QColor &color);
344 void setAlternateBackgroundColor(const QColor &color);
345 void setHighlightColor(const QColor &color);
346 void setActiveBackgroundColor(const QColor &color);
347 void setLinkBackgroundColor(const QColor &color);
348 void setVisitedLinkBackgroundColor(const QColor &color);
349 void setNegativeBackgroundColor(const QColor &color);
350 void setNeutralBackgroundColor(const QColor &color);
351 void setPositiveBackgroundColor(const QColor &color);
352
353 // decoration colors
354 void setFocusColor(const QColor &color);
355 void setHoverColor(const QColor &color);
356
357 void setDefaultFont(const QFont &defaultFont);
358 void setSmallFont(const QFont &smallFont);
359
360 bool event(QEvent *event) override;
361
362private:
363 KIRIGAMIPLATFORM_NO_EXPORT void update();
364 KIRIGAMIPLATFORM_NO_EXPORT void updateChildren(QObject *item);
365 KIRIGAMIPLATFORM_NO_EXPORT QObject *determineParent(QObject *object);
366 KIRIGAMIPLATFORM_NO_EXPORT void emitSignalsForChanges(int changes);
367
368 PlatformThemePrivate *d;
369 friend class PlatformThemePrivate;
370 friend class PlatformThemeData;
371 friend class PlatformThemeChangeTracker;
372};
373
374/**
375 * A class that tracks changes to PlatformTheme properties and emits signals at the right moment.
376 *
377 * This should be used by PlatformTheme implementations to ensure that multiple
378 * changes to a PlatformTheme's properties do not emit multiple change signals,
379 * instead batching all of them into a single signal emission. This then ensures
380 * things making use of PlatformTheme aren't needlessly redrawn or redrawn in a
381 * partially changed state.
382 *
383 * @since 6.7
384 *
385 */
386class KIRIGAMIPLATFORM_EXPORT PlatformThemeChangeTracker
387{
388public:
389 /**
390 * Flags used to indicate changes made to certain properties.
391 */
392 enum class PropertyChange : uint8_t {
393 None = 0,
394 ColorSet = 1 << 0,
395 ColorGroup = 1 << 1,
396 Color = 1 << 2,
397 Palette = 1 << 3,
398 Font = 1 << 4,
399 Data = 1 << 5,
400 All = ColorSet | ColorGroup | Color | Palette | Font | Data,
401 };
402 Q_DECLARE_FLAGS(PropertyChanges, PropertyChange)
403
404 PlatformThemeChangeTracker(PlatformTheme *theme, PropertyChanges changes = PropertyChange::None);
406
407 void markDirty(PropertyChanges changes);
408
409private:
410 PlatformTheme *m_theme;
411
412 // Per-PlatformTheme data that we need for PlatformThemeChangeBlocker.
413 // We don't want to store this in PlatformTheme since that would increase the
414 // size of every instance of PlatformTheme while it's only used when we want to
415 // block property change signal emissions. So instead we store it in a separate
416 // hash using the PlatformTheme as key.
417 struct Data {
418 PropertyChanges changes;
419 };
420
421 std::shared_ptr<Data> m_data;
422
423 inline static QHash<PlatformTheme *, std::weak_ptr<Data>> s_blockedChanges;
424};
425
426namespace PlatformThemeEvents
427{
428// To avoid the overhead of Qt's signal/slot connections, we use custom events
429// to communicate with subclasses. This way, we can indicate what actually
430// changed without needing to add new virtual functions to PlatformTheme which
431// would break binary compatibility.
432//
433// To handle these events in your subclass, override QObject::event() and check
434// if you receive one of these events, then do what is needed. Finally, make
435// sure to call PlatformTheme::event() since that will also do some processing
436// of these events.
437
438template<typename T>
439class KIRIGAMIPLATFORM_EXPORT PropertyChangedEvent : public QEvent
440{
441public:
442 PropertyChangedEvent(PlatformTheme *theme, const T &previous, const T &current)
443 : QEvent(PropertyChangedEvent<T>::type)
444 , sender(theme)
445 , oldValue(previous)
446 , newValue(current)
447 {
448 }
449
450 PlatformTheme *sender;
451 T oldValue;
452 T newValue;
453
454 static QEvent::Type type;
455};
456
457using DataChangedEvent = PropertyChangedEvent<std::shared_ptr<PlatformThemeData>>;
458using ColorSetChangedEvent = PropertyChangedEvent<PlatformTheme::ColorSet>;
459using ColorGroupChangedEvent = PropertyChangedEvent<PlatformTheme::ColorGroup>;
460using ColorChangedEvent = PropertyChangedEvent<QColor>;
461using FontChangedEvent = PropertyChangedEvent<QFont>;
462
463}
464
465}
466} // namespace Kirigami
467
469
470#endif // PLATFORMTHEME_H
A class that tracks changes to PlatformTheme properties and emits signals at the right moment.
PropertyChange
Flags used to indicate changes made to certain properties.
This class is the base for color management in Kirigami, different platforms can reimplement this cla...
@ Tooltip
Color set used by tooltips.
@ Button
Color set used by buttons.
@ Header
Color set to be used by heading areas of applications, such as toolbars.
@ Window
Default Color set for windows and "chrome" areas.
@ Selection
Color set used by selected areas.
@ Complementary
Color set meant to be complementary to Window: usually is a dark theme for light themes.
Type type(const QSqlDatabase &db)
transparent
This file is part of the KDE documentation.
Documentation copyright © 1996-2024 The KDE developers.
Generated on Mon Nov 18 2024 12:16:21 by doxygen 1.12.0 written by Dimitri van Heesch, © 1997-2006

KDE's Doxygen guidelines are available online.