mirror of
https://github.com/AyuGram/AyuGramDesktop.git
synced 2025-04-16 06:07:06 +02:00
Added ability to set forward options from ShareBox.
This commit is contained in:
parent
02c9b61840
commit
641bb01ba2
7 changed files with 229 additions and 52 deletions
|
@ -1116,7 +1116,8 @@ void ShareInviteLinkBox(not_null<PeerData*> peer, const QString &link) {
|
|||
auto submitCallback = [=](
|
||||
std::vector<not_null<PeerData*>> &&result,
|
||||
TextWithTags &&comment,
|
||||
Api::SendOptions options) {
|
||||
Api::SendOptions options,
|
||||
Data::ForwardOptions) {
|
||||
if (*sending || result.empty()) {
|
||||
return;
|
||||
}
|
||||
|
|
|
@ -15,11 +15,15 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
#include "storage/storage_account.h"
|
||||
#include "ui/boxes/confirm_box.h"
|
||||
#include "apiwrap.h"
|
||||
#include "ui/chat/forward_options_box.h"
|
||||
#include "ui/toast/toast.h"
|
||||
#include "ui/widgets/checkbox.h"
|
||||
#include "ui/widgets/multi_select.h"
|
||||
#include "ui/widgets/buttons.h"
|
||||
#include "ui/widgets/scroll_area.h"
|
||||
#include "ui/widgets/input_fields.h"
|
||||
#include "ui/widgets/menu/menu_action.h"
|
||||
#include "ui/widgets/popup_menu.h"
|
||||
#include "ui/wrap/slide_wrap.h"
|
||||
#include "ui/text/text_options.h"
|
||||
#include "chat_helpers/message_field.h"
|
||||
|
@ -40,6 +44,44 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
#include "styles/style_layers.h"
|
||||
#include "styles/style_boxes.h"
|
||||
#include "styles/style_chat.h"
|
||||
#include "styles/style_menu_icons.h"
|
||||
#include "styles/style_media_player.h"
|
||||
|
||||
namespace {
|
||||
|
||||
class ForwardOptionItem final : public Ui::Menu::Action {
|
||||
public:
|
||||
using Ui::Menu::Action::Action;
|
||||
|
||||
void init(bool checked) {
|
||||
enableMouseSelecting();
|
||||
|
||||
AbstractButton::setDisabled(true);
|
||||
|
||||
_checkView = std::make_unique<Ui::CheckView>(st::defaultCheck, false);
|
||||
_checkView->checkedChanges(
|
||||
) | rpl::start_with_next([=](bool checked) {
|
||||
setIcon(checked ? &st::mediaPlayerMenuCheck : nullptr);
|
||||
}, lifetime());
|
||||
|
||||
_checkView->setChecked(checked, anim::type::normal);
|
||||
AbstractButton::clicks(
|
||||
) | rpl::start_with_next([=] {
|
||||
_checkView->setChecked(
|
||||
!_checkView->checked(),
|
||||
anim::type::normal);
|
||||
}, lifetime());
|
||||
}
|
||||
|
||||
not_null<Ui::CheckView*> checkView() const {
|
||||
return _checkView.get();
|
||||
}
|
||||
|
||||
private:
|
||||
std::unique_ptr<Ui::CheckView> _checkView;
|
||||
};
|
||||
|
||||
} // namespace
|
||||
|
||||
class ShareBox::Inner final : public Ui::RpWidget {
|
||||
public:
|
||||
|
@ -442,17 +484,68 @@ SendMenu::Type ShareBox::sendMenuType() const {
|
|||
: SendMenu::Type::Scheduled;
|
||||
}
|
||||
|
||||
void ShareBox::showMenu(not_null<Ui::RpWidget*> parent) {
|
||||
if (_menu) {
|
||||
_menu = nullptr;
|
||||
return;
|
||||
}
|
||||
_menu.emplace(parent, st::popupMenuWithIcons);
|
||||
|
||||
if (_descriptor.forwardOptions.show) {
|
||||
auto createView = [&](rpl::producer<QString> &&text, bool checked) {
|
||||
auto item = base::make_unique_q<ForwardOptionItem>(
|
||||
_menu->menu(),
|
||||
st::popupMenuWithIcons.menu,
|
||||
new QAction(QString(), _menu->menu()),
|
||||
nullptr,
|
||||
nullptr);
|
||||
std::move(
|
||||
text
|
||||
) | rpl::start_with_next([action = item->action()](QString text) {
|
||||
action->setText(text);
|
||||
}, item->lifetime());
|
||||
item->init(checked);
|
||||
const auto view = item->checkView();
|
||||
_menu->addAction(std::move(item));
|
||||
return view;
|
||||
};
|
||||
Ui::FillForwardOptions(
|
||||
std::move(createView),
|
||||
_descriptor.forwardOptions.messagesCount,
|
||||
_forwardOptions,
|
||||
[=](Ui::ForwardOptions value) { _forwardOptions = value; },
|
||||
_menu->lifetime());
|
||||
|
||||
_menu->addSeparator();
|
||||
}
|
||||
|
||||
const auto result = SendMenu::FillSendMenu(
|
||||
_menu.get(),
|
||||
sendMenuType(),
|
||||
[=] { submitSilent(); },
|
||||
[=] { submitScheduled(); });
|
||||
const auto success = (result == SendMenu::FillMenuResult::Success);
|
||||
if (_descriptor.forwardOptions.show || success) {
|
||||
_menu->setForcedOrigin(Ui::PanelAnimation::Origin::BottomRight);
|
||||
_menu->popup(QCursor::pos());
|
||||
}
|
||||
}
|
||||
|
||||
void ShareBox::createButtons() {
|
||||
clearButtons();
|
||||
if (_hasSelected) {
|
||||
const auto send = addButton(tr::lng_share_confirm(), [=] {
|
||||
submit({});
|
||||
});
|
||||
SendMenu::SetupMenuAndShortcuts(
|
||||
send,
|
||||
[=] { return sendMenuType(); },
|
||||
[=] { submitSilent(); },
|
||||
[=] { submitScheduled(); });
|
||||
_forwardOptions.hasCaptions = _descriptor.forwardOptions.hasCaptions;
|
||||
|
||||
send->setAcceptBoth();
|
||||
send->clicks(
|
||||
) | rpl::start_with_next([=](Qt::MouseButton button) {
|
||||
if (button == Qt::RightButton) {
|
||||
showMenu(send);
|
||||
}
|
||||
}, send->lifetime());
|
||||
} else if (_descriptor.copyCallback) {
|
||||
addButton(_copyLinkText.value(), [=] { copyLink(); });
|
||||
}
|
||||
|
@ -488,10 +581,17 @@ void ShareBox::innerSelectedChanged(PeerData *peer, bool checked) {
|
|||
|
||||
void ShareBox::submit(Api::SendOptions options) {
|
||||
if (const auto onstack = _descriptor.submitCallback) {
|
||||
const auto forwardOptions = (_forwardOptions.hasCaptions
|
||||
&& _forwardOptions.dropCaptions)
|
||||
? Data::ForwardOptions::NoNamesAndCaptions
|
||||
: _forwardOptions.dropNames
|
||||
? Data::ForwardOptions::NoSenderNames
|
||||
: Data::ForwardOptions::PreserveInfo;
|
||||
onstack(
|
||||
_inner->selected(),
|
||||
_comment->entity()->getTextWithAppliedMarkdown(),
|
||||
options);
|
||||
options,
|
||||
forwardOptions);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -10,6 +10,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
#include "boxes/abstract_box.h"
|
||||
#include "base/observer.h"
|
||||
#include "base/timer.h"
|
||||
#include "ui/chat/forward_options_box.h"
|
||||
#include "ui/effects/animations.h"
|
||||
#include "ui/effects/round_checkbox.h"
|
||||
#include "mtproto/sender.h"
|
||||
|
@ -41,12 +42,17 @@ class Row;
|
|||
class IndexedList;
|
||||
} // namespace Dialogs
|
||||
|
||||
namespace Data {
|
||||
enum class ForwardOptions;
|
||||
} // namespace Data
|
||||
|
||||
namespace Ui {
|
||||
class MultiSelect;
|
||||
class InputField;
|
||||
struct ScrollToRequest;
|
||||
template <typename Widget>
|
||||
class SlideWrap;
|
||||
class PopupMenu;
|
||||
} // namespace Ui
|
||||
|
||||
QString AppendShareGameScoreUrl(
|
||||
|
@ -63,7 +69,8 @@ public:
|
|||
using SubmitCallback = Fn<void(
|
||||
std::vector<not_null<PeerData*>>&&,
|
||||
TextWithTags&&,
|
||||
Api::SendOptions)>;
|
||||
Api::SendOptions,
|
||||
Data::ForwardOptions option)>;
|
||||
using FilterCallback = Fn<bool(PeerData*)>;
|
||||
|
||||
struct Descriptor {
|
||||
|
@ -79,6 +86,11 @@ public:
|
|||
const style::MultiSelect *stMultiSelect = nullptr;
|
||||
const style::InputField *stComment = nullptr;
|
||||
const style::PeerList *st = nullptr;
|
||||
struct {
|
||||
int messagesCount = 0;
|
||||
bool show = false;
|
||||
bool hasCaptions = false;
|
||||
} forwardOptions;
|
||||
};
|
||||
ShareBox(QWidget*, Descriptor &&descriptor);
|
||||
|
||||
|
@ -119,6 +131,8 @@ private:
|
|||
mtpRequestId requestId);
|
||||
void peopleFail(const MTP::Error &error, mtpRequestId requestId);
|
||||
|
||||
void showMenu(not_null<Ui::RpWidget*> parent);
|
||||
|
||||
Descriptor _descriptor;
|
||||
MTP::Sender _api;
|
||||
|
||||
|
@ -126,6 +140,9 @@ private:
|
|||
object_ptr<Ui::SlideWrap<Ui::InputField>> _comment;
|
||||
object_ptr<Ui::RpWidget> _bottomWidget;
|
||||
|
||||
base::unique_qptr<Ui::PopupMenu> _menu;
|
||||
Ui::ForwardOptions _forwardOptions;
|
||||
|
||||
class Inner;
|
||||
QPointer<Inner> _inner;
|
||||
|
||||
|
|
|
@ -129,7 +129,8 @@ object_ptr<ShareBox> ShareInviteLinkBox(
|
|||
auto submitCallback = [=](
|
||||
std::vector<not_null<PeerData*>> &&result,
|
||||
TextWithTags &&comment,
|
||||
Api::SendOptions options) {
|
||||
Api::SendOptions options,
|
||||
Data::ForwardOptions) {
|
||||
if (*sending || result.empty()) {
|
||||
return;
|
||||
}
|
||||
|
|
|
@ -209,6 +209,18 @@ void FastShareMessage(not_null<HistoryItem*> item) {
|
|||
&& (item->media()->game() != nullptr);
|
||||
const auto canCopyLink = item->hasDirectLink() || isGame;
|
||||
|
||||
const auto items = owner->idsToItems(data->msgIds);
|
||||
const auto hasCaptions = ranges::any_of(items, [](auto item) {
|
||||
return item->media()
|
||||
&& !item->originalText().text.isEmpty()
|
||||
&& item->media()->allowsEditCaption();
|
||||
});
|
||||
const auto hasOnlyForcedForwardedInfo = hasCaptions
|
||||
? false
|
||||
: ranges::all_of(items, [](auto item) {
|
||||
return item->media() && item->media()->forceForwardedInfo();
|
||||
});
|
||||
|
||||
auto copyCallback = [=]() {
|
||||
if (const auto item = owner->message(data->msgIds[0])) {
|
||||
if (item->hasDirectLink()) {
|
||||
|
@ -235,7 +247,8 @@ void FastShareMessage(not_null<HistoryItem*> item) {
|
|||
auto submitCallback = [=](
|
||||
std::vector<not_null<PeerData*>> &&result,
|
||||
TextWithTags &&comment,
|
||||
Api::SendOptions options) {
|
||||
Api::SendOptions options,
|
||||
Data::ForwardOptions forwardOptions) {
|
||||
if (!data->requests.empty()) {
|
||||
return; // Share clicked already.
|
||||
}
|
||||
|
@ -274,6 +287,12 @@ void FastShareMessage(not_null<HistoryItem*> item) {
|
|||
| MTPmessages_ForwardMessages::Flag::f_with_my_score
|
||||
| (options.scheduled
|
||||
? MTPmessages_ForwardMessages::Flag::f_schedule_date
|
||||
: MTPmessages_ForwardMessages::Flag(0))
|
||||
| ((forwardOptions != Data::ForwardOptions::PreserveInfo)
|
||||
? MTPmessages_ForwardMessages::Flag::f_drop_author
|
||||
: MTPmessages_ForwardMessages::Flag(0))
|
||||
| ((forwardOptions == Data::ForwardOptions::NoNamesAndCaptions)
|
||||
? MTPmessages_ForwardMessages::Flag::f_drop_media_captions
|
||||
: MTPmessages_ForwardMessages::Flag(0));
|
||||
auto msgIds = QVector<MTPint>();
|
||||
msgIds.reserve(data->msgIds.size());
|
||||
|
@ -346,7 +365,13 @@ void FastShareMessage(not_null<HistoryItem*> item) {
|
|||
.copyCallback = std::move(copyLinkCallback),
|
||||
.submitCallback = std::move(submitCallback),
|
||||
.filterCallback = std::move(filterCallback),
|
||||
.navigation = App::wnd()->sessionController() }));
|
||||
.navigation = App::wnd()->sessionController(),
|
||||
.forwardOptions = {
|
||||
.messagesCount = int(data->msgIds.size()),
|
||||
.show = !hasOnlyForcedForwardedInfo,
|
||||
.hasCaptions = hasCaptions,
|
||||
},
|
||||
}));
|
||||
}
|
||||
|
||||
void RequestDependentMessageData(
|
||||
|
|
|
@ -15,6 +15,56 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
|
||||
namespace Ui {
|
||||
|
||||
void FillForwardOptions(
|
||||
Fn<not_null<AbstractCheckView*>(
|
||||
rpl::producer<QString> &&,
|
||||
bool)> createView,
|
||||
int count,
|
||||
ForwardOptions options,
|
||||
Fn<void(ForwardOptions)> optionsChanged,
|
||||
rpl::lifetime &lifetime) {
|
||||
Expects(optionsChanged != nullptr);
|
||||
|
||||
const auto names = createView(
|
||||
(count == 1
|
||||
? tr::lng_forward_show_sender
|
||||
: tr::lng_forward_show_senders)(),
|
||||
!options.dropNames);
|
||||
const auto captions = options.hasCaptions
|
||||
? createView(
|
||||
(count == 1
|
||||
? tr::lng_forward_show_caption
|
||||
: tr::lng_forward_show_captions)(),
|
||||
!options.dropCaptions).get()
|
||||
: nullptr;
|
||||
|
||||
const auto notify = [=] {
|
||||
optionsChanged({
|
||||
.dropNames = !names->checked(),
|
||||
.hasCaptions = options.hasCaptions,
|
||||
.dropCaptions = (captions && !captions->checked()),
|
||||
});
|
||||
};
|
||||
names->checkedChanges(
|
||||
) | rpl::start_with_next([=](bool showNames) {
|
||||
if (showNames && captions && !captions->checked()) {
|
||||
captions->setChecked(true, anim::type::normal);
|
||||
} else {
|
||||
notify();
|
||||
}
|
||||
}, lifetime);
|
||||
if (captions) {
|
||||
captions->checkedChanges(
|
||||
) | rpl::start_with_next([=](bool showCaptions) {
|
||||
if (!showCaptions && names->checked()) {
|
||||
names->setChecked(false, anim::type::normal);
|
||||
} else {
|
||||
notify();
|
||||
}
|
||||
}, lifetime);
|
||||
}
|
||||
}
|
||||
|
||||
void ForwardOptionsBox(
|
||||
not_null<GenericBox*> box,
|
||||
int count,
|
||||
|
@ -45,51 +95,23 @@ void ForwardOptionsBox(
|
|||
st::boxRowPadding.left(),
|
||||
st::boxRowPadding.right(),
|
||||
st::boxRowPadding.bottom());
|
||||
const auto names = box->addRow(
|
||||
object_ptr<Ui::Checkbox>(
|
||||
box.get(),
|
||||
(count == 1
|
||||
? tr::lng_forward_show_sender
|
||||
: tr::lng_forward_show_senders)(),
|
||||
!options.dropNames,
|
||||
st::defaultBoxCheckbox),
|
||||
checkboxPadding);
|
||||
const auto captions = options.hasCaptions
|
||||
? box->addRow(
|
||||
|
||||
auto createView = [&](rpl::producer<QString> &&text, bool checked) {
|
||||
return box->addRow(
|
||||
object_ptr<Ui::Checkbox>(
|
||||
box.get(),
|
||||
(count == 1
|
||||
? tr::lng_forward_show_caption
|
||||
: tr::lng_forward_show_captions)(),
|
||||
!options.dropCaptions,
|
||||
std::move(text),
|
||||
checked,
|
||||
st::defaultBoxCheckbox),
|
||||
checkboxPadding)
|
||||
: nullptr;
|
||||
const auto notify = [=] {
|
||||
optionsChanged({
|
||||
.dropNames = !names->checked(),
|
||||
.hasCaptions = options.hasCaptions,
|
||||
.dropCaptions = (captions && !captions->checked()),
|
||||
});
|
||||
checkboxPadding)->checkView();
|
||||
};
|
||||
names->checkedChanges(
|
||||
) | rpl::start_with_next([=](bool showNames) {
|
||||
if (showNames && captions && !captions->checked()) {
|
||||
captions->setChecked(true);
|
||||
} else {
|
||||
notify();
|
||||
}
|
||||
}, names->lifetime());
|
||||
if (captions) {
|
||||
captions->checkedChanges(
|
||||
) | rpl::start_with_next([=](bool showCaptions) {
|
||||
if (!showCaptions && names->checked()) {
|
||||
names->setChecked(false);
|
||||
} else {
|
||||
notify();
|
||||
}
|
||||
}, captions->lifetime());
|
||||
}
|
||||
FillForwardOptions(
|
||||
std::move(createView),
|
||||
count,
|
||||
options,
|
||||
std::move(optionsChanged),
|
||||
box->lifetime());
|
||||
|
||||
box->addRow(
|
||||
object_ptr<Ui::LinkButton>(
|
||||
box.get(),
|
||||
|
|
|
@ -11,12 +11,23 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
|
||||
namespace Ui {
|
||||
|
||||
class AbstractCheckView;
|
||||
|
||||
struct ForwardOptions {
|
||||
bool dropNames = false;
|
||||
bool hasCaptions = false;
|
||||
bool dropCaptions = false;
|
||||
};
|
||||
|
||||
void FillForwardOptions(
|
||||
Fn<not_null<AbstractCheckView*>(
|
||||
rpl::producer<QString> &&,
|
||||
bool)> createView,
|
||||
int count,
|
||||
ForwardOptions options,
|
||||
Fn<void(ForwardOptions)> optionsChanged,
|
||||
rpl::lifetime &lifetime);
|
||||
|
||||
void ForwardOptionsBox(
|
||||
not_null<GenericBox*> box,
|
||||
int count,
|
||||
|
|
Loading…
Add table
Reference in a new issue