Qt
Internal/Contributor docs for the Qt SDK. Note: These are NOT official API docs; those are found at https://doc.qt.io/
Loading...
Searching...
No Matches
qmetasequence.cpp
Go to the documentation of this file.
1// Copyright (C) 2025 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
5#include "qmetatype.h"
6
8
9/*!
10 \class QMetaSequence
11 \inmodule QtCore
12 \since 6.0
13 \brief The QMetaSequence class allows type erased access to sequential containers.
14
15 \ingroup objectmodel
16
17 \compares equality
18
19 The class provides a number of primitive container operations, using void*
20 as operands. This way, you can manipulate a generic container retrieved from
21 a Variant without knowing its type.
22
23 The void* arguments to the various methods are typically created by using
24 a \l QVariant of the respective container or value type, and calling
25 its \l QVariant::data() or \l QVariant::constData() methods. However, you
26 can also pass plain pointers to objects of the container or value type.
27
28 Iterator invalidation follows the rules given by the underlying containers
29 and is not expressed in the API. Therefore, for a truly generic container,
30 any iterators should be considered invalid after any write operation.
31*/
32
33/*!
34 \fn template<typename C> QMetaSequence QMetaSequence::fromContainer()
35 \since 6.0
36
37 Returns the QMetaSequence corresponding to the type given as template parameter.
38*/
39
40/*!
41 Returns the meta type for values stored in the container.
42 */
43QMetaType QMetaSequence::valueMetaType() const
44{
45 if (auto iface = d())
46 return QMetaType(iface->valueMetaType);
47 return QMetaType();
48}
49
50/*!
51 Returns \c true if the underlying container is sortable, otherwise returns
52 \c false. A container is considered sortable if values added to it are
53 placed in a defined location. Inserting into or adding to a sortable
54 container will always succeed. Inserting into or adding to an unsortable
55 container may not succeed, for example if the container is a QSet that
56 already contains the value being inserted.
57
58 \sa addValue(), insertValueAtIterator(), canAddValueAtBegin(),
59 canAddValueAtEnd(), canRemoveValueAtBegin(), canRemoveValueAtEnd()
60 */
61bool QMetaSequence::isSortable() const
62{
63 if (auto iface = d()) {
64 return (iface->addRemoveCapabilities
65 & (QtMetaContainerPrivate::CanAddAtBegin | QtMetaContainerPrivate::CanAddAtEnd))
66 && (iface->addRemoveCapabilities
67 & (QtMetaContainerPrivate::CanRemoveAtBegin
68 | QtMetaContainerPrivate::CanRemoveAtEnd));
69 }
70 return false;
71}
72
73/*!
74 Returns \c true if values added using \l addValue() can be placed at the
75 beginning of the container, otherwise returns \c false.
76
77 \sa addValueAtBegin(), canAddValueAtEnd()
78 */
79bool QMetaSequence::canAddValueAtBegin() const
80{
81 if (auto iface = d()) {
82 return iface->addValueFn
83 && iface->addRemoveCapabilities & QtMetaContainerPrivate::CanAddAtBegin;
84 }
85 return false;
86}
87
88/*!
89 Adds \a value to the beginning of \a container if possible. If
90 \l canAddValueAtBegin() returns \c false, the \a value is not added.
91
92 \sa canAddValueAtBegin(), isSortable(), removeValueAtBegin()
93 */
94void QMetaSequence::addValueAtBegin(void *container, const void *value) const
95{
96 if (canAddValueAtBegin())
97 d()->addValueFn(container, value, QtMetaContainerPrivate::QMetaSequenceInterface::AtBegin);
98}
99
100/*!
101 Returns \c true if values can be removed from the beginning of the container
102 using \l removeValue(), otherwise returns \c false.
103
104 \sa removeValueAtBegin(), canRemoveValueAtEnd()
105 */
106bool QMetaSequence::canRemoveValueAtBegin() const
107{
108 if (auto iface = d()) {
109 return iface->removeValueFn
110 && iface->addRemoveCapabilities & QtMetaContainerPrivate::CanRemoveAtBegin;
111 }
112 return false;
113}
114
115/*!
116 Removes a value from the beginning of \a container if possible. If
117 \l canRemoveValueAtBegin() returns \c false, the value is not removed.
118
119 \sa canRemoveValueAtBegin(), isSortable(), addValueAtBegin()
120 */
121void QMetaSequence::removeValueAtBegin(void *container) const
122{
123 if (canRemoveValueAtBegin())
124 d()->removeValueFn(container, QtMetaContainerPrivate::QMetaSequenceInterface::AtBegin);
125}
126
127/*!
128 Returns \c true if values added using \l addValue() can be placed at the
129 end of the container, otherwise returns \c false.
130
131 \sa addValueAtEnd(), canAddValueAtBegin()
132 */
133bool QMetaSequence::canAddValueAtEnd() const
134{
135 if (auto iface = d()) {
136 return iface->addValueFn
137 && iface->addRemoveCapabilities & QtMetaContainerPrivate::CanAddAtEnd;
138 }
139 return false;
140}
141
142/*!
143 Adds \a value to the end of \a container if possible. If
144 \l canAddValueAtEnd() returns \c false, the \a value is not added.
145
146 \sa canAddValueAtEnd(), isSortable(), removeValueAtEnd()
147 */
148void QMetaSequence::addValueAtEnd(void *container, const void *value) const
149{
150 if (canAddValueAtEnd())
151 d()->addValueFn(container, value, QtMetaContainerPrivate::QMetaSequenceInterface::AtEnd);
152}
153
154/*!
155 Returns \c true if values can be removed from the end of the container
156 using \l removeValue(), otherwise returns \c false.
157
158 \sa removeValueAtEnd(), canRemoveValueAtBegin()
159 */
160bool QMetaSequence::canRemoveValueAtEnd() const
161{
162 if (auto iface = d()) {
163 return iface->removeValueFn
164 && iface->addRemoveCapabilities & QtMetaContainerPrivate::CanRemoveAtEnd;
165 }
166 return false;
167}
168
169/*!
170 Removes a value from the end of \a container if possible. If
171 \l canRemoveValueAtEnd() returns \c false, the value is not removed.
172
173 \sa canRemoveValueAtEnd(), isSortable(), addValueAtEnd()
174 */
175void QMetaSequence::removeValueAtEnd(void *container) const
176{
177 if (canRemoveValueAtEnd())
178 d()->removeValueFn(container, QtMetaContainerPrivate::QMetaSequenceInterface::AtEnd);
179}
180
181/*!
182 Returns \c true if values can be retrieved from the container by index,
183 otherwise \c false.
184
185 \sa valueAtIndex()
186 */
187bool QMetaSequence::canGetValueAtIndex() const
188{
189 if (auto iface = d())
190 return iface->valueAtIndexFn;
191 return false;
192}
193
194/*!
195 Retrieves the value at \a index in the \a container and places it in the
196 memory location pointed to by \a result, if that is possible.
197
198 \sa canGetValueAtIndex()
199 */
200void QMetaSequence::valueAtIndex(const void *container, qsizetype index, void *result) const
201{
202 if (canGetValueAtIndex())
203 d()->valueAtIndexFn(container, index, result);
204}
205
206/*!
207 Returns \c true if a value can be written to the container by index,
208 otherwise \c false.
209
210 \sa setValueAtIndex()
211*/
212bool QMetaSequence::canSetValueAtIndex() const
213{
214 if (auto iface = d())
215 return iface->setValueAtIndexFn;
216 return false;
217}
218
219/*!
220 Overwrites the value at \a index in the \a container using the \a value
221 passed as parameter if that is possible.
222
223 \sa canSetValueAtIndex()
224 */
225void QMetaSequence::setValueAtIndex(void *container, qsizetype index, const void *value) const
226{
227 if (canSetValueAtIndex())
228 d()->setValueAtIndexFn(container, index, value);
229}
230
231/*!
232 Returns \c true if values can be added to the container, \c false
233 otherwise.
234
235 \sa addValue(), isSortable()
236 */
237bool QMetaSequence::canAddValue() const
238{
239 if (auto iface = d())
240 return iface->addValueFn;
241 return false;
242}
243
244/*!
245 Adds \a value to the \a container if possible. If \l canAddValue()
246 returns \c false, the \a value is not added. Else, if
247 \l canAddValueAtEnd() returns \c true, the \a value is added
248 to the end of the \a container. Else, if
249 \l canAddValueAtBegin() returns \c true, the \a value is added to
250 the beginning of the container. Else, the value is added in an unspecified
251 place or not at all. The latter is the case for adding values to an
252 unordered container, for example \l QSet.
253
254 \sa canAddValue(), canAddValueAtBegin(),
255 canAddValueAtEnd(), isSortable(), removeValue()
256 */
257void QMetaSequence::addValue(void *container, const void *value) const
258{
259 if (canAddValue()) {
260 d()->addValueFn(container, value,
261 QtMetaContainerPrivate::QMetaSequenceInterface::Unspecified);
262 }
263}
264
265/*!
266 Returns \c true if values can be removed from the container, \c false
267 otherwise.
268
269 \sa removeValue(), isSortable()
270 */
271bool QMetaSequence::canRemoveValue() const
272{
273 if (auto iface = d())
274 return iface->removeValueFn;
275 return false;
276}
277
278/*!
279 Removes a value from the \a container if possible. If
280 \l canRemoveValue() returns \c false, no value is removed. Else, if
281 \l canRemoveValueAtEnd() returns \c true, the last value in
282 the \a container is removed. Else, if \l canRemoveValueAtBegin()
283 returns \c true, the first value in the \a container is removed. Else,
284 an unspecified value or nothing is removed.
285
286 \sa canRemoveValue(), canRemoveValueAtBegin(),
287 canRemoveValueAtEnd(), isSortable(), addValue()
288 */
289void QMetaSequence::removeValue(void *container) const
290{
291 if (canRemoveValue()) {
292 d()->removeValueFn(container,
293 QtMetaContainerPrivate::QMetaSequenceInterface::Unspecified);
294 }
295}
296
297
298/*!
299 Returns \c true if the underlying container can retrieve the value pointed
300 to by a non-const iterator, \c false otherwise.
301
302 \sa hasIterator(), valueAtIterator()
303 */
304bool QMetaSequence::canGetValueAtIterator() const
305{
306 if (auto iface = d())
307 return iface->valueAtIteratorFn;
308 return false;
309}
310
311/*!
312 Retrieves the value pointed to by the non-const \a iterator and stores it
313 in the memory location pointed to by \a result, if possible.
314
315 \sa canGetValueAtIterator(), begin(), end()
316 */
317void QMetaSequence::valueAtIterator(const void *iterator, void *result) const
318{
319 if (canGetValueAtIterator())
320 d()->valueAtIteratorFn(iterator, result);
321}
322
323/*!
324 Returns \c true if the underlying container can write to the value pointed
325 to by a non-const iterator, \c false otherwise.
326
327 \sa hasIterator(), setValueAtIterator()
328 */
329bool QMetaSequence::canSetValueAtIterator() const
330{
331 if (auto iface = d())
332 return iface->setValueAtIteratorFn;
333 return false;
334}
335
336/*!
337 Writes \a value to the value pointed to by the non-const \a iterator, if
338 possible.
339
340 \sa canSetValueAtIterator(), begin(), end()
341 */
342void QMetaSequence::setValueAtIterator(const void *iterator, const void *value) const
343{
344 if (canSetValueAtIterator())
345 d()->setValueAtIteratorFn(iterator, value);
346}
347
348/*!
349 Returns \c true if the underlying container can insert a new value, taking
350 the location pointed to by a non-const iterator into account.
351
352 \sa hasIterator(), insertValueAtIterator()
353 */
354bool QMetaSequence::canInsertValueAtIterator() const
355{
356 if (auto iface = d())
357 return iface->insertValueAtIteratorFn;
358 return false;
359}
360
361/*!
362 Inserts \a value into the \a container, if possible, taking the non-const
363 \a iterator into account. If \l canInsertValueAtIterator() returns
364 \c false, the \a value is not inserted. Else if \l isSortable() returns
365 \c true, the value is inserted before the value pointed to by
366 \a iterator. Else, the \a value is inserted at an unspecified place or not
367 at all. In the latter case, the \a iterator is taken as a hint. If it points
368 to the correct place for the \a value, the operation may be faster than a
369 \l addValue() without iterator.
370
371 \sa canInsertValueAtIterator(), isSortable(), begin(), end()
372 */
373void QMetaSequence::insertValueAtIterator(void *container, const void *iterator,
374 const void *value) const
375{
376 if (canInsertValueAtIterator())
377 d()->insertValueAtIteratorFn(container, iterator, value);
378}
379
380/*!
381 Returns \c true if the value pointed to by a non-const iterator can be
382 erased, \c false otherwise.
383
384 \sa hasIterator(), eraseValueAtIterator()
385 */
386bool QMetaSequence::canEraseValueAtIterator() const
387{
388 if (auto iface = d())
389 return iface->eraseValueAtIteratorFn;
390 return false;
391}
392
393/*!
394 Erases the value pointed to by the non-const \a iterator from the
395 \a container, if possible.
396
397 \sa canEraseValueAtIterator(), begin(), end()
398 */
399void QMetaSequence::eraseValueAtIterator(void *container, const void *iterator) const
400{
401 if (canEraseValueAtIterator())
402 d()->eraseValueAtIteratorFn(container, iterator);
403}
404
405/*!
406 Returns \c true if a range between two iterators can be erased from the
407 container, \c false otherwise.
408 */
409bool QMetaSequence::canEraseRangeAtIterator() const
410{
411 if (auto iface = d())
412 return iface->eraseRangeAtIteratorFn;
413 return false;
414}
415
416/*!
417 Erases the range of values between the iterators \a iterator1 and
418 \a iterator2 from the \a container, if possible.
419
420 \sa canEraseValueAtIterator(), begin(), end()
421 */
422void QMetaSequence::eraseRangeAtIterator(void *container, const void *iterator1,
423 const void *iterator2) const
424{
425 if (canEraseRangeAtIterator())
426 d()->eraseRangeAtIteratorFn(container, iterator1, iterator2);
427}
428
429
430/*!
431 Returns \c true if the underlying container can retrieve the value pointed
432 to by a const iterator, \c false otherwise.
433
434 \sa hasConstIterator(), valueAtConstIterator()
435 */
436bool QMetaSequence::canGetValueAtConstIterator() const
437{
438 if (auto iface = d())
439 return iface->valueAtConstIteratorFn;
440 return false;
441}
442
443/*!
444 Retrieves the value pointed to by the const \a iterator and stores it
445 in the memory location pointed to by \a result, if possible.
446
447 \sa canGetValueAtConstIterator(), constBegin(), constEnd()
448 */
449void QMetaSequence::valueAtConstIterator(const void *iterator, void *result) const
450{
451 if (canGetValueAtConstIterator())
452 d()->valueAtConstIteratorFn(iterator, result);
453}
454
455/*!
456 \fn bool QMetaSequence::operator==(const QMetaSequence &lhs, const QMetaSequence &rhs)
457 \since 6.0
458
459 Returns \c true if the QMetaSequence \a lhs represents the same container type
460 as the QMetaSequence \a rhs, otherwise returns \c false.
461*/
462
463/*!
464 \fn bool QMetaSequence::operator!=(const QMetaSequence &lhs, const QMetaSequence &rhs)
465 \since 6.0
466
467 Returns \c true if the QMetaSequence \a lhs represents a different container
468 type than the QMetaSequence \a rhs, otherwise returns \c false.
469*/
470
471QT_END_NAMESPACE
Combined button and popup list for selecting options.