summary refs log tree commit diff
diff options
context:
space:
mode:
authorKonstantinos Sideris <sideris.konstantin@gmail.com>2017-11-30 13:19:34 +0200
committerKonstantinos Sideris <sideris.konstantin@gmail.com>2017-11-30 13:19:34 +0200
commit5663c58dd92150422b8f881cf0720859173091b8 (patch)
treef9bab72660d2b62c25e8cdd4f4474dfee310e267
parentSimplify timeline item creation (diff)
downloadnheko-5663c58dd92150422b8f881cf0720859173091b8.tar.xz
Use templates for the TimelineItem generation
-rw-r--r--include/TimelineView.h88
-rw-r--r--src/TimelineView.cc141
2 files changed, 90 insertions, 139 deletions
diff --git a/include/TimelineView.h b/include/TimelineView.h
index 5453ea5c..898a304e 100644
--- a/include/TimelineView.h
+++ b/include/TimelineView.h
@@ -18,6 +18,7 @@
 #pragma once
 
 #include <QApplication>
+#include <QDebug>
 #include <QLayout>
 #include <QList>
 #include <QQueue>
@@ -90,15 +91,6 @@ public:
                      const QString &room_id,
                      QWidget *parent = 0);
 
-        // For events with custom display widgets.
-        template<class Event, class Widget>
-        TimelineItem *createTimelineItem(const Event &event, bool withSender);
-
-        // For events without custom display widgets.
-        // TODO: All events should have custom widgets.
-        template<class Event>
-        TimelineItem *createTimelineItem(const Event &event, bool withSender);
-
         // Add new events at the end of the timeline.
         int addEvents(const Timeline &timeline);
         void addUserMessage(matrix::events::MessageEventType ty, const QString &msg);
@@ -141,6 +133,22 @@ private:
         void readLastEvent() const;
         QString getLastEventId() const;
 
+        template<class Event, class Widget>
+        TimelineItem *processMessageEvent(const QJsonObject &event, TimelineDirection direction);
+
+        // TODO: Remove this eventually.
+        template<class Event>
+        TimelineItem *processMessageEvent(const QJsonObject &event, TimelineDirection direction);
+
+        // For events with custom display widgets.
+        template<class Event, class Widget>
+        TimelineItem *createTimelineItem(const Event &event, bool withSender);
+
+        // For events without custom display widgets.
+        // TODO: All events should have custom widgets.
+        template<class Event>
+        TimelineItem *createTimelineItem(const Event &event, bool withSender);
+
         // Used to determine whether or not we should prefix a message with the
         // sender's name.
         bool isSenderRendered(const QString &user_id, TimelineDirection direction);
@@ -238,3 +246,65 @@ TimelineView::createTimelineItem(const Event &event, bool withSender)
 
         return item;
 }
+
+template<class Event>
+TimelineItem *
+TimelineView::processMessageEvent(const QJsonObject &data, TimelineDirection direction)
+{
+        Event event;
+
+        try {
+                event.deserialize(data);
+        } catch (const DeserializationException &e) {
+                qWarning() << e.what() << data;
+                return nullptr;
+        }
+
+        if (isDuplicate(event.eventId()))
+                return nullptr;
+
+        eventIds_[event.eventId()] = true;
+
+        QString txnid = event.unsignedData().transactionId();
+        if (!txnid.isEmpty() && isPendingMessage(txnid, event.sender(), local_user_)) {
+                removePendingMessage(txnid);
+                return nullptr;
+        }
+
+        auto with_sender = isSenderRendered(event.sender(), direction);
+
+        updateLastSender(event.sender(), direction);
+
+        return createTimelineItem<Event>(event, with_sender);
+}
+
+template<class Event, class Widget>
+TimelineItem *
+TimelineView::processMessageEvent(const QJsonObject &data, TimelineDirection direction)
+{
+        Event event;
+
+        try {
+                event.deserialize(data);
+        } catch (const DeserializationException &e) {
+                qWarning() << e.what() << data;
+                return nullptr;
+        }
+
+        if (isDuplicate(event.eventId()))
+                return nullptr;
+
+        eventIds_[event.eventId()] = true;
+
+        QString txnid = event.unsignedData().transactionId();
+        if (!txnid.isEmpty() && isPendingMessage(txnid, event.sender(), local_user_)) {
+                removePendingMessage(txnid);
+                return nullptr;
+        }
+
+        auto with_sender = isSenderRendered(event.sender(), direction);
+
+        updateLastSender(event.sender(), direction);
+
+        return createTimelineItem<Event, Widget>(event, with_sender);
+}
diff --git a/src/TimelineView.cc b/src/TimelineView.cc
index e61307fa..7bbda051 100644
--- a/src/TimelineView.cc
+++ b/src/TimelineView.cc
@@ -16,7 +16,6 @@
  */
 
 #include <QApplication>
-#include <QDebug>
 #include <QFileInfo>
 #include <QTimer>
 
@@ -229,140 +228,22 @@ TimelineView::parseMessageEvent(const QJsonObject &event, TimelineDirection dire
         if (ty == events::EventType::RoomMessage) {
                 events::MessageEventType msg_type = events::extractMessageEventType(event);
 
-                if (msg_type == events::MessageEventType::Text) {
-                        events::MessageEvent<msgs::Text> text;
-
-                        try {
-                                text.deserialize(event);
-                        } catch (const DeserializationException &e) {
-                                qWarning() << e.what() << event;
-                                return nullptr;
-                        }
-
-                        if (isDuplicate(text.eventId()))
-                                return nullptr;
-
-                        eventIds_[text.eventId()] = true;
-
-                        QString txnid = text.unsignedData().transactionId();
-                        if (!txnid.isEmpty() &&
-                            isPendingMessage(txnid, text.sender(), local_user_)) {
-                                removePendingMessage(txnid);
-                                return nullptr;
-                        }
+                using Emote  = events::MessageEvent<msgs::Emote>;
+                using File   = events::MessageEvent<msgs::File>;
+                using Image  = events::MessageEvent<msgs::Image>;
+                using Notice = events::MessageEvent<msgs::Notice>;
+                using Text   = events::MessageEvent<msgs::Text>;
 
-                        auto with_sender = isSenderRendered(text.sender(), direction);
-
-                        updateLastSender(text.sender(), direction);
-
-                        using Text = events::MessageEvent<msgs::Text>;
-                        return createTimelineItem<Text>(text, with_sender);
+                if (msg_type == events::MessageEventType::Text) {
+                        return processMessageEvent<Text>(event, direction);
                 } else if (msg_type == events::MessageEventType::Notice) {
-                        events::MessageEvent<msgs::Notice> notice;
-
-                        try {
-                                notice.deserialize(event);
-                        } catch (const DeserializationException &e) {
-                                qWarning() << e.what() << event;
-                                return nullptr;
-                        }
-
-                        if (isDuplicate(notice.eventId()))
-                                return nullptr;
-
-                        eventIds_[notice.eventId()] = true;
-
-                        auto with_sender = isSenderRendered(notice.sender(), direction);
-
-                        updateLastSender(notice.sender(), direction);
-
-                        using Notice = events::MessageEvent<msgs::Notice>;
-                        return createTimelineItem<Notice>(notice, with_sender);
+                        return processMessageEvent<Notice>(event, direction);
                 } else if (msg_type == events::MessageEventType::Image) {
-                        events::MessageEvent<msgs::Image> img;
-
-                        try {
-                                img.deserialize(event);
-                        } catch (const DeserializationException &e) {
-                                qWarning() << e.what() << event;
-                                return nullptr;
-                        }
-
-                        if (isDuplicate(img.eventId()))
-                                return nullptr;
-
-                        eventIds_[img.eventId()] = true;
-
-                        QString txnid = img.unsignedData().transactionId();
-                        if (!txnid.isEmpty() &&
-                            isPendingMessage(txnid, img.sender(), local_user_)) {
-                                removePendingMessage(txnid);
-                                return nullptr;
-                        }
-
-                        auto with_sender = isSenderRendered(img.sender(), direction);
-
-                        updateLastSender(img.sender(), direction);
-
-                        using Image = events::MessageEvent<msgs::Image>;
-                        return createTimelineItem<Image, ImageItem>(img, with_sender);
+                        return processMessageEvent<Image, ImageItem>(event, direction);
                 } else if (msg_type == events::MessageEventType::Emote) {
-                        events::MessageEvent<msgs::Emote> emote;
-
-                        try {
-                                emote.deserialize(event);
-                        } catch (const DeserializationException &e) {
-                                qWarning() << e.what() << event;
-                                return nullptr;
-                        }
-
-                        if (isDuplicate(emote.eventId()))
-                                return nullptr;
-
-                        eventIds_[emote.eventId()] = true;
-
-                        QString txnid = emote.unsignedData().transactionId();
-                        if (!txnid.isEmpty() &&
-                            isPendingMessage(txnid, emote.sender(), local_user_)) {
-                                removePendingMessage(txnid);
-                                return nullptr;
-                        }
-
-                        auto with_sender = isSenderRendered(emote.sender(), direction);
-
-                        updateLastSender(emote.sender(), direction);
-
-                        using Emote = events::MessageEvent<msgs::Emote>;
-                        return createTimelineItem<Emote>(emote, with_sender);
+                        return processMessageEvent<Emote>(event, direction);
                 } else if (msg_type == events::MessageEventType::File) {
-                        events::MessageEvent<msgs::File> file;
-
-                        try {
-                                file.deserialize(event);
-                        } catch (const DeserializationException &e) {
-                                qWarning() << e.what() << event;
-                                return nullptr;
-                        }
-
-                        if (isDuplicate(file.eventId()))
-                                return nullptr;
-
-                        eventIds_[file.eventId()] = true;
-
-                        QString txnid = file.unsignedData().transactionId();
-
-                        if (!txnid.isEmpty() &&
-                            isPendingMessage(txnid, file.sender(), local_user_)) {
-                                removePendingMessage(txnid);
-                                return nullptr;
-                        }
-
-                        auto withSender = isSenderRendered(file.sender(), direction);
-
-                        updateLastSender(file.sender(), direction);
-
-                        using File = events::MessageEvent<msgs::File>;
-                        return createTimelineItem<File, FileItem>(file, withSender);
+                        return processMessageEvent<File, FileItem>(event, direction);
                 } else if (msg_type == events::MessageEventType::Unknown) {
                         // TODO Handle redacted messages.
                         // Silenced for now.