Allow sending silent messages.

This commit is contained in:
John Preston 2019-07-26 18:06:22 +02:00
parent f1cd70d8a8
commit 3f2cc01f48
16 changed files with 118 additions and 66 deletions

View File

@ -1233,6 +1233,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
"lng_cant_invite_make_admin" = "Make admin";
"lng_send_button" = "Send";
"lng_send_silent_message" = "Send without sound";
"lng_message_ph" = "Write a message...";
"lng_broadcast_ph" = "Broadcast a message...";
"lng_broadcast_silent_ph" = "Silent broadcast...";

View File

@ -31,7 +31,8 @@ void SendExistingMedia(
const MTPInputMedia &inputMedia,
Data::FileOrigin origin,
TextWithEntities caption,
MsgId replyToId) {
MsgId replyToId,
bool silent) {
const auto peer = history->peer;
const auto session = &history->session();
const auto api = &session->api();
@ -40,6 +41,7 @@ void SendExistingMedia(
options.clearDraft = false;
options.replyTo = replyToId;
options.generateLocal = true;
options.silent = silent;
api->sendAction(options);
@ -52,8 +54,9 @@ void SendExistingMedia(
flags |= MTPDmessage::Flag::f_reply_to_msg_id;
sendFlags |= MTPmessages_SendMedia::Flag::f_reply_to_msg_id;
}
bool channelPost = peer->isChannel() && !peer->isMegagroup();
bool silentPost = channelPost && session->data().notifySilentPosts(peer);
const auto channelPost = peer->isChannel() && !peer->isMegagroup();
const auto silentPost = options.silent
|| (channelPost && session->data().notifySilentPosts(peer));
if (channelPost) {
flags |= MTPDmessage::Flag::f_views;
flags |= MTPDmessage::Flag::f_post;
@ -131,7 +134,7 @@ void SendExistingMedia(
performRequest();
if (const auto main = App::main()) {
main->finishForwarding(history);
main->finishForwarding(history, options.silent);
}
}
@ -139,15 +142,17 @@ void SendExistingMedia(
void SendExistingDocument(
not_null<History*> history,
not_null<DocumentData*> document) {
SendExistingDocument(history, document, {});
not_null<DocumentData*> document,
bool silent) {
SendExistingDocument(history, document, {}, 0, silent);
}
void SendExistingDocument(
not_null<History*> history,
not_null<DocumentData*> document,
TextWithEntities caption,
MsgId replyToId) {
MsgId replyToId,
bool silent) {
SendExistingMedia(
history,
document,
@ -157,7 +162,8 @@ void SendExistingDocument(
MTPint()),
document->stickerOrGifOrigin(),
caption,
replyToId);
replyToId,
silent);
if (document->sticker()) {
if (const auto main = App::main()) {
@ -169,15 +175,17 @@ void SendExistingDocument(
void SendExistingPhoto(
not_null<History*> history,
not_null<PhotoData*> photo) {
SendExistingPhoto(history, photo, {});
not_null<PhotoData*> photo,
bool silent) {
SendExistingPhoto(history, photo, {}, 0, silent);
}
void SendExistingPhoto(
not_null<History*> history,
not_null<PhotoData*> photo,
TextWithEntities caption,
MsgId replyToId) {
MsgId replyToId,
bool silent) {
SendExistingMedia(
history,
photo,
@ -187,7 +195,8 @@ void SendExistingPhoto(
MTPint()),
Data::FileOrigin(),
caption,
replyToId);
replyToId,
silent);
}
} // namespace Api

View File

@ -15,22 +15,26 @@ namespace Api {
void SendExistingDocument(
not_null<History*> history,
not_null<DocumentData*> document);
not_null<DocumentData*> document,
bool silent = false);
void SendExistingDocument(
not_null<History*> history,
not_null<DocumentData*> document,
TextWithEntities caption,
MsgId replyToId = 0);
MsgId replyToId = 0,
bool silent = false);
void SendExistingPhoto(
not_null<History*> history,
not_null<PhotoData*> photo);
not_null<PhotoData*> photo,
bool silent = false);
void SendExistingPhoto(
not_null<History*> history,
not_null<PhotoData*> photo,
TextWithEntities caption,
MsgId replyToId = 0);
MsgId replyToId = 0,
bool silent = false);
} // namespace Api

View File

@ -97,13 +97,6 @@ using PhotoFileLocationId = Data::PhotoFileLocationId;
using DocumentFileLocationId = Data::DocumentFileLocationId;
using UpdatedFileReferences = Data::UpdatedFileReferences;
bool IsSilentPost(not_null<HistoryItem*> item, bool silent) {
const auto history = item->history();
return silent
&& history->peer->isChannel()
&& !history->peer->isMegagroup();
}
MTPVector<MTPDocumentAttribute> ComposeSendingDocumentAttributes(
not_null<DocumentData*> document) {
const auto filenameAttribute = MTP_documentAttributeFilename(
@ -4406,8 +4399,8 @@ void ApiWrap::forwardMessages(
readServerHistory(history);
const auto channelPost = peer->isChannel() && !peer->isMegagroup();
const auto silentPost = channelPost
&& _session->data().notifySilentPosts(peer);
const auto silentPost = options.silent
|| (channelPost && _session->data().notifySilentPosts(peer));
auto flags = MTPDmessage::Flags(0);
auto sendFlags = MTPmessages_ForwardMessages::Flags(0);
@ -4875,6 +4868,7 @@ void ApiWrap::sendMessage(MessageToSend &&message) {
auto options = ApiWrap::SendOptions(history);
options.clearDraft = message.clearDraft;
options.replyTo = message.replyTo;
options.silent = message.silent;
options.generateLocal = true;
options.webPageId = message.webPageId;
options.handleSupportSwitch = message.handleSupportSwitch;
@ -4924,9 +4918,9 @@ void ApiWrap::sendMessage(MessageToSend &&message) {
MTP_int(page->pendingTill)));
flags |= MTPDmessage::Flag::f_media;
}
bool channelPost = peer->isChannel() && !peer->isMegagroup();
bool silentPost = channelPost
&& _session->data().notifySilentPosts(peer);
const auto channelPost = peer->isChannel() && !peer->isMegagroup();
const auto silentPost = message.silent
|| (channelPost && _session->data().notifySilentPosts(peer));
if (channelPost) {
flags |= MTPDmessage::Flag::f_views;
flags |= MTPDmessage::Flag::f_post;
@ -4995,7 +4989,7 @@ void ApiWrap::sendMessage(MessageToSend &&message) {
}
if (const auto main = App::main()) {
main->finishForwarding(history);
main->finishForwarding(history, message.silent);
}
}
@ -5049,7 +5043,8 @@ void ApiWrap::sendInlineResult(
sendFlags |= MTPmessages_SendInlineBotResult::Flag::f_reply_to_msg_id;
}
bool channelPost = peer->isChannel() && !peer->isMegagroup();
bool silentPost = channelPost && _session->data().notifySilentPosts(peer);
bool silentPost = options.silent
|| (channelPost && _session->data().notifySilentPosts(peer));
if (channelPost) {
flags |= MTPDmessage::Flag::f_views;
flags |= MTPDmessage::Flag::f_post;
@ -5106,7 +5101,7 @@ void ApiWrap::sendInlineResult(
).send();
if (const auto main = App::main()) {
main->finishForwarding(history);
main->finishForwarding(history, options.silent);
}
}
@ -5213,7 +5208,7 @@ void ApiWrap::sendMediaWithRandomId(
| (replyTo
? MTPmessages_SendMedia::Flag::f_reply_to_msg_id
: MTPmessages_SendMedia::Flag(0))
| (IsSilentPost(item, silent)
| (silent
? MTPmessages_SendMedia::Flag::f_silent
: MTPmessages_SendMedia::Flag(0))
| (!sentEntities.v.isEmpty()
@ -5309,7 +5304,7 @@ void ApiWrap::sendAlbumIfReady(not_null<SendingAlbum*> album) {
| (replyTo
? MTPmessages_SendMultiMedia::Flag::f_reply_to_msg_id
: MTPmessages_SendMultiMedia::Flag(0))
| (IsSilentPost(sample, album->silent)
| (album->silent
? MTPmessages_SendMultiMedia::Flag::f_silent
: MTPmessages_SendMultiMedia::Flag(0));
const auto peer = history->peer;
@ -5338,7 +5333,7 @@ FileLoadTo ApiWrap::fileLoadTaskOptions(const SendOptions &options) const {
const auto peer = options.history->peer;
return FileLoadTo(
peer->id,
_session->data().notifySilentPosts(peer),
options.silent || _session->data().notifySilentPosts(peer),
options.replyTo);
}
@ -5788,8 +5783,8 @@ void ApiWrap::createPoll(
history->clearCloudDraft();
}
const auto channelPost = peer->isChannel() && !peer->isMegagroup();
const auto silentPost = channelPost
&& _session->data().notifySilentPosts(peer);
const auto silentPost = options.silent
|| (channelPost && _session->data().notifySilentPosts(peer));
if (silentPost) {
sendFlags |= MTPmessages_SendMedia::Flag::f_silent;
}

View File

@ -381,6 +381,7 @@ public:
not_null<History*> history;
MsgId replyTo = 0;
WebPageId webPageId = 0;
bool silent = false;
bool clearDraft = false;
bool generateLocal = true;
bool handleSupportSwitch = false;
@ -453,6 +454,7 @@ public:
TextWithTags textWithTags;
MsgId replyTo = 0;
WebPageId webPageId = 0;
bool silent = false;
bool clearDraft = true;
bool handleSupportSwitch = false;
};

View File

@ -1469,6 +1469,7 @@ void SendFilesBox::setupShadows(
void SendFilesBox::prepare() {
_send = addButton(tr::lng_send_button(), [=] { send(); });
SetupSendWithoutSound(_send, [=] { return true; }, [=] { send(true); });
addButton(tr::lng_cancel(), [=] { closeBox(); });
initSendWay();
setupCaption();
@ -1637,7 +1638,7 @@ void SendFilesBox::setupCaption() {
const auto ctrlShiftEnter = modifiers.testFlag(Qt::ShiftModifier)
&& (modifiers.testFlag(Qt::ControlModifier)
|| modifiers.testFlag(Qt::MetaModifier));
send(ctrlShiftEnter);
send(false, ctrlShiftEnter);
});
connect(_caption, &Ui::InputField::cancelled, [=] { closeBox(); });
_caption->setMimeDataHook([=](
@ -1838,7 +1839,7 @@ void SendFilesBox::keyPressEvent(QKeyEvent *e) {
const auto ctrl = modifiers.testFlag(Qt::ControlModifier)
|| modifiers.testFlag(Qt::MetaModifier);
const auto shift = modifiers.testFlag(Qt::ShiftModifier);
send(ctrl && shift);
send(false, ctrl && shift);
} else {
BoxContent::keyPressEvent(e);
}
@ -1909,7 +1910,7 @@ void SendFilesBox::setInnerFocus() {
}
}
void SendFilesBox::send(bool ctrlShiftEnter) {
void SendFilesBox::send(bool silent, bool ctrlShiftEnter) {
using Way = SendFilesWay;
const auto way = _sendWay ? _sendWay->value() : Way::Files;
@ -1938,6 +1939,7 @@ void SendFilesBox::send(bool ctrlShiftEnter) {
std::move(_list),
way,
std::move(caption),
silent,
ctrlShiftEnter);
}
closeBox();

View File

@ -60,6 +60,7 @@ public:
Storage::PreparedList &&list,
SendFilesWay way,
TextWithTags &&caption,
bool silent,
bool ctrlShiftEnter)> callback) {
_confirmedCallback = std::move(callback);
}
@ -100,7 +101,7 @@ private:
void prepareAlbumPreview();
void applyAlbumOrder();
void send(bool ctrlShiftEnter = false);
void send(bool silent = false, bool ctrlShiftEnter = false);
void captionResized();
void setupTitleText();
@ -127,6 +128,7 @@ private:
Storage::PreparedList &&list,
SendFilesWay way,
TextWithTags &&caption,
bool silent,
bool ctrlShiftEnter)> _confirmedCallback;
Fn<void()> _cancelledCallback;
bool _confirmed = false;

View File

@ -408,7 +408,13 @@ void ShareBox::keyPressEvent(QKeyEvent *e) {
void ShareBox::createButtons() {
clearButtons();
if (_hasSelected) {
addButton(tr::lng_share_confirm(), [=] { submit(); });
const auto send = addButton(tr::lng_share_confirm(), [=] {
submit();
});
SetupSendWithoutSound(
send,
[=] { return true; },
[=] { submit(true); });
} else if (_copyCallback) {
addButton(tr::lng_share_copy_link(), [=] { copyLink(); });
}
@ -442,11 +448,12 @@ void ShareBox::innerSelectedChanged(PeerData *peer, bool checked) {
update();
}
void ShareBox::submit() {
void ShareBox::submit(bool silent) {
if (_submitCallback) {
_submitCallback(
_inner->selected(),
_comment->entity()->getTextWithAppliedMarkdown());
_comment->entity()->getTextWithAppliedMarkdown(),
silent);
}
}

View File

@ -49,7 +49,10 @@ void ShareGameScoreByHash(
class ShareBox : public BoxContent, public RPCSender {
public:
using CopyCallback = Fn<void()>;
using SubmitCallback = Fn<void(QVector<PeerData*>&&, TextWithTags&&)>;
using SubmitCallback = Fn<void(
QVector<PeerData*>&&,
TextWithTags&&,
bool)>;
using FilterCallback = Fn<bool(PeerData*)>;
ShareBox(
@ -70,7 +73,7 @@ private:
void prepareCommentField();
void scrollAnimationCallback();
void submit();
void submit(bool silent = false);
void copyLink();
bool searchByUsername(bool useCache = false);

View File

@ -14,8 +14,10 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "base/qthelp_url.h"
#include "boxes/abstract_box.h"
#include "ui/wrap/vertical_layout.h"
#include "ui/widgets/popup_menu.h"
#include "data/data_session.h"
#include "data/data_user.h"
#include "core/event_filter.h"
#include "chat_helpers/emoji_suggestions_widget.h"
#include "window/window_session_controller.h"
#include "lang/lang_keys.h"
@ -772,3 +774,19 @@ void MessageLinksParser::apply(
}
_list = std::move(parsed);
}
void SetupSendWithoutSound(
not_null<Ui::RpWidget*> button,
Fn<bool()> enabled,
Fn<void()> send) {
const auto menu = std::make_shared<base::unique_qptr<Ui::PopupMenu>>();
Core::InstallEventFilter(button, [=](not_null<QEvent*> e) {
if (e->type() == QEvent::ContextMenu && enabled()) {
*menu = base::make_unique_q<Ui::PopupMenu>(button);
(*menu)->addAction(tr::lng_send_silent_message(tr::now), send);
(*menu)->popup(QCursor::pos());
return true;
}
return false;
});
}

View File

@ -101,4 +101,9 @@ private:
base::Timer _timer;
QtConnectionOwner _connection;
};
};
void SetupSendWithoutSound(
not_null<Ui::RpWidget*> button,
Fn<bool()> enabled,
Fn<void()> send);

View File

@ -216,7 +216,8 @@ void FastShareMessage(not_null<HistoryItem*> item) {
};
auto submitCallback = [=](
QVector<PeerData*> &&result,
TextWithTags &&comment) {
TextWithTags &&comment,
bool silent) {
if (!data->requests.empty()) {
return; // Share clicked already.
}
@ -264,6 +265,9 @@ void FastShareMessage(not_null<HistoryItem*> item) {
| MTPmessages_ForwardMessages::Flag::f_with_my_score
| (isGroup
? MTPmessages_ForwardMessages::Flag::f_grouped
: MTPmessages_ForwardMessages::Flag(0))
| (silent
? MTPmessages_ForwardMessages::Flag::f_silent
: MTPmessages_ForwardMessages::Flag(0));
auto msgIds = QVector<MTPint>();
msgIds.reserve(data->msgIds.size());

View File

@ -304,6 +304,10 @@ HistoryWidget::HistoryWidget(
_unreadMentions->addClickHandler([=] { showNextUnreadMention(); });
_fieldBarCancel->addClickHandler([=] { cancelFieldAreaState(); });
_send->addClickHandler([=] { sendButtonClicked(); });
SetupSendWithoutSound(_send, [=] {
return (_send->type() == Ui::SendButton::Type::Send)
&& !_send->isDisabled();
}, [=] { send(true); });
_unblock->addClickHandler([=] { unblockUser(); });
_botStart->addClickHandler([=] { sendBotStartCommand(); });
_joinChannel->addClickHandler([=] { joinChannel(); });
@ -954,7 +958,7 @@ void HistoryWidget::onHashtagOrBotCommandInsert(
// Send bot command at once, if it was not inserted by pressing Tab.
if (str.at(0) == '/' && method != FieldAutocomplete::ChooseMethod::ByTab) {
App::sendBotCommand(_peer, nullptr, str, replyToId());
App::main()->finishForwarding(_history);
App::main()->finishForwarding(_history, false);
setFieldText(_field->getTextWithTagsPart(_field->textCursor().position()));
} else {
_field->insertTag(str);
@ -2814,7 +2818,7 @@ void HistoryWidget::hideSelectorControlsAnimated() {
}
}
void HistoryWidget::send(Qt::KeyboardModifiers modifiers) {
void HistoryWidget::send(bool silent, Qt::KeyboardModifiers modifiers) {
if (!_history) {
return;
} else if (_editMsgId) {
@ -2834,6 +2838,7 @@ void HistoryWidget::send(Qt::KeyboardModifiers modifiers) {
message.textWithTags = _field->getTextWithAppliedMarkdown();
message.replyTo = replyToId();
message.webPageId = webPageId;
message.silent = silent;
message.handleSupportSwitch = Support::HandleSwitch(modifiers);
const auto error = GetErrorTextForForward(
@ -4079,6 +4084,7 @@ bool HistoryWidget::confirmSendingFiles(
Storage::PreparedList &&list,
SendFilesWay way,
TextWithTags &&caption,
bool silent,
bool ctrlShiftEnter) {
if (showSendingFilesError(list)) {
return;
@ -4094,6 +4100,7 @@ bool HistoryWidget::confirmSendingFiles(
type,
std::move(caption),
replyToId(),
silent,
album);
}));
box->setCancelledCallback(crl::guard(this, [=] {
@ -4197,23 +4204,12 @@ bool HistoryWidget::confirmSendingFiles(
return false;
}
void HistoryWidget::uploadFiles(
Storage::PreparedList &&list,
SendMediaType type) {
ActivateWindow(controller());
uploadFilesAfterConfirmation(
std::move(list),
type,
TextWithTags(),
replyToId());
}
void HistoryWidget::uploadFilesAfterConfirmation(
Storage::PreparedList &&list,
SendMediaType type,
TextWithTags &&caption,
MsgId replyTo,
bool silent,
std::shared_ptr<SendingAlbum> album) {
Assert(canWriteMessage());
@ -4230,6 +4226,7 @@ void HistoryWidget::uploadFilesAfterConfirmation(
auto options = ApiWrap::SendOptions(_history);
options.replyTo = replyTo;
options.silent = silent;
session().api().sendFiles(
std::move(list),
type,
@ -4353,7 +4350,7 @@ void HistoryWidget::sendFileConfirmed(
flags |= MTPDmessage::Flag::f_reply_to_msg_id;
}
const auto channelPost = peer->isChannel() && !peer->isMegagroup();
const auto silentPost = channelPost && file->to.silent;
const auto silentPost = file->to.silent;
if (channelPost) {
flags |= MTPDmessage::Flag::f_views;
flags |= MTPDmessage::Flag::f_post;

View File

@ -324,7 +324,9 @@ private:
void initTabbedSelector();
void updateField();
void send(Qt::KeyboardModifiers modifiers = Qt::KeyboardModifiers());
void send(
bool silent = false,
Qt::KeyboardModifiers modifiers = Qt::KeyboardModifiers());
void handlePendingHistoryUpdate();
void fullPeerUpdated(PeerData *peer);
void toggleTabbedSelectorMode();
@ -401,7 +403,6 @@ private:
const QString &insertTextOnCancel = QString());
bool showSendingFilesError(const Storage::PreparedList &list) const;
void uploadFiles(Storage::PreparedList &&list, SendMediaType type);
void uploadFile(const QByteArray &fileContent, SendMediaType type);
void uploadFilesAfterConfirmation(
@ -409,6 +410,7 @@ private:
SendMediaType type,
TextWithTags &&caption,
MsgId replyTo,
bool silent,
std::shared_ptr<SendingAlbum> album = nullptr);
void subscribeToUploader();

View File

@ -679,7 +679,7 @@ void MainWidget::cancelForwarding(not_null<History*> history) {
_history->updateForwarding();
}
void MainWidget::finishForwarding(not_null<History*> history) {
void MainWidget::finishForwarding(not_null<History*> history, bool silent) {
auto toForward = history->validateForwardDraft();
if (!toForward.empty()) {
const auto error = GetErrorTextForForward(history->peer, toForward);
@ -688,6 +688,7 @@ void MainWidget::finishForwarding(not_null<History*> history) {
}
auto options = ApiWrap::SendOptions(history);
options.silent = silent;
session().api().forwardMessages(std::move(toForward), options);
cancelForwarding(history);
}

View File

@ -231,7 +231,7 @@ public:
void pushReplyReturn(not_null<HistoryItem*> item);
void cancelForwarding(not_null<History*> history);
void finishForwarding(not_null<History*> history);
void finishForwarding(not_null<History*> history, bool silent);
// Does offerPeer or showPeerHistory.
void choosePeer(PeerId peerId, MsgId showAtMsgId);