aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--lib/room.cpp17
-rw-r--r--lib/room.h18
2 files changed, 33 insertions, 2 deletions
diff --git a/lib/room.cpp b/lib/room.cpp
index 41a8888c..60b9a684 100644
--- a/lib/room.cpp
+++ b/lib/room.cpp
@@ -948,12 +948,27 @@ void Room::removeTag(const QString& name)
<< "not found, nothing to remove";
}
-void Room::setTags(TagsMap newTags)
+void Room::setTags(TagsMap newTags, ActionScope applyOn)
{
+ bool propagate = applyOn != ActionScope::ThisRoomOnly;
+ auto joinStates =
+ applyOn == ActionScope::WithinSameState ? joinState() :
+ applyOn == ActionScope::OmitLeftState ? JoinState::Join|JoinState::Invite :
+ JoinState::Join|JoinState::Invite|JoinState::Leave;
+ if (propagate) {
+ for (auto* r = this; (r = r->predecessor(joinStates));)
+ r->setTags(newTags, ActionScope::ThisRoomOnly);
+ }
+
d->setTags(move(newTags));
connection()->callApi<SetAccountDataPerRoomJob>(
localUser()->id(), id(), TagEvent::matrixTypeId(),
TagEvent(d->tags).contentJson());
+
+ if (propagate) {
+ for (auto* r = this; (r = r->successor(joinStates));)
+ r->setTags(newTags, ActionScope::ThisRoomOnly);
+ }
}
void Room::Private::setTags(TagsMap newTags)
diff --git a/lib/room.h b/lib/room.h
index 10f18742..ad19792e 100644
--- a/lib/room.h
+++ b/lib/room.h
@@ -396,6 +396,19 @@ public:
/// Remove a tag from the room
Q_INVOKABLE void removeTag(const QString& name);
+ /// The scope to apply an action on
+ /*! This enumeration is used to pick a strategy to propagate certain
+ * actions on the room to its predecessors and successors.
+ */
+ enum ActionScope {
+ ThisRoomOnly, //< Do not apply to predecessors and successors
+ WithinSameState, //< Apply to predecessors and successors in the same
+ //< state as the current one
+ OmitLeftState, //< Apply to all reachable predecessors and successors
+ //< except those in Leave state
+ WholeSequence //< Apply to all reachable predecessors and successors
+ };
+
/** Overwrite the room's tags
* This completely replaces the existing room's tags with a set
* of new ones and updates the new set on the server. Unlike
@@ -403,8 +416,11 @@ public:
* immediately, not waiting for confirmation from the server
* (because tags are saved in account data rather than in shared
* room state).
+ * \param applyOn setting this to Room::OnAllConversations will set tags
+ * on this and all _known_ predecessors and successors;
+ * by default only the current room is changed
*/
- void setTags(TagsMap newTags);
+ void setTags(TagsMap newTags, ActionScope applyOn = ThisRoomOnly);
/// Check whether the list of tags has m.favourite
bool isFavourite() const;