1 /****************************************************************************
2 **
3 ** Copyright (C) 2019 The Qt Company Ltd.
4 ** Contact: https://www.qt.io/licensing/
5 **
6 ** This file is part of Qt Creator.
7 **
8 ** Commercial License Usage
9 ** Licensees holding valid commercial Qt licenses may use this file in
10 ** accordance with the commercial license agreement provided with the
11 ** Software or, alternatively, in accordance with the terms contained in
12 ** a written agreement between you and The Qt Company. For licensing terms
13 ** and conditions see https://www.qt.io/terms-conditions. For further
14 ** information use the contact form at https://www.qt.io/contact-us.
15 **
16 ** GNU General Public License Usage
17 ** Alternatively, this file may be used under the terms of the GNU
18 ** General Public License version 3 as published by the Free Software
19 ** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
20 ** included in the packaging of this file. Please review the following
21 ** information to ensure the GNU General Public License requirements will
22 ** be met: https://www.gnu.org/licenses/gpl-3.0.html.
23 **
24 ****************************************************************************/
25 
26 #include "infolabel.h"
27 
28 #include <utils/icon.h>
29 #include <utils/utilsicons.h>
30 
31 #include <QPainter>
32 #include <QPaintEvent>
33 #include <QLabel>
34 
35 namespace Utils {
36 
37 constexpr int iconSize = 16;
38 
InfoLabel(QWidget * parent)39 InfoLabel::InfoLabel(QWidget *parent)
40     : InfoLabel({}, Information, parent)
41 {
42 }
43 
InfoLabel(const QString & text,InfoType type,QWidget * parent)44 InfoLabel::InfoLabel(const QString &text, InfoType type, QWidget *parent)
45     : ElidingLabel(text, parent)
46 {
47     setType(type);
48 }
49 
type() const50 InfoLabel::InfoType InfoLabel::type() const
51 {
52     return m_type;
53 }
54 
setType(InfoType type)55 void InfoLabel::setType(InfoType type)
56 {
57     m_type = type;
58     setContentsMargins(m_type == None ? 0 : iconSize + 2, 0, 0, 0);
59     update();
60 }
61 
filled() const62 bool InfoLabel::filled() const
63 {
64     return m_filled;
65 }
66 
setFilled(bool filled)67 void InfoLabel::setFilled(bool filled)
68 {
69     m_filled = filled;
70 }
71 
minimumSizeHint() const72 QSize InfoLabel::minimumSizeHint() const
73 {
74     QSize baseHint = ElidingLabel::minimumSizeHint();
75     baseHint.setHeight(qMax(baseHint.height(), iconSize));
76     return baseHint;
77 }
78 
fillColorForType(InfoLabel::InfoType type)79 static Utils::Theme::Color fillColorForType(InfoLabel::InfoType type)
80 {
81     using namespace Utils;
82     switch (type) {
83     case InfoLabel::Warning:
84         return Theme::IconsWarningColor;
85     case InfoLabel::Ok:
86         return Theme::IconsRunColor;
87     case InfoLabel::Error:
88     case InfoLabel::NotOk:
89         return Theme::IconsErrorColor;
90     case InfoLabel::Information:
91     default:
92         return Theme::IconsInfoColor;
93     }
94 }
95 
iconForType(InfoLabel::InfoType type)96 static const QIcon &iconForType(InfoLabel::InfoType type)
97 {
98     using namespace Utils;
99     switch (type) {
100     case InfoLabel::Information: {
101         static const QIcon icon = Icons::INFO.icon();
102         return icon;
103     }
104     case InfoLabel::Warning: {
105         static const QIcon icon = Icons::WARNING.icon();
106         return icon;
107     }
108     case InfoLabel::Error: {
109         static const QIcon icon = Icons::CRITICAL.icon();
110         return icon;
111     }
112     case InfoLabel::Ok: {
113         static const QIcon icon = Icons::OK.icon();
114         return icon;
115     }
116     case InfoLabel::NotOk: {
117         static const QIcon icon = Icons::BROKEN.icon();
118         return icon;
119     }
120     default: {
121         static const QIcon undefined;
122         return undefined;
123     }
124     }
125 }
126 
paintEvent(QPaintEvent * event)127 void InfoLabel::paintEvent(QPaintEvent *event)
128 {
129     if (m_type == None)
130         return ElidingLabel::paintEvent(event);
131 
132     const bool centerIconVertically = wordWrap() || elideMode() == Qt::ElideNone;
133     const QRect iconRect(0, centerIconVertically ? 0 : ((height() - iconSize) / 2),
134                          iconSize, iconSize);
135 
136     QPainter p(this);
137     if (m_filled && isEnabled()) {
138         p.save();
139         p.setOpacity(0.175);
140         p.fillRect(rect(), creatorTheme()->color(fillColorForType(m_type)));
141         p.restore();
142     }
143     const QIcon &icon = iconForType(m_type);
144     QWindow *window = this->window()->windowHandle();
145     const QIcon::Mode mode = !this->isEnabled() ? QIcon::Disabled : QIcon::Normal;
146     const QPixmap iconPx =
147             icon.pixmap(window, QSize(iconSize, iconSize) * devicePixelRatio(), mode);
148     p.drawPixmap(iconRect, iconPx);
149     ElidingLabel::paintEvent(event);
150 }
151 
152 } // namespace Utils
153