1 /****************************************************************************
2 **
3 ** Copyright (C) 2016 The Qt Company Ltd.
4 ** Contact: https://www.qt.io/licensing/
5 **
6 ** This file is part of the QtDBus module of the Qt Toolkit.
7 **
8 ** $QT_BEGIN_LICENSE:LGPL$
9 ** Commercial License Usage
10 ** Licensees holding valid commercial Qt licenses may use this file in
11 ** accordance with the commercial license agreement provided with the
12 ** Software or, alternatively, in accordance with the terms contained in
13 ** a written agreement between you and The Qt Company. For licensing terms
14 ** and conditions see https://www.qt.io/terms-conditions. For further
15 ** information use the contact form at https://www.qt.io/contact-us.
16 **
17 ** GNU Lesser General Public License Usage
18 ** Alternatively, this file may be used under the terms of the GNU Lesser
19 ** General Public License version 3 as published by the Free Software
20 ** Foundation and appearing in the file LICENSE.LGPL3 included in the
21 ** packaging of this file. Please review the following information to
22 ** ensure the GNU Lesser General Public License version 3 requirements
23 ** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
24 **
25 ** GNU General Public License Usage
26 ** Alternatively, this file may be used under the terms of the GNU
27 ** General Public License version 2.0 or (at your option) the GNU General
28 ** Public license version 3 or any later version approved by the KDE Free
29 ** Qt Foundation. The licenses are as published by the Free Software
30 ** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
31 ** included in the packaging of this file. Please review the following
32 ** information to ensure the GNU General Public License requirements will
33 ** be met: https://www.gnu.org/licenses/gpl-2.0.html and
34 ** https://www.gnu.org/licenses/gpl-3.0.html.
35 **
36 ** $QT_END_LICENSE$
37 **
38 ****************************************************************************/
39 
40 #ifndef QDBUSREPLY_H
41 #define QDBUSREPLY_H
42 
43 #include <QtDBus/qtdbusglobal.h>
44 #include <QtCore/qvariant.h>
45 
46 #include <QtDBus/qdbusmessage.h>
47 #include <QtDBus/qdbuserror.h>
48 #include <QtDBus/qdbusextratypes.h>
49 #include <QtDBus/qdbuspendingreply.h>
50 
51 #ifndef QT_NO_DBUS
52 
53 QT_BEGIN_NAMESPACE
54 
55 
56 Q_DBUS_EXPORT void qDBusReplyFill(const QDBusMessage &reply, QDBusError &error, QVariant &data);
57 
58 template<typename T>
59 class QDBusReply
60 {
61     typedef T Type;
62 public:
QDBusReply(const QDBusMessage & reply)63     inline QDBusReply(const QDBusMessage &reply)
64     {
65         *this = reply;
66     }
67     inline QDBusReply(const QDBusReply &) = default;
68     inline QDBusReply& operator=(const QDBusMessage &reply)
69     {
70         QVariant data(qMetaTypeId<Type>(), nullptr);
71         qDBusReplyFill(reply, m_error, data);
72         m_data = qvariant_cast<Type>(data);
73         return *this;
74     }
75 
QDBusReply(const QDBusPendingCall & pcall)76     inline QDBusReply(const QDBusPendingCall &pcall)
77     {
78         *this = pcall;
79     }
80     inline QDBusReply &operator=(const QDBusPendingCall &pcall)
81     {
82         QDBusPendingCall other(pcall);
83         other.waitForFinished();
84         return *this = other.reply();
85     }
QDBusReply(const QDBusPendingReply<T> & reply)86     inline QDBusReply(const QDBusPendingReply<T> &reply)
87     {
88         *this = static_cast<QDBusPendingCall>(reply);
89     }
90 
91     inline QDBusReply(const QDBusError &dbusError = QDBusError())
m_error(dbusError)92         : m_error(dbusError), m_data(Type())
93     {
94     }
95     inline QDBusReply& operator=(const QDBusError& dbusError)
96     {
97         m_error = dbusError;
98         m_data = Type();
99         return *this;
100     }
101 
102     inline QDBusReply& operator=(const QDBusReply& other)
103     {
104         m_error = other.m_error;
105         m_data = other.m_data;
106         return *this;
107     }
108 
isValid()109     inline bool isValid() const { return !m_error.isValid(); }
110 
error()111     inline const QDBusError& error() { return m_error; }
error()112     inline const QDBusError& error() const { return m_error; }
113 
value()114     inline Type value() const
115     {
116         return m_data;
117     }
118 
Type()119     inline operator Type () const
120     {
121         return m_data;
122     }
123 
124 private:
125     QDBusError m_error;
126     Type m_data;
127 };
128 
129 # ifndef Q_QDOC
130 // specialize for QVariant:
131 template<> inline QDBusReply<QVariant>&
132 QDBusReply<QVariant>::operator=(const QDBusMessage &reply)
133 {
134     void *null = nullptr;
135     QVariant data(qMetaTypeId<QDBusVariant>(), null);
136     qDBusReplyFill(reply, m_error, data);
137     m_data = qvariant_cast<QDBusVariant>(data).variant();
138     return *this;
139 }
140 
141 // specialize for void:
142 template<>
143 class QDBusReply<void>
144 {
145 public:
QDBusReply(const QDBusMessage & reply)146     inline QDBusReply(const QDBusMessage &reply)
147         : m_error(reply)
148     {
149     }
150     inline QDBusReply& operator=(const QDBusMessage &reply)
151     {
152         m_error = QDBusError(reply);
153         return *this;
154     }
155     inline QDBusReply(const QDBusError &dbusError = QDBusError())
m_error(dbusError)156         : m_error(dbusError)
157     {
158     }
QDBusReply(const QDBusPendingCall & pcall)159     inline QDBusReply(const QDBusPendingCall &pcall)
160     {
161         *this = pcall;
162     }
163     inline QDBusReply &operator=(const QDBusPendingCall &pcall)
164     {
165         QDBusPendingCall other(pcall);
166         other.waitForFinished();
167         return *this = other.reply();
168     }
169     inline QDBusReply& operator=(const QDBusError& dbusError)
170     {
171         m_error = dbusError;
172         return *this;
173     }
174 
175     inline QDBusReply(const QDBusReply &) = default;
176 
177     inline QDBusReply& operator=(const QDBusReply& other)
178     {
179         m_error = other.m_error;
180         return *this;
181     }
182 
isValid()183     inline bool isValid() const { return !m_error.isValid(); }
184 
error()185     inline const QDBusError& error() { return m_error; }
error()186     inline const QDBusError& error() const { return m_error; }
187 
188 private:
189     QDBusError m_error;
190 };
191 # endif
192 
193 QT_END_NAMESPACE
194 
195 #endif // QT_NO_DBUS
196 #endif
197