Apply updates correctly.

This commit is contained in:
John Preston 2023-05-26 18:48:33 +04:00
parent 2e6790c45c
commit 9f548b523e
6 changed files with 82 additions and 9 deletions

View File

@ -166,7 +166,7 @@ Main::Session &Stories::session() const {
} }
void Stories::apply(const MTPDupdateStories &data) { void Stories::apply(const MTPDupdateStories &data) {
pushToFront(parse(data.vstories())); applyChanges(parse(data.vstories()));
_allChanged.fire({}); _allChanged.fire({});
} }
@ -402,14 +402,42 @@ void Stories::applyDeleted(FullStoryId id) {
session().changes().storyUpdated( session().changes().storyUpdated(
story.get(), story.get(),
UpdateFlag::Destroyed); UpdateFlag::Destroyed);
removeDependencyStory(story.get());
if (i->second.empty()) { if (i->second.empty()) {
_stories.erase(i); _stories.erase(i);
} }
} }
} }
const auto j = ranges::find(_all, id.peer, [](const StoriesList &list) {
return list.user->id;
});
if (j != end(_all)) {
const auto till = ranges::remove(j->ids, id.story);
const auto removed = int(std::distance(till, end(j->ids)));
if (till != end(j->ids)) {
j->ids.erase(till, end(j->ids));
j->total = std::max(j->total - removed, 0);
if (j->ids.empty()) {
_all.erase(j);
}
_allChanged.fire({});
}
}
_deleted.emplace(id); _deleted.emplace(id);
} }
void Stories::removeDependencyStory(not_null<Story*> story) {
const auto i = _dependentMessages.find(story);
if (i != end(_dependentMessages)) {
const auto items = std::move(i->second);
_dependentMessages.erase(i);
for (const auto &dependent : items) {
dependent->dependencyStoryRemoved(story);
}
}
}
const std::vector<StoriesList> &Stories::all() { const std::vector<StoriesList> &Stories::all() {
return _all; return _all;
} }
@ -465,12 +493,21 @@ void Stories::pushToBack(StoriesList &&list) {
} }
} }
void Stories::pushToFront(StoriesList &&list) { void Stories::applyChanges(StoriesList &&list) {
const auto i = ranges::find(_all, list.user, &StoriesList::user); const auto i = ranges::find(_all, list.user, &StoriesList::user);
if (i != end(_all)) { if (i != end(_all)) {
*i = std::move(list); auto added = false;
ranges::rotate(begin(_all), i, i + 1); for (const auto id : list.ids) {
} else { if (!ranges::contains(i->ids, id)) {
i->ids.insert(begin(i->ids), id);
++i->total;
added = true;
}
}
if (added) {
ranges::rotate(begin(_all), i, i + 1);
}
} else if (!list.ids.empty()) {
_all.insert(begin(_all), std::move(list)); _all.insert(begin(_all), std::move(list));
} }
} }

View File

@ -123,8 +123,9 @@ private:
void finalizeResolve(FullStoryId id); void finalizeResolve(FullStoryId id);
void pushToBack(StoriesList &&list); void pushToBack(StoriesList &&list);
void pushToFront(StoriesList &&list); void applyChanges(StoriesList &&list);
void applyDeleted(FullStoryId id); void applyDeleted(FullStoryId id);
void removeDependencyStory(not_null<Story*> story);
const not_null<Session*> _owner; const not_null<Session*> _owner;
base::flat_map< base::flat_map<

View File

@ -725,6 +725,18 @@ void HistoryItem::dependencyItemRemoved(not_null<HistoryItem*> dependency) {
} }
} }
void HistoryItem::dependencyStoryRemoved(
not_null<Data::Story*> dependency) {
if (const auto reply = Get<HistoryMessageReply>()) {
const auto documentId = reply->replyToDocumentId;
reply->storyRemoved(this, dependency);
if (documentId != reply->replyToDocumentId
&& generateLocalEntitiesByReply()) {
_history->owner().requestItemTextRefresh(this);
}
}
}
void HistoryItem::updateDependencyItem() { void HistoryItem::updateDependencyItem() {
if (const auto reply = Get<HistoryMessageReply>()) { if (const auto reply = Get<HistoryMessageReply>()) {
const auto documentId = reply->replyToDocumentId; const auto documentId = reply->replyToDocumentId;

View File

@ -57,6 +57,7 @@ class MessageReactions;
class ForumTopic; class ForumTopic;
class Thread; class Thread;
struct SponsoredFrom; struct SponsoredFrom;
class Story;
} // namespace Data } // namespace Data
namespace Main { namespace Main {
@ -185,6 +186,7 @@ public:
}; };
void dependencyItemRemoved(not_null<HistoryItem*> dependency); void dependencyItemRemoved(not_null<HistoryItem*> dependency);
void dependencyStoryRemoved(not_null<Data::Story*> dependency);
void updateDependencyItem(); void updateDependencyItem();
[[nodiscard]] MsgId dependencyMsgId() const; [[nodiscard]] MsgId dependencyMsgId() const;
[[nodiscard]] bool notificationReady() const; [[nodiscard]] bool notificationReady() const;

View File

@ -369,7 +369,14 @@ void HistoryMessageReply::clearData(not_null<HistoryItem*> holder) {
replyToMsg.get()); replyToMsg.get());
replyToMsg = nullptr; replyToMsg = nullptr;
} }
if (replyToStory) {
holder->history()->owner().stories().unregisterDependentMessage(
holder,
replyToStory.get());
replyToStory = nullptr;
}
replyToMsgId = 0; replyToMsgId = 0;
replyToStoryId = 0;
refreshReplyToMedia(); refreshReplyToMedia();
} }
@ -466,14 +473,23 @@ void HistoryMessageReply::resize(int width) const {
} }
void HistoryMessageReply::itemRemoved( void HistoryMessageReply::itemRemoved(
HistoryItem *holder, not_null<HistoryItem*> holder,
HistoryItem *removed) { not_null<HistoryItem*> removed) {
if (replyToMsg.get() == removed) { if (replyToMsg.get() == removed) {
clearData(holder); clearData(holder);
holder->history()->owner().requestItemResize(holder); holder->history()->owner().requestItemResize(holder);
} }
} }
void HistoryMessageReply::storyRemoved(
not_null<HistoryItem*> holder,
not_null<Data::Story*> removed) {
if (replyToStory.get() == removed) {
clearData(holder);
holder->history()->owner().requestItemResize(holder);
}
}
void HistoryMessageReply::paint( void HistoryMessageReply::paint(
Painter &p, Painter &p,
not_null<const HistoryView::Element*> holder, not_null<const HistoryView::Element*> holder,

View File

@ -249,7 +249,12 @@ struct HistoryMessageReply
[[nodiscard]] bool isNameUpdated(not_null<HistoryItem*> holder) const; [[nodiscard]] bool isNameUpdated(not_null<HistoryItem*> holder) const;
void updateName(not_null<HistoryItem*> holder) const; void updateName(not_null<HistoryItem*> holder) const;
void resize(int width) const; void resize(int width) const;
void itemRemoved(HistoryItem *holder, HistoryItem *removed); void itemRemoved(
not_null<HistoryItem*> holder,
not_null<HistoryItem*> removed);
void storyRemoved(
not_null<HistoryItem*> holder,
not_null<Data::Story*> removed);
void paint( void paint(
Painter &p, Painter &p,