From 377ee7df063ef368395a53a8f59d3a123cd57489 Mon Sep 17 00:00:00 2001 From: 23rd <23rd@vivaldi.net> Date: Tue, 29 Nov 2022 20:41:11 +0300 Subject: [PATCH] Added ability to apply TTL for multiple chats. --- Telegram/Resources/langs/lang.strings | 6 +- .../settings/settings_global_ttl.cpp | 165 +++++++++++++++++- 2 files changed, 167 insertions(+), 4 deletions(-) diff --git a/Telegram/Resources/langs/lang.strings b/Telegram/Resources/langs/lang.strings index b4ea0fc21..de010e537 100644 --- a/Telegram/Resources/langs/lang.strings +++ b/Telegram/Resources/langs/lang.strings @@ -693,8 +693,10 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL "lng_settings_ttl_select_chats_subtitle_chosen" = "will have the self-destruct timer"; "lng_settings_ttl_select_chats_status" = "auto-delete after {after_duration}"; "lng_settings_ttl_select_chats_status_disabled" = "auto-deletion disabled"; -"lng_settings_ttl_select_chats_status_toast#one" = "Self-destruct timer for {duration} has been enabled in {count} selected chat."; -"lng_settings_ttl_select_chats_status_toast#other" = "Self-destruct timer for {duration} has been enabled in {count} selected chats."; +"lng_settings_ttl_select_chats_toast#one" = "Self-destruct timer for {duration} has been enabled in {count} selected chat."; +"lng_settings_ttl_select_chats_toast#other" = "Self-destruct timer for {duration} has been enabled in {count} selected chats."; +"lng_settings_ttl_select_chats_disabled_toast#one" = "Self-destruct timer has been disabled in {count} selected chat."; +"lng_settings_ttl_select_chats_disabled_toast#other" = "Self-destruct timer has been disabled in {count} selected chats."; "lng_clear_payment_info_title" = "Clear payment info"; "lng_clear_payment_info_sure" = "Are you sure you want to clear your payment and shipping info?"; diff --git a/Telegram/SourceFiles/settings/settings_global_ttl.cpp b/Telegram/SourceFiles/settings/settings_global_ttl.cpp index aef9a8407..627f5cade 100644 --- a/Telegram/SourceFiles/settings/settings_global_ttl.cpp +++ b/Telegram/SourceFiles/settings/settings_global_ttl.cpp @@ -9,12 +9,17 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL #include "api/api_self_destruct.h" #include "apiwrap.h" +#include "boxes/peer_list_controllers.h" +#include "data/data_changes.h" +#include "data/data_peer.h" +#include "history/history.h" #include "lang/lang_keys.h" #include "lottie/lottie_icon.h" #include "main/main_session.h" #include "menu/menu_ttl.h" #include "settings/settings_common.h" #include "ui/boxes/confirm_box.h" +#include "ui/painter.h" #include "ui/text/format_values.h" #include "ui/text/text_utilities.h" #include "ui/toasts/common_toasts.h" @@ -26,10 +31,124 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL #include "styles/style_boxes.h" #include "styles/style_layers.h" #include "styles/style_settings.h" +#include "styles/style_calls.h" namespace Settings { namespace { +class TTLRow : public ChatsListBoxController::Row { +public: + using ChatsListBoxController::Row::Row; + + void paintStatusText( + Painter &p, + const style::PeerListItem &st, + int x, + int y, + int availableWidth, + int outerWidth, + bool selected) override; + +}; + +void TTLRow::paintStatusText( + Painter &p, + const style::PeerListItem &st, + int x, + int y, + int availableWidth, + int outerWidth, + bool selected) { + auto icon = history()->peer->messagesTTL() + ? &st::callArrowIn + : &st::callArrowOut; + icon->paint( + p, + x + st::callArrowPosition.x(), + y + st::callArrowPosition.y(), + outerWidth); + auto shift = st::callArrowPosition.x() + + icon->width() + + st::callArrowSkip; + x += shift; + availableWidth -= shift; + + PeerListRow::paintStatusText( + p, + st, + x, + y, + availableWidth, + outerWidth, + selected); +} + +class TTLChatsBoxController : public ChatsListBoxController { +public: + + TTLChatsBoxController(not_null session); + + Main::Session &session() const override; + void rowClicked(not_null row) override; + +protected: + void prepareViewHook() override; + std::unique_ptr createRow(not_null history) override; + +private: + const not_null _session; + + rpl::lifetime _lifetime; + +}; + +TTLChatsBoxController::TTLChatsBoxController(not_null session) +: ChatsListBoxController(session) +, _session(session) { +} + +Main::Session &TTLChatsBoxController::session() const { + return *_session; +} + +void TTLChatsBoxController::prepareViewHook() { + delegate()->peerListSetTitle(tr::lng_settings_ttl_title()); +} + +void TTLChatsBoxController::rowClicked(not_null row) { + delegate()->peerListSetRowChecked(row, !row->checked()); +} + +std::unique_ptr TTLChatsBoxController::createRow( + not_null history) { + if (history->peer->isSelf() || history->peer->isRepliesChat()) { + return nullptr; + } else if (!history->peer->canWrite()) { + return nullptr; + } + auto result = std::make_unique(history); + const auto applyStatus = [=, raw = result.get()] { + const auto ttl = history->peer->messagesTTL(); + raw->setCustomStatus( + ttl + ? tr::lng_settings_ttl_select_chats_status( + tr::now, + lt_after_duration, + Ui::FormatTTLAfter(ttl)) + : tr::lng_settings_ttl_select_chats_status_disabled(tr::now), + ttl); + }; + if (!history->peer->messagesTTL()) { + session().api().requestFullPeer(history->peer); + session().changes().peerUpdates( + history->peer, + Data::PeerUpdate::Flag::FullInfo + ) | rpl::take(1) | rpl::start_with_next(applyStatus, _lifetime); + } + applyStatus(); + return result; +} + void SetupTopContent( not_null parent, rpl::producer<> showFinished) { @@ -252,8 +371,50 @@ void GlobalTTL::setupContent() { ) | rpl::map([](QString s) { return Ui::Text::Link(s, 1); }), Ui::Text::WithEntities), st::boxDividerLabel); - footer->overrideLinkClickHandler([=] { - }); + footer->setLink(1, std::make_shared([=] { + const auto session = &_controller->session(); + auto controller = std::make_unique(session); + auto initBox = [=, controller = controller.get()]( + not_null box) { + box->addButton(tr::lng_background_apply(), crl::guard(this, [=] { + const auto &peers = box->collectSelectedRows(); + if (peers.empty()) { + return; + } + const auto &apiTTL = session->api().selfDestruct(); + const auto ttl = apiTTL.periodDefaultHistoryTTLCurrent(); + for (const auto &peer : peers) { + peer->session().api().request(MTPmessages_SetHistoryTTL( + peer->input, + MTP_int(ttl) + )).done([=](const MTPUpdates &result) { + peer->session().api().applyUpdates(result); + }).send(); + } + Ui::ShowMultilineToast({ + .parentOverride = Ui::BoxShow(box).toastParent(), + .text = ttl + ? tr::lng_settings_ttl_select_chats_toast( + tr::now, + lt_count, + peers.size(), + lt_duration, + { .text = Ui::FormatTTL(ttl) }, + Ui::Text::WithEntities) + : tr::lng_settings_ttl_select_chats_disabled_toast( + tr::now, + lt_count, + peers.size(), + Ui::Text::WithEntities), + }); + box->closeBox(); + })); + box->addButton(tr::lng_cancel(), [=] { box->closeBox(); }); + }; + _controller->show( + Box(std::move(controller), std::move(initBox)), + Ui::LayerOption::KeepOther); + })); content->add(object_ptr( content, std::move(footer),