Qt
Internal/Contributor docs for the Qt SDK. Note: These are NOT official API docs; those are found at https://doc.qt.io/
Toggle main menu visibility
Loading...
Searching...
No Matches
qprogressbar.cpp
Go to the documentation of this file.
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
// Qt-Security score:significant reason:default
4
5
#
include
"qprogressbar.h"
6
7
#
include
<
qlocale
.
h
>
8
#
include
<
qevent
.
h
>
9
#
include
<
qpainter
.
h
>
10
#
include
<
qstylepainter
.
h
>
11
#
include
<
qstyleoption
.
h
>
12
#
include
<
private
/
qwidget_p
.
h
>
13
#
if
QT_CONFIG
(
accessibility
)
14
#
include
<
qaccessible
.
h
>
15
#
endif
16
#
include
<
limits
.
h
>
17
18
QT_BEGIN_NAMESPACE
19
20
using
namespace
Qt::StringLiterals;
21
22
class
QProgressBarPrivate
:
public
QWidgetPrivate
23
{
24
Q_DECLARE_PUBLIC(QProgressBar)
25
26
public
:
27
QProgressBarPrivate
();
28
29
void
init
();
30
void
initDefaultFormat
();
31
inline
void
resetLayoutItemMargins
();
32
33
int
minimum
;
34
int
maximum
;
35
int
value
;
36
Qt
::
Alignment
alignment
;
37
uint
textVisible
: 1;
38
uint
defaultFormat
: 1;
39
int
lastPaintedValue
;
40
Qt
::
Orientation
orientation
;
41
bool
invertedAppearance
;
42
QProgressBar
::
Direction
textDirection
;
43
QString
format
;
44
inline
int
bound
(
int
val)
const
{
return
qMax(
minimum
-1, qMin(
maximum
, val)); }
45
bool
repaintRequired
()
const
;
46
};
47
48
QProgressBarPrivate
::QProgressBarPrivate()
49
:
minimum
(0),
maximum
(100),
value
(-1), alignment(Qt::AlignLeft), textVisible(
true
),
50
defaultFormat(
true
),
lastPaintedValue
(-1), orientation(Qt::Horizontal),
invertedAppearance
(
false
),
51
textDirection(QProgressBar::TopToBottom)
52
{
53
initDefaultFormat
(
)
;
54
}
55
56
void
QProgressBarPrivate
::
initDefaultFormat
()
57
{
58
if
(defaultFormat) {
59
//: %p is the percent value, % is the percent sign. When translated
60
//: to the identical %p%, then the second % symbol will be replaced
61
//: by the percentage-symbol from the user's locale.
62
format = QProgressBar::tr(
"%p%"
);
63
}
64
65
if
(format ==
"%p%"_L1
)
66
format =
"%p"_L1
+ locale.percent();
67
}
68
69
void
QProgressBarPrivate
::
init
()
70
{
71
Q_Q(QProgressBar);
72
QSizePolicy sp(QSizePolicy::Expanding, QSizePolicy::Fixed);
73
if
(orientation == Qt::Vertical)
74
sp.transpose();
75
q->setSizePolicy(sp);
76
q->setAttribute(Qt::WA_WState_OwnSizePolicy,
false
);
77
resetLayoutItemMargins
(
)
;
78
}
79
80
void
QProgressBarPrivate
::
resetLayoutItemMargins
()
81
{
82
Q_Q(QProgressBar);
83
QStyleOptionProgressBar option;
84
// ### It seems like this can be called directly from the constructor which should be avoided
85
// ### if possible, since we will not call a possible re-implemented version
86
q->initStyleOption(&option);
87
setLayoutItemMargins(QStyle::SE_ProgressBarLayoutItem, &option);
88
}
89
90
/*!
91
Initialize \a option with the values from this QProgressBar. This method is useful
92
for subclasses when they need a QStyleOptionProgressBar,
93
but don't want to fill in all the information themselves.
94
95
\sa QStyleOption::initFrom()
96
*/
97
void
QProgressBar::initStyleOption(QStyleOptionProgressBar *option)
const
98
{
99
if
(!option)
100
return
;
101
Q_D(
const
QProgressBar);
102
option->initFrom(
this
);
103
104
if
(d->orientation == Qt::Horizontal)
105
option->state |= QStyle::State_Horizontal;
106
option->minimum = d->minimum;
107
option->maximum = d->maximum;
108
option->progress = d->value;
109
option->textAlignment = d->alignment;
110
option->textVisible = d->textVisible;
111
option->text = text();
112
option->invertedAppearance = d->invertedAppearance;
113
option->bottomToTop = d->textDirection == QProgressBar::BottomToTop;
114
}
115
116
bool
QProgressBarPrivate
::
repaintRequired
()
const
117
{
118
Q_Q(
const
QProgressBar);
119
if
(
value
==
lastPaintedValue
)
120
return
false
;
121
122
const
qint64 valueDifference = qAbs(qint64(
value
) - qint64(
lastPaintedValue
));
123
124
if
(
value
==
minimum
||
value
==
maximum
)
125
return
true
;
126
127
const
int
totalSteps =
maximum
-
minimum
;
128
129
const
int
currentPercentage = totalSteps ? (
value
-
minimum
) * 100 / totalSteps : 0;
130
const
int
lastPaintedPercentage = totalSteps ? (
lastPaintedValue
-
minimum
) * 100 / totalSteps
131
: 0;
132
133
const
int
percentageChangeConstant = 1;
134
const
bool
percentageChanged = (qAbs(currentPercentage - lastPaintedPercentage) >= percentageChangeConstant);
135
136
if
(textVisible) {
137
if
(format.contains(
"%v"_L1
))
138
return
true
;
139
if
(format.contains(
"%p"_L1
) && percentageChanged)
140
return
true
;
141
}
142
143
// Check if the bar needs to be repainted based on pixel-level differences
144
QStyleOptionProgressBar opt;
145
q->initStyleOption(&opt);
146
QRect groove = q->style()->subElementRect(QStyle::SE_ProgressBarGroove, &opt, q);
147
int
grooveBlock = (q->orientation() == Qt::Horizontal) ? groove.width() : groove.height();
148
const
double
pixelSize =
static_cast
<
double
>(totalSteps) / grooveBlock;
149
return
valueDifference > pixelSize;
150
}
151
152
/*!
153
\class QProgressBar
154
\brief The QProgressBar widget provides a horizontal or vertical progress bar.
155
156
\ingroup basicwidgets
157
\inmodule QtWidgets
158
159
\image fusion-progressbar.png {Progress bar showing 42%}
160
161
A progress bar is used to give the user an indication of the
162
progress of an operation and to reassure them that the application
163
is still running.
164
165
The progress bar uses the concept of \e steps. You set it up by
166
specifying the minimum and maximum possible step values, and it
167
will display the percentage of steps that have been completed
168
when you later give it the current step value. The percentage is
169
calculated by dividing the progress (value() - minimum()) divided
170
by maximum() - minimum().
171
172
You can specify the minimum and maximum number of steps with
173
setMinimum() and setMaximum. The current number of steps is set
174
with setValue(). The progress bar can be rewound to the
175
beginning with reset().
176
177
If minimum and maximum both are set to 0, the bar shows a busy
178
indicator instead of a percentage of steps. This is useful, for
179
example, when using QNetworkAccessManager to download items when
180
they are unable to determine the size of the item being downloaded.
181
182
\sa QProgressDialog
183
*/
184
185
/*!
186
\since 4.1
187
\enum QProgressBar::Direction
188
\brief Specifies the reading direction of the \l text for vertical progress bars.
189
190
\value TopToBottom The text is rotated 90 degrees clockwise.
191
\value BottomToTop The text is rotated 90 degrees counter-clockwise.
192
193
Note that whether or not the text is drawn is dependent on the style.
194
Currently CleanLooks and Plastique draw the text. Mac, Windows
195
and WindowsVista style do not.
196
197
\sa textDirection
198
*/
199
200
/*!
201
\fn void QProgressBar::valueChanged(int value)
202
203
This signal is emitted when the value shown in the progress bar changes.
204
\a value is the new value shown by the progress bar.
205
*/
206
207
/*!
208
Constructs a progress bar with the given \a parent.
209
210
By default, the minimum step value is set to 0, and the maximum to 100.
211
212
\sa setRange()
213
*/
214
215
QProgressBar::QProgressBar(QWidget *parent)
216
: QWidget(*(
new
QProgressBarPrivate), parent, { })
217
{
218
d_func()->init();
219
}
220
221
/*!
222
Destructor.
223
*/
224
QProgressBar::~QProgressBar()
225
{
226
}
227
228
/*!
229
Reset the progress bar. The progress bar "rewinds" and shows no
230
progress.
231
*/
232
233
void
QProgressBar::reset()
234
{
235
Q_D(QProgressBar);
236
if
(d->minimum == INT_MIN)
237
d->value = INT_MIN;
238
else
239
d->value = d->minimum - 1;
240
repaint();
241
}
242
243
/*!
244
\property QProgressBar::minimum
245
\brief the progress bar's minimum value
246
247
When setting this property, the \l maximum is adjusted if
248
necessary to ensure that the range remains valid. If the
249
current value falls outside the new range, the progress bar is reset
250
with reset().
251
*/
252
void
QProgressBar::setMinimum(
int
minimum)
253
{
254
setRange(minimum, qMax(d_func()->maximum, minimum));
255
}
256
257
int
QProgressBar::minimum()
const
258
{
259
return
d_func()->minimum;
260
}
261
262
263
/*!
264
\property QProgressBar::maximum
265
\brief the progress bar's maximum value
266
267
When setting this property, the \l minimum is adjusted if
268
necessary to ensure that the range remains valid. If the
269
current value falls outside the new range, the progress bar is reset
270
with reset().
271
*/
272
273
void
QProgressBar::setMaximum(
int
maximum)
274
{
275
setRange(qMin(d_func()->minimum, maximum), maximum);
276
}
277
278
int
QProgressBar::maximum()
const
279
{
280
return
d_func()->maximum;
281
}
282
283
/*!
284
\property QProgressBar::value
285
\brief the progress bar's current value
286
287
Attempting to change the current value to one outside
288
the minimum-maximum range has no effect on the current value.
289
*/
290
void
QProgressBar::setValue(
int
value)
291
{
292
Q_D(QProgressBar);
293
if
(d->value == value
294
|| ((value > d->maximum || value < d->minimum)
295
&& (d->maximum != 0 || d->minimum != 0)))
296
return
;
297
d->value = value;
298
emit valueChanged(value);
299
#
if
QT_CONFIG
(
accessibility
)
300
if
(isVisible()) {
301
QAccessibleValueChangeEvent event(
this
, value);
302
QAccessible::updateAccessibility(&event);
303
}
304
#
endif
305
if
(d->repaintRequired())
306
repaint();
307
}
308
309
int
QProgressBar::value()
const
310
{
311
return
d_func()->value;
312
}
313
314
/*!
315
Sets the progress bar's minimum and maximum values to \a minimum and
316
\a maximum respectively.
317
318
If \a maximum is smaller than \a minimum, \a minimum becomes the only
319
legal value.
320
321
If the current value falls outside the new range, the progress bar is reset
322
with reset().
323
324
The QProgressBar can be set to undetermined state by using setRange(0, 0).
325
326
\sa minimum, maximum
327
*/
328
void
QProgressBar::setRange(
int
minimum,
int
maximum)
329
{
330
Q_D(QProgressBar);
331
if
(minimum != d->minimum || maximum != d->maximum) {
332
d->minimum = minimum;
333
d->maximum = qMax(minimum, maximum);
334
335
if
(d->value < qint64(d->minimum) - 1 || d->value > d->maximum)
336
reset();
337
else
338
update();
339
}
340
}
341
342
/*!
343
\property QProgressBar::textVisible
344
\brief whether the current completed percentage should be displayed
345
346
This property may be ignored by the style (e.g., QMacStyle never draws the text).
347
348
\sa textDirection
349
*/
350
void
QProgressBar::setTextVisible(
bool
visible)
351
{
352
Q_D(QProgressBar);
353
if
(d->textVisible != visible) {
354
d->textVisible = visible;
355
repaint();
356
}
357
}
358
359
bool
QProgressBar::isTextVisible()
const
360
{
361
return
d_func()->textVisible;
362
}
363
364
/*!
365
\property QProgressBar::alignment
366
\brief the alignment of the progress bar
367
*/
368
void
QProgressBar::setAlignment(Qt::Alignment alignment)
369
{
370
if
(d_func()->alignment != alignment) {
371
d_func()->alignment = alignment;
372
repaint();
373
}
374
}
375
376
Qt::Alignment QProgressBar::alignment()
const
377
{
378
return
d_func()->alignment;
379
}
380
381
/*!
382
\reimp
383
*/
384
void
QProgressBar::paintEvent(QPaintEvent *)
385
{
386
QStylePainter paint(
this
);
387
QStyleOptionProgressBar opt;
388
initStyleOption(&opt);
389
paint.drawControl(QStyle::CE_ProgressBar, opt);
390
d_func()->lastPaintedValue = d_func()->value;
391
}
392
393
/*!
394
\reimp
395
*/
396
QSize QProgressBar::sizeHint()
const
397
{
398
ensurePolished();
399
QFontMetrics fm = fontMetrics();
400
QStyleOptionProgressBar opt;
401
initStyleOption(&opt);
402
int
cw = style()->pixelMetric(QStyle::PM_ProgressBarChunkWidth, &opt,
this
);
403
QSize size = QSize(qMax(9, cw) * 7 + fm.horizontalAdvance(u'0') * 4, fm.height() + 8);
404
if
(!(opt.state & QStyle::State_Horizontal))
405
size = size.transposed();
406
return
style()->sizeFromContents(QStyle::CT_ProgressBar, &opt, size,
this
);
407
}
408
409
/*!
410
\reimp
411
*/
412
QSize QProgressBar::minimumSizeHint()
const
413
{
414
QSize size;
415
if
(orientation() == Qt::Horizontal)
416
size = QSize(sizeHint().width(), fontMetrics().height() + 2);
417
else
418
size = QSize(fontMetrics().height() + 2, sizeHint().height());
419
return
size;
420
}
421
422
/*!
423
\property QProgressBar::text
424
\brief the descriptive text shown with the progress bar
425
426
The text returned is the same as the text displayed in the center
427
(or in some styles, to the left) of the progress bar.
428
429
The progress shown in the text may be smaller than the minimum value,
430
indicating that the progress bar is in the "reset" state before any
431
progress is set.
432
433
In the default implementation, the text either contains a percentage
434
value that indicates the progress so far, or it is blank because the
435
progress bar is in the reset state.
436
*/
437
QString QProgressBar::text()
const
438
{
439
Q_D(
const
QProgressBar);
440
if
((d->maximum == 0 && d->minimum == 0) || d->value < d->minimum
441
|| (d->value == INT_MIN && d->minimum == INT_MIN))
442
return
QString();
443
444
qint64 totalSteps = qint64(d->maximum) - d->minimum;
445
446
QString result = d->format;
447
QLocale locale = d->locale;
// Omit group separators for compatibility with previous versions that were non-localized.
448
locale.setNumberOptions(locale.numberOptions() | QLocale::OmitGroupSeparator);
449
result.replace(
"%m"_L1
, locale.toString(totalSteps));
450
result.replace(
"%v"_L1
, locale.toString(d->value));
451
452
// If max and min are equal and we get this far, it means that the
453
// progress bar has one step and that we are on that step. Return
454
// 100% here in order to avoid division by zero further down.
455
if
(totalSteps == 0) {
456
result.replace(
"%p"_L1
, locale.toString(100));
457
return
result;
458
}
459
460
const
auto
progress =
static_cast
<
int
>((qint64(d->value) - d->minimum) * 100.0 / totalSteps);
461
result.replace(
"%p"_L1
, locale.toString(progress));
462
return
result;
463
}
464
465
/*!
466
\since 4.1
467
\property QProgressBar::orientation
468
\brief the orientation of the progress bar
469
470
The orientation must be \l Qt::Horizontal (the default) or \l
471
Qt::Vertical.
472
473
\sa invertedAppearance, textDirection
474
*/
475
476
void
QProgressBar::setOrientation(Qt::Orientation orientation)
477
{
478
Q_D(QProgressBar);
479
if
(d->orientation == orientation)
480
return
;
481
d->orientation = orientation;
482
if
(!testAttribute(Qt::WA_WState_OwnSizePolicy)) {
483
setSizePolicy(sizePolicy().transposed());
484
setAttribute(Qt::WA_WState_OwnSizePolicy,
false
);
485
}
486
d->resetLayoutItemMargins();
487
update();
488
updateGeometry();
489
}
490
491
Qt::Orientation QProgressBar::orientation()
const
492
{
493
Q_D(
const
QProgressBar);
494
return
d->orientation;
495
}
496
497
/*!
498
\since 4.1
499
\property QProgressBar::invertedAppearance
500
\brief whether or not a progress bar shows its progress inverted
501
502
If this property is \c true, the progress bar grows in the other
503
direction (e.g. from right to left). By default, the progress bar
504
is not inverted.
505
506
\sa orientation, layoutDirection
507
*/
508
509
void
QProgressBar::setInvertedAppearance(
bool
invert)
510
{
511
Q_D(QProgressBar);
512
d->invertedAppearance = invert;
513
update();
514
}
515
516
bool
QProgressBar::invertedAppearance()
const
517
{
518
Q_D(
const
QProgressBar);
519
return
d->invertedAppearance;
520
}
521
522
/*!
523
\since 4.1
524
\property QProgressBar::textDirection
525
\brief the reading direction of the \l text for vertical progress bars
526
527
This property has no impact on horizontal progress bars.
528
By default, the reading direction is QProgressBar::TopToBottom.
529
530
\sa orientation, textVisible
531
*/
532
void
QProgressBar::setTextDirection(QProgressBar::Direction textDirection)
533
{
534
Q_D(QProgressBar);
535
d->textDirection = textDirection;
536
update();
537
}
538
539
QProgressBar::Direction QProgressBar::textDirection()
const
540
{
541
Q_D(
const
QProgressBar);
542
return
d->textDirection;
543
}
544
545
/*! \reimp */
546
bool
QProgressBar::event(QEvent *e)
547
{
548
Q_D(QProgressBar);
549
switch
(e->type()) {
550
case
QEvent::StyleChange:
551
#
ifdef
Q_OS_MACOS
552
case
QEvent::MacSizeChange:
553
#
endif
554
d->resetLayoutItemMargins();
555
break
;
556
case
QEvent::LocaleChange:
557
d->initDefaultFormat();
558
break
;
559
default
:
560
break
;
561
}
562
return
QWidget::event(e);
563
}
564
565
/*!
566
\since 4.2
567
\property QProgressBar::format
568
\brief the string used to generate the current text
569
570
%p - is replaced by the percentage completed.
571
%v - is replaced by the current value.
572
%m - is replaced by the total number of steps.
573
574
The default value is "%p%".
575
576
\sa text()
577
*/
578
void
QProgressBar::setFormat(
const
QString &format)
579
{
580
Q_D(QProgressBar);
581
if
(d->format == format)
582
return
;
583
d->format = format;
584
d->defaultFormat =
false
;
585
update();
586
}
587
588
void
QProgressBar::resetFormat()
589
{
590
Q_D(QProgressBar);
591
d->defaultFormat =
true
;
592
d->initDefaultFormat();
593
update();
594
}
595
596
QString QProgressBar::format()
const
597
{
598
Q_D(
const
QProgressBar);
599
return
d->format;
600
}
601
602
QT_END_NAMESPACE
603
604
#
include
"moc_qprogressbar.cpp"
QProgressBarPrivate
Definition
qprogressbar.cpp:23
QProgressBarPrivate::repaintRequired
bool repaintRequired() const
Definition
qprogressbar.cpp:116
QProgressBarPrivate::invertedAppearance
bool invertedAppearance
Definition
qprogressbar.cpp:41
QProgressBarPrivate::alignment
Qt::Alignment alignment
Definition
qprogressbar.cpp:36
QProgressBarPrivate::resetLayoutItemMargins
void resetLayoutItemMargins()
Definition
qprogressbar.cpp:80
QProgressBarPrivate::bound
int bound(int val) const
Definition
qprogressbar.cpp:44
QProgressBarPrivate::minimum
int minimum
Definition
qprogressbar.cpp:33
QProgressBarPrivate::textVisible
uint textVisible
Definition
qprogressbar.cpp:37
QProgressBarPrivate::orientation
Qt::Orientation orientation
Definition
qprogressbar.cpp:40
QProgressBarPrivate::defaultFormat
uint defaultFormat
Definition
qprogressbar.cpp:38
QProgressBarPrivate::value
int value
Definition
qprogressbar.cpp:35
QProgressBarPrivate::lastPaintedValue
int lastPaintedValue
Definition
qprogressbar.cpp:39
QProgressBarPrivate::maximum
int maximum
Definition
qprogressbar.cpp:34
QProgressBarPrivate::initDefaultFormat
void initDefaultFormat()
Definition
qprogressbar.cpp:56
QProgressBarPrivate::init
void init()
Definition
qprogressbar.cpp:69
QProgressBarPrivate::format
QString format
Definition
qprogressbar.cpp:43
QT_BEGIN_NAMESPACE
Combined button and popup list for selecting options.
Definition
qsequentialanimationgroup.cpp:47
qtbase
src
widgets
widgets
qprogressbar.cpp
Generated on
for Qt by
1.18.0