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 "qsizepolicy.h" |
5 | |
6 | #include <qdatastream.h> |
7 | #include <qdebug.h> |
8 | #include <qvariant.h> |
9 | |
10 | QT_BEGIN_NAMESPACE |
11 | |
12 | /*! |
13 | \class QSizePolicy |
14 | \brief The QSizePolicy class is a layout attribute describing horizontal |
15 | and vertical resizing policy. |
16 | |
17 | \ingroup geomanagement |
18 | \inmodule QtWidgets |
19 | |
20 | The size policy of a widget is an expression of its willingness to |
21 | be resized in various ways, and affects how the widget is treated |
22 | by the \l{Layout Management}{layout engine}. Each widget returns a |
23 | QSizePolicy that describes the horizontal and vertical resizing |
24 | policy it prefers when being laid out. You can change this for |
25 | a specific widget by changing its QWidget::sizePolicy property. |
26 | |
27 | QSizePolicy contains two independent QSizePolicy::Policy values |
28 | and two stretch factors; one describes the widgets's horizontal |
29 | size policy, and the other describes its vertical size policy. It |
30 | also contains a flag to indicate whether the height and width of |
31 | its preferred size are related. |
32 | |
33 | The horizontal and vertical policies can be set in the |
34 | constructor, and altered using the setHorizontalPolicy() and |
35 | setVerticalPolicy() functions. The stretch factors can be set |
36 | using the setHorizontalStretch() and setVerticalStretch() |
37 | functions. The flag indicating whether the widget's |
38 | \l{QWidget::sizeHint()}{sizeHint()} is width-dependent (such as a |
39 | menu bar or a word-wrapping label) can be set using the |
40 | setHeightForWidth() function. |
41 | |
42 | The current size policies and stretch factors be retrieved using |
43 | the horizontalPolicy(), verticalPolicy(), horizontalStretch() and |
44 | verticalStretch() functions. Alternatively, use the transpose() |
45 | function to swap the horizontal and vertical policies and |
46 | stretches. The hasHeightForWidth() function returns the current |
47 | status of the flag indicating the size hint dependencies. |
48 | |
49 | Use the expandingDirections() function to determine whether the |
50 | associated widget can make use of more space than its |
51 | \l{QWidget::sizeHint()}{sizeHint()} function indicates, as well as |
52 | find out in which directions it can expand. |
53 | |
54 | Finally, the QSizePolicy class provides operators comparing this |
55 | size policy to a given policy, as well as a QVariant operator |
56 | storing this QSizePolicy as a QVariant object. |
57 | |
58 | \sa QSize, QWidget::sizeHint(), QWidget::sizePolicy, |
59 | QLayoutItem::sizeHint() |
60 | */ |
61 | |
62 | /*! |
63 | \enum QSizePolicy::PolicyFlag |
64 | |
65 | These flags are combined together to form the various \l{Policy} |
66 | values: |
67 | |
68 | \value GrowFlag The widget can grow beyond its size hint if necessary. |
69 | \value ExpandFlag The widget should get as much space as possible. |
70 | \value ShrinkFlag The widget can shrink below its size hint if necessary. |
71 | \value IgnoreFlag The widget's size hint is ignored. The widget will get |
72 | as much space as possible. |
73 | |
74 | \sa Policy |
75 | */ |
76 | |
77 | /*! |
78 | \enum QSizePolicy::Policy |
79 | |
80 | This enum describes the various per-dimension sizing types used |
81 | when constructing a QSizePolicy. |
82 | |
83 | \value Fixed The QWidget::sizeHint() is the only acceptable |
84 | alternative, so the widget can never grow or shrink (e.g. the |
85 | vertical direction of a push button). |
86 | |
87 | \value Minimum The sizeHint() is minimal, and sufficient. The |
88 | widget can be expanded, but there is no advantage to it being |
89 | larger (e.g. the horizontal direction of a push button). |
90 | It cannot be smaller than the size provided by sizeHint(). |
91 | |
92 | \value Maximum The sizeHint() is a maximum. The widget can be |
93 | shrunk any amount without detriment if other widgets need the |
94 | space (e.g. a separator line). |
95 | It cannot be larger than the size provided by sizeHint(). |
96 | |
97 | \value Preferred The sizeHint() is best, but the widget can be |
98 | shrunk and still be useful. The widget can be expanded, but there |
99 | is no advantage to it being larger than sizeHint() (the default |
100 | QWidget policy). |
101 | |
102 | \value Expanding The sizeHint() is a sensible size, but the |
103 | widget can be shrunk and still be useful. The widget can make use |
104 | of extra space, so it should get as much space as possible (e.g. |
105 | the horizontal direction of a horizontal slider). |
106 | |
107 | \value MinimumExpanding The sizeHint() is minimal, and sufficient. |
108 | The widget can make use of extra space, so it should get as much |
109 | space as possible (e.g. the horizontal direction of a horizontal |
110 | slider). |
111 | |
112 | \value Ignored The sizeHint() is ignored. The widget will get as |
113 | much space as possible. |
114 | |
115 | \sa PolicyFlag, setHorizontalPolicy(), setVerticalPolicy() |
116 | */ |
117 | |
118 | /*! |
119 | \fn QSizePolicy::QSizePolicy() |
120 | |
121 | Constructs a QSizePolicy object with \l Fixed as its horizontal |
122 | and vertical policies. |
123 | |
124 | The policies can be altered using the setHorizontalPolicy() and |
125 | setVerticalPolicy() functions. Use the setHeightForWidth() |
126 | function if the preferred height of the widget is dependent on the |
127 | width of the widget (for example, a QLabel with line wrapping). |
128 | |
129 | \sa setHorizontalStretch(), setVerticalStretch() |
130 | */ |
131 | |
132 | /*! |
133 | \fn QSizePolicy::QSizePolicy(Policy horizontal, Policy vertical, ControlType type) |
134 | \since 4.3 |
135 | |
136 | Constructs a QSizePolicy object with the given \a horizontal and |
137 | \a vertical policies, and the specified control \a type. |
138 | |
139 | Use setHeightForWidth() if the preferred height of the widget is |
140 | dependent on the width of the widget (for example, a QLabel with |
141 | line wrapping). |
142 | |
143 | \sa setHorizontalStretch(), setVerticalStretch(), controlType() |
144 | */ |
145 | |
146 | /*! |
147 | \fn QSizePolicy::Policy QSizePolicy::horizontalPolicy() const |
148 | |
149 | Returns the horizontal component of the size policy. |
150 | |
151 | \sa setHorizontalPolicy(), verticalPolicy(), horizontalStretch() |
152 | */ |
153 | |
154 | /*! |
155 | \fn QSizePolicy::Policy QSizePolicy::verticalPolicy() const |
156 | |
157 | Returns the vertical component of the size policy. |
158 | |
159 | \sa setVerticalPolicy(), horizontalPolicy(), verticalStretch() |
160 | */ |
161 | |
162 | /*! |
163 | \fn void QSizePolicy::setHorizontalPolicy(Policy policy) |
164 | |
165 | Sets the horizontal component to the given \a policy. |
166 | |
167 | \sa horizontalPolicy(), setVerticalPolicy(), setHorizontalStretch() |
168 | */ |
169 | |
170 | /*! |
171 | \fn void QSizePolicy::setVerticalPolicy(Policy policy) |
172 | |
173 | Sets the vertical component to the given \a policy. |
174 | |
175 | \sa verticalPolicy(), setHorizontalPolicy(), setVerticalStretch() |
176 | */ |
177 | |
178 | /*! |
179 | \fn Qt::Orientations QSizePolicy::expandingDirections() const |
180 | |
181 | Returns whether a widget can make use of more space than the |
182 | QWidget::sizeHint() function indicates. |
183 | |
184 | A value of Qt::Horizontal or Qt::Vertical means that the widget |
185 | can grow horizontally or vertically (i.e., the horizontal or |
186 | vertical policy is \l Expanding or \l MinimumExpanding), whereas |
187 | Qt::Horizontal | Qt::Vertical means that it can grow in both |
188 | dimensions. |
189 | |
190 | \sa horizontalPolicy(), verticalPolicy() |
191 | */ |
192 | |
193 | /*! |
194 | \since 4.3 |
195 | |
196 | Returns the control type associated with the widget for which |
197 | this size policy applies. |
198 | */ |
199 | QSizePolicy::ControlType QSizePolicy::controlType() const noexcept |
200 | { |
201 | return QSizePolicy::ControlType(1 << bits.ctype); |
202 | } |
203 | |
204 | |
205 | /*! |
206 | \since 4.3 |
207 | |
208 | Sets the control type associated with the widget for which this |
209 | size policy applies to \a type. |
210 | |
211 | The control type specifies the type of the widget for which this |
212 | size policy applies. It is used by some styles, notably |
213 | QMacStyle, to insert proper spacing between widgets. For example, |
214 | the \macos Aqua guidelines specify that push buttons should be |
215 | separated by 12 pixels, whereas vertically stacked radio buttons |
216 | only require 6 pixels. |
217 | |
218 | \sa QStyle::layoutSpacing() |
219 | */ |
220 | void QSizePolicy::setControlType(ControlType type) noexcept |
221 | { |
222 | bits.ctype = toControlTypeFieldValue(type); |
223 | } |
224 | |
225 | /*! |
226 | \fn void QSizePolicy::setHeightForWidth(bool dependent) |
227 | |
228 | Sets the flag determining whether the widget's preferred height |
229 | depends on its width, to \a dependent. |
230 | |
231 | \sa hasHeightForWidth(), setWidthForHeight() |
232 | */ |
233 | |
234 | /*! |
235 | \fn bool QSizePolicy::hasHeightForWidth() const |
236 | |
237 | Returns \c true if the widget's preferred height depends on its |
238 | width; otherwise returns \c false. |
239 | |
240 | \sa setHeightForWidth() |
241 | */ |
242 | |
243 | /*! |
244 | \fn void QSizePolicy::setWidthForHeight(bool dependent) |
245 | |
246 | Sets the flag determining whether the widget's width |
247 | depends on its height, to \a dependent. |
248 | |
249 | This is only supported for QGraphicsLayout's subclasses. |
250 | It is not possible to have a layout with both height-for-width |
251 | and width-for-height constraints at the same time. |
252 | |
253 | \sa hasWidthForHeight(), setHeightForWidth() |
254 | */ |
255 | |
256 | /*! |
257 | \fn bool QSizePolicy::hasWidthForHeight() const |
258 | |
259 | Returns \c true if the widget's width depends on its |
260 | height; otherwise returns \c false. |
261 | |
262 | \sa setWidthForHeight() |
263 | */ |
264 | |
265 | /*! |
266 | \fn bool QSizePolicy::operator==(const QSizePolicy &other) const |
267 | |
268 | Returns \c true if this policy is equal to \a other; otherwise |
269 | returns \c false. |
270 | |
271 | \sa operator!=() |
272 | */ |
273 | |
274 | /*! |
275 | \fn bool QSizePolicy::operator!=(const QSizePolicy &other) const |
276 | |
277 | Returns \c true if this policy is different from \a other; otherwise |
278 | returns \c false. |
279 | |
280 | \sa operator==() |
281 | */ |
282 | |
283 | /*! |
284 | \fn size_t QSizePolicy::qHash(QSizePolicy key, size_t seed = 0) |
285 | \since 5.6 |
286 | |
287 | Returns the hash value for \a key, using |
288 | \a seed to seed the calculation. |
289 | */ |
290 | |
291 | /*! |
292 | \fn int QSizePolicy::horizontalStretch() const |
293 | |
294 | Returns the horizontal stretch factor of the size policy. |
295 | |
296 | \sa setHorizontalStretch(), verticalStretch(), horizontalPolicy() |
297 | */ |
298 | |
299 | /*! |
300 | \fn int QSizePolicy::verticalStretch() const |
301 | |
302 | Returns the vertical stretch factor of the size policy. |
303 | |
304 | \sa setVerticalStretch(), horizontalStretch(), verticalPolicy() |
305 | */ |
306 | |
307 | /*! |
308 | \fn void QSizePolicy::setHorizontalStretch(int stretchFactor) |
309 | |
310 | Sets the horizontal stretch factor of the size policy to the given \a |
311 | stretchFactor. \a stretchFactor must be in the range [0,255]. |
312 | |
313 | When two widgets are adjacent to each other in a horizontal layout, |
314 | setting the horizontal stretch factor of the widget on the left to 2 |
315 | and the factor of widget on the right to 1 will ensure that the widget |
316 | on the left will always be twice the size of the one on the right. |
317 | |
318 | \sa horizontalStretch(), setVerticalStretch(), setHorizontalPolicy() |
319 | */ |
320 | |
321 | /*! |
322 | \fn void QSizePolicy::setVerticalStretch(int stretchFactor) |
323 | |
324 | Sets the vertical stretch factor of the size policy to the given |
325 | \a stretchFactor. \a stretchFactor must be in the range [0,255]. |
326 | |
327 | When two widgets are adjacent to each other in a vertical layout, |
328 | setting the vertical stretch factor of the widget on the top to 2 |
329 | and the factor of widget on the bottom to 1 will ensure that |
330 | the widget on the top will always be twice the size of the one |
331 | on the bottom. |
332 | |
333 | \sa verticalStretch(), setHorizontalStretch(), setVerticalPolicy() |
334 | */ |
335 | |
336 | /*! |
337 | \fn void QSizePolicy::transpose() |
338 | |
339 | Swaps the horizontal and vertical policies and stretches. |
340 | |
341 | \sa transposed() |
342 | */ |
343 | |
344 | /*! |
345 | \fn QSizePolicy QSizePolicy::transposed() const |
346 | \since 5.9 |
347 | |
348 | Returns a size policy object with the horizontal and vertical |
349 | policies and stretches swapped. |
350 | |
351 | \sa transpose() |
352 | */ |
353 | |
354 | /*! |
355 | \fn void QSizePolicy::retainSizeWhenHidden() const |
356 | \since 5.2 |
357 | |
358 | Returns whether the layout should retain the widget's size when it is hidden. |
359 | This is \c false by default. |
360 | |
361 | \sa setRetainSizeWhenHidden() |
362 | */ |
363 | |
364 | /*! |
365 | \fn void QSizePolicy::setRetainSizeWhenHidden(bool retainSize) |
366 | \since 5.2 |
367 | |
368 | Sets whether a layout should retain the widget's size when it is hidden. |
369 | If \a retainSize is \c true, the layout will not be changed by hiding the widget. |
370 | |
371 | \sa retainSizeWhenHidden() |
372 | */ |
373 | |
374 | /*! |
375 | \enum QSizePolicy::ControlType |
376 | \since 4.3 |
377 | |
378 | This enum specifies the different types of widgets in terms of |
379 | layout interaction: |
380 | |
381 | \value DefaultType The default type, when none is specified. |
382 | \value ButtonBox A QDialogButtonBox instance. |
383 | \value CheckBox A QCheckBox instance. |
384 | \value ComboBox A QComboBox instance. |
385 | \value Frame A QFrame instance. |
386 | \value GroupBox A QGroupBox instance. |
387 | \value Label A QLabel instance. |
388 | \value Line A QFrame instance with QFrame::HLine or QFrame::VLine. |
389 | \value LineEdit A QLineEdit instance. |
390 | \value PushButton A QPushButton instance. |
391 | \value RadioButton A QRadioButton instance. |
392 | \value Slider A QAbstractSlider instance. |
393 | \value SpinBox A QAbstractSpinBox instance. |
394 | \value TabWidget A QTabWidget instance. |
395 | \value ToolButton A QToolButton instance. |
396 | |
397 | \sa setControlType(), controlType() |
398 | */ |
399 | |
400 | /*! |
401 | Returns a QVariant storing this QSizePolicy. |
402 | */ |
403 | QSizePolicy::operator QVariant() const |
404 | { |
405 | return QVariant::fromValue(value: *this); |
406 | } |
407 | |
408 | #ifndef QT_NO_DATASTREAM |
409 | |
410 | /*! |
411 | \relates QSizePolicy |
412 | \since 4.2 |
413 | |
414 | Writes the size \a policy to the data stream \a stream. |
415 | |
416 | \sa{Serializing Qt Data Types}{Format of the QDataStream operators} |
417 | */ |
418 | QDataStream &operator<<(QDataStream &stream, const QSizePolicy &policy) |
419 | { |
420 | // The order here is for historical reasons. (compatibility with Qt4) |
421 | quint32 data = (policy.bits.horPolicy | // [0, 3] |
422 | policy.bits.verPolicy << 4 | // [4, 7] |
423 | policy.bits.hfw << 8 | // [8] |
424 | policy.bits.ctype << 9 | // [9, 13] |
425 | policy.bits.wfh << 14 | // [14] |
426 | policy.bits.retainSizeWhenHidden << 15 | // [15] |
427 | policy.bits.verStretch << 16 | // [16, 23] |
428 | policy.bits.horStretch << 24); // [24, 31] |
429 | return stream << data; |
430 | } |
431 | |
432 | #define VALUE_OF_BITS(data, bitstart, bitcount) ((data >> bitstart) & ((1 << bitcount) -1)) |
433 | |
434 | /*! |
435 | \relates QSizePolicy |
436 | \since 4.2 |
437 | |
438 | Reads the size \a policy from the data stream \a stream. |
439 | |
440 | \sa{Serializing Qt Data Types}{Format of the QDataStream operators} |
441 | */ |
442 | QDataStream &operator>>(QDataStream &stream, QSizePolicy &policy) |
443 | { |
444 | quint32 data; |
445 | stream >> data; |
446 | policy.bits.horPolicy = VALUE_OF_BITS(data, 0, 4); |
447 | policy.bits.verPolicy = VALUE_OF_BITS(data, 4, 4); |
448 | policy.bits.hfw = VALUE_OF_BITS(data, 8, 1); |
449 | policy.bits.ctype = VALUE_OF_BITS(data, 9, 5); |
450 | policy.bits.wfh = VALUE_OF_BITS(data, 14, 1); |
451 | policy.bits.retainSizeWhenHidden = VALUE_OF_BITS(data, 15, 1); |
452 | policy.bits.verStretch = VALUE_OF_BITS(data, 16, 8); |
453 | policy.bits.horStretch = VALUE_OF_BITS(data, 24, 8); |
454 | return stream; |
455 | } |
456 | #endif // QT_NO_DATASTREAM |
457 | |
458 | #ifndef QT_NO_DEBUG_STREAM |
459 | QDebug operator<<(QDebug dbg, const QSizePolicy &p) |
460 | { |
461 | QDebugStateSaver saver(dbg); |
462 | dbg.nospace() << "QSizePolicy(horizontalPolicy = " << p.horizontalPolicy() |
463 | << ", verticalPolicy = " << p.verticalPolicy() << ')'; |
464 | return dbg; |
465 | } |
466 | #endif |
467 | |
468 | QT_END_NAMESPACE |
469 | |
470 | #include "moc_qsizepolicy.cpp" |
471 | |