1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
|
// SPDX-FileCopyrightText: 2018 Kitsune Ral <kitsune-ral@users.sf.net>
// SPDX-License-Identifier: LGPL-2.1-or-later
#pragma once
#include "events/stateevent.h"
#include <any>
#include <utility>
namespace Quotient {
class StateEventBase;
class EventStatus {
Q_GADGET
public:
/** Special marks an event can assume
*
* This is used to hint at a special status of some events in UI.
* All values except Redacted and Hidden are mutually exclusive.
*/
enum Code {
Normal = 0x0, //< No special designation
Submitted = 0x01, //< The event has just been submitted for sending
FileUploaded = 0x02, //< The file attached to the event has been
// uploaded to the server
Departed = 0x03, //< The event has left the client
ReachedServer = 0x04, //< The server has received the event
SendingFailed = 0x05, //< The server could not receive the event
Redacted = 0x08, //< The event has been redacted
Replaced = 0x10, //< The event has been replaced
Hidden = 0x100, //< The event should not be shown in the timeline
};
Q_DECLARE_FLAGS(Status, Code)
Q_FLAG(Status)
};
class EventItemBase {
public:
explicit EventItemBase(RoomEventPtr&& e) : evt(std::move(e))
{
Q_ASSERT(evt);
}
const RoomEvent* event() const { return rawPtr(evt); }
const RoomEvent* get() const { return event(); }
template <typename EventT>
const EventT* viewAs() const
{
return eventCast<const EventT>(evt);
}
const RoomEventPtr& operator->() const { return evt; }
const RoomEvent& operator*() const { return *evt; }
// Used for event redaction
RoomEventPtr replaceEvent(RoomEventPtr&& other)
{
return std::exchange(evt, move(other));
}
/// Store arbitrary data with the event item
void setUserData(std::any userData) { data = userData; }
/// Obtain custom data previously stored with the event item
const std::any& userdata() const { return data; }
std::any& userData() { return data; }
protected:
template <typename EventT>
EventT* getAs()
{
return eventCast<EventT>(evt);
}
private:
RoomEventPtr evt;
std::any data;
};
class TimelineItem : public EventItemBase {
public:
// For compatibility with Qt containers, even though we use
// a std:: container now for the room timeline
using index_t = int;
TimelineItem(RoomEventPtr&& e, index_t number)
: EventItemBase(std::move(e)), idx(number)
{}
index_t index() const { return idx; }
private:
index_t idx;
};
template <>
inline const StateEventBase* EventItemBase::viewAs<StateEventBase>() const
{
return evt->isStateEvent() ? weakPtrCast<const StateEventBase>(evt)
: nullptr;
}
template <>
inline const CallEventBase* EventItemBase::viewAs<CallEventBase>() const
{
return evt->isCallEvent() ? weakPtrCast<const CallEventBase>(evt) : nullptr;
}
class PendingEventItem : public EventItemBase {
Q_GADGET
public:
using EventItemBase::EventItemBase;
EventStatus::Code deliveryStatus() const { return _status; }
QDateTime lastUpdated() const { return _lastUpdated; }
QString annotation() const { return _annotation; }
void setDeparted() { setStatus(EventStatus::Departed); }
void setFileUploaded(const QUrl& remoteUrl);
void setReachedServer(const QString& eventId)
{
setStatus(EventStatus::ReachedServer);
(*this)->addId(eventId);
}
void setSendingFailed(QString errorText)
{
setStatus(EventStatus::SendingFailed);
_annotation = std::move(errorText);
}
void resetStatus() { setStatus(EventStatus::Submitted); }
private:
EventStatus::Code _status = EventStatus::Submitted;
QDateTime _lastUpdated = QDateTime::currentDateTimeUtc();
QString _annotation;
void setStatus(EventStatus::Code status)
{
_status = status;
_lastUpdated = QDateTime::currentDateTimeUtc();
_annotation.clear();
}
};
inline QDebug& operator<<(QDebug& d, const TimelineItem& ti)
{
QDebugStateSaver dss(d);
d.nospace() << "(" << ti.index() << "|" << ti->id() << ")";
return d;
}
} // namespace Quotient
Q_DECLARE_METATYPE(Quotient::EventStatus)
|