Qt Utilities: misc/dialogutils.cpp Source File

Qt Utilities 6.22.1 Common Qt related C++ classes and routines used by my applications such as dialogs, widgets and models

Loading...
Searching...
No Matches
dialogutils.cpp
Go to the documentation of this file.
1#include "./dialogutils.h"
2
3#include "../misc/desktoputils.h"
4
5#include <QCoreApplication>
6#include <QDir>
7#include <QFileInfo>
8
9#if defined(QT_UTILITIES_GUI_QTWIDGETS) || defined(QT_UTILITIES_GUI_QTQUICK)
10#include <QGuiApplication>
11#include <QPalette>
12#endif
13
14#if defined(QT_UTILITIES_GUI_QTWIDGETS)
15#include <QApplication>
16#include <QCursor>
17#if (QT_VERSION < QT_VERSION_CHECK(5, 10, 0))
18#include <QDesktopWidget>
19#endif
20#include <QScreen>
21#include <QStyle>
22#include <QWidget>
23#endif
24
25namespace QtUtilities {
26
31QString generateWindowTitle(DocumentStatus documentStatus, const QString &documentPath)
32{
33 switch (documentStatus) {
34 case DocumentStatus::Saved:
35 if (documentPath.isEmpty()) {
36 return QCoreApplication::translate("Utilities::windowTitle", "Unsaved - %1").arg(QCoreApplication::applicationName());
37 } else {
38 const QFileInfo file(documentPath);
39 return QCoreApplication::translate("Utilities::windowTitle", "%1 - %2 - %3")
40 .arg(file.fileName(), file.dir().path(), QCoreApplication::applicationName());
41 }
42 case DocumentStatus::Unsaved:
43 if (documentPath.isEmpty()) {
44 return QCoreApplication::translate("Utilities::windowTitle", "*Unsaved - %1").arg(QCoreApplication::applicationName());
45 } else {
46 const QFileInfo file(documentPath);
47 return QCoreApplication::translate("Utilities::windowTitle", "*%1 - %2 - %3")
48 .arg(file.fileName(), file.dir().path(), QCoreApplication::applicationName());
49 }
50 case DocumentStatus::NoDocument:
51 return QCoreApplication::applicationName();
52 default:
53 return QString(); // to suppress warning: "control reaches end of non-void
54 // function"
55 }
56}
57
58#if defined(QT_UTILITIES_GUI_QTWIDGETS) || defined(QT_UTILITIES_GUI_QTQUICK)
59
60#ifdef Q_OS_WIN32
64QColor windowFrameColorForPalette(const QPalette &palette)
65{
66 return palette.window().color().darker(108);
67}
68
72QColor windowFrameColor()
73{
74 return windowFrameColorForPalette(QGuiApplication::palette());
75}
76
80QColor instructionTextColorForPalette(const QPalette &palette)
81{
82 return isPaletteDark(palette) ? palette.text().color() :
83#if QT_VERSION >= QT_VERSION_CHECK(6, 6, 0)
84 palette.accent().color()
85#else
86 QColor(0x00, 0x33, 0x99)
87#endif
88 ;
89}
90
94QColor instructionTextColor()
95{
96 return instructionTextColorForPalette(QGuiApplication::palette());
97}
98#endif
99
104QString dialogStyleForPalette(const QPalette &palette)
105{
106#ifdef Q_OS_WINDOWS
107 return QStringLiteral("#mainWidget { color: palette(text); background-color: "
108 "palette(base); border: none; }"
109 "#bottomWidget { background-color: palette(window); "
110 "color: palette(window-text); border-top: 1px solid %1; }"
111 "*[classNames~=\"heading\"] { font-size: 12pt; color: %2; }"
112 "*[classNames~=\"input-invalid\"] { color: red; }")
113 .arg(windowFrameColorForPalette(palette).name(), instructionTextColorForPalette(palette).name());
114#else
115 Q_UNUSED(palette)
116 return QStringLiteral("*[classNames~=\"heading\"] { font-weight: bold; }"
117 "*[classNames~=\"input-invalid\"] { color: red; }");
118#endif
119}
120
125const QString &dialogStyle()
126{
127 static const auto style = dialogStyleForPalette(QGuiApplication::palette());
128 return style;
129}
130
131#ifdef QT_UTILITIES_GUI_QTWIDGETS
132
133QRect availableScreenGeometryAtPoint(const QPoint &point)
134{
135#if (QT_VERSION >= QT_VERSION_CHECK(5, 10, 0))
136 QScreen *const screen = QGuiApplication::screenAt(point);
137 if (!screen) {
138 return QRect();
139 }
140 return screen->availableGeometry();
141#else
142 return QApplication::desktop()->availableGeometry(point);
143#endif
144}
145
147static QRect shrinkRectByMargins(QRect rect, const QMargins &margins)
148{
149 rect.setLeft(rect.left() + margins.left());
150 rect.setTop(rect.top() + margins.top());
151 rect.setRight(rect.right() - margins.right());
152 rect.setBottom(rect.bottom() - margins.bottom());
153 return rect;
154}
155
156static QRect limitRect(QRect rect, const QRect &bounds)
157{
158 if (rect.left() < bounds.left()) {
159 rect.setLeft(bounds.left());
160 }
161 if (rect.top() < bounds.top()) {
162 rect.setTop(bounds.top());
163 }
164 if (rect.right() > bounds.right()) {
165 rect.setRight(bounds.right());
166 }
167 if (rect.bottom() > bounds.bottom()) {
168 rect.setBottom(bounds.bottom());
169 }
170 return rect;
171}
172
173static QMargins widgetFrame(QWidget *widget, const QMargins &defaultAssumption = QMargins(10, 25, 10, 10))
174{
175 if (!widget->isWindow()) {
176 return QMargins();
177 }
178 const auto widgetGeometry = widget->geometry();
179 const auto frameGeometry = widget->frameGeometry();
180 const auto frame = QMargins(widgetGeometry.left() - frameGeometry.left(), widgetGeometry.top() - frameGeometry.top(),
181 frameGeometry.right() - widgetGeometry.right(), frameGeometry.bottom() - widgetGeometry.bottom());
182 return frame.isNull() ? defaultAssumption : frame;
183}
184
185static bool centerWidgetInternal(QWidget *widget, const QWidget *parent, const QPoint *position, bool avoidOverflow)
186{
187 const auto availableGeometry = parent ? parent->geometry() : availableScreenGeometryAtPoint(position ? *position : QCursor::pos());
188 const auto alignedRect = QStyle::alignedRect(Qt::LeftToRight, Qt::AlignCenter, widget->size(), availableGeometry);
189 if (!avoidOverflow) {
190 widget->setGeometry(alignedRect);
191 return false;
192 }
193 const auto limitedRect = limitRect(alignedRect, shrinkRectByMargins(availableGeometry, widgetFrame(widget)));
194 widget->setGeometry(limitedRect);
195 return alignedRect != limitedRect;
196}
198
204void centerWidget(QWidget *widget, const QWidget *parent, const QPoint *position)
205{
206 centerWidgetInternal(widget, parent, position, false);
207}
208
219bool centerWidgetAvoidingOverflow(QWidget *widget, const QWidget *parent, const QPoint *position)
220{
221 return centerWidgetInternal(widget, parent, position, true);
222}
223
231void cornerWidget(QWidget *widget, const QPoint *position)
232{
233 const QPoint cursorPos(position ? *position : QCursor::pos());
234 const QRect availableGeometry(availableScreenGeometryAtPoint(cursorPos));
235 const Qt::Alignment alignment
236 = (cursorPos.x() - availableGeometry.left() < availableGeometry.right() - cursorPos.x() ? Qt::AlignLeft : Qt::AlignRight)
237 | (cursorPos.y() - availableGeometry.top() < availableGeometry.bottom() - cursorPos.y() ? Qt::AlignTop : Qt::AlignBottom);
238 widget->setGeometry(QStyle::alignedRect(Qt::LeftToRight, alignment, widget->size(), availableGeometry));
239}
240
244void makeHeading(QWidget *widget)
245{
246 widget->setProperty("classNames", widget->property("classNames").toStringList() << QStringLiteral("heading"));
247}
248
255void updateStyle(QWidget *widget)
256{
257 widget->style()->unpolish(widget);
258 widget->style()->polish(widget);
259 widget->update();
260}
261
262#endif
263
264#endif
265
266} // namespace QtUtilities
desktoputils.h
dialogutils.h
QtUtilities
!
Definition trylocker.h:8
QtUtilities::DocumentStatus
DocumentStatus
The DocumentStatus enum specifies the status of the document in a window.
Definition dialogutils.h:21
QtUtilities::DocumentStatus::Unsaved
@ Unsaved
Definition dialogutils.h:26
QtUtilities::DocumentStatus::Saved
@ Saved
Definition dialogutils.h:24
QtUtilities::DocumentStatus::NoDocument
@ NoDocument
Definition dialogutils.h:22
QtUtilities::generateWindowTitle
QT_UTILITIES_EXPORT QString generateWindowTitle(DocumentStatus documentStatus, const QString &documentPath)
Generates the window title string for the specified documentStatus and documentPath.
Definition dialogutils.cpp:31
QtUtilities::isPaletteDark
QT_UTILITIES_EXPORT bool isPaletteDark(const QPalette &palette=QPalette())
Returns whether palette is dark.
Definition desktoputils.cpp:129