diff --git a/Telegram/CMakeLists.txt b/Telegram/CMakeLists.txt index a86a14484..aa61a3336 100644 --- a/Telegram/CMakeLists.txt +++ b/Telegram/CMakeLists.txt @@ -112,6 +112,8 @@ PRIVATE api/api_bot.h api/api_chat_filters.cpp api/api_chat_filters.h + api/api_chat_filters_remove_manager.cpp + api/api_chat_filters_remove_manager.h api/api_chat_invite.cpp api/api_chat_invite.h api/api_chat_links.cpp diff --git a/Telegram/SourceFiles/api/api_chat_filters_remove_manager.cpp b/Telegram/SourceFiles/api/api_chat_filters_remove_manager.cpp new file mode 100644 index 000000000..fe96accd6 --- /dev/null +++ b/Telegram/SourceFiles/api/api_chat_filters_remove_manager.cpp @@ -0,0 +1,128 @@ +/* +This file is part of Telegram Desktop, +the official desktop application for the Telegram messaging service. + +For license and copyright information please follow this link: +https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL +*/ +#include "api/api_chat_filters_remove_manager.h" + +#include "api/api_chat_filters.h" +#include "apiwrap.h" +#include "data/data_chat_filters.h" +#include "data/data_peer.h" +#include "data/data_session.h" +#include "lang/lang_keys.h" +#include "main/main_session.h" +#include "ui/boxes/confirm_box.h" +#include "ui/ui_utility.h" +#include "window/window_controller.h" +#include "window/window_session_controller.h" +#include "styles/style_layers.h" + +namespace Api { +namespace { + +void RemoveChatFilter( + not_null session, + FilterId filterId, + std::vector> leave) { + const auto api = &session->api(); + session->data().chatsFilters().apply(MTP_updateDialogFilter( + MTP_flags(MTPDupdateDialogFilter::Flag(0)), + MTP_int(filterId), + MTPDialogFilter())); + if (leave.empty()) { + api->request(MTPmessages_UpdateDialogFilter( + MTP_flags(MTPmessages_UpdateDialogFilter::Flag(0)), + MTP_int(filterId), + MTPDialogFilter() + )).send(); + } else { + api->request(MTPchatlists_LeaveChatlist( + MTP_inputChatlistDialogFilter(MTP_int(filterId)), + MTP_vector(ranges::views::all( + leave + ) | ranges::views::transform([](not_null peer) { + return MTPInputPeer(peer->input); + }) | ranges::to>()) + )).done([=](const MTPUpdates &result) { + api->applyUpdates(result); + }).send(); + } +} + +} // namespace + +RemoveComplexChatFilter::RemoveComplexChatFilter() = default; + +void RemoveComplexChatFilter::request( + QPointer widget, + base::weak_ptr weak, + FilterId id) { + const auto session = &weak->session(); + const auto &list = session->data().chatsFilters().list(); + const auto i = ranges::find(list, id, &Data::ChatFilter::id); + const auto filter = (i != end(list)) ? *i : Data::ChatFilter(); + const auto has = filter.hasMyLinks(); + const auto confirm = [=](Fn action, bool onlyWhenHas = false) { + if (!has && onlyWhenHas) { + action(); + return; + } + weak->window().show(Ui::MakeConfirmBox({ + .text = (has + ? tr::lng_filters_delete_sure() + : tr::lng_filters_remove_sure()), + .confirmed = [=](Fn &&close) { close(); action(); }, + .confirmText = (has + ? tr::lng_box_delete() + : tr::lng_filters_remove_yes()), + .confirmStyle = &st::attentionBoxButton, + })); + }; + const auto simple = [=] { + confirm([=] { RemoveChatFilter(session, id, {}); }); + }; + const auto suggestRemoving = Api::ExtractSuggestRemoving(filter); + if (suggestRemoving.empty()) { + simple(); + return; + } else if (_removingRequestId) { + if (_removingId == id) { + return; + } + session->api().request(_removingRequestId).cancel(); + } + _removingId = id; + _removingRequestId = session->api().request( + MTPchatlists_GetLeaveChatlistSuggestions( + MTP_inputChatlistDialogFilter( + MTP_int(id))) + ).done(crl::guard(widget, [=, this](const MTPVector &result) { + _removingRequestId = 0; + const auto suggestRemovePeers = ranges::views::all( + result.v + ) | ranges::views::transform([=](const MTPPeer &peer) { + return session->data().peer(peerFromMTP(peer)); + }) | ranges::to_vector; + const auto chosen = crl::guard(widget, [=]( + std::vector> peers) { + RemoveChatFilter(session, id, std::move(peers)); + }); + confirm(crl::guard(widget, [=] { + Api::ProcessFilterRemove( + weak, + filter.title(), + filter.iconEmoji(), + suggestRemoving, + suggestRemovePeers, + chosen); + }), true); + })).fail(crl::guard(widget, [=, this] { + _removingRequestId = 0; + simple(); + })).send(); +} + +} // namespace Api diff --git a/Telegram/SourceFiles/api/api_chat_filters_remove_manager.h b/Telegram/SourceFiles/api/api_chat_filters_remove_manager.h new file mode 100644 index 000000000..ce92b2df3 --- /dev/null +++ b/Telegram/SourceFiles/api/api_chat_filters_remove_manager.h @@ -0,0 +1,35 @@ +/* +This file is part of Telegram Desktop, +the official desktop application for the Telegram messaging service. + +For license and copyright information please follow this link: +https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL +*/ +#pragma once + +namespace Window { +class SessionController; +} // namespace Window + +namespace Ui { +class RpWidget; +} // namespace Ui + +namespace Api { + +class RemoveComplexChatFilter final { +public: + RemoveComplexChatFilter(); + + void request( + QPointer widget, + base::weak_ptr weak, + FilterId id); + +private: + FilterId _removingId = 0; + mtpRequestId _removingRequestId = 0; + +}; + +} // namespace Api diff --git a/Telegram/SourceFiles/window/window_filters_menu.cpp b/Telegram/SourceFiles/window/window_filters_menu.cpp index 8577ebf0b..db6e05c4a 100644 --- a/Telegram/SourceFiles/window/window_filters_menu.cpp +++ b/Telegram/SourceFiles/window/window_filters_menu.cpp @@ -367,7 +367,7 @@ void FiltersMenu::showMenu(QPoint position, FilterId id) { if (id) { addAction( tr::lng_filters_context_edit(tr::now), - [=] { showEditBox(id); }, + [=] { EditExistingFilter(_session, id); }, &st::menuIconEdit); auto filteredChats = [=] { @@ -380,7 +380,7 @@ void FiltersMenu::showMenu(QPoint position, FilterId id) { addAction( tr::lng_filters_context_remove(tr::now), - [=] { showRemoveBox(id); }, + [=] { _removeApi.request(Ui::MakeWeak(&_outer), _session, id); }, &st::menuIconDelete); } else { auto customUnreadState = [=] { @@ -407,105 +407,6 @@ void FiltersMenu::showMenu(QPoint position, FilterId id) { _popupMenu->popup(position); } -void FiltersMenu::showEditBox(FilterId id) { - EditExistingFilter(_session, id); -} - -void FiltersMenu::showRemoveBox(FilterId id) { - const auto session = &_session->session(); - const auto &list = session->data().chatsFilters().list(); - const auto i = ranges::find(list, id, &Data::ChatFilter::id); - const auto filter = (i != end(list)) ? *i : Data::ChatFilter(); - const auto has = filter.hasMyLinks(); - const auto confirm = [=](Fn action, bool onlyWhenHas = false) { - if (!has && onlyWhenHas) { - action(); - return; - } - _session->window().show(Ui::MakeConfirmBox({ - .text = (has - ? tr::lng_filters_delete_sure() - : tr::lng_filters_remove_sure()), - .confirmed = [=](Fn &&close) { close(); action(); }, - .confirmText = (has - ? tr::lng_box_delete() - : tr::lng_filters_remove_yes()), - .confirmStyle = &st::attentionBoxButton, - })); - }; - const auto simple = [=] { - confirm([=] { remove(id); }); - }; - const auto suggestRemoving = Api::ExtractSuggestRemoving(filter); - if (suggestRemoving.empty()) { - simple(); - return; - } else if (_removingRequestId) { - if (_removingId == id) { - return; - } - session->api().request(_removingRequestId).cancel(); - } - _removingId = id; - _removingRequestId = session->api().request( - MTPchatlists_GetLeaveChatlistSuggestions( - MTP_inputChatlistDialogFilter( - MTP_int(id))) - ).done(crl::guard(&_outer, [=](const MTPVector &result) { - _removingRequestId = 0; - const auto suggestRemovePeers = ranges::views::all( - result.v - ) | ranges::views::transform([=](const MTPPeer &peer) { - return session->data().peer(peerFromMTP(peer)); - }) | ranges::to_vector; - const auto chosen = crl::guard(&_outer, [=]( - std::vector> peers) { - remove(id, std::move(peers)); - }); - confirm(crl::guard(&_outer, [=] { - Api::ProcessFilterRemove( - _session, - filter.title(), - filter.iconEmoji(), - suggestRemoving, - suggestRemovePeers, - chosen); - }), true); - })).fail(crl::guard(&_outer, [=] { - _removingRequestId = 0; - simple(); - })).send(); -} - -void FiltersMenu::remove( - FilterId id, - std::vector> leave) { - const auto session = &_session->session(); - const auto api = &session->api(); - session->data().chatsFilters().apply(MTP_updateDialogFilter( - MTP_flags(MTPDupdateDialogFilter::Flag(0)), - MTP_int(id), - MTPDialogFilter())); - if (leave.empty()) { - api->request(MTPmessages_UpdateDialogFilter( - MTP_flags(MTPmessages_UpdateDialogFilter::Flag(0)), - MTP_int(id), - MTPDialogFilter() - )).send(); - } else { - api->request(MTPchatlists_LeaveChatlist( - MTP_inputChatlistDialogFilter(MTP_int(id)), - MTP_vector(ranges::views::all( - leave - ) | ranges::views::transform([](not_null peer) { - return MTPInputPeer(peer->input); - }) | ranges::to>()) - )).done([=](const MTPUpdates &result) { - api->applyUpdates(result); - }).send(); - } -} - void FiltersMenu::applyReorder( not_null widget, int oldPosition, diff --git a/Telegram/SourceFiles/window/window_filters_menu.h b/Telegram/SourceFiles/window/window_filters_menu.h index 54e3189c1..805ae18c5 100644 --- a/Telegram/SourceFiles/window/window_filters_menu.h +++ b/Telegram/SourceFiles/window/window_filters_menu.h @@ -7,6 +7,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL */ #pragma once +#include "api/api_chat_filters_remove_manager.h" #include "base/timer.h" #include "ui/effects/animations.h" #include "ui/widgets/side_bar_button.h" @@ -48,9 +49,6 @@ private: bool toBeginning = false); void setupMainMenuIcon(); void showMenu(QPoint position, FilterId id); - void showEditBox(FilterId id); - void showRemoveBox(FilterId id); - void remove(FilterId id, std::vector> leave = {}); void scrollToButton(not_null widget); void openFiltersSettings(); @@ -70,6 +68,8 @@ private: bool _ignoreRefresh = false; bool _waitingSuggested = false; + Api::RemoveComplexChatFilter _removeApi; + FilterId _removingId = 0; mtpRequestId _removingRequestId = 0;