Fix display of pinned messages in sublists.

This commit is contained in:
John Preston 2025-06-02 16:43:39 +04:00
parent dfc1ec3ccf
commit cd05586d51
8 changed files with 48 additions and 15 deletions

View file

@ -83,7 +83,9 @@ void PinMessageBox(
object->setAllowTextLines(); object->setAllowTextLines();
state->pinForPeer = Ui::MakeWeak(object.data()); state->pinForPeer = Ui::MakeWeak(object.data());
return object; return object;
} else if (!pinningOld && (peer->isChat() || peer->isMegagroup())) { } else if (!pinningOld
&& (peer->isChat() || peer->isMegagroup())
&& !peer->isMonoforum()) {
auto object = object_ptr<Ui::Checkbox>( auto object = object_ptr<Ui::Checkbox>(
box, box,
tr::lng_pinned_notify(tr::now), tr::lng_pinned_notify(tr::now),

View file

@ -151,12 +151,16 @@ void ChatMemento::setFromTopic(not_null<Data::ForumTopic*> topic) {
} }
Data::ForumTopic *ChatMemento::topicForRemoveRequests() const {// #TODO monoforums Data::ForumTopic *ChatMemento::topicForRemoveRequests() const {
return _id.repliesRootId return _id.repliesRootId
? _id.history->peer->forumTopicFor(_id.repliesRootId) ? _id.history->peer->forumTopicFor(_id.repliesRootId)
: nullptr; : nullptr;
} }
Data::SavedSublist *ChatMemento::sublistForRemoveRequests() const {
return _id.sublist;
}
void ChatMemento::setReadInformation( void ChatMemento::setReadInformation(
MsgId inboxReadTillId, MsgId inboxReadTillId,
int unreadCount, int unreadCount,
@ -656,7 +660,8 @@ void ChatWidget::subscribeToPinnedMessages() {
) | rpl::start_with_next([=](const Data::EntryUpdate &update) { ) | rpl::start_with_next([=](const Data::EntryUpdate &update) {
if (_pinnedTracker if (_pinnedTracker
&& (update.flags & EntryUpdateFlag::HasPinnedMessages) && (update.flags & EntryUpdateFlag::HasPinnedMessages)
&& (_topic == update.entry.get())) { && (_topic == update.entry.get()
|| _sublist == update.entry.get())) {
checkPinnedBarState(); checkPinnedBarState();
} }
}, lifetime()); }, lifetime());
@ -1833,7 +1838,7 @@ void ChatWidget::refreshUnreadCountBadge(std::optional<int> count) {
} }
void ChatWidget::updatePinnedViewer() { void ChatWidget::updatePinnedViewer() {
if (_scroll->isHidden() || !_topic || !_pinnedTracker) { if (_scroll->isHidden() || (!_topic && !_sublist) || !_pinnedTracker) {
return; return;
} }
const auto visibleBottom = _scroll->scrollTop() + _scroll->height(); const auto visibleBottom = _scroll->scrollTop() + _scroll->height();
@ -1866,7 +1871,7 @@ void ChatWidget::updatePinnedViewer() {
void ChatWidget::checkLastPinnedClickedIdReset( void ChatWidget::checkLastPinnedClickedIdReset(
int wasScrollTop, int wasScrollTop,
int nowScrollTop) { int nowScrollTop) {
if (_scroll->isHidden() || !_topic) { if (_scroll->isHidden() || (!_topic && !_sublist)) {
return; return;
} }
if (wasScrollTop < nowScrollTop && _pinnedClickedId) { if (wasScrollTop < nowScrollTop && _pinnedClickedId) {
@ -1948,15 +1953,16 @@ void ChatWidget::setupTranslateBar() {
} }
void ChatWidget::setupPinnedTracker() { void ChatWidget::setupPinnedTracker() {
Expects(_topic != nullptr); Expects(_topic || _sublist);
_pinnedTracker = std::make_unique<HistoryView::PinnedTracker>(_topic); const auto thread = _topic ? (Data::Thread*)_topic : _sublist;
_pinnedTracker = std::make_unique<HistoryView::PinnedTracker>(thread);
_pinnedBar = nullptr; _pinnedBar = nullptr;
SharedMediaViewer( SharedMediaViewer(
&_topic->session(), &session(),
Storage::SharedMediaKey( Storage::SharedMediaKey(
_topic->channel()->id, _peer->id,
_repliesRootId, _repliesRootId,
_monoforumPeerId, _monoforumPeerId,
Storage::SharedMediaType::Pinned, Storage::SharedMediaType::Pinned,
@ -1966,7 +1972,7 @@ void ChatWidget::setupPinnedTracker() {
) | rpl::filter([=](const SparseIdsSlice &result) { ) | rpl::filter([=](const SparseIdsSlice &result) {
return result.fullCount().has_value(); return result.fullCount().has_value();
}) | rpl::start_with_next([=](const SparseIdsSlice &result) { }) | rpl::start_with_next([=](const SparseIdsSlice &result) {
_topic->setHasPinnedMessages(*result.fullCount() != 0); thread->setHasPinnedMessages(*result.fullCount() != 0);
if (result.skippedAfter() == 0) { if (result.skippedAfter() == 0) {
auto &settings = _history->session().settings(); auto &settings = _history->session().settings();
const auto peerId = _peer->id; const auto peerId = _peer->id;
@ -1985,7 +1991,7 @@ void ChatWidget::setupPinnedTracker() {
} }
} }
checkPinnedBarState(); checkPinnedBarState();
}, _topicLifetime); }, lifetime());
} }
void ChatWidget::checkPinnedBarState() { void ChatWidget::checkPinnedBarState() {
@ -2138,8 +2144,9 @@ void ChatWidget::refreshPinnedBarButton(bool many, HistoryItem *item) {
if (!id.message) { if (!id.message) {
return; return;
} }
const auto thread = _topic ? (Data::Thread*)_topic : _sublist;
controller()->showSection( controller()->showSection(
std::make_shared<PinnedMemento>(_topic, id.message.msg)); std::make_shared<PinnedMemento>(thread, id.message.msg));
}; };
const auto context = [copy = _inner](FullMsgId itemId) { const auto context = [copy = _inner](FullMsgId itemId) {
if (const auto raw = copy.data()) { if (const auto raw = copy.data()) {
@ -2591,6 +2598,7 @@ void ChatWidget::subscribeToSublist() {
}, lifetime()); }, lifetime());
unreadCountUpdated(); unreadCountUpdated();
subscribeToPinnedMessages();
} }
void ChatWidget::unreadCountUpdated() { void ChatWidget::unreadCountUpdated() {
@ -2782,7 +2790,10 @@ void ChatWidget::updateInnerVisibleArea() {
} }
void ChatWidget::updatePinnedVisibility() { void ChatWidget::updatePinnedVisibility() {
if (!_loaded || !_repliesRootId) { if (_sublist) {
setPinnedVisibility(true);
return;
} else if (!_loaded || !_repliesRootId) {
return; return;
} else if (!_topic && (!_repliesRoot || _repliesRoot->isEmpty())) { } else if (!_topic && (!_repliesRoot || _repliesRoot->isEmpty())) {
setPinnedVisibility(!_repliesRoot); setPinnedVisibility(!_repliesRoot);
@ -2803,7 +2814,10 @@ void ChatWidget::updatePinnedVisibility() {
} }
void ChatWidget::setPinnedVisibility(bool shown) { void ChatWidget::setPinnedVisibility(bool shown) {
if (animatingShow() || !_repliesRootId) { if (animatingShow()) {
} else if (_sublist) {
_repliesRootVisible = shown;
} else if (!_repliesRootId) {
return; return;
} else if (!_topic) { } else if (!_topic) {
if (!_repliesRootViewInitScheduled) { if (!_repliesRootViewInitScheduled) {

View file

@ -503,6 +503,7 @@ public:
} }
Data::ForumTopic *topicForRemoveRequests() const override; Data::ForumTopic *topicForRemoveRequests() const override;
Data::SavedSublist *sublistForRemoveRequests() const override;
[[nodiscard]] not_null<ListMemento*> list() { [[nodiscard]] not_null<ListMemento*> list() {
return &_list; return &_list;

View file

@ -756,8 +756,12 @@ bool AddPinMessageAction(
return false; return false;
} }
const auto topic = item->topic(); const auto topic = item->topic();
const auto sublist = item->savedSublist();
if (context != Context::History && context != Context::Pinned) { if (context != Context::History && context != Context::Pinned) {
if (context != Context::Replies || !topic) { if ((context != Context::Replies || !topic)
&& (context != Context::Monoforum
|| !sublist
|| !item->history()->amMonoforumAdmin())) {
return false; return false;
} }
} }

View file

@ -90,6 +90,10 @@ Data::ForumTopic *PinnedMemento::topicForRemoveRequests() const {
return _thread->asTopic(); return _thread->asTopic();
} }
Data::SavedSublist *PinnedMemento::sublistForRemoveRequests() const {
return _thread->asSublist();
}
PinnedWidget::PinnedWidget( PinnedWidget::PinnedWidget(
QWidget *parent, QWidget *parent,
not_null<Window::SessionController*> controller, not_null<Window::SessionController*> controller,

View file

@ -225,6 +225,7 @@ public:
} }
Data::ForumTopic *topicForRemoveRequests() const override; Data::ForumTopic *topicForRemoveRequests() const override;
Data::SavedSublist *sublistForRemoveRequests() const override;
private: private:
const not_null<Data::Thread*> _thread; const not_null<Data::Thread*> _thread;

View file

@ -223,6 +223,8 @@ StackItemSection::StackItemSection(
rpl::producer<> StackItemSection::sectionRemoveRequests() const { rpl::producer<> StackItemSection::sectionRemoveRequests() const {
if (const auto topic = _memento->topicForRemoveRequests()) { if (const auto topic = _memento->topicForRemoveRequests()) {
return rpl::merge(_memento->removeRequests(), topic->destroyed()); return rpl::merge(_memento->removeRequests(), topic->destroyed());
} else if (const auto sublist = _memento->sublistForRemoveRequests()) {
return rpl::merge(_memento->removeRequests(), sublist->destroyed());
} }
return _memento->removeRequests(); return _memento->removeRequests();
} }

View file

@ -13,6 +13,7 @@ class LayerWidget;
namespace Data { namespace Data {
class ForumTopic; class ForumTopic;
class SavedSublist;
} // namespace Data } // namespace Data
namespace Window { namespace Window {
@ -41,6 +42,10 @@ public:
[[nodiscard]] virtual Data::ForumTopic *topicForRemoveRequests() const { [[nodiscard]] virtual Data::ForumTopic *topicForRemoveRequests() const {
return nullptr; return nullptr;
} }
[[nodiscard]] virtual auto sublistForRemoveRequests() const
-> Data::SavedSublist* {
return nullptr;
}
[[nodiscard]] virtual rpl::producer<> removeRequests() const { [[nodiscard]] virtual rpl::producer<> removeRequests() const {
return rpl::never<>(); return rpl::never<>();
} }