1 | // Copyright (C) 2016 The Qt Company Ltd. |
2 | // SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only |
3 | |
4 | #include "qstatusbar.h" |
5 | |
6 | #include "qlist.h" |
7 | #include "qdebug.h" |
8 | #include "qevent.h" |
9 | #include "qlayout.h" |
10 | #include "qpainter.h" |
11 | #include "qtimer.h" |
12 | #include "qstyle.h" |
13 | #include "qstyleoption.h" |
14 | #if QT_CONFIG(sizegrip) |
15 | #include "qsizegrip.h" |
16 | #endif |
17 | #if QT_CONFIG(mainwindow) |
18 | #include "qmainwindow.h" |
19 | #endif |
20 | |
21 | #if QT_CONFIG(accessibility) |
22 | #include "qaccessible.h" |
23 | #endif |
24 | |
25 | #include <private/qlayoutengine_p.h> |
26 | #include <private/qwidget_p.h> |
27 | |
28 | QT_BEGIN_NAMESPACE |
29 | |
30 | class QStatusBarPrivate : public QWidgetPrivate |
31 | { |
32 | Q_DECLARE_PUBLIC(QStatusBar) |
33 | public: |
34 | QStatusBarPrivate() {} |
35 | |
36 | enum ItemCategory |
37 | { |
38 | Normal, |
39 | Permanent |
40 | }; |
41 | |
42 | struct SBItem { |
43 | QWidget *widget = nullptr; |
44 | int stretch = 0; |
45 | ItemCategory category = Normal; |
46 | bool isPermanent() const { return category == Permanent; } |
47 | }; |
48 | |
49 | QList<SBItem> items; |
50 | QString tempItem; |
51 | |
52 | QBoxLayout *box; |
53 | QTimer *timer; |
54 | |
55 | #if QT_CONFIG(sizegrip) |
56 | QSizeGrip *resizer; |
57 | bool showSizeGrip; |
58 | #endif |
59 | |
60 | int savedStrut; |
61 | |
62 | int indexToLastNonPermanentWidget() const |
63 | { |
64 | int i = items.size() - 1; |
65 | for (; i >= 0; --i) { |
66 | const SBItem &item = items.at(i); |
67 | if (!item.isPermanent()) |
68 | break; |
69 | } |
70 | return i; |
71 | } |
72 | |
73 | #if QT_CONFIG(sizegrip) |
74 | void tryToShowSizeGrip() |
75 | { |
76 | if (!showSizeGrip) |
77 | return; |
78 | showSizeGrip = false; |
79 | if (!resizer || resizer->isVisible()) |
80 | return; |
81 | resizer->setAttribute(Qt::WA_WState_ExplicitShowHide, on: false); |
82 | QMetaObject::invokeMethod(obj: resizer, member: "_q_showIfNotHidden" , c: Qt::DirectConnection); |
83 | resizer->setAttribute(Qt::WA_WState_ExplicitShowHide, on: false); |
84 | } |
85 | #endif |
86 | |
87 | QRect messageRect() const; |
88 | }; |
89 | |
90 | |
91 | QRect QStatusBarPrivate::messageRect() const |
92 | { |
93 | Q_Q(const QStatusBar); |
94 | const bool rtl = q->layoutDirection() == Qt::RightToLeft; |
95 | |
96 | int left = 6; |
97 | int right = q->width() - 12; |
98 | |
99 | #if QT_CONFIG(sizegrip) |
100 | if (resizer && resizer->isVisible()) { |
101 | if (rtl) |
102 | left = resizer->x() + resizer->width(); |
103 | else |
104 | right = resizer->x(); |
105 | } |
106 | #endif |
107 | |
108 | for (const auto &item : items) { |
109 | if (item.isPermanent() && item.widget->isVisible()) { |
110 | if (rtl) |
111 | left = qMax(a: left, b: item.widget->x() + item.widget->width() + 2); |
112 | else |
113 | right = qMin(a: right, b: item.widget->x() - 2); |
114 | break; |
115 | } |
116 | } |
117 | return QRect(left, 0, right-left, q->height()); |
118 | } |
119 | |
120 | |
121 | /*! |
122 | \class QStatusBar |
123 | \brief The QStatusBar class provides a horizontal bar suitable for |
124 | presenting status information. |
125 | |
126 | \ingroup mainwindow-classes |
127 | \ingroup helpsystem |
128 | \inmodule QtWidgets |
129 | |
130 | Each status indicator falls into one of three categories: |
131 | |
132 | \list |
133 | \li \e Temporary - briefly occupies most of the status bar. Used |
134 | to explain tool tip texts or menu entries, for example. |
135 | \li \e Normal - occupies part of the status bar and may be hidden |
136 | by temporary messages. Used to display the page and line |
137 | number in a word processor, for example. |
138 | \li \e Permanent - is never hidden. Used for important mode |
139 | indications, for example, some applications put a Caps Lock |
140 | indicator in the status bar. |
141 | \endlist |
142 | |
143 | QStatusBar lets you display all three types of indicators. |
144 | |
145 | Typically, a request for the status bar functionality occurs in |
146 | relation to a QMainWindow object. QMainWindow provides a main |
147 | application window, with a menu bar, tool bars, dock widgets \e |
148 | and a status bar around a large central widget. The status bar can |
149 | be retrieved using the QMainWindow::statusBar() function, and |
150 | replaced using the QMainWindow::setStatusBar() function. |
151 | |
152 | Use the showMessage() slot to display a \e temporary message: |
153 | |
154 | \snippet code/src_gui_widgets_qstatusbar.cpp 1 |
155 | |
156 | To remove a temporary message, use the clearMessage() slot, or set |
157 | a time limit when calling showMessage(). For example: |
158 | |
159 | \snippet code/src_gui_widgets_qstatusbar.cpp 2 |
160 | |
161 | Use the currentMessage() function to retrieve the temporary |
162 | message currently shown. The QStatusBar class also provide the |
163 | messageChanged() signal which is emitted whenever the temporary |
164 | status message changes. |
165 | |
166 | \target permanent message |
167 | \e Normal and \e Permanent messages are displayed by creating a |
168 | small widget (QLabel, QProgressBar or even QToolButton) and then |
169 | adding it to the status bar using the addWidget() or the |
170 | addPermanentWidget() function. Use the removeWidget() function to |
171 | remove such messages from the status bar. |
172 | |
173 | \snippet code/src_gui_widgets_qstatusbar.cpp 0 |
174 | |
175 | By default QStatusBar provides a QSizeGrip in the lower-right |
176 | corner. You can disable it using the setSizeGripEnabled() |
177 | function. Use the isSizeGripEnabled() function to determine the |
178 | current status of the size grip. |
179 | |
180 | \image fusion-statusbar-sizegrip.png A status bar shown in the Fusion widget style |
181 | |
182 | \sa QMainWindow, QStatusTipEvent |
183 | */ |
184 | |
185 | |
186 | /*! |
187 | Constructs a status bar with a size grip and the given \a parent. |
188 | |
189 | \sa setSizeGripEnabled() |
190 | */ |
191 | QStatusBar::QStatusBar(QWidget * parent) |
192 | : QWidget(*new QStatusBarPrivate, parent, { }) |
193 | { |
194 | Q_D(QStatusBar); |
195 | d->box = nullptr; |
196 | d->timer = nullptr; |
197 | |
198 | #if QT_CONFIG(sizegrip) |
199 | d->resizer = nullptr; |
200 | setSizeGripEnabled(true); // causes reformat() |
201 | #else |
202 | reformat(); |
203 | #endif |
204 | } |
205 | |
206 | /*! |
207 | Destroys this status bar and frees any allocated resources and |
208 | child widgets. |
209 | */ |
210 | QStatusBar::~QStatusBar() |
211 | { |
212 | } |
213 | |
214 | |
215 | /*! |
216 | Adds the given \a widget to this status bar, reparenting the |
217 | widget if it isn't already a child of this QStatusBar object. The |
218 | \a stretch parameter is used to compute a suitable size for the |
219 | given \a widget as the status bar grows and shrinks. The default |
220 | stretch factor is 0, i.e giving the widget a minimum of space. |
221 | |
222 | The widget is located to the far left of the first permanent |
223 | widget (see addPermanentWidget()) and may be obscured by temporary |
224 | messages. |
225 | |
226 | \sa insertWidget(), removeWidget(), addPermanentWidget() |
227 | */ |
228 | |
229 | void QStatusBar::addWidget(QWidget * widget, int stretch) |
230 | { |
231 | if (!widget) |
232 | return; |
233 | insertWidget(index: d_func()->indexToLastNonPermanentWidget() + 1, widget, stretch); |
234 | } |
235 | |
236 | /*! |
237 | \since 4.2 |
238 | |
239 | Inserts the given \a widget at the given \a index to this status bar, |
240 | reparenting the widget if it isn't already a child of this |
241 | QStatusBar object. If \a index is out of range, the widget is appended |
242 | (in which case it is the actual index of the widget that is returned). |
243 | |
244 | The \a stretch parameter is used to compute a suitable size for |
245 | the given \a widget as the status bar grows and shrinks. The |
246 | default stretch factor is 0, i.e giving the widget a minimum of |
247 | space. |
248 | |
249 | The widget is located to the far left of the first permanent |
250 | widget (see addPermanentWidget()) and may be obscured by temporary |
251 | messages. |
252 | |
253 | \sa addWidget(), removeWidget(), addPermanentWidget() |
254 | */ |
255 | int QStatusBar::insertWidget(int index, QWidget *widget, int stretch) |
256 | { |
257 | if (!widget) |
258 | return -1; |
259 | |
260 | Q_D(QStatusBar); |
261 | QStatusBarPrivate::SBItem item{.widget: widget, .stretch: stretch, .category: QStatusBarPrivate::Normal}; |
262 | |
263 | int idx = d->indexToLastNonPermanentWidget(); |
264 | if (Q_UNLIKELY(index < 0 || index > d->items.size() || (idx >= 0 && index > idx + 1))) { |
265 | qWarning(msg: "QStatusBar::insertWidget: Index out of range (%d), appending widget" , index); |
266 | index = idx + 1; |
267 | } |
268 | d->items.insert(i: index, t: item); |
269 | |
270 | if (!d->tempItem.isEmpty()) |
271 | widget->hide(); |
272 | |
273 | reformat(); |
274 | if (!widget->isHidden() || !widget->testAttribute(attribute: Qt::WA_WState_ExplicitShowHide)) |
275 | widget->show(); |
276 | |
277 | return index; |
278 | } |
279 | |
280 | /*! |
281 | Adds the given \a widget permanently to this status bar, |
282 | reparenting the widget if it isn't already a child of this |
283 | QStatusBar object. The \a stretch parameter is used to compute a |
284 | suitable size for the given \a widget as the status bar grows and |
285 | shrinks. The default stretch factor is 0, i.e giving the widget a |
286 | minimum of space. |
287 | |
288 | Permanently means that the widget may not be obscured by temporary |
289 | messages. It is located at the far right of the status bar. |
290 | |
291 | \sa insertPermanentWidget(), removeWidget(), addWidget() |
292 | */ |
293 | |
294 | void QStatusBar::addPermanentWidget(QWidget * widget, int stretch) |
295 | { |
296 | if (!widget) |
297 | return; |
298 | insertPermanentWidget(index: d_func()->items.size(), widget, stretch); |
299 | } |
300 | |
301 | /*! |
302 | \since 4.2 |
303 | |
304 | Inserts the given \a widget at the given \a index permanently to this status bar, |
305 | reparenting the widget if it isn't already a child of this |
306 | QStatusBar object. If \a index is out of range, the widget is appended |
307 | (in which case it is the actual index of the widget that is returned). |
308 | |
309 | The \a stretch parameter is used to compute a |
310 | suitable size for the given \a widget as the status bar grows and |
311 | shrinks. The default stretch factor is 0, i.e giving the widget a |
312 | minimum of space. |
313 | |
314 | Permanently means that the widget may not be obscured by temporary |
315 | messages. It is located at the far right of the status bar. |
316 | |
317 | \sa addPermanentWidget(), removeWidget(), addWidget() |
318 | */ |
319 | int QStatusBar::insertPermanentWidget(int index, QWidget *widget, int stretch) |
320 | { |
321 | if (!widget) |
322 | return -1; |
323 | |
324 | Q_D(QStatusBar); |
325 | QStatusBarPrivate::SBItem item{.widget: widget, .stretch: stretch, .category: QStatusBarPrivate::Permanent}; |
326 | |
327 | int idx = d->indexToLastNonPermanentWidget(); |
328 | if (Q_UNLIKELY(index < 0 || index > d->items.size() || (idx >= 0 && index <= idx))) { |
329 | qWarning(msg: "QStatusBar::insertPermanentWidget: Index out of range (%d), appending widget" , index); |
330 | index = d->items.size(); |
331 | } |
332 | d->items.insert(i: index, t: item); |
333 | |
334 | reformat(); |
335 | if (!widget->isHidden() || !widget->testAttribute(attribute: Qt::WA_WState_ExplicitShowHide)) |
336 | widget->show(); |
337 | |
338 | return index; |
339 | } |
340 | |
341 | /*! |
342 | Removes the specified \a widget from the status bar. |
343 | |
344 | \note This function does not delete the widget but \e hides it. |
345 | To add the widget again, you must call both the addWidget() and |
346 | show() functions. |
347 | |
348 | \sa addWidget(), addPermanentWidget(), clearMessage() |
349 | */ |
350 | |
351 | void QStatusBar::removeWidget(QWidget *widget) |
352 | { |
353 | if (!widget) |
354 | return; |
355 | |
356 | Q_D(QStatusBar); |
357 | if (d->items.removeIf(pred: [widget](const auto &item) { return item.widget == widget; })) { |
358 | widget->hide(); |
359 | reformat(); |
360 | } |
361 | #if defined(QT_DEBUG) |
362 | else |
363 | qDebug(msg: "QStatusBar::removeWidget(): Widget not found." ); |
364 | #endif |
365 | } |
366 | |
367 | /*! |
368 | \property QStatusBar::sizeGripEnabled |
369 | |
370 | \brief whether the QSizeGrip in the bottom-right corner of the |
371 | status bar is enabled |
372 | |
373 | The size grip is enabled by default. |
374 | */ |
375 | |
376 | bool QStatusBar::isSizeGripEnabled() const |
377 | { |
378 | #if !QT_CONFIG(sizegrip) |
379 | return false; |
380 | #else |
381 | Q_D(const QStatusBar); |
382 | return !!d->resizer; |
383 | #endif |
384 | } |
385 | |
386 | void QStatusBar::setSizeGripEnabled(bool enabled) |
387 | { |
388 | #if !QT_CONFIG(sizegrip) |
389 | Q_UNUSED(enabled); |
390 | #else |
391 | Q_D(QStatusBar); |
392 | if (!enabled != !d->resizer) { |
393 | if (enabled) { |
394 | d->resizer = new QSizeGrip(this); |
395 | d->resizer->hide(); |
396 | d->resizer->installEventFilter(filterObj: this); |
397 | d->showSizeGrip = true; |
398 | } else { |
399 | delete d->resizer; |
400 | d->resizer = nullptr; |
401 | d->showSizeGrip = false; |
402 | } |
403 | reformat(); |
404 | if (d->resizer && isVisible()) |
405 | d->tryToShowSizeGrip(); |
406 | } |
407 | #endif |
408 | } |
409 | |
410 | |
411 | /*! |
412 | Changes the status bar's appearance to account for item changes. |
413 | |
414 | Special subclasses may need this function, but geometry management |
415 | will usually take care of any necessary rearrangements. |
416 | */ |
417 | void QStatusBar::reformat() |
418 | { |
419 | Q_D(QStatusBar); |
420 | if (d->box) |
421 | delete d->box; |
422 | |
423 | QBoxLayout *vbox; |
424 | #if QT_CONFIG(sizegrip) |
425 | if (d->resizer) { |
426 | d->box = new QHBoxLayout(this); |
427 | d->box->setContentsMargins(QMargins()); |
428 | vbox = new QVBoxLayout; |
429 | d->box->addLayout(layout: vbox); |
430 | } else |
431 | #endif |
432 | { |
433 | vbox = d->box = new QVBoxLayout(this); |
434 | d->box->setContentsMargins(QMargins()); |
435 | } |
436 | vbox->addSpacing(size: 3); |
437 | QBoxLayout* l = new QHBoxLayout; |
438 | vbox->addLayout(layout: l); |
439 | l->addSpacing(size: 2); |
440 | l->setSpacing(6); |
441 | |
442 | int maxH = fontMetrics().height(); |
443 | |
444 | qsizetype i; |
445 | for (i = 0; i < d->items.size(); ++i) { |
446 | const auto &item = d->items.at(i); |
447 | if (item.isPermanent()) |
448 | break; |
449 | l->addWidget(item.widget, stretch: item.stretch); |
450 | int itemH = qMin(a: qSmartMinSize(w: item.widget).height(), b: item.widget->maximumHeight()); |
451 | maxH = qMax(a: maxH, b: itemH); |
452 | } |
453 | |
454 | l->addStretch(stretch: 0); |
455 | |
456 | for (; i < d->items.size(); ++i) { |
457 | const auto &item = d->items.at(i); |
458 | l->addWidget(item.widget, stretch: item.stretch); |
459 | int itemH = qMin(a: qSmartMinSize(w: item.widget).height(), b: item.widget->maximumHeight()); |
460 | maxH = qMax(a: maxH, b: itemH); |
461 | } |
462 | #if QT_CONFIG(sizegrip) |
463 | if (d->resizer) { |
464 | maxH = qMax(a: maxH, b: d->resizer->sizeHint().height()); |
465 | d->box->addSpacing(size: 1); |
466 | d->box->addWidget(d->resizer, stretch: 0, alignment: Qt::AlignBottom); |
467 | } |
468 | #endif |
469 | l->addStrut(maxH); |
470 | d->savedStrut = maxH; |
471 | vbox->addSpacing(size: 2); |
472 | d->box->activate(); |
473 | update(); |
474 | } |
475 | |
476 | /*! |
477 | |
478 | Hides the normal status indications and displays the given \a |
479 | message for the specified number of milli-seconds (\a{timeout}). If |
480 | \a{timeout} is 0 (default), the \a {message} remains displayed until |
481 | the clearMessage() slot is called or until the showMessage() slot is |
482 | called again to change the message. |
483 | |
484 | Note that showMessage() is called to show temporary explanations of |
485 | tool tip texts, so passing a \a{timeout} of 0 is not sufficient to |
486 | display a \l{permanent message}{permanent message}. |
487 | |
488 | \sa messageChanged(), currentMessage(), clearMessage() |
489 | */ |
490 | void QStatusBar::showMessage(const QString &message, int timeout) |
491 | { |
492 | Q_D(QStatusBar); |
493 | |
494 | if (timeout > 0) { |
495 | if (!d->timer) { |
496 | d->timer = new QTimer(this); |
497 | connect(sender: d->timer, SIGNAL(timeout()), receiver: this, SLOT(clearMessage())); |
498 | } |
499 | d->timer->start(msec: timeout); |
500 | } else if (d->timer) { |
501 | delete d->timer; |
502 | d->timer = nullptr; |
503 | } |
504 | if (d->tempItem == message) |
505 | return; |
506 | d->tempItem = message; |
507 | |
508 | hideOrShow(); |
509 | } |
510 | |
511 | /*! |
512 | Removes any temporary message being shown. |
513 | |
514 | \sa currentMessage(), showMessage(), removeWidget() |
515 | */ |
516 | |
517 | void QStatusBar::clearMessage() |
518 | { |
519 | Q_D(QStatusBar); |
520 | if (d->tempItem.isEmpty()) |
521 | return; |
522 | if (d->timer) { |
523 | qDeleteInEventHandler(o: d->timer); |
524 | d->timer = nullptr; |
525 | } |
526 | d->tempItem.clear(); |
527 | hideOrShow(); |
528 | } |
529 | |
530 | /*! |
531 | Returns the temporary message currently shown, |
532 | or an empty string if there is no such message. |
533 | |
534 | \sa showMessage() |
535 | */ |
536 | QString QStatusBar::currentMessage() const |
537 | { |
538 | Q_D(const QStatusBar); |
539 | return d->tempItem; |
540 | } |
541 | |
542 | /*! |
543 | \fn void QStatusBar::messageChanged(const QString &message) |
544 | |
545 | This signal is emitted whenever the temporary status message |
546 | changes. The new temporary message is passed in the \a message |
547 | parameter which is a null-string when the message has been |
548 | removed. |
549 | |
550 | \sa showMessage(), clearMessage() |
551 | */ |
552 | |
553 | /*! |
554 | Ensures that the right widgets are visible. |
555 | |
556 | Used by the showMessage() and clearMessage() functions. |
557 | */ |
558 | void QStatusBar::hideOrShow() |
559 | { |
560 | Q_D(QStatusBar); |
561 | bool haveMessage = !d->tempItem.isEmpty(); |
562 | |
563 | for (const auto &item : std::as_const(t&: d->items)) { |
564 | if (item.isPermanent()) |
565 | break; |
566 | if (haveMessage && item.widget->isVisible()) { |
567 | item.widget->hide(); |
568 | item.widget->setAttribute(Qt::WA_WState_ExplicitShowHide, on: false); |
569 | } else if (!haveMessage && !item.widget->testAttribute(attribute: Qt::WA_WState_ExplicitShowHide)) { |
570 | item.widget->show(); |
571 | } |
572 | } |
573 | |
574 | emit messageChanged(text: d->tempItem); |
575 | |
576 | #if QT_CONFIG(accessibility) |
577 | if (QAccessible::isActive()) { |
578 | QAccessibleEvent event(this, QAccessible::NameChanged); |
579 | QAccessible::updateAccessibility(event: &event); |
580 | } |
581 | #endif |
582 | |
583 | update(d->messageRect()); |
584 | } |
585 | |
586 | /*! |
587 | \reimp |
588 | */ |
589 | void QStatusBar::showEvent(QShowEvent *) |
590 | { |
591 | #if QT_CONFIG(sizegrip) |
592 | Q_D(QStatusBar); |
593 | if (d->resizer && d->showSizeGrip) |
594 | d->tryToShowSizeGrip(); |
595 | #endif |
596 | } |
597 | |
598 | /*! |
599 | \reimp |
600 | \fn void QStatusBar::paintEvent(QPaintEvent *event) |
601 | |
602 | Shows the temporary message, if appropriate, in response to the |
603 | paint \a event. |
604 | */ |
605 | void QStatusBar::paintEvent(QPaintEvent *event) |
606 | { |
607 | Q_D(QStatusBar); |
608 | bool haveMessage = !d->tempItem.isEmpty(); |
609 | |
610 | QPainter p(this); |
611 | QStyleOption opt; |
612 | opt.initFrom(w: this); |
613 | style()->drawPrimitive(pe: QStyle::PE_PanelStatusBar, opt: &opt, p: &p, w: this); |
614 | |
615 | for (const auto &item : std::as_const(t&: d->items)) { |
616 | if (item.widget->isVisible() && (!haveMessage || item.isPermanent())) { |
617 | QRect ir = item.widget->geometry().adjusted(xp1: -2, yp1: -1, xp2: 2, yp2: 1); |
618 | if (event->rect().intersects(r: ir)) { |
619 | QStyleOption opt(0); |
620 | opt.rect = ir; |
621 | opt.palette = palette(); |
622 | opt.state = QStyle::State_None; |
623 | style()->drawPrimitive(pe: QStyle::PE_FrameStatusBarItem, opt: &opt, p: &p, w: item.widget); |
624 | } |
625 | } |
626 | } |
627 | if (haveMessage) { |
628 | p.setPen(palette().windowText().color()); |
629 | p.drawText(r: d->messageRect(), flags: Qt::AlignLeading | Qt::AlignVCenter | Qt::TextSingleLine, text: d->tempItem); |
630 | } |
631 | } |
632 | |
633 | /*! |
634 | \reimp |
635 | */ |
636 | void QStatusBar::resizeEvent(QResizeEvent * e) |
637 | { |
638 | QWidget::resizeEvent(event: e); |
639 | } |
640 | |
641 | /*! |
642 | \reimp |
643 | */ |
644 | |
645 | bool QStatusBar::event(QEvent *e) |
646 | { |
647 | Q_D(QStatusBar); |
648 | |
649 | switch (e->type()) { |
650 | case QEvent::LayoutRequest: { |
651 | // Calculate new strut height and call reformat() if it has changed |
652 | int maxH = fontMetrics().height(); |
653 | |
654 | for (const auto &item : std::as_const(t&: d->items)) { |
655 | const int itemH = qMin(a: qSmartMinSize(w: item.widget).height(), b: item.widget->maximumHeight()); |
656 | maxH = qMax(a: maxH, b: itemH); |
657 | } |
658 | |
659 | #if QT_CONFIG(sizegrip) |
660 | if (d->resizer) |
661 | maxH = qMax(a: maxH, b: d->resizer->sizeHint().height()); |
662 | #endif |
663 | |
664 | if (maxH != d->savedStrut) |
665 | reformat(); |
666 | else |
667 | update(); |
668 | break; |
669 | } |
670 | case QEvent::ChildRemoved: |
671 | for (int i = 0; i < d->items.size(); ++i) { |
672 | const auto &item = d->items.at(i); |
673 | if (item.widget == static_cast<QChildEvent *>(e)->child()) |
674 | d->items.removeAt(i); |
675 | } |
676 | break; |
677 | default: |
678 | break; |
679 | } |
680 | |
681 | return QWidget::event(event: e); |
682 | } |
683 | |
684 | QT_END_NAMESPACE |
685 | |
686 | #include "moc_qstatusbar.cpp" |
687 | |