swift
Loading...
Searching...
No Matches
variant.cpp
1// SPDX-FileCopyrightText: Copyright (C) 2013 swift Project Community / Contributors
2// SPDX-License-Identifier: GPL-3.0-or-later OR LicenseRef-swift-pilot-client-1
3
5
6#include "misc/variant.h"
7
8#include <QDBusArgument>
9#include <QDBusVariant>
10#include <QDataStream>
11#include <QDate>
12#include <QFlags>
13#include <QHash>
14#include <QJsonArray>
15#include <QJsonValue>
16#include <QString>
17#include <QTime>
18#include <Qt>
19#include <QtDebug>
20
21#include "misc/imageutils.h"
22#include "misc/logmessage.h"
24#include "misc/statusmessage.h"
25#include "misc/stringutils.h"
26
27namespace swift::misc
28{
30 int qMetaTypeId_CVariantList = -1; // referenced in variantlist.cpp
31
32 private_ns::IValueObjectMetaInfo *private_ns::getValueObjectMetaInfo(QMetaType mt)
33 {
34 return getValueObjectMetaInfo(QVariant(mt, nullptr));
35 }
36
37 private_ns::IValueObjectMetaInfo *private_ns::getValueObjectMetaInfo(const QVariant &v)
38 {
39 return v.value<IValueObjectMetaInfo *>();
40 }
41
42 bool CVariant::canConvert(int typeId) const
43 {
44 const QMetaType mt(typeId);
45 if (m_v.canConvert(mt))
46 {
47 return true;
48 }
49 if (typeId == qMetaTypeId_CVariantList)
50 {
51 return m_v.canConvert<QVector<CVariant>>() || m_v.canConvert<QVariantList>();
52 }
53 if (userType() == qMetaTypeId_CVariantList)
54 {
55 return QVariant::fromValue(QVector<CVariant>()).canConvert(mt) ||
56 QVariant(QMetaType(typeId), nullptr).canConvert<QVariantList>();
57 }
58 return false;
59 }
60
61 bool CVariant::convert(int typeId)
62 {
63 const QMetaType mt(typeId);
64 if (!m_v.canConvert(mt))
65 {
66 if (!canConvert(typeId))
67 {
68 return false;
69 }
70 if (typeId == qMetaTypeId_CVariantList)
71 {
72 if (m_v.canConvert<QVector<CVariant>>())
73 {
74 if (!m_v.convert(QMetaType(qMetaTypeId<QVector<CVariant>>())))
75 {
76 return false;
77 }
78 }
79 else if (m_v.canConvert<QVariantList>())
80 {
81 QVector<CVariant> vec;
82 const auto seqit = m_v.value<QMetaSequence::Iterable>();
83 vec.reserve(seqit.size());
84 for (auto it = seqit.begin(); it != seqit.end(); ++it)
85 {
86 vec.push_back(*it);
87 }
88 m_v.setValue(vec);
89 }
90 else
91 {
92 return false;
93 }
94 }
95 if (userType() == qMetaTypeId_CVariantList)
96 {
97 if (QVariant::fromValue(QVector<CVariant>()).canConvert(mt))
98 {
99 if (!m_v.convert(QMetaType(qMetaTypeId<QVector<CVariant>>())))
100 {
101 return false;
102 }
103 }
104 else
105 {
106 return false;
107 }
108 }
109 }
110 return m_v.convert(mt);
111 }
112
113 bool CVariant::isVariantList() const { return userType() == qMetaTypeId_CVariantList; }
114
115 QString CVariant::convertToQString(bool i18n) const
116 {
117 auto *meta = getValueObjectMetaInfo();
118 if (meta)
119 {
120 return meta->toQString(data(), i18n);
121 }
122 return m_v.toString();
123 }
124
125 bool CVariant::isIntegral() const
126 {
127 switch (type())
128 {
129 case QMetaType::Bool:
130 case QMetaType::Char:
131 case QMetaType::UChar:
132 case QMetaType::SChar:
133 case QMetaType::Short:
135 case QMetaType::Int:
136 case QMetaType::UInt:
137 case QMetaType::Long:
138 case QMetaType::ULong:
140 case QMetaType::ULongLong: return true;
141 default: return false;
142 }
143 }
144
145 bool CVariant::isArithmetic() const
146 {
147 return isIntegral() || type() == QMetaType::Float || type() == QMetaType::Double;
148 }
149
150 qint64 CVariant::toQInt64(bool *ok) const
151 {
152 if (this->type() == QMetaType::LongLong)
153 {
154 return this->toLongLong(ok);
155 }
156 return this->toInt(ok);
157 }
158
159 int CVariant::compareImpl(const CVariant &a, const CVariant &b)
160 {
161 if (a.userType() < b.userType())
162 {
163 return -1;
164 }
165 if (a.userType() > b.userType())
166 {
167 return 1;
168 }
169 auto *aMeta = a.getValueObjectMetaInfo();
170 auto *bMeta = b.getValueObjectMetaInfo();
171 if (aMeta && bMeta)
172 {
173 try
174 {
175 const void *casted = nullptr;
176 if (casted = aMeta->upCastTo(a.data(), bMeta->getMetaTypeId()); casted)
177 {
178 return bMeta->compareImpl(casted, b.data());
179 }
180 if (casted = bMeta->upCastTo(b.data(), aMeta->getMetaTypeId()); casted)
181 {
182 return aMeta->compareImpl(a.data(), casted);
183 }
184 CLogMessage(&a).warning(
185 u"Comparing two CVariants containing unrelated value objects: %1 (%2) and %3 (%4)")
186 << a.typeName() << a.userType() << b.typeName() << b.userType();
187 return 0;
188 }
189 catch (const private_ns::CVariantException &ex)
190 {
191 CLogMessage(&a).debug() << ex.what();
192 return 0;
193 }
194 }
195 const QPartialOrdering order = QVariant::compare(a.m_v, b.m_v);
196 if (order == QPartialOrdering::Less)
197 {
198 return -1;
199 }
200 if (order == QPartialOrdering::Greater)
201 {
202 return 1;
203 }
204 return 0; // for "Equivalent" and "Unordered"
205 }
206
207 QJsonObject CVariant::toJson() const
208 {
209 QJsonObject json;
210 json.insert("type", this->typeName());
211
212 switch (m_v.metaType().id())
213 {
214 case QMetaType::UnknownType: json.insert("value", 0); break;
215 case QMetaType::Int: json.insert("value", m_v.toInt()); break;
216 case QMetaType::UInt: json.insert("value", m_v.toInt()); break;
217 case QMetaType::Bool: json.insert("value", m_v.toBool()); break;
218 case QMetaType::Double: json.insert("value", m_v.toDouble()); break;
219 case QMetaType::LongLong: json.insert("value", m_v.toLongLong()); break;
220 case QMetaType::ULongLong: json.insert("value", m_v.toLongLong()); break;
221 case QMetaType::QString: json.insert("value", m_v.toString()); break;
222 case QMetaType::Char: json.insert("value", m_v.toString()); break;
223 case QMetaType::QByteArray: json.insert("value", m_v.toString()); break;
224 case QMetaType::QDateTime: json.insert("value", m_v.toDateTime().toString(Qt::ISODate)); break;
225 case QMetaType::QDate: json.insert("value", m_v.toDate().toString(Qt::ISODate)); break;
226 case QMetaType::QTime: json.insert("value", m_v.toTime().toString(Qt::ISODate)); break;
227 case QMetaType::QStringList: json.insert("value", QJsonArray::fromStringList(m_v.toStringList())); break;
228 default:
229 try
230 {
231 auto *meta = getValueObjectMetaInfo();
232 if (meta)
233 {
234 json.insert("value", meta->toJson(data()));
235 }
236 else if (m_v.canConvert<QString>())
237 {
238 json.insert("value", m_v.toString());
239 }
240 else
241 {
242 CLogMessage(this).warning(u"Unsupported CVariant type for toJson: %1 (%2)")
243 << typeName() << userType();
244 }
245 }
246 catch (const private_ns::CVariantException &ex)
247 {
248 CLogMessage(this).debug() << ex.what();
249 }
250 }
251 return json;
252 }
253
255 {
256 QJsonDocument jsonDoc(toJson());
257 return jsonDoc.toJson(format);
258 }
259
260 void CVariant::convertFromJson(const QJsonObject &json)
261 {
262 // Remark: Names "type" and "value" are also used for drag and drop
263 // Changing the names here requires the change for drag and drop too
264 const QJsonValue typeValue = json.value("type");
265 if (typeValue.isUndefined())
266 {
267 throw CJsonException("Missing 'type'");
268 }
269 const QString typeName = typeValue.toString();
270 if (typeName.isEmpty())
271 {
272 m_v.clear();
273 return;
274 }
275
276 const QMetaType mt = QMetaType::fromName(qPrintable(typeName));
277
278 const QJsonValue value = json.value("value");
279 if (value.isUndefined())
280 {
281 throw CJsonException("Missing 'value'");
282 }
283 switch (mt.id())
284 {
285 case QMetaType::UnknownType: throw CJsonException("Type not recognized by QMetaType");
286 case QMetaType::Int: m_v.setValue(value.toInt()); break;
287 case QMetaType::UInt: m_v.setValue<uint>(static_cast<uint>(value.toInt())); break;
288 case QMetaType::Bool: m_v.setValue(value.toBool()); break;
289 case QMetaType::Double: m_v.setValue(value.toDouble()); break;
290 case QMetaType::LongLong: m_v.setValue(static_cast<qlonglong>(value.toDouble())); break;
291 case QMetaType::ULongLong: m_v.setValue(static_cast<qulonglong>(value.toDouble())); break;
292 case QMetaType::QString: m_v.setValue(value.toString()); break;
293 case QMetaType::Char: m_v.setValue(value.toString().size() > 0 ? value.toString().at(0) : '\0'); break;
294 case QMetaType::QByteArray: m_v.setValue(value.toString().toLatin1()); break;
295 case QMetaType::QDateTime: m_v.setValue(fromStringUtc(value.toString(), Qt::ISODate)); break;
296 case QMetaType::QDate: m_v.setValue(QDate::fromString(value.toString(), Qt::ISODate)); break;
297 case QMetaType::QTime: m_v.setValue(QTime::fromString(value.toString(), Qt::ISODate)); break;
298 case QMetaType::QStringList: m_v.setValue(QVariant(value.toArray().toVariantList()).toStringList()); break;
299 default:
300 try
301 {
302 auto *meta = private_ns::getValueObjectMetaInfo(mt);
303 if (meta)
304 {
305 CJsonScope scope("value"); // tracker
306 Q_UNUSED(scope);
307 m_v = QVariant(mt, nullptr);
308
309 // this will call convertFromJson if there is no MemoizedJson
310 meta->convertFromMemoizedJson(value.toObject(), data(), true);
311 }
312 else if (QMetaType::hasRegisteredConverterFunction(QMetaType(qMetaTypeId<QString>()), mt))
313 {
314 m_v.setValue(value.toString());
315 if (!m_v.convert(mt))
316 {
317 throw CJsonException("Failed to convert from JSON string");
318 }
319 }
320 else
321 {
322 throw CJsonException("Type not supported by convertFromJson");
323 }
324 }
325 catch (const private_ns::CVariantException &ex)
326 {
327 throw CJsonException(ex.what());
328 }
329 }
330 }
331
332 CStatusMessage CVariant::convertFromJsonNoThrow(const QJsonObject &json, const CLogCategoryList &categories,
333 const QString &prefix)
334 {
335 try
336 {
337 convertFromJson(json);
338 }
339 catch (const CJsonException &ex)
340 {
341 return CStatusMessage::fromJsonException(ex, categories, prefix);
342 }
343 return {};
344 }
345
346 QJsonObject CVariant::toMemoizedJson() const
347 {
348 auto *meta = getValueObjectMetaInfo();
349 if (meta)
350 {
351 try
352 {
353 QJsonObject json;
354 json.insert("type", this->typeName());
355 json.insert("value", meta->toMemoizedJson(data()));
356 return json;
357 }
358 catch (const private_ns::CVariantException &ex)
359 {
360 CLogMessage(this).debug() << ex.what();
361 return {};
362 }
363 }
364 else
365 {
366 return toJson();
367 }
368 }
369
370 void CVariant::convertFromMemoizedJson(const QJsonObject &json, bool allowFallbackToJson)
371 {
372 QJsonValue typeValue = json.value("type");
373 if (typeValue.isUndefined())
374 {
375 throw CJsonException("Missing 'type'");
376 }
377 QString typeName = typeValue.toString();
378 if (typeName.isEmpty())
379 {
380 m_v.clear();
381 return;
382 }
383 const QMetaType mt = QMetaType::fromName(qPrintable(typeName));
384
385 auto *meta = private_ns::getValueObjectMetaInfo(mt);
386 if (meta)
387 {
388 try
389 {
390 QJsonValue value = json.value("value");
391 if (value.isUndefined())
392 {
393 throw CJsonException("Missing 'value'");
394 }
395
396 CJsonScope scope("value");
397 m_v = QVariant(mt, nullptr);
398 meta->convertFromMemoizedJson(value.toObject(), data(), allowFallbackToJson);
399 }
400 catch (const private_ns::CVariantException &ex)
401 {
402 throw CJsonException(ex.what());
403 }
404 }
405 else
406 {
407 convertFromJson(json);
408 }
409 }
410
411 CStatusMessage CVariant::convertFromMemoizedJsonNoThrow(const QJsonObject &json, const CLogCategoryList &categories,
412 const QString &prefix)
413 {
414 try
415 {
416 convertFromMemoizedJson(json, false);
417 }
418 catch (const CJsonException &ex)
419 {
420 return CStatusMessage::fromJsonException(ex, categories, prefix);
421 }
422 return {};
423 }
424
425 size_t CVariant::getValueHash() const
426 {
427 switch (m_v.metaType().id())
428 {
429 case QMetaType::UnknownType: return 0;
430 case QMetaType::Int: return qHash(m_v.toInt());
431 case QMetaType::UInt: return qHash(m_v.toUInt());
432 case QMetaType::Bool: return qHash(m_v.toUInt());
433 case QMetaType::Double: return qHash(m_v.toUInt());
434 case QMetaType::LongLong: return qHash(m_v.toLongLong());
435 case QMetaType::ULongLong: return qHash(m_v.toULongLong());
436 case QMetaType::QString: return qHash(m_v.toString());
437 case QMetaType::Char: return qHash(m_v.toChar());
438 case QMetaType::QByteArray: return qHash(m_v.toByteArray());
439 default:
440 try
441 {
442 auto *meta = getValueObjectMetaInfo();
443 if (meta)
444 {
445 return meta->getValueHash(data());
446 }
447 else if (m_v.canConvert<QString>())
448 {
449 return qHash(m_v.toString());
450 }
451 else
452 {
453 CLogMessage(this).warning(u"Unsupported CVariant type for getValueHash: %1 (%2)")
454 << typeName() << userType();
455 return 0;
456 }
457 }
458 catch (const private_ns::CVariantException &ex)
459 {
460 CLogMessage(this).debug() << ex.what();
461 return 0;
462 }
463 }
464 }
465
466 void CVariant::marshallToDbus(QDBusArgument &arg) const
467 {
468 if (isValid())
469 {
470 arg << QString(typeName()) << QDBusVariant(getQVariant());
471 }
472 else
473 {
474 arg << QString() << QDBusVariant(QVariant(0));
475 }
476 }
477
479
483 QVariant fixQVariantFromDbusArgument(const QVariant &variant, QMetaType localUserType, const QString &typeName);
484 QVariant complexQtTypeFromDbusArgument(const QDBusArgument &argument, int type);
486
487 void CVariant::unmarshallFromDbus(const QDBusArgument &arg)
488 {
489 QString typeName;
490 QDBusVariant dbusVar;
491 arg >> typeName >> dbusVar;
492
493 if (typeName.isEmpty())
494 {
495 *this = CVariant();
496 }
497 else
498 {
499 *this = fixQVariantFromDbusArgument(dbusVar.variant(), QMetaType::fromName(qPrintable(typeName)), typeName);
500 }
501 }
502
503 void CVariant::marshalToDataStream(QDataStream &stream) const { stream << m_v; }
504
505 void CVariant::unmarshalFromDataStream(QDataStream &stream) { stream >> m_v; }
506
507 void CVariant::setPropertyByIndex(CPropertyIndexRef index, const QVariant &variant)
508 {
509 auto *meta = getValueObjectMetaInfo();
510 Q_ASSERT(meta);
511 try
512 {
513 meta->setPropertyByIndex(data(), variant, index);
514 }
515 catch (const private_ns::CVariantException &ex)
516 {
517 CLogMessage(this).debug() << ex.what();
518 }
519 }
520
521 QVariant CVariant::propertyByIndex(swift::misc::CPropertyIndexRef index) const
522 {
523 auto *meta = getValueObjectMetaInfo();
524 Q_ASSERT(meta);
525 try
526 {
527 QVariant result;
528 meta->propertyByIndex(data(), result, index);
529 return result;
530 }
531 catch (const private_ns::CVariantException &ex)
532 {
533 CLogMessage(this).debug() << ex.what();
534 return {};
535 }
536 }
537
538 bool CVariant::equalsPropertyByIndex(const CVariant &compareValue, CPropertyIndexRef index) const
539 {
540 auto *meta = getValueObjectMetaInfo();
541 Q_ASSERT(meta);
542 try
543 {
544 return meta->equalsPropertyByIndex(data(), compareValue, index);
545 }
546 catch (const private_ns::CVariantException &ex)
547 {
548 CLogMessage(this).debug() << ex.what();
549 return false;
550 }
551 }
552
554 {
555 auto *meta = getValueObjectMetaInfo();
556 if (!meta)
557 {
558 return {};
559 }
560 try
561 {
562 return static_cast<CIcons::IconIndex>(meta->toIcon(data()));
563 }
564 catch (const private_ns::CVariantException &ex)
565 {
566 CLogMessage(this).debug() << ex.what();
567 return CIcons::StandardIconError16;
568 }
569 }
570
571 QPixmap CVariant::toPixmap() const
572 {
573 if (m_v.typeId() == QMetaType::QPixmap)
574 {
575 return m_v.value<QPixmap>();
576 }
577 if (m_v.typeId() == QMetaType::QImage)
578 {
579 return QPixmap::fromImage(m_v.value<QImage>());
580 }
581 if (m_v.typeId() == QMetaType::QIcon)
582 {
583 return iconToPixmap(m_v.value<QIcon>());
584 }
585 return CIcon(toIcon()).toPixmap();
586 }
587
588 void CVariant::registerMetadata() { private_ns::MetaTypeHelper<CVariant>::maybeRegisterMetaType(); }
589
590 int CVariant::getMetaTypeId() const { return private_ns::MetaTypeHelper<CVariant>::maybeGetMetaTypeId(); }
591
592 QString CVariant::getClassName() const { return QMetaType(getMetaTypeId()).name(); }
593
594 bool CVariant::isA(int metaTypeId) const
595 {
596 if (metaTypeId == QMetaType::UnknownType)
597 {
598 return false;
599 }
600 return metaTypeId == getMetaTypeId();
601 }
602
603 bool CVariant::matches(const CVariant &value) const
604 {
605 if (!isValid())
606 {
607 return false;
608 }
609 auto *meta = getValueObjectMetaInfo();
610 if (!meta)
611 {
612 CLogMessage(this).warning(u"Invalid type for CVariant::matches: %1") << typeName();
613 return false;
614 }
615 try
616 {
617 return meta->matches(data(), value);
618 }
619 catch (const private_ns::CVariantException &ex)
620 {
621 CLogMessage(this).debug() << ex.what();
622 return false;
623 }
624 }
625
626 QVariant fixQVariantFromDbusArgument(const QVariant &variant, QMetaType localUserType, const QString &typeName)
627 {
628 if (localUserType.id() == static_cast<int>(QMetaType::UnknownType))
629 {
630 CLogMessage(&variant).warning(u"Invalid type for unmarshall: %1") << typeName;
631 }
632 // my business?
633 if (!variant.canConvert<QDBusArgument>())
634 {
635 return variant;
636 }
637
638 // complex, user type
639 // it has to be made sure, that the cast works
640 const auto arg = variant.value<QDBusArgument>();
641 constexpr int userType = static_cast<int>(QMetaType::User);
642 if (localUserType.id() < userType)
643 {
644 // complex Qt type, e.g. QDateTime
645 return complexQtTypeFromDbusArgument(arg, localUserType.id());
646 }
647 else if (QMetaType(localUserType).flags() & QMetaType::IsEnumeration)
648 {
649 arg.beginStructure();
650 int i {};
651 arg >> i;
652 arg.endStructure();
653
654 QVariant valueVariant = QVariant::fromValue(i);
655 bool ok = valueVariant.convert(localUserType);
656 Q_ASSERT_X(ok, Q_FUNC_INFO, "int could not be converted to enum");
657 Q_UNUSED(ok);
658 return valueVariant;
659 }
660 else
661 {
662 QVariant valueVariant(QMetaType(localUserType), nullptr);
663 auto *meta = private_ns::getValueObjectMetaInfo(valueVariant);
664 if (meta)
665 {
666 meta->unmarshall(arg, valueVariant.data());
667 return valueVariant;
668 }
669 Q_ASSERT_X(false, Q_FUNC_INFO, "no meta");
670 return valueVariant;
671 }
672 }
673
674 QVariant complexQtTypeFromDbusArgument(const QDBusArgument &argument, int type)
675 {
676 // QDate = 14, QTime = 15, QDateTime = 16, QUrl = 17,
677
678 switch (type)
679 {
681 {
682 QDateTime dt;
683 argument >> dt;
684 return QVariant::fromValue(dt);
685 }
686 case QMetaType::QDate:
687 {
688 QDate date;
689 argument >> date;
690 return QVariant::fromValue(date);
691 }
692 case QMetaType::QTime:
693 {
694 QTime time;
695 argument >> time;
696 return QVariant::fromValue(time);
697 }
698 default:
699 {
700 const char *name = QMetaType(type).name();
701 qFatal("Type cannot be resolved: %s (%d)", name ? name : "", type);
702 }
703 }
704 return {}; // suppress compiler warning
705 }
706
707} // namespace swift::misc
708
IconIndex
Index for each icon, allows to send them via DBus, efficiently store them, etc.
Definition icons.h:32
A sequence of log categories.
Class for emitting a log message.
Definition logmessage.h:27
Derived & warning(const char16_t(&format)[N])
Set the severity to warning, providing a format string.
Non-owning reference to a CPropertyIndex with a subset of its features.
Streamable status message, e.g.
static CStatusMessage fromJsonException(const CJsonException &ex, const CLogCategoryList &categories, const QString &prefix)
Object from JSON exception message.
Wrapper around QVariant which provides transparent access to CValueObject methods of the contained ob...
Definition variant.h:69
friend size_t qHash(const CVariant &var)
qHash overload, needed for storing value in a QSet.
Definition variant.h:103
void setPropertyByIndex(CPropertyIndexRef index, const QVariant &variant)
Set property by index.
void marshallToDbus(QDBusArgument &argument) const
Marshall without begin/endStructure, for when composed within another object.
CStatusMessage convertFromMemoizedJsonNoThrow(const QJsonObject &json, const CLogCategoryList &categories, const QString &prefix)
Call convertFromMemoizedJson, catch any CJsonException that is thrown and return it as CStatusMessage...
T value() const
Return the value converted to the type T.
Definition variant.h:154
const char * typeName() const
Return the typename of the value in this variant.
Definition variant.h:240
bool isIntegral() const
True if this variant's type is an integral type.
QJsonObject toMemoizedJson() const
To compact JSON format.
CIcons::IconIndex toIcon() const
As icon, not implemented by all classes.
void unmarshalFromDataStream(QDataStream &stream)
Unmarshal a value from a QDataStream.
static void registerMetadata()
Register metadata.
qint64 toQInt64(bool *ok=nullptr) const
COnvert to qint64, which is used for all timestamps.
bool canConvert() const
True if this variant can be converted to the type T.
Definition variant.h:182
QString getClassName() const
Class name.
void convertFromMemoizedJson(const QJsonObject &json, bool allowFallbackToJson)
From compact JSON format.
void unmarshallFromDbus(const QDBusArgument &argument)
Unmarshall without begin/endStructure, for when composed within another object.
CVariant()=default
Default constructor.
bool convert(int typeId)
Convert this variant to the type with the given metatype ID and return true if successful.
int userType() const
Return the metatype ID of the value in this variant.
Definition variant.h:243
bool isValid() const
True if this variant is valid.
Definition variant.h:230
void convertFromJson(const QJsonObject &json)
Assign from JSON object.
QVariant propertyByIndex(swift::misc::CPropertyIndexRef index) const
Property by index.
bool equalsPropertyByIndex(const CVariant &compareValue, CPropertyIndexRef index) const
Is given variant equal to value of property index?
const QVariant & getQVariant() const
Return the internal QVariant.
Definition variant.h:169
bool isArithmetic() const
True if this variant's type is an integral or floating-point type.
bool matches(const CVariant &event) const
If this is an event subscription, return true if it matches the given event.
QMetaType::Type type() const
Return the metatype ID of the value in this variant, or QMetaType::User if it is a user type.
Definition variant.h:233
qlonglong toLongLong(bool *ok=nullptr) const
Convert this variant to a longlong integer.
Definition variant.h:206
void marshalToDataStream(QDataStream &stream) const
Marshal a value to a QDataStream.
QString convertToQString(bool i18n=false) const
Cast as QString.
CStatusMessage convertFromJsonNoThrow(const QJsonObject &json, const CLogCategoryList &categories, const QString &prefix)
Call convertFromJson, catch any CJsonException that is thrown and return it as CStatusMessage.
int toInt(bool *ok=nullptr) const
Convert this variant to an integer.
Definition variant.h:203
QPixmap toPixmap() const
Corresponding pixmap.
int getMetaTypeId() const
Returns the Qt meta type ID of this object.
bool isA(int metaTypeId) const
Returns true if this object is an instance of the class with the given meta type ID,...
QJsonObject toJson() const
Cast to JSON object.
QString toJsonString(QJsonDocument::JsonFormat format=QJsonDocument::Indented) const
Convenience function JSON as string.
Free functions in swift::misc.
SWIFT_MISC_EXPORT QPixmap iconToPixmap(const QIcon &icon)
Icon to pixmap.
SWIFT_MISC_EXPORT QDateTime fromStringUtc(const QString &dateTimeString, const QString &format)
Same as QDateTime::fromString but QDateTime will be set to UTC.
QDate fromString(QStringView string, QStringView format, QCalendar cal)
QVariant variant() const const
QJsonArray fromStringList(const QStringList &list)
QJsonObject::iterator insert(QLatin1StringView key, const QJsonValue &value)
QJsonValue value(QLatin1StringView key) const const
bool isUndefined() const const
QString toString() const const
void push_back(QList< T >::parameter_type value)
void reserve(qsizetype size)
QMetaType fromName(QByteArrayView typeName)
bool hasRegisteredConverterFunction()
int id() const const
QPixmap fromImage(QImage &&image, Qt::ImageConversionFlags flags)
QTime fromString(QStringView string, QStringView format)
bool canConvert() const const
QPartialOrdering compare(const QVariant &lhs, const QVariant &rhs)
bool convert(QMetaType targetType)
void * data()
QVariant fromValue(T &&value)
T value() const &const