diff --git a/src/contents/ui/Bubble.qml b/src/contents/ui/Bubble.qml
--- a/src/contents/ui/Bubble.qml
+++ b/src/contents/ui/Bubble.qml
@@ -21,7 +21,7 @@
   property var currentEvent: event
   property var menuContent: []
   property var shouldDisplayTime: displayTime || (!compactMode && !event.isLocalEcho)
-  property var eventPinned: event.eventId && pinnedEvents.eventIds.includes(event.eventId)
+  property var eventPinned: event.eventId && pinnedEvents.eventIds.hasOwnProperty(event.eventId)
   readonly property var eventReactions: event.reactions()
 
   topPadding: 0
@@ -170,7 +170,7 @@
               event,
               sender: room.member(event.sender || matrixSdk.userId),
               stateKeyUser: event.stateKey ? room.member(event.stateKey) : {},
-              isGapped: timeline.gaps.includes(event.eventId),
+              isGapped: timeline.gaps.hasOwnProperty(event.eventId),
             })
           }
         }
diff --git a/src/contents/ui/EventViewWrapper.qml b/src/contents/ui/EventViewWrapper.qml
--- a/src/contents/ui/EventViewWrapper.qml
+++ b/src/contents/ui/EventViewWrapper.qml
@@ -15,5 +15,5 @@
 Kazv.EventView {
   sender: room.member(event.sender || matrixSdk.userId)
   stateKeyUser: event.stateKey ? room.member(event.stateKey) : {}
-  isGapped: timeline?.gaps?.includes(event.eventId)
+  isGapped: timeline?.gaps?.hasOwnProperty(event.eventId)
 }
diff --git a/src/contents/ui/RoomTimelineView.qml b/src/contents/ui/RoomTimelineView.qml
--- a/src/contents/ui/RoomTimelineView.qml
+++ b/src/contents/ui/RoomTimelineView.qml
@@ -16,8 +16,6 @@
   objectName: 'roomTimelineView'
   property var timeline
 
-  property var eventIds: timeline.eventIds
-
   property string selectedEventId
 
   signal pinEventRequested(string eventId)
diff --git a/src/matrix-room-pinned-events-timeline.hpp b/src/matrix-room-pinned-events-timeline.hpp
--- a/src/matrix-room-pinned-events-timeline.hpp
+++ b/src/matrix-room-pinned-events-timeline.hpp
@@ -8,6 +8,7 @@
 #include <kazv-defs.hpp>
 #include <QObject>
 #include <QQmlEngine>
+#include <QJsonObject>
 #include "matrix-room-timeline.hpp"
 
 class MatrixRoomPinnedEventsTimeline : public MatrixRoomTimeline
@@ -20,5 +21,5 @@
     explicit MatrixRoomPinnedEventsTimeline(Kazv::Room room, QObject *parent = 0);
     ~MatrixRoomPinnedEventsTimeline() override;
 
-    LAGER_QT_READER(QSet<QString>, eventIds);
+    LAGER_QT_READER(QJsonObject, eventIds);
 };
diff --git a/src/matrix-room-pinned-events-timeline.cpp b/src/matrix-room-pinned-events-timeline.cpp
--- a/src/matrix-room-pinned-events-timeline.cpp
+++ b/src/matrix-room-pinned-events-timeline.cpp
@@ -6,6 +6,7 @@
 
 #include <kazv-defs.hpp>
 #include "matrix-room-pinned-events-timeline.hpp"
+#include <QJsonValue>
 
 using namespace Kazv;
 
@@ -19,9 +20,9 @@
         parent
     )
     , LAGER_QT(eventIds)(room.pinnedEvents().map([](const auto &ids) {
-        QSet<QString> res;
+        QJsonObject res;
         for (const auto &id : ids) {
-            res.insert(QString::fromStdString(id));
+            res.insert(QString::fromStdString(id), QJsonValue(true));
         }
         return res;
     }))
diff --git a/src/matrix-room-timeline.hpp b/src/matrix-room-timeline.hpp
--- a/src/matrix-room-timeline.hpp
+++ b/src/matrix-room-timeline.hpp
@@ -9,7 +9,7 @@
 
 #include <QObject>
 #include <QQmlEngine>
-
+#include <QJsonObject>
 #include <lager/extra/qt.hpp>
 
 #include <client/room/room.hpp>
@@ -35,7 +35,7 @@
     explicit MatrixRoomTimeline(lager::reader<immer::flex_vector<std::string>> eventIds, lager::reader<immer::map<std::string, Kazv::Event>> messagesMap, lager::reader<immer::flex_vector<Kazv::LocalEchoDesc>> localEchoes, lager::reader<immer::map<std::string, std::string>> timelineGaps, Kazv::Room room, QObject *parent = 0);
     ~MatrixRoomTimeline() override;
 
-    LAGER_QT_READER(QSet<QString>, gaps);
+    LAGER_QT_READER(QJsonObject, gaps);
 
     Q_INVOKABLE MatrixEvent *at(int index) const;
 
diff --git a/src/matrix-room-timeline.cpp b/src/matrix-room-timeline.cpp
--- a/src/matrix-room-timeline.cpp
+++ b/src/matrix-room-timeline.cpp
@@ -11,7 +11,7 @@
 #include <lager/lenses/optional.hpp>
 
 #include <QTimer>
-
+#include <QJsonValue>
 #include <cursorutil.hpp>
 
 #include "matrix-room-timeline.hpp"
@@ -31,9 +31,9 @@
     , m_localEchoes(localEchoes)
     , m_timelineGaps(timelineGaps)
     , LAGER_QT(gaps)(m_timelineGaps.map([](auto g) {
-        QSet<QString> res{};
+        QJsonObject res;
         for (const auto &[k, _v] : g) {
-            res.insert(QString::fromStdString(k));
+            res.insert(QString::fromStdString(k), QJsonValue(true));
         }
         return res;
     }))
diff --git a/src/tests/quick-tests/tst_EventView.qml b/src/tests/quick-tests/tst_EventView.qml
--- a/src/tests/quick-tests/tst_EventView.qml
+++ b/src/tests/quick-tests/tst_EventView.qml
@@ -25,12 +25,15 @@
   property var deleteEventRequested: mockHelper.noop()
 
   property var timeline: ({
-    gaps: [],
+    gaps: {},
   })
 
   property var pinnedEvents: ({
     count: 2,
-    eventIds: ['$123', '$456'],
+    eventIds: {
+      '$123': true,
+      '$456': true,
+    },
   })
 
   property var room: ({
@@ -306,7 +309,6 @@
       id: eventViewFailed
       event: item.failedLocalEcho
       sender: item.sender
-      property int index: 0
     }
 
     Kazv.EventView {
diff --git a/src/tests/quick-tests/tst_SendMessageBox.qml b/src/tests/quick-tests/tst_SendMessageBox.qml
--- a/src/tests/quick-tests/tst_SendMessageBox.qml
+++ b/src/tests/quick-tests/tst_SendMessageBox.qml
@@ -23,8 +23,7 @@
       timeline () {
         return {
           count: 0,
-          eventIds: [],
-          gaps: [],
+          gaps: {},
           at () { return {}; },
         };
       },
diff --git a/src/tests/quick-tests/tst_SendMessageBoxDrafts.qml b/src/tests/quick-tests/tst_SendMessageBoxDrafts.qml
--- a/src/tests/quick-tests/tst_SendMessageBoxDrafts.qml
+++ b/src/tests/quick-tests/tst_SendMessageBoxDrafts.qml
@@ -23,8 +23,7 @@
       timeline () {
         return {
           count: 0,
-          eventIds: [],
-          gaps: [],
+          gaps: {},
           at () { return {}; },
         };
       },