From 91fda6b65402be705ce23ef5a6f3dcffa8de7354 Mon Sep 17 00:00:00 2001 From: John Preston Date: Tue, 1 Aug 2017 14:43:50 +0300 Subject: [PATCH] Add search from group member button to dialogs. --- Telegram/Resources/icons/dialogs_calendar.png | Bin 209 -> 173 bytes .../Resources/icons/dialogs_calendar@2x.png | Bin 275 -> 255 bytes .../Resources/icons/dialogs_search_from.png | Bin 0 -> 343 bytes .../icons/dialogs_search_from@2x.png | Bin 0 -> 660 bytes Telegram/SourceFiles/apiwrap.cpp | 42 ++++++++ Telegram/SourceFiles/apiwrap.h | 2 + Telegram/SourceFiles/dialogs/dialogs.style | 9 +- Telegram/SourceFiles/dialogswidget.cpp | 17 +++- Telegram/SourceFiles/dialogswidget.h | 2 + .../history/history_inner_widget.cpp | 2 +- Telegram/SourceFiles/mainwidget.cpp | 94 +----------------- Telegram/SourceFiles/mainwidget.h | 4 +- .../SourceFiles/window/window_controller.cpp | 50 ++++++++++ .../SourceFiles/window/window_controller.h | 2 + 14 files changed, 124 insertions(+), 100 deletions(-) create mode 100644 Telegram/Resources/icons/dialogs_search_from.png create mode 100644 Telegram/Resources/icons/dialogs_search_from@2x.png diff --git a/Telegram/Resources/icons/dialogs_calendar.png b/Telegram/Resources/icons/dialogs_calendar.png index b87305a0031af3fe3b02e41fe628ec55b34583d9..b62520990f4776900ec89c689d2a52983345977f 100644 GIT binary patch literal 173 zcmeAS@N?(olHy`uVBq!ia0vp^;y^6M!3HF?%h*|gREejHV~9oX+sU`N4k&Oql)m|2 z@AX&jy9kf3w6?sI^#x~6_IyPK4Uxi-PJ5m3(15r7D&4k|&OdtM@?=xi_um^0m5Pd3 zHg_!!G8QmAU!%J8lQGu~A>&11?`}_vzo&X<+RXD;3T7IA)}Gk0!~FZ-@J;U>yq}8y Xv$xSJxRrYmXg`CetDnm{r-UW|RW?A` literal 209 zcmV;?051QDP)BDx6=c;SQI(ha&Mk~ z`M2L7V|&5;?zyv~zRj2Vb6~lUor{aGpk?lf*LjVRPBOk7i#ZET-rscjUi4@Alz+3r zH|HL8mhlarGt)ElR*(E#W%xhD#B;p)vfCBTc4{f_b3Bquwq|YMflFwN~>;edlXw}>|7!8WRCvd?6}KH zkJ8w7f9QW)Ao%m|sraeSzx`O%Vlhj=ee>EM?2LcnOy4c~)d}^0bfrQlg)tn*Q zd%ZalGv}G-X}cMkoJlftd%3rJRbJBhf4fchJ$<>?yXWJSIZ;Z_*R0lDI^&v_lGKqO za+jN9V;jG2dm`!FoRqOcboM*Z_1}uZ((;qHi!PRs5&?+@@bGpm1lx4%OZA)hWnuFR zq764kto?efbVkP7xxen4MEYvJlt{iQV)1;9=FFVdQ&MBb@0O&Y$6951J diff --git a/Telegram/Resources/icons/dialogs_search_from.png b/Telegram/Resources/icons/dialogs_search_from.png new file mode 100644 index 0000000000000000000000000000000000000000..d0022e366e80bb24669926e48996436578a85e06 GIT binary patch literal 343 zcmV-d0jU0oP)Zt~5JhJp9d0O1L1hWfvs7?7OvyEX26F)@LAFFi=Z1pWA|l0Zz(&z3k@6*1Gyhrs z9{UCW2yc?}F7Q8q2SETuQGikklv2Ps2TG~c26(mzA=q^tK1&FJgpgCO5uRn)3wT$W zrl($GEKw94*5Wum^%~*BFdWwUzBk#;nF}FaB5B(eJ$;dE36^Dv<2d5F zu3vet>x$zzVp*1Wzu(byUHi-#V_4Vq;e0=)H;kwZ073THC$Q pd7f?V+32}6idXgf|M{PUKLA$4r=Vl$$#nn#002ovPDHLkV1g*amE-^b literal 0 HcmV?d00001 diff --git a/Telegram/Resources/icons/dialogs_search_from@2x.png b/Telegram/Resources/icons/dialogs_search_from@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..0cfbdd56b2588316fea867ae4e4577df560bb771 GIT binary patch literal 660 zcmV;F0&D$=P);MwV*qKZTrQL4a(P#Ju~?8|u}CHBL$jwv zBoaZXR6;tPMmQV>08Azmv|24R8VyV)6Dm2>#Wfrb2b@kP0N`{w;e0+*J^y9mujbbd zpg%MZ<2VknSPX$c0Diw8E|&`ca6BHdSS&D~&oLg4vDs`4XBiT=+wDjs5=bVKNTpJU z$K!Cj-FN>%6h*;)zsG1aLc85Yr_({V+r{m6dn*6oR>W}};d!161_Rwg=POiICH;P% z@H|gAj(cq%&tx)WG#VKa{)*vnNHUqsYsBmII(6Z{snu$9#dEpb%cV84*(^Qre!p*; zc(2!^H}bdJEj%8No>If?b~|{z-hbBU9zZsmd9zASmTnun-EK(c5%gr~9zdJT2G{G= ukdR&uhr_ou)=!q%SmI`5iJOfjZZ@CLP~-R_03(M00000 peer, const QDate &date) { + // API returns a message with date <= offset_date. + // So we request a message with offset_date = desired_date - 1 and add_offset = -1. + // This should give us the first message with date >= desired_date. + auto offset_date = static_cast(QDateTime(date).toTime_t()) - 1; + auto add_offset = -1; + auto limit = 1; + request(MTPmessages_GetHistory(peer->input, MTP_int(0), MTP_int(offset_date), MTP_int(add_offset), MTP_int(limit), MTP_int(0), MTP_int(0))).done([peer](const MTPmessages_Messages &result) { + auto getMessagesList = [&result, peer]() -> const QVector* { + auto handleMessages = [](auto &messages) { + App::feedUsers(messages.vusers); + App::feedChats(messages.vchats); + return &messages.vmessages.v; + }; + switch (result.type()) { + case mtpc_messages_messages: return handleMessages(result.c_messages_messages()); + case mtpc_messages_messagesSlice: return handleMessages(result.c_messages_messagesSlice()); + case mtpc_messages_channelMessages: { + auto &messages = result.c_messages_channelMessages(); + if (peer && peer->isChannel()) { + peer->asChannel()->ptsReceived(messages.vpts.v); + } else { + LOG(("API Error: received messages.channelMessages when no channel was passed! (MainWidget::showJumpToDate)")); + } + return handleMessages(messages); + } break; + } + return nullptr; + }; + + if (auto list = getMessagesList()) { + App::feedMsgs(*list, NewMessageExisting); + for (auto &message : *list) { + auto id = idFromMessage(message); + Ui::showPeerHistory(peer, id); + return; + } + } + Ui::showPeerHistory(peer, ShowAtUnreadMsgId); + }).send(); +} + ApiWrap::~ApiWrap() = default; diff --git a/Telegram/SourceFiles/apiwrap.h b/Telegram/SourceFiles/apiwrap.h index be78fb311..ed347e6db 100644 --- a/Telegram/SourceFiles/apiwrap.h +++ b/Telegram/SourceFiles/apiwrap.h @@ -94,6 +94,8 @@ public: void applyUpdatesNoPtsCheck(const MTPUpdates &updates); void applyUpdateNoPtsCheck(const MTPUpdate &update); + void jumpToDate(gsl::not_null peer, const QDate &date); + ~ApiWrap(); private: diff --git a/Telegram/SourceFiles/dialogs/dialogs.style b/Telegram/SourceFiles/dialogs/dialogs.style index 231686f77..08b79eeaf 100644 --- a/Telegram/SourceFiles/dialogs/dialogs.style +++ b/Telegram/SourceFiles/dialogs/dialogs.style @@ -100,12 +100,17 @@ dialogsLock: IconButton(dialogsMenuToggle) { dialogsUnlockIcon: icon {{ "dialogs_unlock", dialogsMenuIconFg }}; dialogsUnlockIconOver: icon {{ "dialogs_unlock", dialogsMenuIconFgOver }}; dialogsCalendar: IconButton { - width: 32px; + width: 29px; height: 32px; icon: icon {{ "dialogs_calendar", dialogsMenuIconFg }}; iconOver: icon {{ "dialogs_calendar", dialogsMenuIconFgOver }}; - iconPosition: point(3px, 3px); + iconPosition: point(0px, 5px); +} +dialogsSearchFrom: IconButton(dialogsCalendar) { + width: 26px; + icon: icon {{ "dialogs_search_from", dialogsMenuIconFg }}; + iconOver: icon {{ "dialogs_search_from", dialogsMenuIconFgOver }}; } dialogsFilter: FlatInput(defaultFlatInput) { diff --git a/Telegram/SourceFiles/dialogswidget.cpp b/Telegram/SourceFiles/dialogswidget.cpp index 9189b6bfc..9efff93c8 100644 --- a/Telegram/SourceFiles/dialogswidget.cpp +++ b/Telegram/SourceFiles/dialogswidget.cpp @@ -2329,6 +2329,7 @@ void DialogsWidget::UpdateButton::paintEvent(QPaintEvent *e) { DialogsWidget::DialogsWidget(QWidget *parent, gsl::not_null controller) : Window::AbstractSectionWidget(parent, controller) , _mainMenuToggle(this, st::dialogsMenuToggle) , _filter(this, st::dialogsFilter, langFactory(lng_dlg_filter)) +, _searchFromUser(this, object_ptr(this, st::dialogsSearchFrom)) , _jumpToDate(this, object_ptr(this, st::dialogsCalendar)) , _cancelSearch(this, st::dialogsCancelSearch) , _lockUnlock(this, st::dialogsLock) @@ -2358,7 +2359,8 @@ DialogsWidget::DialogsWidget(QWidget *parent, gsl::not_null subscribe(Adaptive::Changed(), [this] { updateForwardBar(); }); _cancelSearch->setClickedCallback([this] { onCancelSearch(); }); - _jumpToDate->entity()->setClickedCallback([this] { if (_searchInPeer) App::main()->showJumpToDate(_searchInPeer, QDate()); }); + _jumpToDate->entity()->setClickedCallback([this] { if (_searchInPeer) this->controller()->showJumpToDate(_searchInPeer, QDate()); }); + _searchFromUser->entity()->setClickedCallback([this] { if (_searchInPeer->isChat() || _searchInPeer->isMegagroup()) showSearchFrom(); }); _lockUnlock->setVisible(Global::LocalPasscode()); subscribe(Global::RefLocalPasscodeChanged(), [this] { updateLockUnlockVisibility(); }); _lockUnlock->setClickedCallback([this] { @@ -2485,6 +2487,7 @@ void DialogsWidget::showAnimated(Window::SlideDirection direction, const Window: _filter->hide(); _cancelSearch->hideFast(); _jumpToDate->hideFast(); + _searchFromUser->hideFast(); _lockUnlock->hide(); int delta = st::slideShift; @@ -3059,6 +3062,10 @@ void DialogsWidget::setSearchInPeer(PeerData *peer) { _inner->searchInPeer(_searchInPeer); } +void DialogsWidget::showSearchFrom() { + +} + void DialogsWidget::onFilterCursorMoved(int from, int to) { if (to < 0) to = _filter->cursorPosition(); QString t = _filter->getLastText(); @@ -3122,6 +3129,13 @@ void DialogsWidget::updateJumpToDateVisibility(bool fast) { } else { _jumpToDate->toggleAnimated(jumpToDateVisible); } + + auto searchFromUserVisible = _searchInPeer && (_searchInPeer->isChat() || _searchInPeer->isMegagroup()); + if (fast) { + _searchFromUser->toggleFast(searchFromUserVisible); + } else { + _searchFromUser->toggleAnimated(searchFromUserVisible); + } } void DialogsWidget::updateControlsGeometry() { @@ -3144,6 +3158,7 @@ void DialogsWidget::updateControlsGeometry() { _lockUnlock->moveToLeft(filterLeft + filterWidth + st::dialogsFilterPadding.x(), filterAreaTop + st::dialogsFilterPadding.y()); _cancelSearch->moveToLeft(filterLeft + filterWidth - _cancelSearch->width(), _filter->y()); _jumpToDate->moveToLeft(filterLeft + filterWidth - _jumpToDate->width(), _filter->y()); + _searchFromUser->moveToLeft(filterLeft + filterWidth - _jumpToDate->width() - _searchFromUser->width(), _filter->y()); auto scrollTop = filterAreaTop + filterAreaHeight; auto addToScroll = App::main() ? App::main()->contentScrollAddToY() : 0; diff --git a/Telegram/SourceFiles/dialogswidget.h b/Telegram/SourceFiles/dialogswidget.h index 5bda639d3..3fb3dc15e 100644 --- a/Telegram/SourceFiles/dialogswidget.h +++ b/Telegram/SourceFiles/dialogswidget.h @@ -401,6 +401,7 @@ private: void peerSearchReceived(const MTPcontacts_Found &result, mtpRequestId requestId); void setSearchInPeer(PeerData *peer); + void showSearchFrom(); void showMainMenu(); void updateLockUnlockVisibility(); void updateJumpToDateVisibility(bool fast = false); @@ -429,6 +430,7 @@ private: object_ptr _forwardCancel = { nullptr }; object_ptr _mainMenuToggle; object_ptr _filter; + object_ptr> _searchFromUser; object_ptr> _jumpToDate; object_ptr _cancelSearch; object_ptr _lockUnlock; diff --git a/Telegram/SourceFiles/history/history_inner_widget.cpp b/Telegram/SourceFiles/history/history_inner_widget.cpp index 403aa0d3b..2d0543f60 100644 --- a/Telegram/SourceFiles/history/history_inner_widget.cpp +++ b/Telegram/SourceFiles/history/history_inner_widget.cpp @@ -49,7 +49,7 @@ public: } void onClick(Qt::MouseButton) const override { - App::main()->showJumpToDate(_peer, _date); + App::wnd()->controller()->showJumpToDate(_peer, _date); } private: diff --git a/Telegram/SourceFiles/mainwidget.cpp b/Telegram/SourceFiles/mainwidget.cpp index 402a7b4c0..36da10026 100644 --- a/Telegram/SourceFiles/mainwidget.cpp +++ b/Telegram/SourceFiles/mainwidget.cpp @@ -66,7 +66,6 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "styles/style_boxes.h" #include "mtproto/dc_options.h" #include "core/file_utilities.h" -#include "boxes/calendar_box.h" #include "auth_session.h" #include "window/notifications_manager.h" #include "window/window_controller.h" @@ -2991,97 +2990,6 @@ void MainWidget::dlgUpdated(PeerData *peer, MsgId msgId) { } } -void MainWidget::showJumpToDate(PeerData *peer, QDate requestedDate) { - Expects(peer != nullptr); - auto currentPeerDate = [peer] { - if (auto history = App::historyLoaded(peer)) { - if (history->scrollTopItem) { - return history->scrollTopItem->date.date(); - } else if (history->loadedAtTop() && !history->isEmpty() && history->peer->migrateFrom()) { - if (auto migrated = App::historyLoaded(history->peer->migrateFrom())) { - if (migrated->scrollTopItem) { - // We're up in the migrated history. - // So current date is the date of first message here. - return history->blocks.front()->items.front()->date.date(); - } - } - } else if (!history->lastMsgDate.isNull()) { - return history->lastMsgDate.date(); - } - } - return QDate::currentDate(); - }; - auto maxPeerDate = [peer] { - if (auto history = App::historyLoaded(peer)) { - if (!history->lastMsgDate.isNull()) { - return history->lastMsgDate.date(); - } - } - return QDate::currentDate(); - }; - auto minPeerDate = [peer] { - if (auto history = App::historyLoaded(peer)) { - if (history->loadedAtTop()) { - if (history->isEmpty()) { - return QDate::currentDate(); - } - return history->blocks.front()->items.front()->date.date(); - } - } - return QDate(2013, 8, 1); // Telegram was launched in August 2013 :) - }; - auto highlighted = requestedDate.isNull() ? currentPeerDate() : requestedDate; - auto month = highlighted; - auto box = Box(month, highlighted, [this, peer](const QDate &date) { jumpToDate(peer, date); }); - box->setMinDate(minPeerDate()); - box->setMaxDate(maxPeerDate()); - Ui::show(std::move(box)); -} - -void MainWidget::jumpToDate(PeerData *peer, const QDate &date) { - // API returns a message with date <= offset_date. - // So we request a message with offset_date = desired_date - 1 and add_offset = -1. - // This should give us the first message with date >= desired_date. - auto offset_date = static_cast(QDateTime(date).toTime_t()) - 1; - auto add_offset = -1; - auto limit = 1; - auto flags = MTPmessages_Search::Flags(0); - auto request = MTPmessages_GetHistory(peer->input, MTP_int(0), MTP_int(offset_date), MTP_int(add_offset), MTP_int(limit), MTP_int(0), MTP_int(0)); - MTP::send(request, ::rpcDone([peer](const MTPmessages_Messages &result) { - auto getMessagesList = [&result, peer]() -> const QVector* { - auto handleMessages = [](auto &messages) { - App::feedUsers(messages.vusers); - App::feedChats(messages.vchats); - return &messages.vmessages.v; - }; - switch (result.type()) { - case mtpc_messages_messages: return handleMessages(result.c_messages_messages()); - case mtpc_messages_messagesSlice: return handleMessages(result.c_messages_messagesSlice()); - case mtpc_messages_channelMessages: { - auto &messages = result.c_messages_channelMessages(); - if (peer && peer->isChannel()) { - peer->asChannel()->ptsReceived(messages.vpts.v); - } else { - LOG(("API Error: received messages.channelMessages when no channel was passed! (MainWidget::showJumpToDate)")); - } - return handleMessages(messages); - } break; - } - return nullptr; - }; - - if (auto list = getMessagesList()) { - App::feedMsgs(*list, NewMessageExisting); - for (auto &message : *list) { - auto id = idFromMessage(message); - Ui::showPeerHistory(peer, id); - return; - } - } - Ui::showPeerHistory(peer, ShowAtUnreadMsgId); - })); -} - void MainWidget::windowShown() { _history->windowShown(); } @@ -3102,7 +3010,7 @@ bool MainWidget::deleteChannelFailed(const RPCError &error) { void MainWidget::inviteToChannelDone(ChannelData *channel, const MTPUpdates &updates) { sentUpdatesReceived(updates); - App::api()->requestParticipantsCountDelayed(channel); + AuthSession::Current().api().requestParticipantsCountDelayed(channel); } void MainWidget::historyToDown(History *history) { diff --git a/Telegram/SourceFiles/mainwidget.h b/Telegram/SourceFiles/mainwidget.h index a95174394..2a904489a 100644 --- a/Telegram/SourceFiles/mainwidget.h +++ b/Telegram/SourceFiles/mainwidget.h @@ -187,8 +187,6 @@ public: void dlgUpdated(Dialogs::Mode list, Dialogs::Row *row); void dlgUpdated(PeerData *peer, MsgId msgId); - void showJumpToDate(PeerData *peer, QDate requestedDate); - void windowShown(); void sentUpdatesReceived(uint64 randomId, const MTPUpdates &updates); @@ -317,7 +315,7 @@ public: void hideSingleUseKeyboard(PeerData *peer, MsgId replyTo); bool insertBotCommand(const QString &cmd); - void jumpToDate(PeerData *peer, const QDate &date); + void jumpToDate(gsl::not_null peer, const QDate &date); void searchMessages(const QString &query, PeerData *inPeer); bool preloadOverview(PeerData *peer, MediaOverviewType type); void changingMsgId(HistoryItem *row, MsgId newId); diff --git a/Telegram/SourceFiles/window/window_controller.cpp b/Telegram/SourceFiles/window/window_controller.cpp index 2cfe90819..97b83c42e 100644 --- a/Telegram/SourceFiles/window/window_controller.cpp +++ b/Telegram/SourceFiles/window/window_controller.cpp @@ -24,6 +24,9 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "mainwidget.h" #include "styles/style_window.h" #include "styles/style_dialogs.h" +#include "boxes/calendar_box.h" +#include "auth_session.h" +#include "apiwrap.h" namespace Window { @@ -133,4 +136,51 @@ void Controller::provideChatWidth(int requestedWidth) { } } +void Controller::showJumpToDate(gsl::not_null peer, QDate requestedDate) { + Expects(peer != nullptr); + auto currentPeerDate = [peer] { + if (auto history = App::historyLoaded(peer)) { + if (history->scrollTopItem) { + return history->scrollTopItem->date.date(); + } else if (history->loadedAtTop() && !history->isEmpty() && history->peer->migrateFrom()) { + if (auto migrated = App::historyLoaded(history->peer->migrateFrom())) { + if (migrated->scrollTopItem) { + // We're up in the migrated history. + // So current date is the date of first message here. + return history->blocks.front()->items.front()->date.date(); + } + } + } else if (!history->lastMsgDate.isNull()) { + return history->lastMsgDate.date(); + } + } + return QDate::currentDate(); + }; + auto maxPeerDate = [peer] { + if (auto history = App::historyLoaded(peer)) { + if (!history->lastMsgDate.isNull()) { + return history->lastMsgDate.date(); + } + } + return QDate::currentDate(); + }; + auto minPeerDate = [peer] { + if (auto history = App::historyLoaded(peer)) { + if (history->loadedAtTop()) { + if (history->isEmpty()) { + return QDate::currentDate(); + } + return history->blocks.front()->items.front()->date.date(); + } + } + return QDate(2013, 8, 1); // Telegram was launched in August 2013 :) + }; + auto highlighted = requestedDate.isNull() ? currentPeerDate() : requestedDate; + auto month = highlighted; + auto box = Box(month, highlighted, [this, peer](const QDate &date) { AuthSession::Current().api().jumpToDate(peer, date); }); + box->setMinDate(minPeerDate()); + box->setMaxDate(maxPeerDate()); + Ui::show(std::move(box)); +} + } // namespace Window diff --git a/Telegram/SourceFiles/window/window_controller.h b/Telegram/SourceFiles/window/window_controller.h index 4fb289e44..a506d0340 100644 --- a/Telegram/SourceFiles/window/window_controller.h +++ b/Telegram/SourceFiles/window/window_controller.h @@ -80,6 +80,8 @@ public: bool canProvideChatWidth(int requestedWidth) const; void provideChatWidth(int requestedWidth); + void showJumpToDate(gsl::not_null peer, QDate requestedDate); + base::Variable &dialogsWidthRatio() { return _dialogsWidthRatio; }