diff --git a/.github/workflows/linux.yml b/.github/workflows/linux.yml
index 8b6ee2b29..cee1f54c8 100644
--- a/.github/workflows/linux.yml
+++ b/.github/workflows/linux.yml
@@ -164,7 +164,7 @@ jobs:
- name: Opus cache.
id: cache-opus
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/opus
key: ${{ runner.OS }}-opus-${{ env.CACHE_KEY }}
@@ -209,7 +209,7 @@ jobs:
- name: FFmpeg cache.
id: cache-ffmpeg
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/ffmpeg-cache
key: ${{ runner.OS }}-ffmpeg-${{ env.CACHE_KEY }}
@@ -363,7 +363,7 @@ jobs:
- name: OpenSSL cache.
id: cache-openssl
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/openssl-cache
key: ${{ runner.OS }}-${{ env.OPENSSL_VER }}-${{ env.CACHE_KEY }}
@@ -419,7 +419,7 @@ jobs:
- name: Qt 5.12.8 cache.
id: cache-qt
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/qt-cache
key: ${{ runner.OS }}-qt-${{ env.CACHE_KEY }}-${{ hashFiles('**/qt*_5_12_8/*') }}
@@ -468,7 +468,7 @@ jobs:
- name: Breakpad cache.
id: cache-breakpad
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/breakpad-cache
key: ${{ runner.OS }}-breakpad-${{ env.CACHE_KEY }}
diff --git a/.github/workflows/mac.yml b/.github/workflows/mac.yml
index d96ae3e77..073f0652e 100644
--- a/.github/workflows/mac.yml
+++ b/.github/workflows/mac.yml
@@ -140,7 +140,7 @@ jobs:
- name: OpenSSL cache.
id: cache-openssl
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/openssl_${{ env.OPENSSL_VER }}
key: ${{ runner.OS }}-${{ env.OPENSSL_VER }}-${{ env.CACHE_KEY }}
@@ -170,7 +170,7 @@ jobs:
- name: Opus cache.
id: cache-opus
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/opus
key: ${{ runner.OS }}-opus-${{ env.CACHE_KEY }}
@@ -192,7 +192,7 @@ jobs:
- name: Libiconv cache.
id: cache-libiconv
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/${{ env.LIBICONV_VER }}
key: ${{ runner.OS }}-${{ env.LIBICONV_VER }}-${{ env.CACHE_KEY }}
@@ -213,7 +213,7 @@ jobs:
- name: FFmpeg cache.
id: cache-ffmpeg
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/ffmpeg-cache
key: ${{ runner.OS }}-ffmpeg-${{ env.CACHE_KEY }}
@@ -369,7 +369,7 @@ jobs:
- name: Crashpad cache.
id: cache-crashpad
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/crashpad
key: ${{ runner.OS }}-crashpad-${{ env.CACHE_KEY }}-${{ hashFiles('**/crashpad.diff') }}-${{ hashFiles('**/mini_chromium.diff') }}
@@ -408,7 +408,7 @@ jobs:
- name: Qt 5.12.8 cache.
id: cache-qt
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/qt-cache
key: ${{ runner.OS }}-qt-${{ env.CACHE_KEY }}-${{ hashFiles('**/qtbase_5_12_8/*') }}
diff --git a/.github/workflows/win.yml b/.github/workflows/win.yml
index b229199d4..44a6e48e1 100644
--- a/.github/workflows/win.yml
+++ b/.github/workflows/win.yml
@@ -140,7 +140,7 @@ jobs:
- name: OpenSSL cache.
id: cache-openssl
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/openssl_${{ env.OPENSSL_VER }}
key: ${{ runner.OS }}-${{ env.CACHE_KEY }}-${{ env.OPENSSL_VER }}
@@ -184,7 +184,7 @@ jobs:
- name: OpenAL Soft cache.
id: cache-openal
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/openal-soft
key: ${{ runner.OS }}-openal-soft-${{ env.CACHE_KEY }}
@@ -208,7 +208,7 @@ jobs:
- name: Breakpad cache.
id: cache-breakpad
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/breakpad
key: ${{ runner.OS }}-breakpad-${{ env.CACHE_KEY }}-${{ hashFiles('**/breakpad.diff') }}
@@ -257,7 +257,7 @@ jobs:
- name: Opus cache.
id: cache-opus
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/opus
key: ${{ runner.OS }}-opus-${{ env.CACHE_KEY }}
@@ -276,7 +276,7 @@ jobs:
- name: FFmpeg cache.
id: cache-ffmpeg
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/ffmpeg
key: ${{ runner.OS }}-ffmpeg-${{ env.CACHE_KEY }}-2-${{ hashFiles('**/build_ffmpeg_win.sh') }}
@@ -298,7 +298,7 @@ jobs:
- name: Qt 5.12.8 cache.
id: cache-qt
- uses: actions/cache@v1
+ uses: actions/cache@v2
with:
path: ${{ env.LibrariesPath }}/Qt-5.12.8
key: ${{ runner.OS }}-qt-${{ env.CACHE_KEY }}-${{ hashFiles('**/qtbase_5_12_8/*') }}
diff --git a/Telegram/Resources/langs/lang.strings b/Telegram/Resources/langs/lang.strings
index 7a7763048..8cfa55d28 100644
--- a/Telegram/Resources/langs/lang.strings
+++ b/Telegram/Resources/langs/lang.strings
@@ -16,6 +16,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
"lng_menu_back" = "Back";
"lng_menu_night_mode" = "Night Mode";
"lng_menu_add_account" = "Add Account";
+"lng_menu_activate" = "Activate";
"lng_disable_notifications_from_tray" = "Disable notifications";
"lng_enable_notifications_from_tray" = "Enable notifications";
@@ -291,6 +292,9 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
"lng_settings_empty_bio" = "None";
"lng_settings_section_notify" = "Notifications";
+"lng_settings_show_from" = "Show notifications from";
+"lng_settings_notify_all" = "All accounts";
+"lng_settings_notify_all_about" = "Turn this off if you want to receive notifications only from the account you are currently using.";
"lng_settings_notify_title" = "Notifications for chats";
"lng_settings_desktop_notify" = "Desktop notifications";
"lng_settings_show_name" = "Show sender's name";
diff --git a/Telegram/Resources/uwp/AppX/AppxManifest.xml b/Telegram/Resources/uwp/AppX/AppxManifest.xml
index feb557542..915dbf61c 100644
--- a/Telegram/Resources/uwp/AppX/AppxManifest.xml
+++ b/Telegram/Resources/uwp/AppX/AppxManifest.xml
@@ -9,7 +9,7 @@
+ Version="2.1.16.0" />
Telegram Desktop
Telegram FZ-LLC
diff --git a/Telegram/Resources/winrc/Telegram.rc b/Telegram/Resources/winrc/Telegram.rc
index 96a5eefb3..98d5d1d2b 100644
--- a/Telegram/Resources/winrc/Telegram.rc
+++ b/Telegram/Resources/winrc/Telegram.rc
@@ -44,8 +44,8 @@ IDI_ICON1 ICON "..\\art\\icon256.ico"
//
VS_VERSION_INFO VERSIONINFO
- FILEVERSION 2,1,14,0
- PRODUCTVERSION 2,1,14,0
+ FILEVERSION 2,1,16,0
+ PRODUCTVERSION 2,1,16,0
FILEFLAGSMASK 0x3fL
#ifdef _DEBUG
FILEFLAGS 0x1L
@@ -62,10 +62,10 @@ BEGIN
BEGIN
VALUE "CompanyName", "Telegram FZ-LLC"
VALUE "FileDescription", "Telegram Desktop"
- VALUE "FileVersion", "2.1.14.0"
+ VALUE "FileVersion", "2.1.16.0"
VALUE "LegalCopyright", "Copyright (C) 2014-2020"
VALUE "ProductName", "Telegram Desktop"
- VALUE "ProductVersion", "2.1.14.0"
+ VALUE "ProductVersion", "2.1.16.0"
END
END
BLOCK "VarFileInfo"
diff --git a/Telegram/Resources/winrc/Updater.rc b/Telegram/Resources/winrc/Updater.rc
index 337a5df9a..a29102114 100644
--- a/Telegram/Resources/winrc/Updater.rc
+++ b/Telegram/Resources/winrc/Updater.rc
@@ -35,8 +35,8 @@ LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US
//
VS_VERSION_INFO VERSIONINFO
- FILEVERSION 2,1,14,0
- PRODUCTVERSION 2,1,14,0
+ FILEVERSION 2,1,16,0
+ PRODUCTVERSION 2,1,16,0
FILEFLAGSMASK 0x3fL
#ifdef _DEBUG
FILEFLAGS 0x1L
@@ -53,10 +53,10 @@ BEGIN
BEGIN
VALUE "CompanyName", "Telegram FZ-LLC"
VALUE "FileDescription", "Telegram Desktop Updater"
- VALUE "FileVersion", "2.1.14.0"
+ VALUE "FileVersion", "2.1.16.0"
VALUE "LegalCopyright", "Copyright (C) 2014-2020"
VALUE "ProductName", "Telegram Desktop"
- VALUE "ProductVersion", "2.1.14.0"
+ VALUE "ProductVersion", "2.1.16.0"
END
END
BLOCK "VarFileInfo"
diff --git a/Telegram/SourceFiles/apiwrap.h b/Telegram/SourceFiles/apiwrap.h
index f88e2ac3b..b3dd94624 100644
--- a/Telegram/SourceFiles/apiwrap.h
+++ b/Telegram/SourceFiles/apiwrap.h
@@ -368,7 +368,6 @@ public:
not_null peer,
const std::vector> &users);
-
rpl::producer sendActions() const {
return _sendActions.events();
}
diff --git a/Telegram/SourceFiles/boxes/background_preview_box.cpp b/Telegram/SourceFiles/boxes/background_preview_box.cpp
index 8de1d447a..e3f45eae5 100644
--- a/Telegram/SourceFiles/boxes/background_preview_box.cpp
+++ b/Telegram/SourceFiles/boxes/background_preview_box.cpp
@@ -781,12 +781,12 @@ bool BackgroundPreviewBox::Start(
Ui::show(Box(tr::lng_background_bad_link(tr::now)));
return false;
}
- controller->session().api().requestWallPaper(slug, [=](
+ controller->session().api().requestWallPaper(slug, crl::guard(controller, [=](
const Data::WallPaper &result) {
Ui::show(Box(
controller,
result.withUrlParams(params)));
- }, [](const RPCError &error) {
+ }), [](const RPCError &error) {
Ui::show(Box(tr::lng_background_bad_link(tr::now)));
});
return true;
diff --git a/Telegram/SourceFiles/boxes/connection_box.cpp b/Telegram/SourceFiles/boxes/connection_box.cpp
index 64a14bc6a..ea364f437 100644
--- a/Telegram/SourceFiles/boxes/connection_box.cpp
+++ b/Telegram/SourceFiles/boxes/connection_box.cpp
@@ -171,7 +171,7 @@ private:
};
-class ProxyBox : public Ui::BoxContent {
+class ProxyBox final : public Ui::BoxContent {
public:
ProxyBox(
QWidget*,
@@ -179,12 +179,14 @@ public:
Fn callback,
Fn shareCallback);
-protected:
- void prepare() override;
-
private:
using Type = ProxyData::Type;
+ void prepare() override;
+ void setInnerFocus() override {
+ _host->setFocusFast();
+ }
+
void refreshButtons();
ProxyData collectData();
void save();
@@ -693,8 +695,8 @@ void ProxiesBox::applyView(View &&view) {
setupButtons(id, i->second.get());
if (_noRows) {
_noRows.reset();
- wrap->resizeToWidth(width());
}
+ wrap->resizeToWidth(width());
} else if (view.host.isEmpty()) {
_rows.erase(i);
} else {
@@ -765,6 +767,31 @@ ProxyBox::ProxyBox(
void ProxyBox::prepare() {
setTitle(tr::lng_proxy_edit());
+ connect(_host.data(), &Ui::InputField::changed, [=] {
+ Ui::PostponeCall(_host, [=] {
+ const auto host = _host->getLastText().trimmed();
+ static const auto mask = u"^\\d+\\.\\d+\\.\\d+\\.\\d+:(\\d*)$"_q;
+ const auto match = QRegularExpression(mask).match(host);
+ if (_host->textCursor().position() == host.size()
+ && match.hasMatch()) {
+ const auto port = match.captured(1);
+ _port->setText(port);
+ _port->setCursorPosition(port.size());
+ _port->setFocus();
+ _host->setText(host.mid(0, host.size() - port.size() - 1));
+ }
+ });
+ });
+ _port.data()->events(
+ ) | rpl::start_with_next([=](not_null e) {
+ if (e->type() == QEvent::KeyPress
+ && (static_cast(e.get())->key() == Qt::Key_Backspace)
+ && _port->cursorPosition() == 0) {
+ _host->setCursorPosition(_host->getLastText().size());
+ _host->setFocus();
+ }
+ }, _port->lifetime());
+
refreshButtons();
setDimensionsToContent(st::boxWideWidth, _content);
}
diff --git a/Telegram/SourceFiles/chat_helpers/field_autocomplete.h b/Telegram/SourceFiles/chat_helpers/field_autocomplete.h
index a0f52ba68..76282a341 100644
--- a/Telegram/SourceFiles/chat_helpers/field_autocomplete.h
+++ b/Telegram/SourceFiles/chat_helpers/field_autocomplete.h
@@ -11,7 +11,6 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "ui/rp_widget.h"
#include "base/timer.h"
#include "base/object_ptr.h"
-#include "data/stickers/data_stickers.h"
namespace Ui {
class ScrollArea;
diff --git a/Telegram/SourceFiles/chat_helpers/stickers_list_widget.cpp b/Telegram/SourceFiles/chat_helpers/stickers_list_widget.cpp
index 1d405bcd6..602a6f447 100644
--- a/Telegram/SourceFiles/chat_helpers/stickers_list_widget.cpp
+++ b/Telegram/SourceFiles/chat_helpers/stickers_list_widget.cpp
@@ -2512,7 +2512,11 @@ void StickersListWidget::refreshRecentStickers(bool performResize) {
externalLayout,
std::move(recentPack));
if (recentIt == _mySets.end()) {
- _mySets.push_back(std::move(set));
+ const auto where = (_mySets.empty()
+ || _mySets.begin()->id != Data::Stickers::FavedSetId)
+ ? _mySets.begin()
+ : (_mySets.begin() + 1);
+ _mySets.insert(where, std::move(set));
} else {
std::swap(*recentIt, set);
takeHeavyData(*recentIt, set);
@@ -2537,7 +2541,7 @@ void StickersListWidget::refreshFavedStickers() {
const auto set = it->second.get();
const auto externalLayout = false;
const auto shortName = QString();
- _mySets.emplace_back(
+ _mySets.insert(_mySets.begin(), Set{
Data::Stickers::FavedSetId,
nullptr,
(MTPDstickerSet::Flag::f_official
@@ -2546,7 +2550,8 @@ void StickersListWidget::refreshFavedStickers() {
shortName,
set->count,
externalLayout,
- PrepareStickers(set->stickers));
+ PrepareStickers(set->stickers)
+ });
_favedStickersMap = base::flat_set> {
set->stickers.begin(),
set->stickers.end()
diff --git a/Telegram/SourceFiles/core/application.cpp b/Telegram/SourceFiles/core/application.cpp
index 8f72e7739..edcbb3cd8 100644
--- a/Telegram/SourceFiles/core/application.cpp
+++ b/Telegram/SourceFiles/core/application.cpp
@@ -174,6 +174,7 @@ Application::~Application() {
_window = nullptr;
_mediaView = nullptr;
+ _notifications->clearAllFast();
_domain->finish();
Local::finish();
@@ -206,6 +207,7 @@ void Application::run() {
refreshGlobalProxy(); // Depends on Global::start().
// Depends on OpenSSL on macOS, so on ThirdParty::start().
+ // Depends on notifications settings.
_notifications = std::make_unique();
startLocalStorage();
diff --git a/Telegram/SourceFiles/core/application.h b/Telegram/SourceFiles/core/application.h
index 0e073493c..83d93a9df 100644
--- a/Telegram/SourceFiles/core/application.h
+++ b/Telegram/SourceFiles/core/application.h
@@ -347,6 +347,11 @@ private:
base::Timer _clearEmojiImageLoaderTimer;
const std::unique_ptr _audio;
mutable std::unique_ptr _fallbackProductionConfig;
+
+ // Notifications should be destroyed before _audio, after _domain.
+ // Mutable because is created in run() after OpenSSL is inited.
+ std::unique_ptr _notifications;
+
const std::unique_ptr _domain;
const std::unique_ptr _exportManager;
const std::unique_ptr _calls;
@@ -363,10 +368,6 @@ private:
Media::Player::FloatDelegate *_defaultFloatPlayerDelegate = nullptr;
Media::Player::FloatDelegate *_replacementFloatPlayerDelegate = nullptr;
- // Notifications should be destroyed before _audio.
- // Mutable because is created in run() after OpenSSL is inited.
- std::unique_ptr _notifications;
-
const QImage _logo;
const QImage _logoBlue;
const QImage _logoGreen;
diff --git a/Telegram/SourceFiles/core/core_settings.cpp b/Telegram/SourceFiles/core/core_settings.cpp
index c88373baf..5e7cb62b5 100644
--- a/Telegram/SourceFiles/core/core_settings.cpp
+++ b/Telegram/SourceFiles/core/core_settings.cpp
@@ -94,7 +94,18 @@ QByteArray Settings::serialize() const {
}
stream
<< qint32(_autoDownloadDictionaries.current() ? 1 : 0)
- << qint32(_mainMenuAccountsShown.current() ? 1 : 0);
+ << qint32(_mainMenuAccountsShown.current() ? 1 : 0)
+ << qint32(_tabbedSelectorSectionEnabled ? 1 : 0)
+ << qint32(_floatPlayerColumn)
+ << qint32(_floatPlayerCorner)
+ << qint32(_thirdSectionInfoEnabled ? 1 : 0)
+ << qint32(snap(
+ qRound(_dialogsWidthRatio.current() * 1000000),
+ 0,
+ 1000000))
+ << qint32(_thirdColumnWidth.current())
+ << qint32(_thirdSectionExtendedBy)
+ << qint32(_notifyFromAll ? 1 : 0);
}
return result;
}
@@ -150,6 +161,14 @@ void Settings::addFromSerialized(const QByteArray &serialized) {
std::vector dictionariesEnabled;
qint32 autoDownloadDictionaries = _autoDownloadDictionaries.current() ? 1 : 0;
qint32 mainMenuAccountsShown = _mainMenuAccountsShown.current() ? 1 : 0;
+ qint32 tabbedSelectorSectionEnabled = 1;
+ qint32 floatPlayerColumn = static_cast(Window::Column::Second);
+ qint32 floatPlayerCorner = static_cast(RectPart::TopRight);
+ qint32 thirdSectionInfoEnabled = 0;
+ float64 dialogsWidthRatio = _dialogsWidthRatio.current();
+ qint32 thirdColumnWidth = _thirdColumnWidth.current();
+ qint32 thirdSectionExtendedBy = _thirdSectionExtendedBy;
+ qint32 notifyFromAll = _notifyFromAll ? 1 : 0;
stream >> themesAccentColors;
if (!stream.atEnd()) {
@@ -211,6 +230,19 @@ void Settings::addFromSerialized(const QByteArray &serialized) {
>> autoDownloadDictionaries
>> mainMenuAccountsShown;
}
+ if (!stream.atEnd()) {
+ auto dialogsWidthRatioInt = qint32();
+ stream
+ >> tabbedSelectorSectionEnabled
+ >> floatPlayerColumn
+ >> floatPlayerCorner
+ >> thirdSectionInfoEnabled
+ >> dialogsWidthRatioInt
+ >> thirdColumnWidth
+ >> thirdSectionExtendedBy
+ >> notifyFromAll;
+ dialogsWidthRatio = snap(dialogsWidthRatioInt / 1000000., 0., 1.);
+ }
if (stream.status() != QDataStream::Ok) {
LOG(("App Error: "
"Bad data for Core::Settings::constructFromSerialized()"));
@@ -281,6 +313,28 @@ void Settings::addFromSerialized(const QByteArray &serialized) {
_dictionariesEnabled = std::move(dictionariesEnabled);
_autoDownloadDictionaries = (autoDownloadDictionaries == 1);
_mainMenuAccountsShown = (mainMenuAccountsShown == 1);
+ _tabbedSelectorSectionEnabled = (tabbedSelectorSectionEnabled == 1);
+ auto uncheckedColumn = static_cast(floatPlayerColumn);
+ switch (uncheckedColumn) {
+ case Window::Column::First:
+ case Window::Column::Second:
+ case Window::Column::Third: _floatPlayerColumn = uncheckedColumn; break;
+ }
+ auto uncheckedCorner = static_cast(floatPlayerCorner);
+ switch (uncheckedCorner) {
+ case RectPart::TopLeft:
+ case RectPart::TopRight:
+ case RectPart::BottomLeft:
+ case RectPart::BottomRight: _floatPlayerCorner = uncheckedCorner; break;
+ }
+ _thirdSectionInfoEnabled = thirdSectionInfoEnabled;
+ _dialogsWidthRatio = dialogsWidthRatio;
+ _thirdColumnWidth = thirdColumnWidth;
+ _thirdSectionExtendedBy = thirdSectionExtendedBy;
+ if (_thirdSectionInfoEnabled) {
+ _tabbedSelectorSectionEnabled = false;
+ }
+ _notifyFromAll = (notifyFromAll == 1);
}
bool Settings::chatWide() const {
@@ -412,6 +466,7 @@ void Settings::resetOnLastLogout() {
_thirdSectionExtendedBy = -1; // per-window
_dialogsWidthRatio = DefaultDialogsWidthRatio(); // per-window
_thirdColumnWidth = kDefaultThirdColumnWidth; // p-w
+ _notifyFromAll = true;
_tabbedReplacedWithInfo = false; // per-window
}
diff --git a/Telegram/SourceFiles/core/core_settings.h b/Telegram/SourceFiles/core/core_settings.h
index 907e37fd5..cedbe6a94 100644
--- a/Telegram/SourceFiles/core/core_settings.h
+++ b/Telegram/SourceFiles/core/core_settings.h
@@ -401,6 +401,12 @@ public:
void setThirdColumnWidth(int width);
[[nodiscard]] int thirdColumnWidth() const;
[[nodiscard]] rpl::producer thirdColumnWidthChanges() const;
+ void setNotifyFromAll(bool value) {
+ _notifyFromAll = value;
+ }
+ [[nodiscard]] bool notifyFromAll() const {
+ return _notifyFromAll;
+ }
[[nodiscard]] static bool ThirdColumnByDefault();
[[nodiscard]] float64 DefaultDialogsWidthRatio();
@@ -467,6 +473,7 @@ private:
int _thirdSectionExtendedBy = -1; // per-window
rpl::variable _dialogsWidthRatio; // per-window
rpl::variable _thirdColumnWidth = kDefaultThirdColumnWidth; // p-w
+ bool _notifyFromAll = true;
bool _tabbedReplacedWithInfo = false; // per-window
rpl::event_stream _tabbedReplacedWithInfoValue; // per-window
diff --git a/Telegram/SourceFiles/core/local_url_handlers.cpp b/Telegram/SourceFiles/core/local_url_handlers.cpp
index 607d65b18..249b6c847 100644
--- a/Telegram/SourceFiles/core/local_url_handlers.cpp
+++ b/Telegram/SourceFiles/core/local_url_handlers.cpp
@@ -304,16 +304,13 @@ bool ResolveUsername(
}
const auto clickFromMessageId = context.value();
const auto searchParam = params.value(qsl("query"));
- if (const auto controller = App::wnd()->sessionController()) {
- controller->content()->openPeerByName(
- domain,
- post,
- startToken,
- clickFromMessageId,
- searchParam);
- return true;
- }
- return false;
+ controller->content()->openPeerByName(
+ domain,
+ post,
+ startToken,
+ clickFromMessageId,
+ searchParam);
+ return true;
}
bool ResolvePrivatePost(
@@ -331,12 +328,12 @@ bool ResolvePrivatePost(
if (!channelId || !IsServerMsgId(msgId)) {
return false;
}
- const auto done = [=](not_null peer) {
- App::wnd()->sessionController()->showPeerHistory(
+ const auto done = crl::guard(controller, [=](not_null peer) {
+ controller->showPeerHistory(
peer->id,
Window::SectionShow::Way::Forward,
msgId);
- };
+ });
const auto fail = [=] {
Ui::show(Box(tr::lng_error_post_link_invalid(tr::now)));
};
@@ -400,7 +397,7 @@ bool HandleUnknown(
return false;
}
const auto request = match->captured(1);
- const auto callback = [=](const MTPDhelp_deepLinkInfo &result) {
+ const auto callback = crl::guard(controller, [=](const MTPDhelp_deepLinkInfo &result) {
const auto text = TextWithEntities{
qs(result.vmessage()),
Api::EntitiesFromMTP(
@@ -420,7 +417,7 @@ bool HandleUnknown(
} else {
Ui::show(Box(text));
}
- };
+ });
controller->session().api().requestDeepLinkInfo(request, callback);
return true;
}
diff --git a/Telegram/SourceFiles/core/version.h b/Telegram/SourceFiles/core/version.h
index 0fc34e9b5..07f94556f 100644
--- a/Telegram/SourceFiles/core/version.h
+++ b/Telegram/SourceFiles/core/version.h
@@ -23,7 +23,7 @@ constexpr auto AppId = "{C4A4AE8F-B9F7-4CC7-8A6C-BF7EEE87ACA5}"_cs;
constexpr auto AppNameOld = "Telegram Win (Unofficial)"_cs;
constexpr auto AppName = "Kotatogram Desktop"_cs;
constexpr auto AppFile = "Kotatogram"_cs;
-constexpr auto AppVersion = 2001014;
-constexpr auto AppVersionStr = "2.1.14";
+constexpr auto AppVersion = 2001016;
+constexpr auto AppVersionStr = "2.1.16";
constexpr auto AppBetaVersion = true;
constexpr auto AppAlphaVersion = TDESKTOP_ALPHA_VERSION;
diff --git a/Telegram/SourceFiles/data/data_chat_filters.cpp b/Telegram/SourceFiles/data/data_chat_filters.cpp
index 56d6c266b..6c1abbbea 100644
--- a/Telegram/SourceFiles/data/data_chat_filters.cpp
+++ b/Telegram/SourceFiles/data/data_chat_filters.cpp
@@ -226,7 +226,7 @@ bool ChatFilter::contains(not_null history) const {
}
ChatFilters::ChatFilters(not_null owner) : _owner(owner) {
- load();
+ crl::on_main(&owner->session(), [=] { load(); });
}
ChatFilters::~ChatFilters() = default;
@@ -242,6 +242,16 @@ not_null ChatFilters::chatsList(FilterId filterId) {
return pointer.get();
}
+void ChatFilters::setPreloaded(const QVector &result) {
+ _loadRequestId = -1;
+ received(result);
+ crl::on_main(&_owner->session(), [=] {
+ if (_loadRequestId == -1) {
+ _loadRequestId = 0;
+ }
+ });
+}
+
void ChatFilters::load() {
load(false);
}
@@ -254,40 +264,44 @@ void ChatFilters::load(bool force) {
api.request(_loadRequestId).cancel();
_loadRequestId = api.request(MTPmessages_GetDialogFilters(
)).done([=](const MTPVector &result) {
- auto position = 0;
- auto changed = false;
- for (const auto &filter : result.v) {
- auto parsed = ChatFilter::FromTL(filter, _owner);
- const auto b = begin(_list) + position, e = end(_list);
- const auto i = ranges::find(b, e, parsed.id(), &ChatFilter::id);
- if (i == e) {
- applyInsert(std::move(parsed), position);
- changed = true;
- } else if (i == b) {
- if (applyChange(*b, std::move(parsed))) {
- changed = true;
- }
- } else {
- std::swap(*i, *b);
- applyChange(*b, std::move(parsed));
- changed = true;
- }
- ++position;
- }
- while (position < _list.size()) {
- applyRemove(position);
- changed = true;
- }
- if (changed || !_loaded) {
- _loaded = true;
- _listChanged.fire({});
- }
+ received(result.v);
_loadRequestId = 0;
}).fail([=](const RPCError &error) {
_loadRequestId = 0;
}).send();
}
+void ChatFilters::received(const QVector &list) {
+ auto position = 0;
+ auto changed = false;
+ for (const auto &filter : list) {
+ auto parsed = ChatFilter::FromTL(filter, _owner);
+ const auto b = begin(_list) + position, e = end(_list);
+ const auto i = ranges::find(b, e, parsed.id(), &ChatFilter::id);
+ if (i == e) {
+ applyInsert(std::move(parsed), position);
+ changed = true;
+ } else if (i == b) {
+ if (applyChange(*b, std::move(parsed))) {
+ changed = true;
+ }
+ } else {
+ std::swap(*i, *b);
+ applyChange(*b, std::move(parsed));
+ changed = true;
+ }
+ ++position;
+ }
+ while (position < _list.size()) {
+ applyRemove(position);
+ changed = true;
+ }
+ if (changed || !_loaded) {
+ _loaded = true;
+ _listChanged.fire({});
+ }
+}
+
void ChatFilters::apply(const MTPUpdate &update) {
update.match([&](const MTPDupdateDialogFilter &data) {
if (const auto filter = data.vfilter()) {
diff --git a/Telegram/SourceFiles/data/data_chat_filters.h b/Telegram/SourceFiles/data/data_chat_filters.h
index 5723c8985..a6ecf18b0 100644
--- a/Telegram/SourceFiles/data/data_chat_filters.h
+++ b/Telegram/SourceFiles/data/data_chat_filters.h
@@ -99,6 +99,8 @@ public:
explicit ChatFilters(not_null owner);
~ChatFilters();
+ void setPreloaded(const QVector &result);
+
void load();
void apply(const MTPUpdate &update);
void set(ChatFilter filter);
@@ -129,6 +131,7 @@ public:
private:
void load(bool force);
+ void received(const QVector &list);
bool applyOrder(const QVector &order);
bool applyChange(ChatFilter &filter, ChatFilter &&updated);
void applyInsert(ChatFilter filter, int position);
diff --git a/Telegram/SourceFiles/data/data_session.cpp b/Telegram/SourceFiles/data/data_session.cpp
index a9c32d861..2dfcc24a9 100644
--- a/Telegram/SourceFiles/data/data_session.cpp
+++ b/Telegram/SourceFiles/data/data_session.cpp
@@ -462,9 +462,6 @@ not_null Session::processUser(const MTPUser &data) {
: QString())
: result->nameOrPhone;
- if (!minimal && data.is_self() && uname != result->username) {
- CrashReports::SetAnnotation("Username", uname);
- }
result->setName(fname, lname, pname, uname);
if (const auto photo = data.vphoto()) {
result->setPhoto(*photo);
@@ -2559,6 +2556,7 @@ not_null Session::processWebpage(const MTPWebPage &data) {
const auto result = webpage(data.c_webPageEmpty().vid().v);
if (result->pendingTill > 0) {
result->pendingTill = -1; // failed
+ notifyWebPageUpdateDelayed(result);
}
return result;
} break;
diff --git a/Telegram/SourceFiles/data/stickers/data_stickers.cpp b/Telegram/SourceFiles/data/stickers/data_stickers.cpp
index 08ef4297c..c60c3db5c 100644
--- a/Telegram/SourceFiles/data/stickers/data_stickers.cpp
+++ b/Telegram/SourceFiles/data/stickers/data_stickers.cpp
@@ -892,7 +892,7 @@ void Stickers::gifsReceived(const QVector &items, int32 hash) {
const auto document = owner().processDocument(item);
if (!document->isGifv()) {
LOG(("API Error: "
- "bad document returned in HistoryWidget::savedGifsGot!"));
+ "bad document returned in Stickers::gifsReceived!"));
continue;
}
diff --git a/Telegram/SourceFiles/dialogs/dialogs_inner_widget.cpp b/Telegram/SourceFiles/dialogs/dialogs_inner_widget.cpp
index 563ab4862..77572ace1 100644
--- a/Telegram/SourceFiles/dialogs/dialogs_inner_widget.cpp
+++ b/Telegram/SourceFiles/dialogs/dialogs_inner_widget.cpp
@@ -3056,7 +3056,7 @@ void InnerWidget::setupShortcuts() {
}) | rpl::start_with_next([=](not_null request) {
using Command = Shortcuts::Command;
- if (_controller->content()->selectingPeer()) {
+ if (_controller->selectingPeer()) {
return;
}
const auto row = _controller->activeChatEntryCurrent();
diff --git a/Telegram/SourceFiles/dialogs/dialogs_widget.cpp b/Telegram/SourceFiles/dialogs/dialogs_widget.cpp
index 43d781b96..c1da80a65 100644
--- a/Telegram/SourceFiles/dialogs/dialogs_widget.cpp
+++ b/Telegram/SourceFiles/dialogs/dialogs_widget.cpp
@@ -212,7 +212,7 @@ Widget::Widget(
});
_inner->chosenRow(
) | rpl::start_with_next([=](const ChosenRow &row) {
- const auto openSearchResult = !controller->content()->selectingPeer()
+ const auto openSearchResult = !controller->selectingPeer()
&& row.filteredRow;
if (const auto history = row.key.history()) {
controller->content()->choosePeer(
@@ -701,7 +701,7 @@ void Widget::escape() {
} else if (controller()->activeChatsFilterCurrent() != cDefaultFilterId()) {
controller()->setActiveChatsFilter(cDefaultFilterId());
}
- } else if (!_searchInChat && !controller()->content()->selectingPeer()) {
+ } else if (!_searchInChat && !controller()->selectingPeer()) {
if (controller()->activeChatEntryCurrent().key) {
emit cancelled();
}
@@ -1267,7 +1267,7 @@ void Widget::peopleFailed(const RPCError &error, mtpRequestId requestId) {
void Widget::dragEnterEvent(QDragEnterEvent *e) {
using namespace Storage;
- if (controller()->content()->selectingPeer()) {
+ if (controller()->selectingPeer()) {
return;
}
@@ -1616,7 +1616,7 @@ void Widget::updateControlsGeometry() {
}
void Widget::updateForwardBar() {
- auto selecting = controller()->content()->selectingPeer();
+ auto selecting = controller()->selectingPeer();
auto oneColumnSelecting = (Adaptive::OneColumn() && selecting);
if (!oneColumnSelecting == !_forwardCancel) {
return;
@@ -1759,7 +1759,7 @@ bool Widget::onCancelSearch() {
void Widget::onCancelSearchInChat() {
cancelSearchRequest();
if (_searchInChat) {
- if (Adaptive::OneColumn() && !controller()->content()->selectingPeer()) {
+ if (Adaptive::OneColumn() && !controller()->selectingPeer()) {
if (const auto peer = _searchInChat.peer()) {
Ui::showPeerHistory(peer, ShowAtUnreadMsgId);
//} else if (const auto feed = _searchInChat.feed()) { // #feed
@@ -1774,7 +1774,7 @@ void Widget::onCancelSearchInChat() {
_filter->clear();
_filter->updatePlaceholder();
applyFilterUpdate();
- if (!Adaptive::OneColumn() && !controller()->content()->selectingPeer()) {
+ if (!Adaptive::OneColumn() && !controller()->selectingPeer()) {
emit cancelled();
}
}
@@ -1786,6 +1786,8 @@ void Widget::onDialogMoved(int movedFrom, int movedTo) {
}
}
-Widget::~Widget() = default;
+Widget::~Widget() {
+ cancelSearchRequest();
+}
} // namespace Dialogs
diff --git a/Telegram/SourceFiles/history/history_widget.cpp b/Telegram/SourceFiles/history/history_widget.cpp
index 0280af7f4..2198b484a 100644
--- a/Telegram/SourceFiles/history/history_widget.cpp
+++ b/Telegram/SourceFiles/history/history_widget.cpp
@@ -46,6 +46,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "data/data_scheduled_messages.h"
#include "data/data_file_origin.h"
#include "data/data_histories.h"
+#include "data/stickers/data_stickers.h"
#include "history/history.h"
#include "history/history_item.h"
#include "history/history_message.h"
@@ -260,6 +261,7 @@ HistoryWidget::HistoryWidget(
QWidget *parent,
not_null controller)
: Window::AbstractSectionWidget(parent, controller)
+, _api(&controller->session().mtp())
, _updateEditTimeLeftDisplay([=] { updateField(); })
, _fieldBarCancel(this, st::historyReplyCancel)
, _previewTimer([=] { requestPreview(); })
@@ -1219,14 +1221,14 @@ void HistoryWidget::updateInlineBotQuery() {
if (_inlineBotUsername != query.username) {
_inlineBotUsername = query.username;
if (_inlineBotResolveRequestId) {
- session().api().request(_inlineBotResolveRequestId).cancel();
+ _api.request(_inlineBotResolveRequestId).cancel();
_inlineBotResolveRequestId = 0;
}
if (query.lookingUpBot) {
_inlineBot = nullptr;
_inlineLookingUpBot = true;
const auto username = _inlineBotUsername;
- _inlineBotResolveRequestId = session().api().request(MTPcontacts_ResolveUsername(
+ _inlineBotResolveRequestId = _api.request(MTPcontacts_ResolveUsername(
MTP_string(username)
)).done([=](const MTPcontacts_ResolvedPeer &result) {
inlineBotResolveDone(result);
@@ -1477,7 +1479,7 @@ void HistoryWidget::cancelSendAction(
SendAction::Type type) {
const auto i = _sendActionRequests.find({ history, type });
if (i != _sendActionRequests.end()) {
- session().api().request(i->second).cancel();
+ _api.request(i->second).cancel();
_sendActionRequests.erase(i);
}
}
@@ -1518,7 +1520,7 @@ void HistoryWidget::updateSendAction(
case Type::ChooseContact: action = MTP_sendMessageChooseContactAction(); break;
case Type::PlayGame: action = MTP_sendMessageGamePlayAction(); break;
}
- const auto requestId = session().api().request(MTPmessages_SetTyping(
+ const auto requestId = _api.request(MTPmessages_SetTyping(
peer->input,
action
)).done([=](const MTPBool &result, mtpRequestId requestId) {
@@ -3155,6 +3157,7 @@ void HistoryWidget::saveEditMsg() {
sendFlags |= MTPmessages_EditMessage::Flag::f_entities;
}
+ const auto weak = Ui::MakeWeak(this);
const auto history = _history;
_saveEditMsgRequestId = history->session().api().request(
MTPmessages_EditMessage(
@@ -3166,55 +3169,60 @@ void HistoryWidget::saveEditMsg() {
MTPReplyMarkup(),
sentEntities,
MTP_int(0)
- )).done([=](const MTPUpdates &result, mtpRequestId requestId) {
- saveEditMsgDone(history, result, requestId);
- }).fail([=](const RPCError &error, mtpRequestId requestId) {
- saveEditMsgFail(history, error, requestId);
+ )).done([history, weak](const MTPUpdates &result, mtpRequestId requestId) {
+ SaveEditMsgDone(history, result, requestId);
+ if (const auto strong = weak.data()) {
+ if (requestId == strong->_saveEditMsgRequestId) {
+ strong->_saveEditMsgRequestId = 0;
+ strong->cancelEdit();
+ }
+ }
+ }).fail([history, weak](const RPCError &error, mtpRequestId requestId) {
+ SaveEditMsgFail(history, error, requestId);
+ if (const auto strong = weak.data()) {
+ if (requestId == strong->_saveEditMsgRequestId) {
+ strong->_saveEditMsgRequestId = 0;
+ }
+ const auto &err = error.type();
+ if (err == qstr("MESSAGE_ID_INVALID")
+ || err == qstr("CHAT_ADMIN_REQUIRED")
+ || err == qstr("MESSAGE_EDIT_TIME_EXPIRED")) {
+ Ui::show(Box(tr::lng_edit_error(tr::now)));
+ } else if (err == qstr("MESSAGE_NOT_MODIFIED")) {
+ strong->cancelEdit();
+ } else if (err == qstr("MESSAGE_EMPTY")) {
+ strong->_field->selectAll();
+ strong->_field->setFocus();
+ } else {
+ Ui::show(Box(tr::lng_edit_error(tr::now)));
+ }
+ strong->update();
+ }
}).send();
}
-void HistoryWidget::saveEditMsgDone(
+void HistoryWidget::SaveEditMsgDone(
not_null history,
const MTPUpdates &updates,
mtpRequestId requestId) {
- session().api().applyUpdates(updates);
- if (requestId == _saveEditMsgRequestId) {
- _saveEditMsgRequestId = 0;
- cancelEdit();
- }
+ history->session().api().applyUpdates(updates);
if (auto editDraft = history->editDraft()) {
if (editDraft->saveRequestId == requestId) {
history->clearEditDraft();
- session().local().writeDrafts(history);
+ history->session().local().writeDrafts(history);
}
}
}
-void HistoryWidget::saveEditMsgFail(
+void HistoryWidget::SaveEditMsgFail(
not_null history,
const RPCError &error,
mtpRequestId requestId) {
- if (requestId == _saveEditMsgRequestId) {
- _saveEditMsgRequestId = 0;
- }
if (auto editDraft = history->editDraft()) {
if (editDraft->saveRequestId == requestId) {
editDraft->saveRequestId = 0;
}
}
-
- const auto &err = error.type();
- if (err == qstr("MESSAGE_ID_INVALID") || err == qstr("CHAT_ADMIN_REQUIRED") || err == qstr("MESSAGE_EDIT_TIME_EXPIRED")) {
- Ui::show(Box(tr::lng_edit_error(tr::now)));
- } else if (err == qstr("MESSAGE_NOT_MODIFIED")) {
- cancelEdit();
- } else if (err == qstr("MESSAGE_EMPTY")) {
- _field->selectAll();
- _field->setFocus();
- } else {
- Ui::show(Box(tr::lng_edit_error(tr::now)));
- }
- update();
}
void HistoryWidget::hideSelectorControlsAnimated() {
@@ -3775,6 +3783,7 @@ void HistoryWidget::app_sendBotCallback(
using ButtonType = HistoryMessageMarkupButton::Type;
BotCallbackInfo info = {
+ &session(),
bot,
msg->fullId(),
row,
@@ -3789,15 +3798,24 @@ void HistoryWidget::app_sendBotCallback(
flags |= MTPmessages_GetBotCallbackAnswer::Flag::f_data;
sendData = button->data;
}
+ const auto weak = Ui::MakeWeak(this);
button->requestId = session().api().request(MTPmessages_GetBotCallbackAnswer(
MTP_flags(flags),
_peer->input,
MTP_int(msg->id),
MTP_bytes(sendData)
- )).done([=](const MTPmessages_BotCallbackAnswer &result, mtpRequestId requestId) {
- botCallbackDone(info, result, requestId);
- }).fail([=](const RPCError &error, mtpRequestId requestId) {
- botCallbackFail(info, error, requestId);
+ )).done([info, weak](const MTPmessages_BotCallbackAnswer &result, mtpRequestId requestId) {
+ BotCallbackDone(info, result, requestId);
+ result.match([&](const MTPDmessages_botCallbackAnswer &data) {
+ const auto item = info.session->data().message(info.msgId);
+ if (!data.vmessage() && data.vurl() && info.game && item) {
+ if (const auto strong = weak.data()) {
+ strong->updateSendAction(item->history(), SendAction::Type::PlayGame);
+ }
+ }
+ });
+ }).fail([info](const RPCError &error, mtpRequestId requestId) {
+ BotCallbackFail(info, error, requestId);
}).send();
session().data().requestItemRepaint(msg);
@@ -3810,19 +3828,20 @@ void HistoryWidget::app_sendBotCallback(
}
}
-void HistoryWidget::botCallbackDone(
+void HistoryWidget::BotCallbackDone(
BotCallbackInfo info,
const MTPmessages_BotCallbackAnswer &answer,
mtpRequestId req) {
- const auto item = session().data().message(info.msgId);
+ const auto session = info.session;
+ const auto item = session->data().message(info.msgId);
const auto button = HistoryMessageMarkupButton::Get(
- &session().data(),
+ &session->data(),
info.msgId,
info.row,
info.col);
if (button && button->requestId == req) {
button->requestId = 0;
- session().data().requestItemRepaint(item);
+ session->data().requestItemRepaint(item);
}
answer.match([&](const MTPDmessages_botCallbackAnswer &data) {
if (const auto message = data.vmessage()) {
@@ -3834,11 +3853,8 @@ void HistoryWidget::botCallbackDone(
} else if (const auto url = data.vurl()) {
auto link = qs(*url);
if (info.game) {
- link = AppendShareGameScoreUrl(&session(), link, info.msgId);
+ link = AppendShareGameScoreUrl(session, link, info.msgId);
BotGameUrlClickHandler(info.bot, link).onClick({});
- if (item) {
- updateSendAction(item->history(), SendAction::Type::PlayGame);
- }
} else {
UrlClickHandler::Open(link);
}
@@ -3846,21 +3862,21 @@ void HistoryWidget::botCallbackDone(
});
}
-bool HistoryWidget::botCallbackFail(
+void HistoryWidget::BotCallbackFail(
BotCallbackInfo info,
const RPCError &error,
mtpRequestId req) {
// show error?
+ const auto owner = &info.session->data();
const auto button = HistoryMessageMarkupButton::Get(
- &session().data(),
+ owner,
info.msgId,
info.row,
info.col);
if (button && button->requestId == req) {
button->requestId = 0;
- session().data().requestItemRepaint(session().data().message(info.msgId));
+ owner->requestItemRepaint(owner->message(info.msgId));
}
- return true;
}
bool HistoryWidget::insertBotCommand(const QString &cmd) {
@@ -5037,12 +5053,11 @@ void HistoryWidget::updateControlsGeometry() {
}
void HistoryWidget::itemRemoved(not_null item) {
- if (item == _replyEditMsg) {
- if (_editMsgId) {
- cancelEdit();
- } else {
- cancelReply();
- }
+ if (item == _replyEditMsg && _editMsgId) {
+ cancelEdit();
+ }
+ if (item == _replyEditMsg && _replyToId) {
+ cancelReply();
}
while (item == _replyReturn) {
calcNextReplyReturn();
@@ -6129,7 +6144,13 @@ void HistoryWidget::pinMessage(FullMsgId itemId) {
}
void HistoryWidget::unpinMessage(FullMsgId itemId) {
- const auto peer = _peer;
+ if (!_peer) {
+ return;
+ }
+ UnpinMessage(_peer);
+}
+
+void HistoryWidget::UnpinMessage(not_null peer) {
if (!peer) {
return;
}
@@ -6291,7 +6312,7 @@ void HistoryWidget::cancelFieldAreaState() {
}
void HistoryWidget::previewCancel() {
- session().api().request(base::take(_previewRequest)).cancel();
+ _api.request(base::take(_previewRequest)).cancel();
_previewData = nullptr;
_previewLinks.clear();
updatePreview();
@@ -6307,7 +6328,7 @@ void HistoryWidget::checkPreview() {
}
const auto links = _parsedLinks.join(' ');
if (_previewLinks != links) {
- session().api().request(base::take(_previewRequest)).cancel();
+ _api.request(base::take(_previewRequest)).cancel();
_previewLinks = links;
if (_previewLinks.isEmpty()) {
if (_previewData && _previewData->pendingTill >= 0) {
@@ -6316,7 +6337,7 @@ void HistoryWidget::checkPreview() {
} else {
const auto i = _previewCache.constFind(links);
if (i == _previewCache.cend()) {
- _previewRequest = session().api().request(MTPmessages_GetWebPagePreview(
+ _previewRequest = _api.request(MTPmessages_GetWebPagePreview(
MTP_flags(0),
MTP_string(links),
MTPVector()
@@ -6340,7 +6361,7 @@ void HistoryWidget::requestPreview() {
return;
}
const auto links = _previewLinks;
- _previewRequest = session().api().request(MTPmessages_GetWebPagePreview(
+ _previewRequest = _api.request(MTPmessages_GetWebPagePreview(
MTP_flags(0),
MTP_string(links),
MTPVector()
diff --git a/Telegram/SourceFiles/history/history_widget.h b/Telegram/SourceFiles/history/history_widget.h
index dd26b52c0..4d0c51c40 100644
--- a/Telegram/SourceFiles/history/history_widget.h
+++ b/Telegram/SourceFiles/history/history_widget.h
@@ -14,6 +14,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "ui/widgets/input_fields.h"
#include "ui/effects/animations.h"
#include "ui/rp_widget.h"
+#include "mtproto/sender.h"
#include "base/flags.h"
#include "base/timer.h"
@@ -339,6 +340,7 @@ private:
using TabbedSelector = ChatHelpers::TabbedSelector;
using DragState = Storage::MimeDataState;
struct BotCallbackInfo {
+ not_null session;
UserData *bot;
FullMsgId msgId;
int row, col;
@@ -571,8 +573,8 @@ private:
void createUnreadBarAndResize();
void saveEditMsg();
- void saveEditMsgDone(not_null history, const MTPUpdates &updates, mtpRequestId requestId);
- void saveEditMsgFail(not_null history, const RPCError &error, mtpRequestId requestId);
+ static void SaveEditMsgDone(not_null history, const MTPUpdates &updates, mtpRequestId requestId);
+ static void SaveEditMsgFail(not_null history, const RPCError &error, mtpRequestId requestId);
void checkPreview();
void requestPreview();
@@ -582,8 +584,10 @@ private:
void addMessagesToFront(PeerData *peer, const QVector &messages);
void addMessagesToBack(PeerData *peer, const QVector &messages);
- void botCallbackDone(BotCallbackInfo info, const MTPmessages_BotCallbackAnswer &answer, mtpRequestId req);
- bool botCallbackFail(BotCallbackInfo info, const RPCError &error, mtpRequestId req);
+ static void UnpinMessage(not_null peer);
+
+ static void BotCallbackDone(BotCallbackInfo info, const MTPmessages_BotCallbackAnswer &answer, mtpRequestId req);
+ static void BotCallbackFail(BotCallbackInfo info, const RPCError &error, mtpRequestId req);
void updateHistoryGeometry(bool initial = false, bool loadedDown = false, const ScrollChange &change = { ScrollChangeNone, 0 });
void updateListSize();
@@ -648,6 +652,7 @@ private:
void setupScheduledToggle();
void refreshScheduledToggle();
+ MTP::Sender _api;
MsgId _replyToId = 0;
Ui::Text::String _replyToName;
int _replyToNameVersion = 0;
diff --git a/Telegram/SourceFiles/intro/intro_step.cpp b/Telegram/SourceFiles/intro/intro_step.cpp
index 6afdb3670..f8f526c47 100644
--- a/Telegram/SourceFiles/intro/intro_step.cpp
+++ b/Telegram/SourceFiles/intro/intro_step.cpp
@@ -27,6 +27,8 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "ui/effects/slide_animation.h"
#include "data/data_user.h"
#include "data/data_auto_download.h"
+#include "data/data_session.h"
+#include "data/data_chat_filters.h"
#include "window/window_controller.h"
#include "window/themes/window_theme.h"
#include "app.h"
@@ -160,6 +162,18 @@ void Step::finish(const MTPUser &user, QImage &&photo) {
}
}
+ api().request(MTPmessages_GetDialogFilters(
+ )).done([=](const MTPVector &result) {
+ createSession(user, photo, result.v);
+ }).fail([=](const RPCError &error) {
+ createSession(user, photo, QVector());
+ }).send();
+}
+
+void Step::createSession(
+ const MTPUser &user,
+ QImage photo,
+ const QVector &filters) {
// Save the default language if we've suggested some other and user ignored it.
const auto currentId = Lang::Current().id();
const auto defaultId = Lang::DefaultLanguageId();
@@ -168,12 +182,20 @@ void Step::finish(const MTPUser &user, QImage &&photo) {
Lang::Current().switchToId(Lang::DefaultLanguage());
Local::writeLangPack();
}
+
+ auto settings = std::make_unique();
+ settings->setDialogsFiltersEnabled(!filters.isEmpty());
+
const auto account = _account;
- account->createSession(user);
+ account->createSession(user, std::move(settings));
// "this" is already deleted here by creating the main widget.
account->local().writeMtpData();
auto &session = account->session();
+ session.data().chatsFilters().setPreloaded(filters);
+ if (!filters.isEmpty()) {
+ session.saveSettingsDelayed();
+ }
if (!photo.isNull()) {
session.api().uploadPeerPhoto(session.user(), std::move(photo));
}
diff --git a/Telegram/SourceFiles/intro/intro_step.h b/Telegram/SourceFiles/intro/intro_step.h
index bc9548800..b98349a44 100644
--- a/Telegram/SourceFiles/intro/intro_step.h
+++ b/Telegram/SourceFiles/intro/intro_step.h
@@ -106,6 +106,10 @@ protected:
return _data;
}
void finish(const MTPUser &user, QImage &&photo = QImage());
+ void createSession(
+ const MTPUser &user,
+ QImage photo,
+ const QVector &filters);
void goBack();
diff --git a/Telegram/SourceFiles/kotato/settings_menu.cpp b/Telegram/SourceFiles/kotato/settings_menu.cpp
index 365b74583..935fa86f5 100644
--- a/Telegram/SourceFiles/kotato/settings_menu.cpp
+++ b/Telegram/SourceFiles/kotato/settings_menu.cpp
@@ -426,7 +426,7 @@ void SetupKotatoSystem(
AddSkip(container);
AddSubsectionTitle(container, tr::ktg_settings_system());
-#if defined Q_OS_WIN || defined Q_OS_MAC
+#if defined Q_OS_WIN || defined Q_OS_MAC || QT_VERSION >= QT_VERSION_CHECK(5, 15, 0) || defined DESKTOP_APP_QT_PATCHED
const auto useNativeDecorationsToggled = Ui::CreateChild>(
container.get());
AddButton(
@@ -453,7 +453,7 @@ void SetupKotatoSystem(
confirmed,
cancelled));
}, container->lifetime());
-#endif // Q_OS_WIN || Q_OS_MAC
+#endif // Q_OS_WIN || Q_OS_MAC || Qt >= 5.15 || DESKTOP_APP_QT_PATCHED
AddButton(
container,
diff --git a/Telegram/SourceFiles/main/main_account.cpp b/Telegram/SourceFiles/main/main_account.cpp
index c2e9958d4..a4b2eb8fb 100644
--- a/Telegram/SourceFiles/main/main_account.cpp
+++ b/Telegram/SourceFiles/main/main_account.cpp
@@ -131,8 +131,14 @@ uint64 Account::willHaveSessionUniqueId(MTP::Config *config) const {
| (config && config->isTestMode() ? 0x0100'0000'0000'0000ULL : 0ULL);
}
-void Account::createSession(const MTPUser &user) {
- createSession(user, QByteArray(), 0, std::make_unique());
+void Account::createSession(
+ const MTPUser &user,
+ std::unique_ptr settings) {
+ createSession(
+ user,
+ QByteArray(),
+ 0,
+ settings ? std::move(settings) : std::make_unique());
}
void Account::createSession(
diff --git a/Telegram/SourceFiles/main/main_account.h b/Telegram/SourceFiles/main/main_account.h
index d63eab11a..8c14b1793 100644
--- a/Telegram/SourceFiles/main/main_account.h
+++ b/Telegram/SourceFiles/main/main_account.h
@@ -49,7 +49,9 @@ public:
void start(std::unique_ptr config);
[[nodiscard]] uint64 willHaveSessionUniqueId(MTP::Config *config) const;
- void createSession(const MTPUser &user);
+ void createSession(
+ const MTPUser &user,
+ std::unique_ptr settings = nullptr);
void createSession(
UserId id,
QByteArray serialized,
diff --git a/Telegram/SourceFiles/main/main_app_config.cpp b/Telegram/SourceFiles/main/main_app_config.cpp
index 4f86f2bcf..077c97e0a 100644
--- a/Telegram/SourceFiles/main/main_app_config.cpp
+++ b/Telegram/SourceFiles/main/main_app_config.cpp
@@ -24,6 +24,13 @@ AppConfig::AppConfig(not_null account) : _account(account) {
_api.emplace(instance);
refresh();
}, _lifetime);
+
+ account->sessionChanges(
+ ) | rpl::filter([=](Session *session) {
+ return (session != nullptr);
+ }) | rpl::start_with_next([=] {
+ refresh();
+ }, _lifetime);
}
void AppConfig::refresh() {
diff --git a/Telegram/SourceFiles/main/main_domain.cpp b/Telegram/SourceFiles/main/main_domain.cpp
index 6b8fd61cc..d9525fb73 100644
--- a/Telegram/SourceFiles/main/main_domain.cpp
+++ b/Telegram/SourceFiles/main/main_domain.cpp
@@ -9,15 +9,19 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "core/application.h"
#include "core/shortcuts.h"
+#include "core/crash_reports.h"
#include "main/main_account.h"
#include "main/main_session.h"
#include "data/data_session.h"
+#include "data/data_changes.h"
+#include "data/data_user.h"
#include "mtproto/mtproto_config.h"
#include "mtproto/mtproto_dc_options.h"
#include "storage/storage_domain.h"
#include "storage/storage_account.h"
#include "storage/localstorage.h"
#include "export/export_settings.h"
+#include "window/notifications_manager.h"
#include "facades.h"
namespace Main {
@@ -28,6 +32,22 @@ Domain::Domain(const QString &dataName)
_active.changes(
) | rpl::take(1) | rpl::start_with_next([] {
Local::rewriteSettingsIfNeeded();
+ Core::App().notifications().createManager();
+ }, _lifetime);
+
+ _active.changes(
+ ) | rpl::map([](Main::Account *account) {
+ return account ? account->sessionValue() : rpl::never();
+ }) | rpl::flatten_latest(
+ ) | rpl::map([](Main::Session *session) {
+ return session
+ ? session->changes().peerFlagsValue(
+ session->user(),
+ Data::PeerUpdate::Flag::Username)
+ : rpl::never();
+ }) | rpl::flatten_latest(
+ ) | rpl::start_with_next([](const Data::PeerUpdate &update) {
+ CrashReports::SetAnnotation("Username", update.peer->userName());
}, _lifetime);
}
@@ -253,6 +273,20 @@ not_null Domain::add(MTP::Environment environment) {
return account;
}
+void Domain::addActivated(MTP::Environment environment) {
+ if (accounts().size() < Main::Domain::kMaxAccounts) {
+ activate(add(environment));
+ } else {
+ for (auto &[index, account] : accounts()) {
+ if (!account->sessionExists()
+ && account->mtp().environment() == environment) {
+ activate(account.get());
+ break;
+ }
+ }
+ }
+}
+
void Domain::watchSession(not_null account) {
account->sessionValue(
) | rpl::filter([=](Session *session) {
diff --git a/Telegram/SourceFiles/main/main_domain.h b/Telegram/SourceFiles/main/main_domain.h
index 6e9da8386..4adadf21e 100644
--- a/Telegram/SourceFiles/main/main_domain.h
+++ b/Telegram/SourceFiles/main/main_domain.h
@@ -64,6 +64,7 @@ public:
[[nodiscard]] not_null add(MTP::Environment environment);
void activate(not_null account);
+ void addActivated(MTP::Environment environment);
// Interface for Storage::Domain.
void accountAddedInStorage(AccountWithIndex accountWithIndex);
diff --git a/Telegram/SourceFiles/mainwidget.cpp b/Telegram/SourceFiles/mainwidget.cpp
index 8bfccf434..60f4e9bd0 100644
--- a/Telegram/SourceFiles/mainwidget.cpp
+++ b/Telegram/SourceFiles/mainwidget.cpp
@@ -230,6 +230,7 @@ MainWidget::MainWidget(
not_null controller)
: RpWidget(parent)
, _controller(controller)
+, _api(&controller->session().mtp())
, _dialogsWidth(st::columnMinimalWidthLeft)
, _thirdColumnWidth(st::columnMinimalWidthThird)
, _sideShadow(this)
@@ -370,8 +371,6 @@ MainWidget::MainWidget(
cSetOtherOnline(0);
_history->start();
-
- Core::App().checkStartUrl();
}
MainWidget::~MainWidget() = default;
@@ -621,6 +620,8 @@ void MainWidget::clearHider(not_null instance) {
return;
}
_hider.release();
+ controller()->setSelectingPeer(false);
+
if (Adaptive::OneColumn()) {
if (_mainSection || (_history->peer() && _history->peer()->id)) {
auto animationParams = ([=] {
@@ -646,6 +647,8 @@ void MainWidget::hiderLayer(base::unique_qptr hider) {
}
_hider = std::move(hider);
+ controller()->setSelectingPeer(true);
+
_hider->setParent(this);
_hider->hidden(
@@ -1274,7 +1277,6 @@ void MainWidget::scheduleViewIncrement(HistoryItem *item) {
}
void MainWidget::viewsIncrement() {
- const auto api = &session().api();
for (auto i = _viewsToIncrement.begin(); i != _viewsToIncrement.cend();) {
if (_viewsIncrementRequests.contains(i->first)) {
++i;
@@ -1286,7 +1288,7 @@ void MainWidget::viewsIncrement() {
for (const auto msgId : i->second) {
ids.push_back(MTP_int(msgId));
}
- const auto requestId = api->request(MTPmessages_GetMessagesViews(
+ const auto requestId = _api.request(MTPmessages_GetMessagesViews(
i->first->input,
MTP_vector(ids),
MTP_bool(true)
@@ -1417,6 +1419,7 @@ void MainWidget::ui_showPeerHistory(
if (_hider) {
_hider->startHide();
_hider.release();
+ controller()->setSelectingPeer(false);
}
auto animatedShow = [&] {
@@ -2648,7 +2651,7 @@ void MainWidget::openPeerByName(
});
}
} else {
- session().api().request(MTPcontacts_ResolveUsername(
+ _api.request(MTPcontacts_ResolveUsername(
MTP_string(username)
)).done([=](const MTPcontacts_ResolvedPeer &result) {
usernameResolveDone(result, msgId, startToken);
diff --git a/Telegram/SourceFiles/mainwidget.h b/Telegram/SourceFiles/mainwidget.h
index 4a1e5fc67..6dbe28af4 100644
--- a/Telegram/SourceFiles/mainwidget.h
+++ b/Telegram/SourceFiles/mainwidget.h
@@ -12,6 +12,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "ui/rp_widget.h"
#include "ui/effects/animations.h"
#include "media/player/media_player_float.h"
+#include "mtproto/sender.h"
#include "data/data_pts_waiter.h"
class RPCError;
@@ -355,6 +356,7 @@ private:
void handleHistoryBack();
const not_null _controller;
+ MTP::Sender _api;
Ui::Animations::Simple _a_show;
bool _showBack = false;
diff --git a/Telegram/SourceFiles/media/player/media_player_volume_controller.cpp b/Telegram/SourceFiles/media/player/media_player_volume_controller.cpp
index 135453ba5..d21a1fbdc 100644
--- a/Telegram/SourceFiles/media/player/media_player_volume_controller.cpp
+++ b/Telegram/SourceFiles/media/player/media_player_volume_controller.cpp
@@ -39,7 +39,7 @@ VolumeController::VolumeController(
Core::App().settings().setRememberedSongVolume(volume);
}
applyVolumeChange(volume);
- controller->session().saveSettingsDelayed();
+ Core::App().saveSettingsDelayed();
});
Core::App().settings().songVolumeChanges(
) | rpl::start_with_next([=](float64 volume) {
diff --git a/Telegram/SourceFiles/media/player/media_player_widget.cpp b/Telegram/SourceFiles/media/player/media_player_widget.cpp
index 0bc26ebf4..f7fa56b8b 100644
--- a/Telegram/SourceFiles/media/player/media_player_widget.cpp
+++ b/Telegram/SourceFiles/media/player/media_player_widget.cpp
@@ -132,6 +132,7 @@ Widget::Widget(QWidget *parent, not_null session)
? 0.
: Core::App().settings().rememberedSongVolume();
Core::App().settings().setSongVolume(volume);
+ Core::App().saveSettingsDelayed();
mixer()->setSongVolume(volume);
});
Core::App().settings().songVolumeChanges(
diff --git a/Telegram/SourceFiles/media/view/media_view_overlay_widget.cpp b/Telegram/SourceFiles/media/view/media_view_overlay_widget.cpp
index 00d560807..2911c5ca3 100644
--- a/Telegram/SourceFiles/media/view/media_view_overlay_widget.cpp
+++ b/Telegram/SourceFiles/media/view/media_view_overlay_widget.cpp
@@ -2655,10 +2655,8 @@ void OverlayWidget::playbackControlsSeekFinished(crl::time position) {
void OverlayWidget::playbackControlsVolumeChanged(float64 volume) {
Core::App().settings().setVideoVolume(volume);
+ Core::App().saveSettingsDelayed();
updateMixerVideoVolume();
- if (_document) {
- _document->session().saveSettingsDelayed();
- }
}
float64 OverlayWidget::playbackControlsCurrentVolume() {
diff --git a/Telegram/SourceFiles/platform/linux/linux_libs.cpp b/Telegram/SourceFiles/platform/linux/linux_libs.cpp
index e0706f293..0d6a5bf1f 100644
--- a/Telegram/SourceFiles/platform/linux/linux_libs.cpp
+++ b/Telegram/SourceFiles/platform/linux/linux_libs.cpp
@@ -253,11 +253,10 @@ void start() {
// change the icon theme only if it isn't already set by a platformtheme plugin
// if QT_QPA_PLATFORMTHEME=(gtk2|gtk3), then force-apply the icon theme
- if ((((QIcon::themeName() == qstr("hicolor") // QGenericUnixTheme
+ if (((QIcon::themeName() == qstr("hicolor") // QGenericUnixTheme
&& QIcon::fallbackThemeName() == qstr("hicolor"))
|| (QIcon::themeName() == qstr("Adwaita") // QGnomeTheme
&& QIcon::fallbackThemeName() == qstr("gnome")))
- && DesktopEnvironment::IsGtkBased())
|| IsGtkIntegrationForced()) {
DEBUG_LOG(("Set GTK icon theme"));
QIcon::setThemeName(gtkSetting("gtk-icon-theme-name"));
diff --git a/Telegram/SourceFiles/platform/linux/notifications_manager_linux.cpp b/Telegram/SourceFiles/platform/linux/notifications_manager_linux.cpp
index cf12821ce..62463eb7a 100644
--- a/Telegram/SourceFiles/platform/linux/notifications_manager_linux.cpp
+++ b/Telegram/SourceFiles/platform/linux/notifications_manager_linux.cpp
@@ -582,7 +582,9 @@ void Manager::Private::showNotification(
const QString &msg,
bool hideNameAndPhoto,
bool hideReplyButton) {
- if (!Supported()) return;
+ if (!Supported()) {
+ return;
+ }
const auto key = FullPeer{
.sessionId = peer->session().uniqueId(),
@@ -630,7 +632,9 @@ void Manager::Private::showNotification(
}
void Manager::Private::clearAll() {
- if (!Supported()) return;
+ if (!Supported()) {
+ return;
+ }
for (const auto &[key, notifications] : base::take(_notifications)) {
for (const auto &[msgId, notification] : notifications) {
@@ -640,7 +644,9 @@ void Manager::Private::clearAll() {
}
void Manager::Private::clearFromHistory(not_null history) {
- if (!Supported()) return;
+ if (!Supported()) {
+ return;
+ }
const auto key = FullPeer{
.sessionId = history->session().uniqueId(),
@@ -658,23 +664,29 @@ void Manager::Private::clearFromHistory(not_null history) {
}
void Manager::Private::clearFromSession(not_null session) {
- if (!Supported()) return;
+ if (!Supported()) {
+ return;
+ }
const auto sessionId = session->uniqueId();
for (auto i = _notifications.begin(); i != _notifications.end();) {
- if (i->first.sessionId == sessionId) {
- const auto temp = base::take(i->second);
- i = _notifications.erase(i);
+ if (i->first.sessionId != sessionId) {
+ ++i;
+ continue;
+ }
+ const auto temp = base::take(i->second);
+ i = _notifications.erase(i);
- for (const auto &[msgId, notification] : temp) {
- notification->close();
- }
+ for (const auto &[msgId, notification] : temp) {
+ notification->close();
}
}
}
void Manager::Private::clearNotification(NotificationId id) {
- if (!Supported()) return;
+ if (!Supported()) {
+ return;
+ }
auto i = _notifications.find(id.full);
if (i != _notifications.cend()) {
diff --git a/Telegram/SourceFiles/platform/linux/specific_linux.cpp b/Telegram/SourceFiles/platform/linux/specific_linux.cpp
index a3a644158..44ee92c00 100644
--- a/Telegram/SourceFiles/platform/linux/specific_linux.cpp
+++ b/Telegram/SourceFiles/platform/linux/specific_linux.cpp
@@ -520,6 +520,7 @@ QString GetIconName() {
}
bool GtkClipboardSupported() {
+#ifndef TDESKTOP_DISABLE_GTK_INTEGRATION
return (Libs::gtk_clipboard_get != nullptr)
&& (Libs::gtk_clipboard_wait_for_contents != nullptr)
&& (Libs::gtk_clipboard_wait_for_image != nullptr)
@@ -531,6 +532,9 @@ bool GtkClipboardSupported() {
&& (Libs::gdk_pixbuf_get_rowstride != nullptr)
&& (Libs::gdk_pixbuf_get_has_alpha != nullptr)
&& (Libs::gdk_atom_intern != nullptr);
+#endif // !TDESKTOP_DISABLE_GTK_INTEGRATION
+
+ return false;
}
QImage GetImageFromClipboard() {
diff --git a/Telegram/SourceFiles/platform/mac/mac_touchbar.h b/Telegram/SourceFiles/platform/mac/mac_touchbar.h
index 931face15..979e054e7 100644
--- a/Telegram/SourceFiles/platform/mac/mac_touchbar.h
+++ b/Telegram/SourceFiles/platform/mac/mac_touchbar.h
@@ -1,10 +1,13 @@
/*
- This file is part of Telegram Desktop,
- the official desktop application for the Telegram messaging service.
+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
- */
+For license and copyright information please follow this link:
+https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
+*/
+#pragma once
+
+#ifndef OS_OSX
#include "platform/platform_specific.h"
#include "media/audio/media_audio.h"
@@ -12,13 +15,15 @@
#import
namespace Platform {
+
enum class TouchBarType {
None,
Main,
AudioPlayer,
AudioPlayerForce,
};
-} // namespace
+
+} // namespace Platform
@interface TouchBar : NSTouchBar
@@ -31,3 +36,5 @@ enum class TouchBarType {
- (void) showInputFieldItem:(bool)show;
@end
+
+#endif // OS_OSX
diff --git a/Telegram/SourceFiles/platform/mac/mac_touchbar.mm b/Telegram/SourceFiles/platform/mac/mac_touchbar.mm
index 6e4bdd317..e9a9c8697 100644
--- a/Telegram/SourceFiles/platform/mac/mac_touchbar.mm
+++ b/Telegram/SourceFiles/platform/mac/mac_touchbar.mm
@@ -1,13 +1,13 @@
/*
- This file is part of Telegram Desktop,
- the official desktop application for the Telegram messaging service.
+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
- */
+For license and copyright information please follow this link:
+https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
+*/
+#include "platform/mac/mac_touchbar.h"
-#import "mac_touchbar.h"
-#import
+#ifndef OS_OSX
#include "api/api_sending.h"
#include "apiwrap.h"
@@ -49,6 +49,8 @@
#include "window/window_controller.h"
#include "window/window_session_controller.h"
+#import
+
namespace {
//https://developer.apple.com/design/human-interface-guidelines/macos/touch-bar/touch-bar-icons-and-images/
constexpr auto kIdealIconSize = 36;
@@ -1905,3 +1907,5 @@ void AppendEmojiPacks(
}
@end // @implementation TouchBar
+
+#endif // OS_OSX
diff --git a/Telegram/SourceFiles/platform/mac/main_window_mac.mm b/Telegram/SourceFiles/platform/mac/main_window_mac.mm
index f9828dc90..43ec78a07 100644
--- a/Telegram/SourceFiles/platform/mac/main_window_mac.mm
+++ b/Telegram/SourceFiles/platform/mac/main_window_mac.mm
@@ -144,9 +144,9 @@ public:
void didExitFullScreen();
bool clipboardHasText();
-
+#ifndef OS_OSX
TouchBar *_touchBar = nil;
-
+#endif // OS_OSX
~Private();
private:
@@ -197,7 +197,9 @@ private:
}
- (void) darkModeChanged:(NSNotification *)aNotification {
- Core::App().domain().notifyUnreadBadgeChanged();
+ Core::Sandbox::Instance().customEnterFromEventLoop([&] {
+ Core::App().domain().notifyUnreadBadgeChanged();
+ });
}
- (void) screenIsLocked:(NSNotification *)aNotification {
@@ -486,6 +488,7 @@ MainWindow::MainWindow(not_null controller)
}
void MainWindow::initTouchBar() {
+#ifndef OS_OSX
if (!IsMac10_13OrGreater()) {
return;
}
@@ -513,14 +516,17 @@ void MainWindow::initTouchBar() {
destroyCurrentTouchBar();
}
}, lifetime());
+#endif // OS_OSX
}
void MainWindow::destroyCurrentTouchBar() {
+#ifndef OS_OSX
if (_private->_touchBar) {
[_private->_touchBar setTouchBar:Platform::TouchBarType::None];
[_private->_touchBar release];
}
_private->_touchBar = nil;
+#endif // OS_OSX
}
void MainWindow::closeWithoutDestroy() {
@@ -844,9 +850,13 @@ void MainWindow::updateGlobalMenuHook() {
canCopy = list->canCopySelected();
canDelete = list->canDeleteSelected();
}
+
+#ifndef OS_OSX
if (_private->_touchBar) {
[_private->_touchBar showInputFieldItem:showTouchBarItem];
}
+#endif // OS_OSX
+
App::wnd()->updateIsActive();
const auto logged = (sessionController() != nullptr);
const auto inactive = !logged || controller().locked();
diff --git a/Telegram/SourceFiles/platform/win/notifications_manager_win.cpp b/Telegram/SourceFiles/platform/win/notifications_manager_win.cpp
index f5cfdf51d..5fd6c591f 100644
--- a/Telegram/SourceFiles/platform/win/notifications_manager_win.cpp
+++ b/Telegram/SourceFiles/platform/win/notifications_manager_win.cpp
@@ -415,7 +415,9 @@ Manager::Private::~Private() {
}
void Manager::Private::clearAll() {
- if (!_notifier) return;
+ if (!_notifier) {
+ return;
+ }
auto temp = base::take(_notifications);
for (const auto &[key, notifications] : base::take(_notifications)) {
@@ -426,7 +428,9 @@ void Manager::Private::clearAll() {
}
void Manager::Private::clearFromHistory(not_null history) {
- if (!_notifier) return;
+ if (!_notifier) {
+ return;
+ }
auto i = _notifications.find(FullPeer{
.sessionId = history->session().uniqueId(),
@@ -443,17 +447,21 @@ void Manager::Private::clearFromHistory(not_null history) {
}
void Manager::Private::clearFromSession(not_null session) {
- if (!_notifier) return;
+ if (!_notifier) {
+ return;
+ }
const auto sessionId = session->uniqueId();
for (auto i = _notifications.begin(); i != _notifications.end();) {
- if (i->first.sessionId == sessionId) {
- const auto temp = base::take(i->second);
- _notifications.erase(i);
+ if (i->first.sessionId != sessionId) {
+ ++i;
+ continue;
+ }
+ const auto temp = base::take(i->second);
+ _notifications.erase(i);
- for (const auto &[msgId, notification] : temp) {
- _notifier->Hide(notification.p.Get());
- }
+ for (const auto &[msgId, notification] : temp) {
+ _notifier->Hide(notification.p.Get());
}
}
}
diff --git a/Telegram/SourceFiles/settings/settings_calls.cpp b/Telegram/SourceFiles/settings/settings_calls.cpp
index cc8872050..b4b01ec57 100644
--- a/Telegram/SourceFiles/settings/settings_calls.cpp
+++ b/Telegram/SourceFiles/settings/settings_calls.cpp
@@ -52,7 +52,7 @@ Calls::Calls(
Calls::~Calls() {
if (_needWriteSettings) {
- _controller->session().saveSettingsDelayed();
+ Core::App().saveSettingsDelayed();
}
}
@@ -134,7 +134,7 @@ void Calls::setupContent() {
: "default";
Core::App().settings().setCallOutputDeviceID(
QString::fromStdString(deviceId));
- _controller->session().saveSettingsDelayed();
+ Core::App().saveSettingsDelayed();
if (const auto call = Core::App().calls().currentCall()) {
call->setCurrentAudioDevice(false, deviceId);
}
@@ -210,7 +210,7 @@ void Calls::setupContent() {
: "default";
Core::App().settings().setCallInputDeviceID(
QString::fromStdString(deviceId));
- _controller->session().saveSettingsDelayed();
+ Core::App().saveSettingsDelayed();
if (_micTester) {
stopTestingMicrophone();
}
diff --git a/Telegram/SourceFiles/settings/settings_common.cpp b/Telegram/SourceFiles/settings/settings_common.cpp
index 78da4381a..543b3fb02 100644
--- a/Telegram/SourceFiles/settings/settings_common.cpp
+++ b/Telegram/SourceFiles/settings/settings_common.cpp
@@ -16,6 +16,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "settings/settings_folders.h"
#include "settings/settings_calls.h"
#include "kotato/settings_menu.h"
+#include "core/application.h"
#include "ui/wrap/padding_wrap.h"
#include "ui/wrap/vertical_layout.h"
#include "ui/widgets/labels.h"
@@ -30,6 +31,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "mainwindow.h"
#include "app.h"
#include "main/main_session.h"
+#include "main/main_domain.h"
#include "styles/style_layers.h"
#include "styles/style_settings.h"
@@ -200,6 +202,12 @@ void FillMenu(
tr::lng_settings_bg_theme_create(tr::now),
[=] { window->show(Box(Window::Theme::CreateBox, window)); });
} else {
+ const auto &list = Core::App().domain().accounts();
+ if (list.size() < ::Main::Domain::kMaxAccounts) {
+ addAction(tr::lng_menu_add_account(tr::now), [=] {
+ Core::App().domain().addActivated(MTP::Environment{});
+ });
+ }
const auto customSettingsFile = cWorkingDir() + "tdata/kotato-settings-custom.json";
if (type != Type::Kotato && !controller->session().supportMode()) {
addAction(
diff --git a/Telegram/SourceFiles/settings/settings_notifications.cpp b/Telegram/SourceFiles/settings/settings_notifications.cpp
index da8fd0a2b..2dd8fa158 100644
--- a/Telegram/SourceFiles/settings/settings_notifications.cpp
+++ b/Telegram/SourceFiles/settings/settings_notifications.cpp
@@ -22,6 +22,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "mainwindow.h"
#include "core/application.h"
#include "main/main_session.h"
+#include "main/main_account.h"
#include "main/main_domain.h"
#include "apiwrap.h"
#include "facades.h"
@@ -540,9 +541,49 @@ void SetupAdvancedNotifications(
AddSkip(container, st::settingsCheckboxesSkip);
}
+void SetupMultiAccountNotifications(
+ not_null controller,
+ not_null container) {
+ if (Core::App().domain().accounts().size() < 2) {
+ return;
+ }
+ AddSubsectionTitle(container, tr::lng_settings_show_from());
+
+ const auto fromAll = container->add(
+ object_ptr(
+ container,
+ tr::lng_settings_notify_all(tr::now),
+ Core::App().settings().notifyFromAll(),
+ st::settingsCheckbox),
+ st::settingsCheckboxPadding);
+ fromAll->checkedChanges(
+ ) | rpl::filter([](bool checked) {
+ return (checked != Core::App().settings().notifyFromAll());
+ }) | rpl::start_with_next([=](bool checked) {
+ Core::App().settings().setNotifyFromAll(checked);
+ Core::App().saveSettingsDelayed();
+ if (!checked) {
+ auto ¬ifications = Core::App().notifications();
+ const auto &list = Core::App().domain().accounts();
+ for (const auto &[index, account] : list) {
+ if (account.get() == &Core::App().domain().active()) {
+ continue;
+ } else if (const auto session = account->maybeSession()) {
+ notifications.clearFromSession(session);
+ }
+ }
+ }
+ }, fromAll->lifetime());
+
+ AddSkip(container);
+ AddDividerText(container, tr::lng_settings_notify_all_about());
+}
+
void SetupNotificationsContent(
not_null controller,
not_null container) {
+ SetupMultiAccountNotifications(controller, container);
+
AddSubsectionTitle(container, tr::lng_settings_notify_title());
const auto session = &controller->session();
diff --git a/Telegram/SourceFiles/storage/serialize_peer.cpp b/Telegram/SourceFiles/storage/serialize_peer.cpp
index e888b7cac..4e8b896bf 100644
--- a/Telegram/SourceFiles/storage/serialize_peer.cpp
+++ b/Telegram/SourceFiles/storage/serialize_peer.cpp
@@ -204,8 +204,9 @@ PeerData *readPeer(
const auto loaded = (peerId == selfId)
? session->user().get()
: session->data().peerLoaded(peerId);
+ const auto apply = !loaded || (loaded->loadedStatus != PeerData::FullLoaded);
const auto result = loaded ? loaded : session->data().peer(peerId).get();
- if (!loaded) {
+ if (apply) {
result->loadedStatus = PeerData::FullLoaded;
}
if (const auto user = result->asUser()) {
@@ -230,7 +231,7 @@ PeerData *readPeer(
? App::formatPhone(phone)
: QString();
- if (!loaded) {
+ if (apply) {
user->setPhone(phone);
user->setName(first, last, pname, username);
@@ -268,7 +269,7 @@ PeerData *readPeer(
if (oldForbidden) {
flags |= quint32(MTPDchat_ClientFlag::f_forbidden);
}
- if (!loaded) {
+ if (apply) {
chat->setName(name);
chat->count = count;
chat->date = date;
@@ -296,7 +297,7 @@ PeerData *readPeer(
if (oldForbidden) {
flags |= quint32(MTPDchannel_ClientFlag::f_forbidden);
}
- if (!loaded) {
+ if (apply) {
channel->setName(name, QString());
channel->access = access;
channel->date = date;
@@ -312,7 +313,7 @@ PeerData *readPeer(
channel->inputChannel = MTP_inputChannel(MTP_int(peerToChannel(channel->id)), MTP_long(access));
}
}
- if (!loaded) {
+ if (apply) {
using LocationType = StorageFileLocation::Type;
const auto location = (userpic->valid() && userpic->isLegacy())
? userpic->convertToModern(
diff --git a/Telegram/SourceFiles/storage/storage_media_prepare.cpp b/Telegram/SourceFiles/storage/storage_media_prepare.cpp
index 48ce0d75d..2a05a4837 100644
--- a/Telegram/SourceFiles/storage/storage_media_prepare.cpp
+++ b/Telegram/SourceFiles/storage/storage_media_prepare.cpp
@@ -286,7 +286,6 @@ std::optional PreparedList::PreparedFileFromFilesDialog(
}
if (!result.remoteContent.isEmpty()) {
-
auto list = Storage::PrepareMediaFromImage(
QImage(),
std::move(result.remoteContent),
@@ -311,7 +310,7 @@ std::optional PreparedList::PreparedFileFromFilesDialog(
}
}
Expects(list.files.size() == 1);
- return std::move(list);
+ return list;
} else if (!result.paths.isEmpty()) {
const auto isSingleFile = (result.paths.size() == 1);
auto temp = Storage::PrepareMediaList(result.paths, previewWidth);
@@ -366,7 +365,7 @@ std::optional PreparedList::PreparedFileFromFilesDialog(
list.allFilesForCompress = temp.allFilesForCompress;
list.files = std::move(filteredFiles);
- return std::move(list);
+ return list;
}
return std::nullopt;
}
diff --git a/Telegram/SourceFiles/window/notifications_manager.cpp b/Telegram/SourceFiles/window/notifications_manager.cpp
index 2f2edc4f9..c950f269c 100644
--- a/Telegram/SourceFiles/window/notifications_manager.cpp
+++ b/Telegram/SourceFiles/window/notifications_manager.cpp
@@ -52,8 +52,6 @@ constexpr auto kSystemAlertDuration = crl::time(0);
System::System()
: _waitTimer([=] { showNext(); })
, _waitForAllGroupedTimer([=] { showGrouped(); }) {
- createManager();
-
subscribe(settingsChanged(), [=](ChangeType type) {
if (type == ChangeType::DesktopEnabled) {
App::wnd()->updateTrayMenu();
@@ -93,6 +91,9 @@ System::SkipState System::skipNotification(
const auto notifyBy = item->specialNotificationPeer();
if (App::quitting() || !history->currentNotification()) {
return { SkipState::Skip };
+ } else if (!Core::App().settings().notifyFromAll()
+ && &history->session().account() != &Core::App().domain().active()) {
+ return { SkipState::Skip };
}
const auto scheduled = item->out() && item->isFromScheduled();
@@ -176,7 +177,9 @@ void System::schedule(not_null item) {
}
void System::clearAll() {
- _manager->clearAll();
+ if (_manager) {
+ _manager->clearAll();
+ }
for (auto i = _whenMaps.cbegin(), e = _whenMaps.cend(); i != e; ++i) {
i->first->clearNotifications();
@@ -188,7 +191,9 @@ void System::clearAll() {
}
void System::clearFromHistory(not_null history) {
- _manager->clearFromHistory(history);
+ if (_manager) {
+ _manager->clearFromHistory(history);
+ }
history->clearNotifications();
_whenMaps.remove(history);
@@ -201,19 +206,21 @@ void System::clearFromHistory(not_null history) {
}
void System::clearFromSession(not_null session) {
- _manager->clearFromSession(session);
+ if (_manager) {
+ _manager->clearFromSession(session);
+ }
for (auto i = _whenMaps.begin(); i != _whenMaps.end();) {
const auto history = i->first;
- if (&history->session() == session) {
- history->clearNotifications();
- i = _whenMaps.erase(i);
- _whenAlerts.remove(history);
- _waiters.remove(history);
- _settingWaiters.remove(history);
- } else {
+ if (&history->session() != session) {
++i;
+ continue;
}
+ history->clearNotifications();
+ i = _whenMaps.erase(i);
+ _whenAlerts.remove(history);
+ _waiters.remove(history);
+ _settingWaiters.remove(history);
}
const auto clearFrom = [&](auto &map) {
for (auto i = map.begin(); i != map.end();) {
@@ -230,17 +237,23 @@ void System::clearFromSession(not_null session) {
}
void System::clearIncomingFromHistory(not_null history) {
- _manager->clearFromHistory(history);
+ if (_manager) {
+ _manager->clearFromHistory(history);
+ }
history->clearIncomingNotifications();
_whenAlerts.remove(history);
}
void System::clearFromItem(not_null item) {
- _manager->clearFromItem(item);
+ if (_manager) {
+ _manager->clearFromItem(item);
+ }
}
void System::clearAllFast() {
- _manager->clearAllFast();
+ if (_manager) {
+ _manager->clearAllFast();
+ }
_whenMaps.clear();
_whenAlerts.clear();
@@ -295,6 +308,8 @@ void System::checkDelayed() {
}
void System::showGrouped() {
+ Expects(_manager != nullptr);
+
if (const auto session = findSession(_lastHistorySessionId)) {
if (const auto lastItem = session->data().message(_lastHistoryItemId)) {
_waitForAllGroupedTimer.cancel();
@@ -307,7 +322,11 @@ void System::showGrouped() {
}
void System::showNext() {
- if (App::quitting()) return;
+ Expects(_manager != nullptr);
+
+ if (App::quitting()) {
+ return;
+ }
const auto isSameGroup = [=](HistoryItem *item) {
if (!_lastHistorySessionId || !_lastHistoryItemId || !item) {
@@ -538,7 +557,9 @@ void System::ensureSoundCreated() {
}
void System::updateAll() {
- _manager->updateAll();
+ if (_manager) {
+ _manager->updateAll();
+ }
}
Manager::DisplayOptions Manager::GetNotificationOptions(HistoryItem *item) {
@@ -561,7 +582,17 @@ Manager::DisplayOptions Manager::GetNotificationOptions(HistoryItem *item) {
QString Manager::addTargetAccountName(
const QString &title,
not_null session) {
- return (Core::App().domain().accounts().size() > 1)
+ const auto add = [&] {
+ for (const auto &[index, account] : Core::App().domain().accounts()) {
+ if (const auto other = account->maybeSession()) {
+ if (other != session) {
+ return true;
+ }
+ }
+ }
+ return false;
+ }();
+ return add
? (title
+ accountNameSeparator()
+ (session->user()->username.isEmpty()
diff --git a/Telegram/SourceFiles/window/notifications_manager_default.cpp b/Telegram/SourceFiles/window/notifications_manager_default.cpp
index 6091fbb3f..3356a7bf5 100644
--- a/Telegram/SourceFiles/window/notifications_manager_default.cpp
+++ b/Telegram/SourceFiles/window/notifications_manager_default.cpp
@@ -192,7 +192,7 @@ void Manager::showNextFromQueue() {
return;
}
int count = Core::App().settings().notificationsCount();
- for_const (auto ¬ification, _notifications) {
+ for (const auto ¬ification : _notifications) {
if (notification->isUnlinked()) continue;
--count;
}
diff --git a/Telegram/SourceFiles/window/window_controller.cpp b/Telegram/SourceFiles/window/window_controller.cpp
index 6a30f7be8..586868027 100644
--- a/Telegram/SourceFiles/window/window_controller.cpp
+++ b/Telegram/SourceFiles/window/window_controller.cpp
@@ -85,9 +85,6 @@ void Controller::showAccount(not_null account) {
setupIntro();
_widget.updateGlobalMenu();
}
- if (was) {
- was->session().updates().updateOnline();
- }
}, _accountLifetime);
}
diff --git a/Telegram/SourceFiles/window/window_main_menu.cpp b/Telegram/SourceFiles/window/window_main_menu.cpp
index 8f01447b7..4858d8767 100644
--- a/Telegram/SourceFiles/window/window_main_menu.cpp
+++ b/Telegram/SourceFiles/window/window_main_menu.cpp
@@ -30,6 +30,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "settings/settings_common.h"
#include "base/qt_signal_producer.h"
#include "boxes/about_box.h"
+#include "boxes/confirm_box.h"
#include "boxes/peer_list_controllers.h"
#include "calls/calls_box_controller.h"
#include "lang/lang_keys.h"
@@ -53,6 +54,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "styles/style_dialogs.h"
#include "styles/style_settings.h"
#include "styles/style_boxes.h"
+#include "styles/style_layers.h"
#include
#include
@@ -100,13 +102,15 @@ public:
private:
void paintEvent(QPaintEvent *e) override;
+ void contextMenuEvent(QContextMenuEvent *e) override;
void paintUserpic(Painter &p);
- const not_null _account;
+ const not_null _session;
const style::Menu &_st;
std::shared_ptr _userpicView;
InMemoryKey _userpicKey = {};
QImage _userpicCache;
+ base::unique_qptr _menu;
Dialogs::Layout::UnreadBadgeStyle _unreadSt;
int _unreadBadge = 0;
@@ -154,7 +158,7 @@ MainMenu::AccountButton::AccountButton(
QWidget *parent,
not_null account)
: RippleButton(parent, st::defaultRippleAnimation)
-, _account(account)
+, _session(&account->session())
, _st(st::mainMenu){
const auto height = _st.itemPadding.top()
+ _st.itemStyle.font->height
@@ -168,33 +172,27 @@ MainMenu::AccountButton::AccountButton(
}
});
- _account->sessionValue(
- ) | rpl::filter([=](Main::Session *session) {
- return (session != nullptr);
- }) | rpl::start_with_next([=](not_null session) {
- rpl::single(
- rpl::empty_value()
- ) | rpl::then(
- session->data().unreadBadgeChanges()
- ) | rpl::start_with_next([=] {
- _unreadBadge = session->data().unreadBadge();
- _unreadBadgeMuted = session->data().unreadBadgeMuted();
- update();
- }, lifetime());
+ rpl::single(
+ rpl::empty_value()
+ ) | rpl::then(
+ _session->data().unreadBadgeChanges()
+ ) | rpl::start_with_next([=] {
+ _unreadBadge = _session->data().unreadBadge();
+ _unreadBadgeMuted = _session->data().unreadBadgeMuted();
+ update();
}, lifetime());
}
void MainMenu::AccountButton::paintUserpic(Painter &p) {
- Expects(_account->sessionExists());
-
const auto size = st::mainMenuAccountSize;
const auto iconSize = height() - 2 * _st.itemIconPosition.y();
const auto shift = (size - iconSize) / 2;
const auto x = _st.itemIconPosition.x() - shift;
const auto y = (height() - size) / 2;
- const auto check = (_account == &Core::App().domain().active());
- const auto user = _account->session().user();
+ const auto check = (&_session->account()
+ == &Core::App().domain().active());
+ const auto user = _session->user();
if (!check) {
user->paintUserpicLeft(p, _userpicView, x, y, width(), size);
return;
@@ -235,8 +233,6 @@ void MainMenu::AccountButton::paintUserpic(Painter &p) {
}
void MainMenu::AccountButton::paintEvent(QPaintEvent *e) {
- Expects(_account->sessionExists());
-
auto p = Painter(this);
const auto over = isOver();
p.fillRect(rect(), over ? _st.itemBgOver : _st.itemBg);
@@ -245,7 +241,8 @@ void MainMenu::AccountButton::paintEvent(QPaintEvent *e) {
paintUserpic(p);
auto available = width() - _st.itemPadding.left();
- if (_unreadBadge && _account != &Core::App().activeAccount()) {
+ if (_unreadBadge
+ && (&_session->account() != &Core::App().activeAccount())) {
_unreadSt.muted = _unreadBadgeMuted;
const auto string = (_unreadBadge > 99)
? "99+"
@@ -268,13 +265,39 @@ void MainMenu::AccountButton::paintEvent(QPaintEvent *e) {
}
p.setPen(over ? _st.itemFgOver : _st.itemFg);
- _account->session().user()->nameText().drawElided(
+ _session->user()->nameText().drawElided(
p,
_st.itemPadding.left(),
_st.itemPadding.top(),
available);
}
+void MainMenu::AccountButton::contextMenuEvent(QContextMenuEvent *e) {
+ if (&_session->account() == &Core::App().activeAccount() || _menu) {
+ return;
+ }
+ _menu = base::make_unique_q(this);
+ _menu->addAction(tr::lng_menu_activate(tr::now), crl::guard(this, [=] {
+ Core::App().domain().activate(&_session->account());
+ }));
+ _menu->addAction(tr::lng_settings_logout(tr::now), crl::guard(this, [=] {
+ const auto session = _session;
+ const auto box = std::make_shared>();
+ const auto callback = [=] {
+ if (*box) {
+ (*box)->closeBox();
+ }
+ Core::App().logout(&session->account());
+ };
+ *box = Ui::show(Box(
+ tr::lng_sure_logout(tr::now),
+ tr::lng_settings_logout(tr::now),
+ st::attentionBoxButton,
+ crl::guard(session, callback)));
+ }));
+ _menu->popup(QCursor::pos());
+}
+
MainMenu::ToggleAccountsButton::ToggleAccountsButton(QWidget *parent)
: AbstractButton(parent) {
rpl::single(
@@ -642,14 +665,17 @@ void MainMenu::setupCloudButton() {
}
void MainMenu::setupUserpicButton() {
- _userpicButton->setClickedCallback([=] {
- _controller->content()->choosePeer(
- _controller->session().userPeerId(),
- ShowAtUnreadMsgId);
- });
+ _userpicButton->setClickedCallback([=] { toggleAccounts(); });
_userpicButton->show();
}
+void MainMenu::toggleAccounts() {
+ auto &settings = Core::App().settings();
+ const auto shown = !settings.mainMenuAccountsShown();
+ settings.setMainMenuAccountsShown(shown);
+ Core::App().saveSettingsDelayed();
+}
+
void MainMenu::setupAccounts() {
const auto inner = _accounts->entity();
@@ -688,7 +714,6 @@ void MainMenu::setupAccounts() {
rebuildAccounts();
}, lifetime());
- _accounts->toggleOn(Core::App().settings().mainMenuAccountsShownValue());
_accounts->toggleOn(Core::App().settings().mainMenuAccountsShownValue());
_accounts->finishAnimating();
@@ -772,18 +797,7 @@ not_null*> MainMenu::setupAddAccount(
}, button->lifetime());
const auto add = [=](MTP::Environment environment) {
- auto &domain = Core::App().domain();
- if (domain.accounts().size() < Main::Domain::kMaxAccounts) {
- domain.activate(domain.add(environment));
- } else {
- for (auto &[index, account] : domain.accounts()) {
- if (!account->sessionExists()
- && account->mtp().environment() == environment) {
- domain.activate(account.get());
- break;
- }
- }
- }
+ Core::App().domain().addActivated(environment);
};
button->setAcceptBoth(true);
@@ -812,12 +826,7 @@ not_null*> MainMenu::setupAddAccount(
void MainMenu::setupAccountsToggle() {
_toggleAccounts->show();
- _toggleAccounts->setClickedCallback([=] {
- auto &settings = Core::App().settings();
- const auto shown = !settings.mainMenuAccountsShown();
- settings.setMainMenuAccountsShown(shown);
- Core::App().saveSettingsDelayed();
- });
+ _toggleAccounts->setClickedCallback([=] { toggleAccounts(); });
}
void MainMenu::parentResized() {
diff --git a/Telegram/SourceFiles/window/window_main_menu.h b/Telegram/SourceFiles/window/window_main_menu.h
index 51e10a9bf..661364ab2 100644
--- a/Telegram/SourceFiles/window/window_main_menu.h
+++ b/Telegram/SourceFiles/window/window_main_menu.h
@@ -68,6 +68,7 @@ private:
void initResetScaleButton();
void refreshMenu();
void refreshBackground();
+ void toggleAccounts();
const not_null _controller;
object_ptr _userpicButton;
diff --git a/Telegram/SourceFiles/window/window_peer_menu.cpp b/Telegram/SourceFiles/window/window_peer_menu.cpp
index f10961699..2adb9669c 100644
--- a/Telegram/SourceFiles/window/window_peer_menu.cpp
+++ b/Telegram/SourceFiles/window/window_peer_menu.cpp
@@ -1245,7 +1245,7 @@ void PeerMenuAddChannelMembers(
return;
}
const auto api = &channel->session().api();
- api->requestChannelMembersForAdd(channel, [=](
+ api->requestChannelMembersForAdd(channel, crl::guard(navigation, [=](
const MTPchannels_ChannelParticipants &result) {
api->parseChannelParticipants(channel, result, [&](
int availableCount,
@@ -1267,7 +1267,7 @@ void PeerMenuAddChannelMembers(
channel,
{ already.begin(), already.end() });
});
- });
+ }));
}
void PeerMenuAddMuteAction(
diff --git a/Telegram/SourceFiles/window/window_session_controller.h b/Telegram/SourceFiles/window/window_session_controller.h
index 04148ba91..4d753d226 100644
--- a/Telegram/SourceFiles/window/window_session_controller.h
+++ b/Telegram/SourceFiles/window/window_session_controller.h
@@ -116,7 +116,7 @@ struct SectionShow {
class SessionController;
-class SessionNavigation {
+class SessionNavigation : public base::has_weak_ptr {
public:
explicit SessionNavigation(not_null session);
@@ -156,10 +156,7 @@ private:
};
-class SessionController
- : public SessionNavigation
- , public base::has_weak_ptr
- , private base::Subscriber {
+class SessionController : public SessionNavigation, private base::Subscriber {
public:
SessionController(
not_null session,
@@ -171,6 +168,15 @@ public:
[[nodiscard]] not_null<::MainWindow*> widget() const;
[[nodiscard]] not_null content() const;
+ // We need access to this from MainWidget::MainWidget, where
+ // we can't call content() yet.
+ void setSelectingPeer(bool selecting) {
+ _selectingPeer = selecting;
+ }
+ [[nodiscard]] bool selectingPeer() const {
+ return _selectingPeer;
+ }
+
[[nodiscard]] auto tabbedSelector() const
-> not_null;
void takeTabbedSelectorOwnershipFrom(not_null parent);
@@ -335,6 +341,7 @@ private:
base::Variable _dialogsListDisplayForced = { false };
std::deque _chatEntryHistory;
int _chatEntryHistoryPosition = -1;
+ bool _selectingPeer = false;
rpl::variable _activeChatsFilter;
diff --git a/Telegram/SourceFiles/window/window_title_qt.cpp b/Telegram/SourceFiles/window/window_title_qt.cpp
index 17edd2368..92dd3d9da 100644
--- a/Telegram/SourceFiles/window/window_title_qt.cpp
+++ b/Telegram/SourceFiles/window/window_title_qt.cpp
@@ -116,6 +116,12 @@ bool TitleWidgetQt::eventFilter(QObject *obj, QEvent *e) {
return startResize(mouseEvent->windowPos().toPoint());
}
}
+ } else if (e->type() == QEvent::Leave) {
+ if (window() == static_cast(obj)) {
+ while (QGuiApplication::overrideCursor()) {
+ QGuiApplication::restoreOverrideCursor();
+ }
+ }
}
return TitleWidget::eventFilter(obj, e);
diff --git a/Telegram/build/version b/Telegram/build/version
index f96758021..71f03d59c 100644
--- a/Telegram/build/version
+++ b/Telegram/build/version
@@ -1,7 +1,7 @@
-AppVersion 2001014
+AppVersion 2001016
AppVersionStrMajor 2.1
-AppVersionStrSmall 2.1.14
-AppVersionStr 2.1.14
+AppVersionStrSmall 2.1.16
+AppVersionStr 2.1.16
BetaChannel 1
AlphaVersion 0
-AppVersionOriginal 2.1.14.beta
+AppVersionOriginal 2.1.16.beta
diff --git a/changelog.txt b/changelog.txt
index 78c284d2b..756f9b0f7 100644
--- a/changelog.txt
+++ b/changelog.txt
@@ -1,3 +1,13 @@
+2.1.16 beta (01.07.20)
+
+- Crash fix.
+
+2.1.15 beta (30.06.20)
+
+- Receive notifications only from the active account in Settings > Notifications.
+- Fix saving chats list width between application relaunches.
+- Multiple crash fixes.
+
2.1.14 beta (29.06.20)
- Support for multiple accounts.