mirror of
https://github.com/AyuGram/AyuGramDesktop.git
synced 2025-04-16 14:17:12 +02:00
Fix crash in pinned topic deletion.
This commit is contained in:
parent
d01969ff1e
commit
02e2fb1258
14 changed files with 66 additions and 40 deletions
|
@ -76,6 +76,11 @@ rpl::producer<UpdateType> Changes::Manager<DataType, UpdateType>::flagsValue(
|
|||
) | rpl::then(updates(data, flags));
|
||||
}
|
||||
|
||||
template <typename DataType, typename UpdateType>
|
||||
void Changes::Manager<DataType, UpdateType>::drop(not_null<DataType*> data) {
|
||||
_updates.remove(data);
|
||||
}
|
||||
|
||||
template <typename DataType, typename UpdateType>
|
||||
void Changes::Manager<DataType, UpdateType>::sendNotifications() {
|
||||
for (const auto &[data, flags] : base::take(_updates)) {
|
||||
|
@ -166,8 +171,11 @@ rpl::producer<HistoryUpdate> Changes::realtimeHistoryUpdates(
|
|||
void Changes::topicUpdated(
|
||||
not_null<ForumTopic*> topic,
|
||||
TopicUpdate::Flags flags) {
|
||||
_topicChanges.updated(topic, flags);
|
||||
scheduleNotifications();
|
||||
const auto drop = (flags & TopicUpdate::Flag::Destroyed);
|
||||
_topicChanges.updated(topic, flags, drop);
|
||||
if (!drop) {
|
||||
scheduleNotifications();
|
||||
}
|
||||
}
|
||||
|
||||
rpl::producer<TopicUpdate> Changes::topicUpdates(
|
||||
|
@ -192,6 +200,10 @@ rpl::producer<TopicUpdate> Changes::realtimeTopicUpdates(
|
|||
return _topicChanges.realtimeUpdates(flag);
|
||||
}
|
||||
|
||||
void Changes::topicRemoved(not_null<ForumTopic*> topic) {
|
||||
_topicChanges.drop(topic);
|
||||
}
|
||||
|
||||
void Changes::messageUpdated(
|
||||
not_null<HistoryItem*> item,
|
||||
MessageUpdate::Flags flags) {
|
||||
|
@ -227,8 +239,11 @@ rpl::producer<MessageUpdate> Changes::realtimeMessageUpdates(
|
|||
void Changes::entryUpdated(
|
||||
not_null<Dialogs::Entry*> entry,
|
||||
EntryUpdate::Flags flags) {
|
||||
_entryChanges.updated(entry, flags);
|
||||
scheduleNotifications();
|
||||
const auto drop = (flags & EntryUpdate::Flag::Destroyed);
|
||||
_entryChanges.updated(entry, flags, drop);
|
||||
if (!drop) {
|
||||
scheduleNotifications();
|
||||
}
|
||||
}
|
||||
|
||||
rpl::producer<EntryUpdate> Changes::entryUpdates(
|
||||
|
@ -253,6 +268,10 @@ rpl::producer<EntryUpdate> Changes::realtimeEntryUpdates(
|
|||
return _entryChanges.realtimeUpdates(flag);
|
||||
}
|
||||
|
||||
void Changes::entryRemoved(not_null<Dialogs::Entry*> entry) {
|
||||
_entryChanges.drop(entry);
|
||||
}
|
||||
|
||||
void Changes::scheduleNotifications() {
|
||||
if (!_notify) {
|
||||
_notify = true;
|
||||
|
|
|
@ -153,8 +153,9 @@ struct TopicUpdate {
|
|||
CloudDraft = (1U << 8),
|
||||
Closed = (1U << 9),
|
||||
Creator = (1U << 10),
|
||||
Destroyed = (1U << 11),
|
||||
|
||||
LastUsedBit = (1U << 10),
|
||||
LastUsedBit = (1U << 11),
|
||||
};
|
||||
using Flags = base::flags<Flag>;
|
||||
friend inline constexpr auto is_flag_type(Flag) { return true; }
|
||||
|
@ -198,8 +199,9 @@ struct EntryUpdate {
|
|||
ForwardDraft = (1U << 2),
|
||||
LocalDraftSet = (1U << 3),
|
||||
Height = (1U << 4),
|
||||
Destroyed = (1U << 5),
|
||||
|
||||
LastUsedBit = (1U << 4),
|
||||
LastUsedBit = (1U << 5),
|
||||
};
|
||||
using Flags = base::flags<Flag>;
|
||||
friend inline constexpr auto is_flag_type(Flag) { return true; }
|
||||
|
@ -261,6 +263,7 @@ public:
|
|||
TopicUpdate::Flags flags) const;
|
||||
[[nodiscard]] rpl::producer<TopicUpdate> realtimeTopicUpdates(
|
||||
TopicUpdate::Flag flag) const;
|
||||
void topicRemoved(not_null<ForumTopic*> topic);
|
||||
|
||||
void messageUpdated(
|
||||
not_null<HistoryItem*> item,
|
||||
|
@ -289,6 +292,7 @@ public:
|
|||
EntryUpdate::Flags flags) const;
|
||||
[[nodiscard]] rpl::producer<EntryUpdate> realtimeEntryUpdates(
|
||||
EntryUpdate::Flag flag) const;
|
||||
void entryRemoved(not_null<Dialogs::Entry*> entry);
|
||||
|
||||
void sendNotifications();
|
||||
|
||||
|
@ -313,6 +317,8 @@ private:
|
|||
[[nodiscard]] rpl::producer<UpdateType> realtimeUpdates(
|
||||
Flag flag) const;
|
||||
|
||||
void drop(not_null<DataType*> data);
|
||||
|
||||
void sendNotifications();
|
||||
|
||||
private:
|
||||
|
|
|
@ -9,6 +9,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
|
||||
#include "data/data_channel.h"
|
||||
#include "data/data_histories.h"
|
||||
#include "data/data_changes.h"
|
||||
#include "data/data_session.h"
|
||||
#include "data/data_forum_icons.h"
|
||||
#include "data/data_forum_topic.h"
|
||||
|
@ -68,12 +69,16 @@ Forum::~Forum() {
|
|||
if (_requestId) {
|
||||
session().api().request(_requestId).cancel();
|
||||
}
|
||||
auto &storage = session().storage();
|
||||
auto &changes = session().changes();
|
||||
const auto peerId = _history->peer->id;
|
||||
for (const auto &[rootId, topic] : _topics) {
|
||||
session().storage().unload(Storage::SharedMediaUnloadThread(
|
||||
peerId,
|
||||
rootId));
|
||||
storage.unload(Storage::SharedMediaUnloadThread(peerId, rootId));
|
||||
_history->setForwardDraft(rootId, {});
|
||||
|
||||
const auto raw = topic.get();
|
||||
changes.topicRemoved(raw);
|
||||
changes.entryRemoved(raw);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -181,6 +186,12 @@ void Forum::applyTopicDeleted(MsgId rootId) {
|
|||
}
|
||||
|
||||
_topicDestroyed.fire(raw);
|
||||
session().changes().topicUpdated(
|
||||
raw,
|
||||
Data::TopicUpdate::Flag::Destroyed);
|
||||
session().changes().entryUpdated(
|
||||
raw,
|
||||
Data::EntryUpdate::Flag::Destroyed);
|
||||
_topics.erase(i);
|
||||
|
||||
_history->destroyMessagesByTopic(rootId);
|
||||
|
|
|
@ -333,7 +333,7 @@ not_null<Row*> Entry::addToChatList(
|
|||
void Entry::removeFromChatList(
|
||||
FilterId filterId,
|
||||
not_null<MainList*> list) {
|
||||
if (!asTopic() && isPinnedDialog(filterId)) {
|
||||
if (isPinnedDialog(filterId)) {
|
||||
owner().setChatPinned(this, filterId, false);
|
||||
}
|
||||
|
||||
|
|
|
@ -1223,13 +1223,11 @@ void Element::drawRightAction(
|
|||
int outerWidth) const {
|
||||
}
|
||||
|
||||
ClickHandlerPtr Element::rightActionLink() const {
|
||||
ClickHandlerPtr Element::rightActionLink(
|
||||
std::optional<QPoint> pressPoint) const {
|
||||
return ClickHandlerPtr();
|
||||
}
|
||||
|
||||
void Element::applyRightActionLastPoint(QPoint p) const {
|
||||
}
|
||||
|
||||
TimeId Element::displayedEditDate() const {
|
||||
return TimeId(0);
|
||||
}
|
||||
|
|
|
@ -403,8 +403,8 @@ public:
|
|||
int left,
|
||||
int top,
|
||||
int outerWidth) const;
|
||||
[[nodiscard]] virtual ClickHandlerPtr rightActionLink() const;
|
||||
virtual void applyRightActionLastPoint(QPoint p) const;
|
||||
[[nodiscard]] virtual ClickHandlerPtr rightActionLink(
|
||||
std::optional<QPoint> pressPoint) const;
|
||||
[[nodiscard]] virtual TimeId displayedEditDate() const;
|
||||
[[nodiscard]] virtual bool hasVisibleText() const;
|
||||
[[nodiscard]] virtual HistoryMessageReply *displayedReply() const;
|
||||
|
|
|
@ -1963,10 +1963,9 @@ TextState Message::textState(
|
|||
size->width(),
|
||||
size->height()
|
||||
).contains(point)) {
|
||||
result.link = rightActionLink();
|
||||
result.link = rightActionLink(point
|
||||
- QPoint(fastShareLeft, fastShareTop));
|
||||
}
|
||||
applyRightActionLastPoint(point
|
||||
- QPoint(fastShareLeft, fastShareTop));
|
||||
}
|
||||
} else if (media && media->isDisplayed()) {
|
||||
result = media->textState(point - g.topLeft(), request);
|
||||
|
@ -2715,7 +2714,7 @@ auto Message::verticalRepaintRange() const -> VerticalRepaintRange {
|
|||
|
||||
void Message::refreshDataIdHook() {
|
||||
if (_rightAction && base::take(_rightAction->link)) {
|
||||
_rightAction->link = rightActionLink();
|
||||
_rightAction->link = rightActionLink(_rightAction->lastPoint);
|
||||
}
|
||||
if (base::take(_fastReplyLink)) {
|
||||
_fastReplyLink = fastReplyLink();
|
||||
|
@ -2989,11 +2988,6 @@ std::optional<QSize> Message::rightActionSize() const {
|
|||
: std::optional<QSize>();
|
||||
}
|
||||
|
||||
void Message::applyRightActionLastPoint(QPoint p) const {
|
||||
ensureRightAction();
|
||||
_rightAction->lastPoint = std::move(p);
|
||||
}
|
||||
|
||||
bool Message::displayFastShare() const {
|
||||
const auto item = message();
|
||||
const auto peer = item->history()->peer;
|
||||
|
@ -3100,11 +3094,15 @@ void Message::drawRightAction(
|
|||
}
|
||||
}
|
||||
|
||||
ClickHandlerPtr Message::rightActionLink() const {
|
||||
ClickHandlerPtr Message::rightActionLink(
|
||||
std::optional<QPoint> pressPoint) const {
|
||||
ensureRightAction();
|
||||
if (!_rightAction->link) {
|
||||
_rightAction->link = prepareRightActionLink();
|
||||
}
|
||||
if (pressPoint) {
|
||||
_rightAction->lastPoint = *pressPoint;
|
||||
}
|
||||
return _rightAction->link;
|
||||
}
|
||||
|
||||
|
|
|
@ -130,14 +130,14 @@ public:
|
|||
bool displayFastReply() const override;
|
||||
bool displayRightActionComments() const;
|
||||
std::optional<QSize> rightActionSize() const override;
|
||||
void applyRightActionLastPoint(QPoint p) const override;
|
||||
void drawRightAction(
|
||||
Painter &p,
|
||||
const PaintContext &context,
|
||||
int left,
|
||||
int top,
|
||||
int outerWidth) const override;
|
||||
[[nodiscard]] ClickHandlerPtr rightActionLink() const override;
|
||||
[[nodiscard]] ClickHandlerPtr rightActionLink(
|
||||
std::optional<QPoint> pressPoint) const override;
|
||||
[[nodiscard]] TimeId displayedEditDate() const override;
|
||||
[[nodiscard]] HistoryMessageReply *displayedReply() const override;
|
||||
[[nodiscard]] bool toggleSelectionByHandlerClick(
|
||||
|
|
|
@ -393,8 +393,7 @@ TextState ExtendedPreview::textState(QPoint point, StateRequest request) const {
|
|||
auto fastShareLeft = (fullRight + st::historyFastShareLeft);
|
||||
auto fastShareTop = (fullBottom - st::historyFastShareBottom - size->height());
|
||||
if (QRect(fastShareLeft, fastShareTop, size->width(), size->height()).contains(point)) {
|
||||
result.link = _parent->rightActionLink();
|
||||
_parent->applyRightActionLastPoint(point
|
||||
result.link = _parent->rightActionLink(point
|
||||
- QPoint(fastShareLeft, fastShareTop));
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1032,8 +1032,7 @@ TextState Gif::textState(QPoint point, StateRequest request) const {
|
|||
+ st::msgDateImgPadding.y();
|
||||
}
|
||||
if (QRect(QPoint(fastShareLeft, fastShareTop), *size).contains(point)) {
|
||||
result.link = _parent->rightActionLink();
|
||||
_parent->applyRightActionLastPoint(point
|
||||
result.link = _parent->rightActionLink(point
|
||||
- QPoint(fastShareLeft, fastShareTop));
|
||||
}
|
||||
}
|
||||
|
|
|
@ -334,8 +334,7 @@ TextState Location::textState(QPoint point, StateRequest request) const {
|
|||
auto fastShareLeft = (fullRight + st::historyFastShareLeft);
|
||||
auto fastShareTop = (fullBottom - st::historyFastShareBottom - size->height());
|
||||
if (QRect(fastShareLeft, fastShareTop, size->width(), size->height()).contains(point)) {
|
||||
result.link = _parent->rightActionLink();
|
||||
_parent->applyRightActionLastPoint(point
|
||||
result.link = _parent->rightActionLink(point
|
||||
- QPoint(fastShareLeft, fastShareTop));
|
||||
}
|
||||
}
|
||||
|
|
|
@ -461,8 +461,7 @@ TextState GroupedMedia::textState(QPoint point, StateRequest request) const {
|
|||
auto fastShareLeft = (fullRight + st::historyFastShareLeft);
|
||||
auto fastShareTop = (fullBottom - st::historyFastShareBottom - size->height());
|
||||
if (QRect(fastShareLeft, fastShareTop, size->width(), size->height()).contains(point)) {
|
||||
result.link = _parent->rightActionLink();
|
||||
_parent->applyRightActionLastPoint(point
|
||||
result.link = _parent->rightActionLink(point
|
||||
- QPoint(fastShareLeft, fastShareTop));
|
||||
}
|
||||
}
|
||||
|
|
|
@ -485,8 +485,7 @@ TextState UnwrappedMedia::textState(QPoint point, StateRequest request) const {
|
|||
fullRight,
|
||||
*rightActionSize);
|
||||
if (QRect(position.x(), position.y(), rightActionSize->width(), rightActionSize->height()).contains(point)) {
|
||||
result.link = _parent->rightActionLink();
|
||||
_parent->applyRightActionLastPoint(point - position);
|
||||
result.link = _parent->rightActionLink(point - position);
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -563,8 +563,7 @@ TextState Photo::textState(QPoint point, StateRequest request) const {
|
|||
auto fastShareLeft = (fullRight + st::historyFastShareLeft);
|
||||
auto fastShareTop = (fullBottom - st::historyFastShareBottom - size->height());
|
||||
if (QRect(fastShareLeft, fastShareTop, size->width(), size->height()).contains(point)) {
|
||||
result.link = _parent->rightActionLink();
|
||||
_parent->applyRightActionLastPoint(point
|
||||
result.link = _parent->rightActionLink(point
|
||||
- QPoint(fastShareLeft, fastShareTop));
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Add table
Reference in a new issue