mirror of
https://github.com/AyuGram/AyuGramDesktop.git
synced 2025-04-16 06:07:06 +02:00
Implement context menu actions in stories list.
This commit is contained in:
parent
a733b83642
commit
ac534780cc
5 changed files with 116 additions and 45 deletions
|
@ -915,6 +915,11 @@ void ListWidget::showContextMenu(
|
|||
auto canForwardAll = [&] {
|
||||
return ranges::none_of(_selected, [](auto &&item) {
|
||||
return !item.second.canForward;
|
||||
}) && (!_controller->key().storiesPeer() || _selected.size() == 1);
|
||||
};
|
||||
auto canToggleStoryPinAll = [&] {
|
||||
return ranges::none_of(_selected, [](auto &&item) {
|
||||
return !item.second.canToggleStoryPin;
|
||||
});
|
||||
};
|
||||
|
||||
|
@ -1016,6 +1021,16 @@ void ListWidget::showContextMenu(
|
|||
}
|
||||
}
|
||||
if (overSelected == SelectionState::OverSelectedItems) {
|
||||
if (canToggleStoryPinAll()) {
|
||||
const auto tab = _controller->key().storiesTab();
|
||||
const auto pin = (tab == Stories::Tab::Archive);
|
||||
_contextMenu->addAction(
|
||||
(pin
|
||||
? tr::lng_mediaview_save_to_profile
|
||||
: tr::lng_archived_add)(tr::now),
|
||||
crl::guard(this, [this] { toggleStoryPinSelected(); }),
|
||||
(pin ? &st::menuIconStoriesSaved : &st::menuIconArchive));
|
||||
}
|
||||
if (canForwardAll()) {
|
||||
_contextMenu->addAction(
|
||||
tr::lng_context_forward_selected(tr::now),
|
||||
|
@ -1045,6 +1060,18 @@ void ListWidget::showContextMenu(
|
|||
const auto selectionData = _provider->computeSelectionData(
|
||||
item,
|
||||
FullSelection);
|
||||
if (selectionData.canToggleStoryPin) {
|
||||
const auto tab = _controller->key().storiesTab();
|
||||
const auto pin = (tab == Stories::Tab::Archive);
|
||||
_contextMenu->addAction(
|
||||
(pin
|
||||
? tr::lng_mediaview_save_to_profile
|
||||
: tr::lng_mediaview_archive_story)(tr::now),
|
||||
crl::guard(this, [=] {
|
||||
toggleStoryPin({ 1, globalId.itemId });
|
||||
}),
|
||||
(pin ? &st::menuIconStoriesSaved : &st::menuIconArchive));
|
||||
}
|
||||
if (selectionData.canForward) {
|
||||
_contextMenu->addAction(
|
||||
tr::lng_context_forward_msg(tr::now),
|
||||
|
@ -1066,6 +1093,20 @@ void ListWidget::showContextMenu(
|
|||
}
|
||||
}
|
||||
}
|
||||
if (const auto peer = _controller->key().storiesPeer()) {
|
||||
if (!peer->isSelf() && IsStoryMsgId(globalId.itemId.msg)) {
|
||||
const auto storyId = FullStoryId{
|
||||
globalId.itemId.peer,
|
||||
StoryIdFromMsgId(globalId.itemId.msg),
|
||||
};
|
||||
_contextMenu->addAction(
|
||||
tr::lng_profile_report(tr::now),
|
||||
[=] { ::Media::Stories::ReportRequested(
|
||||
_controller->uiShow(),
|
||||
storyId); },
|
||||
&st::menuIconReport);
|
||||
}
|
||||
}
|
||||
if (!_provider->hasSelectRestriction()) {
|
||||
_contextMenu->addAction(
|
||||
tr::lng_context_select_msg(tr::now),
|
||||
|
@ -1105,16 +1146,7 @@ void ListWidget::contextMenuEvent(QContextMenuEvent *e) {
|
|||
}
|
||||
|
||||
void ListWidget::forwardSelected() {
|
||||
if (_controller->storiesPeer()) {
|
||||
const auto ids = collectSelectedIds();
|
||||
if (ids.size() == 1 && IsStoryMsgId(ids.front().msg)) {
|
||||
const auto id = ids.front();
|
||||
_controller->parentController()->show(
|
||||
::Media::Stories::PrepareShareBox(
|
||||
_controller->parentController()->uiShow(),
|
||||
{ id.peer, StoryIdFromMsgId(id.msg) }));
|
||||
}
|
||||
} else if (auto items = collectSelectedIds(); !items.empty()) {
|
||||
if (auto items = collectSelectedIds(); !items.empty()) {
|
||||
forwardItems(std::move(items));
|
||||
}
|
||||
}
|
||||
|
@ -1129,15 +1161,25 @@ void ListWidget::forwardItem(GlobalMsgId globalId) {
|
|||
}
|
||||
|
||||
void ListWidget::forwardItems(MessageIdsList &&items) {
|
||||
auto callback = [weak = Ui::MakeWeak(this)] {
|
||||
if (const auto strong = weak.data()) {
|
||||
strong->clearSelected();
|
||||
if (_controller->storiesPeer()) {
|
||||
if (items.size() == 1 && IsStoryMsgId(items.front().msg)) {
|
||||
const auto id = items.front();
|
||||
_controller->parentController()->show(
|
||||
::Media::Stories::PrepareShareBox(
|
||||
_controller->parentController()->uiShow(),
|
||||
{ id.peer, StoryIdFromMsgId(id.msg) }));
|
||||
}
|
||||
};
|
||||
setActionBoxWeak(Window::ShowForwardMessagesBox(
|
||||
_controller,
|
||||
std::move(items),
|
||||
std::move(callback)));
|
||||
} else {
|
||||
auto callback = [weak = Ui::MakeWeak(this)] {
|
||||
if (const auto strong = weak.data()) {
|
||||
strong->clearSelected();
|
||||
}
|
||||
};
|
||||
setActionBoxWeak(Window::ShowForwardMessagesBox(
|
||||
_controller,
|
||||
std::move(items),
|
||||
std::move(callback)));
|
||||
}
|
||||
}
|
||||
|
||||
void ListWidget::deleteSelected() {
|
||||
|
@ -1147,12 +1189,16 @@ void ListWidget::deleteSelected() {
|
|||
}
|
||||
|
||||
void ListWidget::toggleStoryPinSelected() {
|
||||
auto list = std::vector<FullStoryId>();
|
||||
const auto confirmed = crl::guard(this, [=] {
|
||||
toggleStoryPin(collectSelectedIds(), crl::guard(this, [=] {
|
||||
clearSelected();
|
||||
});
|
||||
for (const auto &item : collectSelectedItems().list) {
|
||||
const auto id = item.globalId.itemId;
|
||||
}));
|
||||
}
|
||||
|
||||
void ListWidget::toggleStoryPin(
|
||||
MessageIdsList &&items,
|
||||
Fn<void()> confirmed) {
|
||||
auto list = std::vector<FullStoryId>();
|
||||
for (const auto &id : items) {
|
||||
if (IsStoryMsgId(id.msg)) {
|
||||
list.push_back({ id.peer, StoryIdFromMsgId(id.msg) });
|
||||
}
|
||||
|
@ -1165,7 +1211,9 @@ void ListWidget::toggleStoryPinSelected() {
|
|||
controller->showToast(
|
||||
::Media::Stories::PrepareTogglePinnedToast(count, pin));
|
||||
close();
|
||||
confirmed();
|
||||
if (confirmed) {
|
||||
confirmed();
|
||||
}
|
||||
};
|
||||
const auto session = &_controller->session();
|
||||
const auto onePhrase = pin
|
||||
|
|
|
@ -192,6 +192,9 @@ private:
|
|||
void toggleStoryPinSelected();
|
||||
void deleteItem(GlobalMsgId globalId);
|
||||
void deleteItems(SelectedItems &&items, Fn<void()> confirmed = nullptr);
|
||||
void toggleStoryPin(
|
||||
MessageIdsList &&items,
|
||||
Fn<void()> confirmed = nullptr);
|
||||
void applyItemSelection(
|
||||
HistoryItem *item,
|
||||
TextSelection selection);
|
||||
|
|
|
@ -314,7 +314,21 @@ ListItemSelectionData Provider::computeSelectionData(
|
|||
auto result = ListItemSelectionData(selection);
|
||||
const auto peer = item->history()->peer;
|
||||
result.canDelete = peer->isSelf();
|
||||
result.canForward = peer->isSelf();
|
||||
result.canForward = [&] {
|
||||
if (!peer->isSelf()) {
|
||||
return false;
|
||||
}
|
||||
const auto id = item->id;
|
||||
if (!IsStoryMsgId(id)) {
|
||||
return false;
|
||||
}
|
||||
const auto maybeStory = peer->owner().stories().lookup(
|
||||
{ peer->id, StoryIdFromMsgId(id) });
|
||||
if (!maybeStory) {
|
||||
return false;
|
||||
}
|
||||
return (*maybeStory)->canShare();
|
||||
}();
|
||||
result.canToggleStoryPin = peer->isSelf();
|
||||
return result;
|
||||
}
|
||||
|
|
|
@ -1278,26 +1278,7 @@ void Controller::deleteRequested() {
|
|||
}
|
||||
|
||||
void Controller::reportRequested() {
|
||||
const auto story = this->story();
|
||||
if (!story) {
|
||||
return;
|
||||
}
|
||||
const auto id = story->fullId();
|
||||
const auto owner = &story->owner();
|
||||
const auto confirmed = [=](Fn<void()> close) {
|
||||
owner->stories().deleteList({ id });
|
||||
close();
|
||||
};
|
||||
const auto show = uiShow();
|
||||
const auto st = &st::storiesReportBox;
|
||||
show->show(Box(Ui::ReportReasonBox, *st, Ui::ReportSource::Story, [=](
|
||||
Ui::ReportReason reason) {
|
||||
const auto done = [=](const QString &text) {
|
||||
owner->stories().report(show, id, reason, text);
|
||||
show->hideLayer();
|
||||
};
|
||||
show->showBox(Box(Ui::ReportDetailsBox, *st, done));
|
||||
}));
|
||||
ReportRequested(uiShow(), _shown, &st::storiesReportBox);
|
||||
}
|
||||
|
||||
void Controller::togglePinnedRequested(bool pinned) {
|
||||
|
@ -1391,4 +1372,20 @@ Ui::Toast::Config PrepareTogglePinnedToast(int count, bool pinned) {
|
|||
};
|
||||
}
|
||||
|
||||
void ReportRequested(
|
||||
std::shared_ptr<Main::SessionShow> show,
|
||||
FullStoryId id,
|
||||
const style::ReportBox *stOverride) {
|
||||
const auto owner = &show->session().data();
|
||||
const auto st = stOverride ? stOverride : &st::defaultReportBox;
|
||||
show->show(Box(Ui::ReportReasonBox, *st, Ui::ReportSource::Story, [=](
|
||||
Ui::ReportReason reason) {
|
||||
const auto done = [=](const QString &text) {
|
||||
owner->stories().report(show, id, reason, text);
|
||||
show->hideLayer();
|
||||
};
|
||||
show->showBox(Box(Ui::ReportDetailsBox, *st, done));
|
||||
}));
|
||||
}
|
||||
|
||||
} // namespace Media::Stories
|
||||
|
|
|
@ -10,6 +10,10 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
#include "data/data_stories.h"
|
||||
#include "ui/effects/animations.h"
|
||||
|
||||
namespace style {
|
||||
struct ReportBox;
|
||||
} // namespace style
|
||||
|
||||
namespace base {
|
||||
class PowerSaveBlocker;
|
||||
} // namespace base
|
||||
|
@ -40,6 +44,7 @@ struct Config;
|
|||
|
||||
namespace Main {
|
||||
class Session;
|
||||
class SessionShow;
|
||||
} // namespace Main
|
||||
|
||||
namespace Media::Player {
|
||||
|
@ -260,5 +265,9 @@ private:
|
|||
[[nodiscard]] Ui::Toast::Config PrepareTogglePinnedToast(
|
||||
int count,
|
||||
bool pinned);
|
||||
void ReportRequested(
|
||||
std::shared_ptr<Main::SessionShow> show,
|
||||
FullStoryId id,
|
||||
const style::ReportBox *stOverride = nullptr);
|
||||
|
||||
} // namespace Media::Stories
|
||||
|
|
Loading…
Add table
Reference in a new issue