Move stickers state variables to AuthSessionData.

Also allow to click on the selected set when choosing megagroup
sticker set and allow to paste a t.me link to the set there.
This commit is contained in:
John Preston 2017-11-05 21:07:27 +04:00
parent 9a56b2d20f
commit 554eb3a342
31 changed files with 673 additions and 479 deletions

View File

@ -49,11 +49,11 @@ constexpr auto kReloadChannelMembersTimeout = 1000; // 1 second wait before relo
constexpr auto kSaveCloudDraftTimeout = 1000; // save draft to the cloud with 1 sec extra delay constexpr auto kSaveCloudDraftTimeout = 1000; // save draft to the cloud with 1 sec extra delay
constexpr auto kSaveDraftBeforeQuitTimeout = 1500; // give the app 1.5 secs to save drafts to cloud when quitting constexpr auto kSaveDraftBeforeQuitTimeout = 1500; // give the app 1.5 secs to save drafts to cloud when quitting
constexpr auto kSmallDelayMs = 5; constexpr auto kSmallDelayMs = 5;
constexpr auto kStickersUpdateTimeout = 3600000; // update not more than once in an hour
constexpr auto kUnreadMentionsPreloadIfLess = 5; constexpr auto kUnreadMentionsPreloadIfLess = 5;
constexpr auto kUnreadMentionsFirstRequestLimit = 10; constexpr auto kUnreadMentionsFirstRequestLimit = 10;
constexpr auto kUnreadMentionsNextRequestLimit = 100; constexpr auto kUnreadMentionsNextRequestLimit = 100;
constexpr auto kSharedMediaLimit = 100; constexpr auto kSharedMediaLimit = 100;
constexpr auto kReadFeaturedSetsTimeout = TimeMs(1000);
} // namespace } // namespace
@ -61,7 +61,8 @@ ApiWrap::ApiWrap(not_null<AuthSession*> session)
: _session(session) : _session(session)
, _messageDataResolveDelayed([this] { resolveMessageDatas(); }) , _messageDataResolveDelayed([this] { resolveMessageDatas(); })
, _webPagesTimer([this] { resolveWebPages(); }) , _webPagesTimer([this] { resolveWebPages(); })
, _draftsSaveTimer([this] { saveDraftsToCloud(); }) { , _draftsSaveTimer([this] { saveDraftsToCloud(); })
, _featuredSetsReadTimer([this] { readFeaturedSets(); }) {
} }
void ApiWrap::start() { void ApiWrap::start() {
@ -838,7 +839,7 @@ void ApiWrap::saveStickerSets(const Stickers::Order &localOrder, const Stickers:
auto writeInstalled = true, writeRecent = false, writeCloudRecent = false, writeFaved = false, writeArchived = false; auto writeInstalled = true, writeRecent = false, writeCloudRecent = false, writeFaved = false, writeArchived = false;
auto &recent = cGetRecentStickers(); auto &recent = cGetRecentStickers();
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
_stickersOrder = localOrder; _stickersOrder = localOrder;
for_const (auto removedSetId, localRemoved) { for_const (auto removedSetId, localRemoved) {
@ -883,8 +884,8 @@ void ApiWrap::saveStickerSets(const Stickers::Order &localOrder, const Stickers:
_stickerSetDisenableRequests.insert(requestId); _stickerSetDisenableRequests.insert(requestId);
int removeIndex = Global::StickerSetsOrder().indexOf(it->id); int removeIndex = Auth().data().stickerSetsOrder().indexOf(it->id);
if (removeIndex >= 0) Global::RefStickerSetsOrder().removeAt(removeIndex); if (removeIndex >= 0) Auth().data().stickerSetsOrderRef().removeAt(removeIndex);
if (!(it->flags & MTPDstickerSet_ClientFlag::f_featured) && !(it->flags & MTPDstickerSet_ClientFlag::f_special)) { if (!(it->flags & MTPDstickerSet_ClientFlag::f_featured) && !(it->flags & MTPDstickerSet_ClientFlag::f_special)) {
sets.erase(it); sets.erase(it);
} else { } else {
@ -904,7 +905,7 @@ void ApiWrap::saveStickerSets(const Stickers::Order &localOrder, const Stickers:
} }
} }
auto &order(Global::RefStickerSetsOrder()); auto &order = Auth().data().stickerSetsOrderRef();
order.clear(); order.clear();
for_const (auto setId, _stickersOrder) { for_const (auto setId, _stickersOrder) {
auto it = sets.find(setId); auto it = sets.find(setId);
@ -943,9 +944,9 @@ void ApiWrap::saveStickerSets(const Stickers::Order &localOrder, const Stickers:
if (writeArchived) Local::writeArchivedStickers(); if (writeArchived) Local::writeArchivedStickers();
if (writeCloudRecent) Local::writeRecentStickers(); if (writeCloudRecent) Local::writeRecentStickers();
if (writeFaved) Local::writeFavedStickers(); if (writeFaved) Local::writeFavedStickers();
Auth().data().stickersUpdated().notify(true); Auth().data().markStickersUpdated();
if (_stickerSetDisenableRequests.isEmpty()) { if (_stickerSetDisenableRequests.empty()) {
stickersSaveOrder(); stickersSaveOrder();
} else { } else {
requestSendDelayed(); requestSendDelayed();
@ -954,7 +955,7 @@ void ApiWrap::saveStickerSets(const Stickers::Order &localOrder, const Stickers:
void ApiWrap::stickerSetDisenabled(mtpRequestId requestId) { void ApiWrap::stickerSetDisenabled(mtpRequestId requestId) {
_stickerSetDisenableRequests.remove(requestId); _stickerSetDisenableRequests.remove(requestId);
if (_stickerSetDisenableRequests.isEmpty()) { if (_stickerSetDisenableRequests.empty()) {
stickersSaveOrder(); stickersSaveOrder();
} }
}; };
@ -1465,7 +1466,7 @@ void ApiWrap::stickersSaveOrder() {
_stickersReorderRequestId = 0; _stickersReorderRequestId = 0;
}).fail([this](const RPCError &error) { }).fail([this](const RPCError &error) {
_stickersReorderRequestId = 0; _stickersReorderRequestId = 0;
Global::SetLastStickersUpdate(0); Auth().data().setLastStickersUpdate(0);
updateStickers(); updateStickers();
}).send(); }).send();
} }
@ -1484,18 +1485,16 @@ void ApiWrap::setGroupStickerSet(not_null<ChannelData*> megagroup, const MTPInpu
Expects(megagroup->mgInfo != nullptr); Expects(megagroup->mgInfo != nullptr);
megagroup->mgInfo->stickerSet = set; megagroup->mgInfo->stickerSet = set;
request(MTPchannels_SetStickers(megagroup->inputChannel, set)).send(); request(MTPchannels_SetStickers(megagroup->inputChannel, set)).send();
Auth().data().stickersUpdated().notify(true); Auth().data().markStickersUpdated();
} }
void ApiWrap::requestStickers(TimeId now) { void ApiWrap::requestStickers(TimeId now) {
if (Global::LastStickersUpdate() != 0 && now < Global::LastStickersUpdate() + kStickersUpdateTimeout) { if (!Auth().data().stickersUpdateNeeded(now)
return; || _stickersUpdateRequest) {
}
if (_stickersUpdateRequest) {
return; return;
} }
auto onDone = [this](const MTPmessages_AllStickers &result) { auto onDone = [this](const MTPmessages_AllStickers &result) {
Global::SetLastStickersUpdate(getms(true)); Auth().data().setLastStickersUpdate(getms(true));
_stickersUpdateRequest = 0; _stickersUpdateRequest = 0;
switch (result.type()) { switch (result.type()) {
@ -1514,14 +1513,12 @@ void ApiWrap::requestStickers(TimeId now) {
} }
void ApiWrap::requestRecentStickers(TimeId now) { void ApiWrap::requestRecentStickers(TimeId now) {
if (Global::LastRecentStickersUpdate() != 0 && now < Global::LastRecentStickersUpdate() + kStickersUpdateTimeout) { if (!Auth().data().recentStickersUpdateNeeded(now)
return; || _recentStickersUpdateRequest) {
}
if (_recentStickersUpdateRequest) {
return; return;
} }
auto onDone = [this](const MTPmessages_RecentStickers &result) { auto onDone = [this](const MTPmessages_RecentStickers &result) {
Global::SetLastRecentStickersUpdate(getms(true)); Auth().data().setLastRecentStickersUpdate(getms(true));
_recentStickersUpdateRequest = 0; _recentStickersUpdateRequest = 0;
switch (result.type()) { switch (result.type()) {
@ -1540,14 +1537,12 @@ void ApiWrap::requestRecentStickers(TimeId now) {
} }
void ApiWrap::requestFavedStickers(TimeId now) { void ApiWrap::requestFavedStickers(TimeId now) {
if (Global::LastFavedStickersUpdate() != 0 && now < Global::LastFavedStickersUpdate() + kStickersUpdateTimeout) { if (!Auth().data().favedStickersUpdateNeeded(now)
return; || _favedStickersUpdateRequest) {
}
if (_favedStickersUpdateRequest) {
return; return;
} }
auto onDone = [this](const MTPmessages_FavedStickers &result) { auto onDone = [this](const MTPmessages_FavedStickers &result) {
Global::SetLastFavedStickersUpdate(getms(true)); Auth().data().setLastFavedStickersUpdate(getms(true));
_favedStickersUpdateRequest = 0; _favedStickersUpdateRequest = 0;
switch (result.type()) { switch (result.type()) {
@ -1566,14 +1561,12 @@ void ApiWrap::requestFavedStickers(TimeId now) {
} }
void ApiWrap::requestFeaturedStickers(TimeId now) { void ApiWrap::requestFeaturedStickers(TimeId now) {
if (Global::LastFeaturedStickersUpdate() != 0 && now < Global::LastFeaturedStickersUpdate() + kStickersUpdateTimeout) { if (!Auth().data().featuredStickersUpdateNeeded(now)
return; || _featuredStickersUpdateRequest) {
}
if (_featuredStickersUpdateRequest) {
return; return;
} }
auto onDone = [this](const MTPmessages_FeaturedStickers &result) { auto onDone = [this](const MTPmessages_FeaturedStickers &result) {
Global::SetLastFeaturedStickersUpdate(getms(true)); Auth().data().setLastFeaturedStickersUpdate(getms(true));
_featuredStickersUpdateRequest = 0; _featuredStickersUpdateRequest = 0;
switch (result.type()) { switch (result.type()) {
@ -1592,14 +1585,12 @@ void ApiWrap::requestFeaturedStickers(TimeId now) {
} }
void ApiWrap::requestSavedGifs(TimeId now) { void ApiWrap::requestSavedGifs(TimeId now) {
if (cLastSavedGifsUpdate() != 0 && now < cLastSavedGifsUpdate() + kStickersUpdateTimeout) { if (!Auth().data().savedGifsUpdateNeeded(now)
return; || _savedGifsUpdateRequest) {
}
if (_savedGifsUpdateRequest) {
return; return;
} }
auto onDone = [this](const MTPmessages_SavedGifs &result) { auto onDone = [this](const MTPmessages_SavedGifs &result) {
cSetLastSavedGifsUpdate(getms(true)); Auth().data().setLastSavedGifsUpdate(getms(true));
_savedGifsUpdateRequest = 0; _savedGifsUpdateRequest = 0;
switch (result.type()) { switch (result.type()) {
@ -1617,6 +1608,42 @@ void ApiWrap::requestSavedGifs(TimeId now) {
}).send(); }).send();
} }
void ApiWrap::readFeaturedSetDelayed(uint64 setId) {
if (!_featuredSetsRead.contains(setId)) {
_featuredSetsRead.insert(setId);
_featuredSetsReadTimer.callOnce(kReadFeaturedSetsTimeout);
}
}
void ApiWrap::readFeaturedSets() {
auto &sets = Auth().data().stickerSetsRef();
auto count = Auth().data().featuredStickerSetsUnreadCount();
QVector<MTPlong> wrappedIds;
wrappedIds.reserve(_featuredSetsRead.size());
for (auto setId : _featuredSetsRead) {
auto it = sets.find(setId);
if (it != sets.cend()) {
it->flags &= ~MTPDstickerSet_ClientFlag::f_unread;
wrappedIds.append(MTP_long(setId));
if (count) {
--count;
}
}
}
_featuredSetsRead.clear();
if (!wrappedIds.empty()) {
auto requestData = MTPmessages_ReadFeaturedStickers(
MTP_vector<MTPlong>(wrappedIds));
request(std::move(requestData)).done([](const MTPBool &result) {
Local::writeFeaturedStickers();
Auth().data().markStickersUpdated();
}).send();
Auth().data().setFeaturedStickerSetsUnreadCount(count);
}
}
void ApiWrap::applyUpdatesNoPtsCheck(const MTPUpdates &updates) { void ApiWrap::applyUpdatesNoPtsCheck(const MTPUpdates &updates) {
switch (updates.type()) { switch (updates.type()) {
case mtpc_updateShortMessage: { case mtpc_updateShortMessage: {

View File

@ -26,6 +26,7 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org
#include "mtproto/sender.h" #include "mtproto/sender.h"
#include "base/flat_map.h" #include "base/flat_map.h"
#include "base/flat_set.h" #include "base/flat_set.h"
#include "chat_helpers/stickers.h"
class AuthSession; class AuthSession;
@ -135,6 +136,7 @@ public:
auto stickerSetInstalled() const { auto stickerSetInstalled() const {
return _stickerSetInstalled.events(); return _stickerSetInstalled.events();
} }
void readFeaturedSetDelayed(uint64 setId);
~ApiWrap(); ~ApiWrap();
@ -177,6 +179,7 @@ private:
void requestFavedStickers(TimeId now); void requestFavedStickers(TimeId now);
void requestFeaturedStickers(TimeId now); void requestFeaturedStickers(TimeId now);
void requestSavedGifs(TimeId now); void requestSavedGifs(TimeId now);
void readFeaturedSets();
void cancelEditChatAdmins(not_null<ChatData*> chat); void cancelEditChatAdmins(not_null<ChatData*> chat);
void saveChatAdmins(not_null<ChatData*> chat); void saveChatAdmins(not_null<ChatData*> chat);
@ -229,7 +232,7 @@ private:
QMap<History*, mtpRequestId> _draftsSaveRequestIds; QMap<History*, mtpRequestId> _draftsSaveRequestIds;
base::Timer _draftsSaveTimer; base::Timer _draftsSaveTimer;
OrderedSet<mtpRequestId> _stickerSetDisenableRequests; base::flat_set<mtpRequestId> _stickerSetDisenableRequests;
Stickers::Order _stickersOrder; Stickers::Order _stickersOrder;
mtpRequestId _stickersReorderRequestId = 0; mtpRequestId _stickersReorderRequestId = 0;
mtpRequestId _stickersClearRecentRequestId = 0; mtpRequestId _stickersClearRecentRequestId = 0;
@ -240,6 +243,9 @@ private:
mtpRequestId _featuredStickersUpdateRequest = 0; mtpRequestId _featuredStickersUpdateRequest = 0;
mtpRequestId _savedGifsUpdateRequest = 0; mtpRequestId _savedGifsUpdateRequest = 0;
base::Timer _featuredSetsReadTimer;
base::flat_set<uint64> _featuredSetsRead;
QMap<mtpTypeId, mtpRequestId> _privacySaveRequests; QMap<mtpTypeId, mtpRequestId> _privacySaveRequests;
mtpRequestId _contactsStatusesRequestId = 0; mtpRequestId _contactsStatusesRequestId = 0;

View File

@ -1079,7 +1079,7 @@ namespace {
} }
void addSavedGif(DocumentData *doc) { void addSavedGif(DocumentData *doc) {
SavedGifs &saved(cRefSavedGifs()); auto &saved = Auth().data().savedGifsRef();
int32 index = saved.indexOf(doc); int32 index = saved.indexOf(doc);
if (index) { if (index) {
if (index > 0) saved.remove(index); if (index > 0) saved.remove(index);
@ -1087,8 +1087,8 @@ namespace {
if (saved.size() > Global::SavedGifsLimit()) saved.pop_back(); if (saved.size() > Global::SavedGifsLimit()) saved.pop_back();
Local::writeSavedGifs(); Local::writeSavedGifs();
Auth().data().savedGifsUpdated().notify(); Auth().data().markSavedGifsUpdated();
cSetLastSavedGifsUpdate(0); Auth().data().setLastSavedGifsUpdate(0);
Auth().api().updateStickers(); Auth().api().updateStickers();
} }
} }
@ -1636,7 +1636,7 @@ namespace {
} }
} }
if (cSavedGifs().indexOf(convert) >= 0) { // id changed if (Auth().data().savedGifs().indexOf(convert) >= 0) { // id changed
Local::writeSavedGifs(); Local::writeSavedGifs();
} }
} }
@ -1682,8 +1682,8 @@ namespace {
} }
if (versionChanged) { if (versionChanged) {
if (result->sticker() && result->sticker()->set.type() == mtpc_inputStickerSetID) { if (result->sticker() && result->sticker()->set.type() == mtpc_inputStickerSetID) {
auto it = Global::StickerSets().constFind(result->sticker()->set.c_inputStickerSetID().vid.v); auto it = Auth().data().stickerSets().constFind(result->sticker()->set.c_inputStickerSetID().vid.v);
if (it != Global::StickerSets().cend()) { if (it != Auth().data().stickerSets().cend()) {
if (it->id == Stickers::CloudRecentSetId) { if (it->id == Stickers::CloudRecentSetId) {
Local::writeRecentStickers(); Local::writeRecentStickers();
} else if (it->id == Stickers::FavedSetId) { } else if (it->id == Stickers::FavedSetId) {
@ -2035,19 +2035,6 @@ namespace {
Auth().api().clearWebPageRequests(); Auth().api().clearWebPageRequests();
} }
cSetRecentStickers(RecentStickerPack()); cSetRecentStickers(RecentStickerPack());
Global::SetStickerSets(Stickers::Sets());
Global::SetStickerSetsOrder(Stickers::Order());
Global::SetLastStickersUpdate(0);
Global::SetLastRecentStickersUpdate(0);
Global::SetFeaturedStickerSetsOrder(Stickers::Order());
if (Global::FeaturedStickerSetsUnreadCount() != 0) {
Global::SetFeaturedStickerSetsUnreadCount(0);
Global::RefFeaturedStickerSetsUnreadCountChanged().notify();
}
Global::SetLastFeaturedStickersUpdate(0);
Global::SetArchivedStickerSetsOrder(Stickers::Order());
cSetSavedGifs(SavedGifs());
cSetLastSavedGifsUpdate(0);
cSetReportSpamStatuses(ReportSpamStatuses()); cSetReportSpamStatuses(ReportSpamStatuses());
cSetAutoDownloadPhoto(0); cSetAutoDownloadPhoto(0);
cSetAutoDownloadAudio(0); cSetAutoDownloadAudio(0);

View File

@ -24,6 +24,7 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org
#include <rpl/filter.h> #include <rpl/filter.h>
#include <rpl/variable.h> #include <rpl/variable.h>
#include "base/timer.h" #include "base/timer.h"
#include "chat_helpers/stickers.h"
namespace Storage { namespace Storage {
class Downloader; class Downloader;
@ -59,12 +60,6 @@ public:
base::Observable<void> &moreChatsLoaded() { base::Observable<void> &moreChatsLoaded() {
return _moreChatsLoaded; return _moreChatsLoaded;
} }
base::Observable<void> &stickersUpdated() {
return _stickersUpdated;
}
base::Observable<void> &savedGifsUpdated() {
return _savedGifsUpdated;
}
base::Observable<void> &pendingHistoryResize() { base::Observable<void> &pendingHistoryResize() {
return _pendingHistoryResize; return _pendingHistoryResize;
} }
@ -230,6 +225,18 @@ public:
return _variables.dialogsWidthRatio.changes(); return _variables.dialogsWidthRatio.changes();
} }
void markStickersUpdated() {
_stickersUpdated.fire({});
}
rpl::producer<> stickersUpdated() const {
return _stickersUpdated.events();
}
void markSavedGifsUpdated() {
_savedGifsUpdated.fire({});
}
rpl::producer<> savedGifsUpdated() const {
return _savedGifsUpdated.events();
}
void setGroupStickersSectionHidden(PeerId peerId) { void setGroupStickersSectionHidden(PeerId peerId) {
_variables.groupStickersSectionHidden.insert(peerId); _variables.groupStickersSectionHidden.insert(peerId);
} }
@ -239,6 +246,75 @@ public:
void removeGroupStickersSectionHidden(PeerId peerId) { void removeGroupStickersSectionHidden(PeerId peerId) {
_variables.groupStickersSectionHidden.remove(peerId); _variables.groupStickersSectionHidden.remove(peerId);
} }
bool stickersUpdateNeeded(TimeMs now) const {
return stickersUpdateNeeded(_lastStickersUpdate, now);
}
void setLastStickersUpdate(TimeMs update) {
_lastStickersUpdate = update;
}
bool recentStickersUpdateNeeded(TimeMs now) const {
return stickersUpdateNeeded(_lastRecentStickersUpdate, now);
}
void setLastRecentStickersUpdate(TimeMs update) {
_lastRecentStickersUpdate = update;
}
bool favedStickersUpdateNeeded(TimeMs now) const {
return stickersUpdateNeeded(_lastFavedStickersUpdate, now);
}
void setLastFavedStickersUpdate(TimeMs update) {
_lastFavedStickersUpdate = update;
}
bool featuredStickersUpdateNeeded(TimeMs now) const {
return stickersUpdateNeeded(_lastFeaturedStickersUpdate, now);
}
void setLastFeaturedStickersUpdate(TimeMs update) {
_lastFeaturedStickersUpdate = update;
}
bool savedGifsUpdateNeeded(TimeMs now) const {
return stickersUpdateNeeded(_lastSavedGifsUpdate, now);
}
void setLastSavedGifsUpdate(TimeMs update) {
_lastSavedGifsUpdate = update;
}
int featuredStickerSetsUnreadCount() const {
return _featuredStickerSetsUnreadCount.current();
}
void setFeaturedStickerSetsUnreadCount(int count) {
_featuredStickerSetsUnreadCount = count;
}
rpl::producer<int> featuredStickerSetsUnreadCountValue() const {
return _featuredStickerSetsUnreadCount.value();
}
const Stickers::Sets &stickerSets() const {
return _stickerSets;
}
Stickers::Sets &stickerSetsRef() {
return _stickerSets;
}
const Stickers::Order &stickerSetsOrder() const {
return _stickerSetsOrder;
}
Stickers::Order &stickerSetsOrderRef() {
return _stickerSetsOrder;
}
const Stickers::Order &featuredStickerSetsOrder() const {
return _featuredStickerSetsOrder;
}
Stickers::Order &featuredStickerSetsOrderRef() {
return _featuredStickerSetsOrder;
}
const Stickers::Order &archivedStickerSetsOrder() const {
return _archivedStickerSetsOrder;
}
Stickers::Order &archivedStickerSetsOrderRef() {
return _archivedStickerSetsOrder;
}
const Stickers::SavedGifs &savedGifs() const {
return _savedGifs;
}
Stickers::SavedGifs &savedGifsRef() {
return _savedGifs;
}
private: private:
struct Variables { struct Variables {
@ -259,11 +335,15 @@ private:
rpl::variable<float64> dialogsWidthRatio = kDefaultDialogsWidthRatio; // per-window rpl::variable<float64> dialogsWidthRatio = kDefaultDialogsWidthRatio; // per-window
}; };
bool stickersUpdateNeeded(TimeMs lastUpdate, TimeMs now) const {
constexpr auto kStickersUpdateTimeout = TimeMs(3600'000);
return (lastUpdate == 0)
|| (now >= lastUpdate + kStickersUpdateTimeout);
}
base::Variable<bool> _contactsLoaded = { false }; base::Variable<bool> _contactsLoaded = { false };
base::Variable<bool> _allChatsLoaded = { false }; base::Variable<bool> _allChatsLoaded = { false };
base::Observable<void> _moreChatsLoaded; base::Observable<void> _moreChatsLoaded;
base::Observable<void> _stickersUpdated;
base::Observable<void> _savedGifsUpdated;
base::Observable<void> _pendingHistoryResize; base::Observable<void> _pendingHistoryResize;
base::Observable<ItemVisibilityQuery> _queryItemVisibility; base::Observable<ItemVisibilityQuery> _queryItemVisibility;
rpl::event_stream<not_null<const HistoryItem*>> _itemLayoutChanged; rpl::event_stream<not_null<const HistoryItem*>> _itemLayoutChanged;
@ -274,6 +354,20 @@ private:
rpl::event_stream<MegagroupParticipant> _megagroupParticipantRemoved; rpl::event_stream<MegagroupParticipant> _megagroupParticipantRemoved;
rpl::event_stream<MegagroupParticipant> _megagroupParticipantAdded; rpl::event_stream<MegagroupParticipant> _megagroupParticipantAdded;
rpl::event_stream<> _stickersUpdated;
rpl::event_stream<> _savedGifsUpdated;
TimeMs _lastStickersUpdate = 0;
TimeMs _lastRecentStickersUpdate = 0;
TimeMs _lastFavedStickersUpdate = 0;
TimeMs _lastFeaturedStickersUpdate = 0;
TimeMs _lastSavedGifsUpdate = 0;
rpl::variable<int> _featuredStickerSetsUnreadCount = 0;
Stickers::Sets _stickerSets;
Stickers::Order _stickerSetsOrder;
Stickers::Order _featuredStickerSetsOrder;
Stickers::Order _archivedStickerSetsOrder;
Stickers::SavedGifs _savedGifs;
rpl::event_stream<bool> _thirdSectionInfoEnabledValue; rpl::event_stream<bool> _thirdSectionInfoEnabledValue;
bool _tabbedReplacedWithInfo = false; bool _tabbedReplacedWithInfo = false;
rpl::event_stream<bool> _tabbedReplacedWithInfoValue; rpl::event_stream<bool> _tabbedReplacedWithInfoValue;

View File

@ -50,7 +50,10 @@ void StickerSetBox::prepare() {
setTitle(langFactory(lng_contacts_loading)); setTitle(langFactory(lng_contacts_loading));
_inner = setInnerWidget(object_ptr<Inner>(this, _set), st::stickersScroll); _inner = setInnerWidget(object_ptr<Inner>(this, _set), st::stickersScroll);
subscribe(Auth().data().stickersUpdated(), [this] { updateButtons(); }); Auth().data().stickersUpdated()
| rpl::start_with_next(
[this] { updateButtons(); },
lifetime());
setDimensions(st::boxWideWidth, st::stickersMaxHeight); setDimensions(st::boxWideWidth, st::stickersMaxHeight);
@ -145,7 +148,7 @@ void StickerSetBox::Inner::gotSet(const MTPmessages_StickerSet &set) {
emoji = emoji->original(); emoji = emoji->original();
auto &stickers = pack.vdocuments.v; auto &stickers = pack.vdocuments.v;
StickerPack p; Stickers::Pack p;
p.reserve(stickers.size()); p.reserve(stickers.size());
for (auto j = 0, c = stickers.size(); j != c; ++j) { for (auto j = 0, c = stickers.size(); j != c; ++j) {
auto doc = App::document(stickers[j].v); auto doc = App::document(stickers[j].v);
@ -165,7 +168,7 @@ void StickerSetBox::Inner::gotSet(const MTPmessages_StickerSet &set) {
_setCount = s.vcount.v; _setCount = s.vcount.v;
_setHash = s.vhash.v; _setHash = s.vhash.v;
_setFlags = s.vflags.v; _setFlags = s.vflags.v;
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
auto it = sets.find(_setId); auto it = sets.find(_setId);
if (it != sets.cend()) { if (it != sets.cend()) {
auto clientFlags = it->flags & (MTPDstickerSet_ClientFlag::f_featured | MTPDstickerSet_ClientFlag::f_not_loaded | MTPDstickerSet_ClientFlag::f_unread | MTPDstickerSet_ClientFlag::f_special); auto clientFlags = it->flags & (MTPDstickerSet_ClientFlag::f_featured | MTPDstickerSet_ClientFlag::f_not_loaded | MTPDstickerSet_ClientFlag::f_unread | MTPDstickerSet_ClientFlag::f_special);
@ -201,13 +204,13 @@ bool StickerSetBox::Inner::failedSet(const RPCError &error) {
} }
void StickerSetBox::Inner::installDone(const MTPmessages_StickerSetInstallResult &result) { void StickerSetBox::Inner::installDone(const MTPmessages_StickerSetInstallResult &result) {
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
bool wasArchived = (_setFlags & MTPDstickerSet::Flag::f_archived); bool wasArchived = (_setFlags & MTPDstickerSet::Flag::f_archived);
if (wasArchived) { if (wasArchived) {
auto index = Global::RefArchivedStickerSetsOrder().indexOf(_setId); auto index = Auth().data().archivedStickerSetsOrderRef().indexOf(_setId);
if (index >= 0) { if (index >= 0) {
Global::RefArchivedStickerSetsOrder().removeAt(index); Auth().data().archivedStickerSetsOrderRef().removeAt(index);
} }
} }
_setFlags &= ~MTPDstickerSet::Flag::f_archived; _setFlags &= ~MTPDstickerSet::Flag::f_archived;
@ -221,7 +224,7 @@ void StickerSetBox::Inner::installDone(const MTPmessages_StickerSetInstallResult
it->stickers = _pack; it->stickers = _pack;
it->emoji = _emoji; it->emoji = _emoji;
auto &order = Global::RefStickerSetsOrder(); auto &order = Auth().data().stickerSetsOrderRef();
int insertAtIndex = 0, currentIndex = order.indexOf(_setId); int insertAtIndex = 0, currentIndex = order.indexOf(_setId);
if (currentIndex != insertAtIndex) { if (currentIndex != insertAtIndex) {
if (currentIndex > 0) { if (currentIndex > 0) {
@ -248,7 +251,7 @@ void StickerSetBox::Inner::installDone(const MTPmessages_StickerSetInstallResult
Local::writeArchivedStickers(); Local::writeArchivedStickers();
} }
Local::writeInstalledStickers(); Local::writeInstalledStickers();
Auth().data().stickersUpdated().notify(true); Auth().data().markStickersUpdated();
} }
_setInstalled.fire_copy(_setId); _setInstalled.fire_copy(_setId);
} }
@ -407,8 +410,8 @@ bool StickerSetBox::Inner::loaded() const {
int32 StickerSetBox::Inner::notInstalled() const { int32 StickerSetBox::Inner::notInstalled() const {
if (!_loaded) return 0; if (!_loaded) return 0;
auto it = Global::StickerSets().constFind(_setId); auto it = Auth().data().stickerSets().constFind(_setId);
if (it == Global::StickerSets().cend() || !(it->flags & MTPDstickerSet::Flag::f_installed) || (it->flags & MTPDstickerSet::Flag::f_archived)) return _pack.size(); if (it == Auth().data().stickerSets().cend() || !(it->flags & MTPDstickerSet::Flag::f_installed) || (it->flags & MTPDstickerSet::Flag::f_archived)) return _pack.size();
return 0; return 0;
} }

View File

@ -21,7 +21,7 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org
#pragma once #pragma once
#include "boxes/abstract_box.h" #include "boxes/abstract_box.h"
#include <vector> #include "chat_helpers/stickers.h"
class ConfirmBox; class ConfirmBox;
@ -105,8 +105,8 @@ private:
} }
std::vector<Animation> _packOvers; std::vector<Animation> _packOvers;
StickerPack _pack; Stickers::Pack _pack;
StickersByEmojiMap _emoji; Stickers::ByEmojiMap _emoji;
bool _loaded = false; bool _loaded = false;
uint64 _setId = 0; uint64 _setId = 0;
uint64 _setAccess = 0; uint64 _setAccess = 0;

View File

@ -52,8 +52,8 @@ constexpr auto kHandleMegagroupSetAddressChangeTimeout = TimeMs(1000);
int stickerPacksCount(bool includeArchivedOfficial) { int stickerPacksCount(bool includeArchivedOfficial) {
auto result = 0; auto result = 0;
auto &order = Global::StickerSetsOrder(); auto &order = Auth().data().stickerSetsOrder();
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
for (auto i = 0, l = order.size(); i < l; ++i) { for (auto i = 0, l = order.size(); i < l; ++i) {
auto it = sets.constFind(order.at(i)); auto it = sets.constFind(order.at(i));
if (it != sets.cend()) { if (it != sets.cend()) {
@ -65,24 +65,23 @@ int stickerPacksCount(bool includeArchivedOfficial) {
return result; return result;
} }
class StickersBox::CounterWidget : public TWidget, private base::Subscriber { class StickersBox::CounterWidget : public Ui::RpWidget {
public: public:
CounterWidget(QWidget *parent); CounterWidget(QWidget *parent);
void setCounter(int counter);
protected: protected:
void paintEvent(QPaintEvent *e) override; void paintEvent(QPaintEvent *e) override;
private: private:
void updateCounter(); void setCounter(int counter);
QString _text; QString _text;
Dialogs::Layout::UnreadBadgeStyle _st; Dialogs::Layout::UnreadBadgeStyle _st;
}; };
StickersBox::CounterWidget::CounterWidget(QWidget *parent) : TWidget(parent) { StickersBox::CounterWidget::CounterWidget(QWidget *parent)
: RpWidget(parent) {
setAttribute(Qt::WA_TransparentForMouseEvents); setAttribute(Qt::WA_TransparentForMouseEvents);
_st.sizeId = Dialogs::Layout::UnreadBadgeInStickersBox; _st.sizeId = Dialogs::Layout::UnreadBadgeInStickersBox;
@ -91,8 +90,11 @@ StickersBox::CounterWidget::CounterWidget(QWidget *parent) : TWidget(parent) {
_st.padding = st::stickersFeaturedBadgePadding; _st.padding = st::stickersFeaturedBadgePadding;
_st.font = st::stickersFeaturedBadgeFont; _st.font = st::stickersFeaturedBadgeFont;
subscribe(Global::RefFeaturedStickerSetsUnreadCountChanged(), [this] { updateCounter(); }); Auth().data().featuredStickerSetsUnreadCountValue()
updateCounter(); | rpl::start_with_next([this](int count) {
setCounter(count);
update();
}, lifetime());
} }
void StickersBox::CounterWidget::setCounter(int counter) { void StickersBox::CounterWidget::setCounter(int counter) {
@ -116,11 +118,6 @@ void StickersBox::CounterWidget::paintEvent(QPaintEvent *e) {
} }
} }
void StickersBox::CounterWidget::updateCounter() {
setCounter(Global::FeaturedStickerSetsUnreadCount());
update();
}
template <typename ...Args> template <typename ...Args>
StickersBox::Tab::Tab(int index, Args&&... args) StickersBox::Tab::Tab(int index, Args&&... args)
: _index(index) : _index(index)
@ -166,7 +163,7 @@ void StickersBox::getArchivedDone(uint64 offsetId, const MTPmessages_ArchivedSti
} }
auto &stickers = result.c_messages_archivedStickers(); auto &stickers = result.c_messages_archivedStickers();
auto &archived = Global::RefArchivedStickerSetsOrder(); auto &archived = Auth().data().archivedStickerSetsOrderRef();
if (offsetId) { if (offsetId) {
auto index = archived.indexOf(offsetId); auto index = archived.indexOf(offsetId);
if (index >= 0) { if (index >= 0) {
@ -241,7 +238,7 @@ void StickersBox::prepare() {
requestArchivedSets(); requestArchivedSets();
} }
if (_tabs) { if (_tabs) {
if (Global::ArchivedStickerSetsOrder().isEmpty()) { if (Auth().data().archivedStickerSetsOrder().isEmpty()) {
preloadArchivedSets(); preloadArchivedSets();
} }
setNoContentMargin(true); setNoContentMargin(true);
@ -280,7 +277,10 @@ void StickersBox::prepare() {
setInnerWidget(_tab->takeWidget(), getTopSkip()); setInnerWidget(_tab->takeWidget(), getTopSkip());
setDimensions(st::boxWideWidth, st::boxMaxListHeight); setDimensions(st::boxWideWidth, st::boxMaxListHeight);
subscribe(Auth().data().stickersUpdated(), [this] { handleStickersUpdated(); }); Auth().data().stickersUpdated()
| rpl::start_with_next(
[this] { handleStickersUpdated(); },
lifetime());
Auth().api().updateStickers(); Auth().api().updateStickers();
if (_installed.widget()) { if (_installed.widget()) {
@ -304,11 +304,11 @@ void StickersBox::refreshTabs() {
auto sections = QStringList(); auto sections = QStringList();
sections.push_back(lang(lng_stickers_installed_tab).toUpper()); sections.push_back(lang(lng_stickers_installed_tab).toUpper());
_tabIndices.push_back(Section::Installed); _tabIndices.push_back(Section::Installed);
if (!Global::FeaturedStickerSetsOrder().isEmpty()) { if (!Auth().data().featuredStickerSetsOrder().isEmpty()) {
sections.push_back(lang(lng_stickers_featured_tab).toUpper()); sections.push_back(lang(lng_stickers_featured_tab).toUpper());
_tabIndices.push_back(Section::Featured); _tabIndices.push_back(Section::Featured);
} }
if (!Global::ArchivedStickerSetsOrder().isEmpty()) { if (!Auth().data().archivedStickerSetsOrder().isEmpty()) {
sections.push_back(lang(lng_stickers_archived_tab).toUpper()); sections.push_back(lang(lng_stickers_archived_tab).toUpper());
_tabIndices.push_back(Section::Archived); _tabIndices.push_back(Section::Archived);
} }
@ -330,10 +330,10 @@ void StickersBox::loadMoreArchived() {
} }
uint64 lastId = 0; uint64 lastId = 0;
for (auto setIt = Global::ArchivedStickerSetsOrder().cend(), e = Global::ArchivedStickerSetsOrder().cbegin(); setIt != e;) { for (auto setIt = Auth().data().archivedStickerSetsOrder().cend(), e = Auth().data().archivedStickerSetsOrder().cbegin(); setIt != e;) {
--setIt; --setIt;
auto it = Global::StickerSets().constFind(*setIt); auto it = Auth().data().stickerSets().constFind(*setIt);
if (it != Global::StickerSets().cend()) { if (it != Auth().data().stickerSets().cend()) {
if (it->flags & MTPDstickerSet::Flag::f_archived) { if (it->flags & MTPDstickerSet::Flag::f_archived) {
lastId = it->id; lastId = it->id;
break; break;
@ -445,7 +445,7 @@ QPixmap StickersBox::grabContentCache() {
} }
void StickersBox::installSet(uint64 setId) { void StickersBox::installSet(uint64 setId) {
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
auto it = sets.find(setId); auto it = sets.find(setId);
if (it == sets.cend()) { if (it == sets.cend()) {
rebuildList(); rebuildList();
@ -474,7 +474,7 @@ void StickersBox::installDone(const MTPmessages_StickerSetInstallResult &result)
bool StickersBox::installFail(uint64 setId, const RPCError &error) { bool StickersBox::installFail(uint64 setId, const RPCError &error) {
if (MTP::isDefaultHandledError(error)) return false; if (MTP::isDefaultHandledError(error)) return false;
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
auto it = sets.find(setId); auto it = sets.find(setId);
if (it == sets.cend()) { if (it == sets.cend()) {
rebuildList(); rebuildList();
@ -498,8 +498,8 @@ void StickersBox::requestArchivedSets() {
preloadArchivedSets(); preloadArchivedSets();
} }
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
for_const (auto setId, Global::ArchivedStickerSetsOrder()) { for_const (auto setId, Auth().data().archivedStickerSetsOrder()) {
auto it = sets.constFind(setId); auto it = sets.constFind(setId);
if (it != sets.cend()) { if (it != sets.cend()) {
if (it->stickers.isEmpty() && (it->flags & MTPDstickerSet_ClientFlag::f_not_loaded)) { if (it->stickers.isEmpty() && (it->flags & MTPDstickerSet_ClientFlag::f_not_loaded)) {
@ -530,7 +530,7 @@ void StickersBox::handleStickersUpdated() {
} else { } else {
_tab->widget()->updateRows(); _tab->widget()->updateRows();
} }
if (Global::ArchivedStickerSetsOrder().isEmpty()) { if (Auth().data().archivedStickerSetsOrder().isEmpty()) {
preloadArchivedSets(); preloadArchivedSets();
} else { } else {
refreshTabs(); refreshTabs();
@ -612,8 +612,20 @@ StickersBox::Inner::Inner(QWidget *parent, not_null<ChannelData*> megagroup) : T
_megagroupSetField->setLinkPlaceholder(Messenger::Instance().createInternalLink(qsl("addstickers/"))); _megagroupSetField->setLinkPlaceholder(Messenger::Instance().createInternalLink(qsl("addstickers/")));
_megagroupSetField->setPlaceholderHidden(false); _megagroupSetField->setPlaceholderHidden(false);
_megagroupSetAddressChangedTimer.setCallback([this] { handleMegagroupSetAddressChange(); }); _megagroupSetAddressChangedTimer.setCallback([this] { handleMegagroupSetAddressChange(); });
connect(_megagroupSetField, &Ui::MaskedInputField::changed, this, [this] { _megagroupSetAddressChangedTimer.callOnce(kHandleMegagroupSetAddressChangeTimeout); }); connect(
connect(_megagroupSetField, &Ui::MaskedInputField::submitted, this, [this] { _megagroupSetAddressChangedTimer.cancel(); handleMegagroupSetAddressChange(); }); _megagroupSetField,
&Ui::MaskedInputField::changed,
[this] {
_megagroupSetAddressChangedTimer.callOnce(
kHandleMegagroupSetAddressChangeTimeout);
});
connect(
_megagroupSetField,
&Ui::MaskedInputField::submitted,
[this] {
_megagroupSetAddressChangedTimer.cancel();
handleMegagroupSetAddressChange();
});
setup(); setup();
} }
@ -717,7 +729,13 @@ void StickersBox::Inner::paintRow(Painter &p, Row *set, int index, TimeMs ms) {
if (xadd || yadd) p.translate(xadd, yadd); if (xadd || yadd) p.translate(xadd, yadd);
if (_megagroupSet) { if (_megagroupSet) {
if (index >= 0 && index == _selected) { auto selectedIndex = [&] {
if (auto index = base::get_if<int>(&_selected)) {
return *index;
}
return -1;
}();
if (index >= 0 && index == selectedIndex) {
p.fillRect(0, 0, width(), _rowHeight, st::contactsBgOver); p.fillRect(0, 0, width(), _rowHeight, st::contactsBgOver);
if (set->ripple) { if (set->ripple) {
set->ripple->paint(p, 0, 0, width(), ms); set->ripple->paint(p, 0, 0, width(), ms);
@ -854,9 +872,11 @@ void StickersBox::Inner::mousePressEvent(QMouseEvent *e) {
if (_actionSel >= 0) { if (_actionSel >= 0) {
setActionDown(_actionSel); setActionDown(_actionSel);
update(0, _itemsTop + _actionSel * _rowHeight, width(), _rowHeight); update(0, _itemsTop + _actionSel * _rowHeight, width(), _rowHeight);
} else if (_selected >= 0 && _section == Section::Installed && !_rows.at(_selected)->isRecentSet() && _inDragArea) { } else if (auto selectedIndex = base::get_if<int>(&_selected)) {
_above = _dragging = _started = _selected; if (_section == Section::Installed && !_rows[*selectedIndex]->isRecentSet() && _inDragArea) {
_dragStart = mapFromGlobal(_mouse); _above = _dragging = _started = *selectedIndex;
_dragStart = mapFromGlobal(_mouse);
}
} }
} }
@ -900,41 +920,65 @@ void StickersBox::Inner::setActionDown(int newActionDown) {
} }
} }
void StickersBox::Inner::setSelected(int selected) { void StickersBox::Inner::setSelected(SelectedRow selected) {
if (_selected == selected) { if (_selected == selected) {
return; return;
} }
if (_megagroupSet && _selected >= 0 && _selected < _rows.size()) { if ((_megagroupSet || _section != Section::Installed)
update(0, _itemsTop + _selected * _rowHeight, width(), _rowHeight); && ((_selected.has_value() || _pressed.has_value()) != (selected.has_value() || _pressed.has_value()))) {
if (!_inDragArea) {
setCursor((selected.has_value() || _pressed.has_value())
? style::cur_pointer
: style::cur_default);
}
}
auto countSelectedIndex = [&] {
if (auto index = base::get_if<int>(&_selected)) {
return *index;
}
return -1;
};
auto selectedIndex = countSelectedIndex();
if (_megagroupSet && selectedIndex >= 0 && selectedIndex < _rows.size()) {
update(0, _itemsTop + selectedIndex * _rowHeight, width(), _rowHeight);
} }
_selected = selected; _selected = selected;
if (_megagroupSet && _selected >= 0 && _selected < _rows.size()) { selectedIndex = countSelectedIndex();
update(0, _itemsTop + _selected * _rowHeight, width(), _rowHeight); if (_megagroupSet && selectedIndex >= 0 && selectedIndex < _rows.size()) {
update(0, _itemsTop + selectedIndex * _rowHeight, width(), _rowHeight);
} }
} }
void StickersBox::Inner::setPressed(int pressed) { void StickersBox::Inner::setPressed(SelectedRow pressed) {
if (_pressed == pressed) { if (_pressed == pressed) {
return; return;
} }
if (_megagroupSet && _pressed >= 0 && _pressed < _rows.size()) { auto countPressedIndex = [&] {
update(0, _itemsTop + _pressed * _rowHeight, width(), _rowHeight); if (auto index = base::get_if<int>(&_pressed)) {
auto &set = _rows[_pressed]; return *index;
}
return -1;
};
auto pressedIndex = countPressedIndex();
if (_megagroupSet && pressedIndex >= 0 && pressedIndex < _rows.size()) {
update(0, _itemsTop + pressedIndex * _rowHeight, width(), _rowHeight);
auto &set = _rows[pressedIndex];
if (set->ripple) { if (set->ripple) {
set->ripple->lastStop(); set->ripple->lastStop();
} }
} }
_pressed = pressed; _pressed = pressed;
if (_megagroupSet && _pressed >= 0 && _pressed < _rows.size()) { pressedIndex = countPressedIndex();
update(0, _itemsTop + _pressed * _rowHeight, width(), _rowHeight); if (_megagroupSet && pressedIndex >= 0 && pressedIndex < _rows.size()) {
auto &set = _rows[_pressed]; update(0, _itemsTop + pressedIndex * _rowHeight, width(), _rowHeight);
auto &set = _rows[pressedIndex];
auto rippleMask = Ui::RippleAnimation::rectMask(QSize(width(), _rowHeight)); auto rippleMask = Ui::RippleAnimation::rectMask(QSize(width(), _rowHeight));
if (!_rows[_pressed]->ripple) { if (!_rows[pressedIndex]->ripple) {
_rows[_pressed]->ripple = std::make_unique<Ui::RippleAnimation>(st::contactsRipple, std::move(rippleMask), [this, index = _pressed] { _rows[pressedIndex]->ripple = std::make_unique<Ui::RippleAnimation>(st::contactsRipple, std::move(rippleMask), [this, pressedIndex] {
update(0, _itemsTop + index * _rowHeight, width(), _rowHeight); update(0, _itemsTop + pressedIndex * _rowHeight, width(), _rowHeight);
}); });
} }
_rows[_pressed]->ripple->add(mapFromGlobal(QCursor::pos()) - QPoint(0, _itemsTop + _pressed * _rowHeight)); _rows[pressedIndex]->ripple->add(mapFromGlobal(QCursor::pos()) - QPoint(0, _itemsTop + pressedIndex * _rowHeight));
} }
} }
@ -997,17 +1041,18 @@ void StickersBox::Inner::onUpdateSelected() {
emit draggingScrollDelta(countDraggingScrollDelta()); emit draggingScrollDelta(countDraggingScrollDelta());
} else { } else {
bool in = rect().marginsRemoved(QMargins(0, _itemsTop, 0, st::membersMarginBottom)).contains(local); bool in = rect().marginsRemoved(QMargins(0, _itemsTop, 0, st::membersMarginBottom)).contains(local);
auto selected = -1; auto selected = SelectedRow();
auto actionSel = -1; auto actionSel = -1;
auto inDragArea = false; auto inDragArea = false;
if (in && !_rows.empty()) { if (in && !_rows.empty()) {
selected = floorclamp(local.y() - _itemsTop, _rowHeight, 0, _rows.size() - 1); auto selectedIndex = floorclamp(local.y() - _itemsTop, _rowHeight, 0, _rows.size() - 1);
local.setY(local.y() - _itemsTop - selected * _rowHeight); selected = selectedIndex;
auto &set = _rows[selected]; local.setY(local.y() - _itemsTop - selectedIndex * _rowHeight);
auto &set = _rows[selectedIndex];
if (!_megagroupSet && (_section == Section::Installed || !set->installed || set->archived || set->removed)) { if (!_megagroupSet && (_section == Section::Installed || !set->installed || set->archived || set->removed)) {
auto removeButton = (_section == Section::Installed && !set->removed); auto removeButton = (_section == Section::Installed && !set->removed);
auto rect = myrtlrect(relativeButtonRect(removeButton)); auto rect = myrtlrect(relativeButtonRect(removeButton));
actionSel = rect.contains(local) ? selected : -1; actionSel = rect.contains(local) ? selectedIndex : -1;
} else { } else {
actionSel = -1; actionSel = -1;
} }
@ -1016,20 +1061,20 @@ void StickersBox::Inner::onUpdateSelected() {
auto dragArea = myrtlrect(0, 0, dragAreaWidth, _rowHeight); auto dragArea = myrtlrect(0, 0, dragAreaWidth, _rowHeight);
inDragArea = dragArea.contains(local); inDragArea = dragArea.contains(local);
} }
} else { } else if (_megagroupSelectedSet) {
selected = -1; auto setTop = _megagroupDivider->y() - _rowHeight;
} if (QRect(0, setTop, width(), _rowHeight).contains(local)) {
if (_selected != selected) { selected = MegagroupSet();
if ((_megagroupSet || _section != Section::Installed) && ((_selected >= 0 || _pressed >= 0) != (selected >= 0 || _pressed >= 0))) {
if (!inDragArea) {
setCursor((selected >= 0 || _pressed >= 0) ? style::cur_pointer : style::cur_default);
}
} }
setSelected(selected);
} }
setSelected(selected);
if (_inDragArea != inDragArea) { if (_inDragArea != inDragArea) {
_inDragArea = inDragArea; _inDragArea = inDragArea;
setCursor(_inDragArea ? style::cur_sizeall : (_selected >= 0 || _pressed >= 0) ? style::cur_pointer : style::cur_default); setCursor(_inDragArea
? style::cur_sizeall
: ((_selected.has_value() || _pressed.has_value())
? style::cur_pointer
: style::cur_default));
} }
setActionSel(actionSel); setActionSel(actionSel);
emit draggingScrollDelta(0); emit draggingScrollDelta(0);
@ -1045,9 +1090,9 @@ float64 StickersBox::Inner::aboveShadowOpacity() const {
} }
void StickersBox::Inner::mouseReleaseEvent(QMouseEvent *e) { void StickersBox::Inner::mouseReleaseEvent(QMouseEvent *e) {
auto pressed = std::exchange(_pressed, -1); auto pressed = std::exchange(_pressed, SelectedRow());
if (_section != Section::Installed && _selected < 0 && pressed >= 0) { if (_section != Section::Installed && !_selected.has_value() && pressed.has_value()) {
setCursor(style::cur_default); setCursor(style::cur_default);
} }
@ -1070,22 +1115,43 @@ void StickersBox::Inner::mouseReleaseEvent(QMouseEvent *e) {
_dragging = _started = -1; _dragging = _started = -1;
} else if (pressed == _selected && _actionSel < 0 && _actionDown < 0) { } else if (pressed == _selected && _actionSel < 0 && _actionDown < 0) {
if (_selected >= 0 && !_inDragArea) { auto selectedIndex = [&] {
auto &sets = Global::RefStickerSets(); if (auto index = base::get_if<int>(&_selected)) {
auto &row = _rows[pressed]; return *index;
if (!row->isRecentSet()) { }
auto it = sets.find(row->id); return -1;
}();
auto getSetByRow = [&](const Row &row) -> const Stickers::Set* {
auto &sets = Auth().data().stickerSetsRef();
if (!row.isRecentSet()) {
auto it = sets.find(row.id);
if (it != sets.cend()) { if (it != sets.cend()) {
if (_megagroupSet) { return &*it;
setMegagroupSelectedSet(MTP_inputStickerSetID(MTP_long(it->id), MTP_long(it->access)));
} else {
setSelected(-1);
Ui::show(
Box<StickerSetBox>(Stickers::inputSetId(*it)),
LayerOption::KeepOther);
}
} }
} }
return nullptr;
};
auto showSetByRow = [&](const Row &row) {
if (auto set = getSetByRow(row)) {
setSelected(SelectedRow());
Ui::show(
Box<StickerSetBox>(Stickers::inputSetId(*set)),
LayerOption::KeepOther);
}
};
if (selectedIndex >= 0 && !_inDragArea) {
auto &row = *_rows[selectedIndex];
if (_megagroupSet) {
if (auto set = getSetByRow(row)) {
setMegagroupSelectedSet(MTP_inputStickerSetID(
MTP_long(set->id),
MTP_long(set->access)));
}
} else {
showSetByRow(row);
}
} else if (_megagroupSelectedSet && _selected.is<MegagroupSet>()) {
showSetByRow(*_megagroupSelectedSet);
} }
} }
setActionDown(-1); setActionDown(-1);
@ -1177,8 +1243,8 @@ void StickersBox::Inner::clear() {
_aboveShadowFadeOpacity = anim::value(); _aboveShadowFadeOpacity = anim::value();
_a_shifting.stop(); _a_shifting.stop();
_above = _dragging = _started = -1; _above = _dragging = _started = -1;
setSelected(-1); setSelected(SelectedRow());
setPressed(-1); setPressed(SelectedRow());
setActionSel(-1); setActionSel(-1);
setActionDown(-1); setActionDown(-1);
update(); update();
@ -1195,12 +1261,39 @@ void StickersBox::Inner::setActionSel(int32 actionSel) {
} }
} }
void StickersBox::Inner::AddressField::correctValue(
const QString &was,
int wasCursor,
QString &now,
int &nowCursor) {
auto newText = now;
auto newCursor = nowCursor;
auto removeFromBeginning = {
qstr("http://"),
qstr("https://"),
qstr("www.t.me/"),
qstr("www.telegram.me/"),
qstr("www.telegram.dog/"),
qstr("t.me/"),
qstr("telegram.me/"),
qstr("telegram.dog/"),
qstr("addstickers/"),
};
for (auto &removePhrase : removeFromBeginning) {
if (newText.startsWith(removePhrase)) {
newText = newText.mid(removePhrase.size());
newCursor = newText.size();
}
}
setCorrectedText(now, nowCursor, newText, newCursor);
}
void StickersBox::Inner::handleMegagroupSetAddressChange() { void StickersBox::Inner::handleMegagroupSetAddressChange() {
auto text = _megagroupSetField->getLastText().trimmed(); auto text = _megagroupSetField->getLastText().trimmed();
if (text.isEmpty()) { if (text.isEmpty()) {
if (_megagroupSelectedSet) { if (_megagroupSelectedSet) {
auto it = Global::StickerSets().constFind(_megagroupSelectedSet->id); auto it = Auth().data().stickerSets().constFind(_megagroupSelectedSet->id);
if (it != Global::StickerSets().end() && !it->shortName.isEmpty()) { if (it != Auth().data().stickerSets().cend() && !it->shortName.isEmpty()) {
setMegagroupSelectedSet(MTP_inputStickerSetEmpty()); setMegagroupSelectedSet(MTP_inputStickerSetEmpty());
} }
} }
@ -1232,7 +1325,7 @@ void StickersBox::Inner::rebuildMegagroupSet() {
} }
auto &set = _megagroupSetInput.c_inputStickerSetID(); auto &set = _megagroupSetInput.c_inputStickerSetID();
auto setId = set.vid.v; auto setId = set.vid.v;
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
auto it = sets.find(setId); auto it = sets.find(setId);
if (it == sets.cend() || (it->flags & MTPDstickerSet_ClientFlag::f_not_loaded)) { if (it == sets.cend() || (it->flags & MTPDstickerSet_ClientFlag::f_not_loaded)) {
Auth().api().scheduleStickerSetRequest(set.vid.v, set.vaccess_hash.v); Auth().api().scheduleStickerSetRequest(set.vid.v, set.vaccess_hash.v);
@ -1279,16 +1372,16 @@ void StickersBox::Inner::rebuild() {
clear(); clear();
auto &order = ([this]() -> const Stickers::Order & { auto &order = ([this]() -> const Stickers::Order & {
if (_section == Section::Installed) { if (_section == Section::Installed) {
return Global::StickerSetsOrder(); return Auth().data().stickerSetsOrder();
} else if (_section == Section::Featured) { } else if (_section == Section::Featured) {
return Global::FeaturedStickerSetsOrder(); return Auth().data().featuredStickerSetsOrder();
} }
return Global::ArchivedStickerSetsOrder(); return Auth().data().archivedStickerSetsOrder();
})(); })();
_rows.reserve(order.size() + 1); _rows.reserve(order.size() + 1);
_animStartTimes.reserve(order.size() + 1); _animStartTimes.reserve(order.size() + 1);
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
if (!_megagroupSet && _section == Section::Installed) { if (!_megagroupSet && _section == Section::Installed) {
auto cloudIt = sets.constFind(Stickers::CloudRecentSetId); auto cloudIt = sets.constFind(Stickers::CloudRecentSetId);
if (cloudIt != sets.cend() && !cloudIt->stickers.isEmpty()) { if (cloudIt != sets.cend() && !cloudIt->stickers.isEmpty()) {
@ -1331,7 +1424,7 @@ void StickersBox::Inner::updateSize(int newWidth) {
void StickersBox::Inner::updateRows() { void StickersBox::Inner::updateRows() {
int maxNameWidth = countMaxNameWidth(); int maxNameWidth = countMaxNameWidth();
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
for_const (auto &row, _rows) { for_const (auto &row, _rows) {
auto it = sets.constFind(row->id); auto it = sets.constFind(row->id);
if (it != sets.cend()) { if (it != sets.cend()) {
@ -1376,9 +1469,14 @@ bool StickersBox::Inner::appendSet(const Stickers::Set &set) {
int StickersBox::Inner::countMaxNameWidth() const { int StickersBox::Inner::countMaxNameWidth() const {
int namex = st::contactsPadding.left() + st::contactsPhotoSize + st::contactsPadding.left(); int namex = st::contactsPadding.left() + st::contactsPhotoSize + st::contactsPadding.left();
if (!_megagroupSet && _section == Section::Installed) {
namex += st::stickersReorderIcon.width() + st::stickersReorderSkip;
}
int namew = st::boxWideWidth - namex - st::contactsPadding.right() - st::contactsCheckPosition.x(); int namew = st::boxWideWidth - namex - st::contactsPadding.right() - st::contactsCheckPosition.x();
if (_section == Section::Installed) { if (_section == Section::Installed) {
namew -= _undoWidth - st::stickersUndoRemove.width; if (!_megagroupSet) {
namew -= _undoWidth - st::stickersUndoRemove.width;
}
} else { } else {
namew -= _addWidth - st::stickersTrendingAdd.width; namew -= _addWidth - st::stickersTrendingAdd.width;
if (_section == Section::Featured) { if (_section == Section::Featured) {
@ -1438,8 +1536,8 @@ void StickersBox::Inner::fillSetCover(const Stickers::Set &set, DocumentData **o
int StickersBox::Inner::fillSetCount(const Stickers::Set &set) const { int StickersBox::Inner::fillSetCount(const Stickers::Set &set) const {
int result = set.stickers.isEmpty() ? set.count : set.stickers.size(), added = 0; int result = set.stickers.isEmpty() ? set.count : set.stickers.size(), added = 0;
if (set.id == Stickers::CloudRecentSetId) { if (set.id == Stickers::CloudRecentSetId) {
auto customIt = Global::StickerSets().constFind(Stickers::CustomSetId); auto customIt = Auth().data().stickerSets().constFind(Stickers::CustomSetId);
if (customIt != Global::StickerSets().cend()) { if (customIt != Auth().data().stickerSets().cend()) {
added = customIt->stickers.size(); added = customIt->stickers.size();
for_const (auto &sticker, cGetRecentStickers()) { for_const (auto &sticker, cGetRecentStickers()) {
if (customIt->stickers.indexOf(sticker.first) < 0) { if (customIt->stickers.indexOf(sticker.first) < 0) {
@ -1572,7 +1670,7 @@ void StickersBox::Inner::readVisibleSets() {
continue; continue;
} }
if (!_rows[i]->sticker || _rows[i]->sticker->thumb->loaded() || _rows[i]->sticker->loaded()) { if (!_rows[i]->sticker || _rows[i]->sticker->thumb->loaded() || _rows[i]->sticker->loaded()) {
Stickers::MarkFeaturedAsRead(_rows[i]->id); Auth().api().readFeaturedSetDelayed(_rows[i]->id);
} }
} }
} }

View File

@ -23,6 +23,8 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org
#include "boxes/abstract_box.h" #include "boxes/abstract_box.h"
#include "base/timer.h" #include "base/timer.h"
#include "mtproto/sender.h" #include "mtproto/sender.h"
#include "chat_helpers/stickers.h"
#include "ui/widgets/input_fields.h"
class ConfirmBox; class ConfirmBox;
@ -35,7 +37,6 @@ class PlainShadow;
class RippleAnimation; class RippleAnimation;
class SettingsSlider; class SettingsSlider;
class SlideAnimation; class SlideAnimation;
class UsernameInput;
class CrossButton; class CrossButton;
} // namespace Ui } // namespace Ui
@ -223,6 +224,27 @@ private:
anim::value yadd; anim::value yadd;
std::unique_ptr<Ui::RippleAnimation> ripple; std::unique_ptr<Ui::RippleAnimation> ripple;
}; };
struct MegagroupSet {
inline bool operator==(const MegagroupSet &other) const {
return true;
}
inline bool operator!=(const MegagroupSet &other) const {
return false;
}
};
using SelectedRow = base::optional_variant<MegagroupSet, int>;
class AddressField : public Ui::UsernameInput {
public:
using UsernameInput::UsernameInput;
protected:
void correctValue(
const QString &was,
int wasCursor,
QString &now,
int &nowCursor) override;
};
template <typename Check> template <typename Check>
Stickers::Order collectSets(Check check) const; Stickers::Order collectSets(Check check) const;
@ -232,9 +254,9 @@ private:
int getRowIndex(uint64 setId) const; int getRowIndex(uint64 setId) const;
void setRowRemoved(int index, bool removed); void setRowRemoved(int index, bool removed);
void setSelected(int selected); void setSelected(SelectedRow selected);
void setActionDown(int newActionDown); void setActionDown(int newActionDown);
void setPressed(int pressed); void setPressed(SelectedRow pressed);
void setup(); void setup();
QRect relativeButtonRect(bool removeButton) const; QRect relativeButtonRect(bool removeButton) const;
void ensureRipple(const style::RippleAnimation &st, QImage mask, bool removeButton); void ensureRipple(const style::RippleAnimation &st, QImage mask, bool removeButton);
@ -255,6 +277,7 @@ private:
QString fillSetTitle(const Stickers::Set &set, int maxNameWidth, int *outTitleWidth) const; QString fillSetTitle(const Stickers::Set &set, int maxNameWidth, int *outTitleWidth) const;
void fillSetFlags(const Stickers::Set &set, bool *outInstalled, bool *outOfficial, bool *outUnread, bool *outArchived); void fillSetFlags(const Stickers::Set &set, bool *outInstalled, bool *outOfficial, bool *outUnread, bool *outArchived);
void rebuildMegagroupSet(); void rebuildMegagroupSet();
void fixupMegagroupSetAddress();
void handleMegagroupSetAddressChange(); void handleMegagroupSetAddressChange();
void setMegagroupSelectedSet(const MTPInputStickerSet &set); void setMegagroupSelectedSet(const MTPInputStickerSet &set);
@ -289,8 +312,8 @@ private:
QPoint _mouse; QPoint _mouse;
bool _inDragArea = false; bool _inDragArea = false;
int _selected = -1; SelectedRow _selected;
int _pressed = -1; SelectedRow _pressed;
QPoint _dragStart; QPoint _dragStart;
int _started = -1; int _started = -1;
int _dragging = -1; int _dragging = -1;
@ -302,7 +325,7 @@ private:
ChannelData *_megagroupSet = nullptr; ChannelData *_megagroupSet = nullptr;
MTPInputStickerSet _megagroupSetInput = MTP_inputStickerSetEmpty(); MTPInputStickerSet _megagroupSetInput = MTP_inputStickerSetEmpty();
std::unique_ptr<Row> _megagroupSelectedSet; std::unique_ptr<Row> _megagroupSelectedSet;
object_ptr<Ui::UsernameInput> _megagroupSetField = { nullptr }; object_ptr<AddressField> _megagroupSetField = { nullptr };
object_ptr<Ui::PlainShadow> _megagroupSelectedShadow = { nullptr }; object_ptr<Ui::PlainShadow> _megagroupSelectedShadow = { nullptr };
object_ptr<Ui::CrossButton> _megagroupSelectedRemove = { nullptr }; object_ptr<Ui::CrossButton> _megagroupSelectedRemove = { nullptr };
object_ptr<BoxContentDivider> _megagroupDivider = { nullptr }; object_ptr<BoxContentDivider> _megagroupDivider = { nullptr };

View File

@ -651,14 +651,14 @@ void EmojiListWidget::refreshRecent() {
updateSize(); updateSize();
} }
bool EmojiListWidget::event(QEvent *e) { bool EmojiListWidget::eventHook(QEvent *e) {
if (e->type() == QEvent::ParentChange) { if (e->type() == QEvent::ParentChange) {
if (_picker->parentWidget() != parentWidget()) { if (_picker->parentWidget() != parentWidget()) {
_picker->setParent(parentWidget()); _picker->setParent(parentWidget());
} }
_picker->raise(); _picker->raise();
} }
return Inner::event(e); return Inner::eventHook(e);
} }
void EmojiListWidget::updateSelected() { void EmojiListWidget::updateSelected() {

View File

@ -122,7 +122,7 @@ protected:
void leaveEventHook(QEvent *e) override; void leaveEventHook(QEvent *e) override;
void leaveToChildEvent(QEvent *e, QWidget *child) override; void leaveToChildEvent(QEvent *e, QWidget *child) override;
void enterFromChildEvent(QEvent *e, QWidget *child) override; void enterFromChildEvent(QEvent *e, QWidget *child) override;
bool event(QEvent *e) override; bool eventHook(QEvent *e) override;
TabbedSelector::InnerFooter *getFooter() const override; TabbedSelector::InnerFooter *getFooter() const override;
void processHideFinished() override; void processHideFinished() override;

View File

@ -113,7 +113,7 @@ void FieldAutocomplete::showStickers(EmojiPtr emoji) {
_emoji = emoji; _emoji = emoji;
_type = Type::Stickers; _type = Type::Stickers;
if (!emoji) { if (!emoji) {
rowsUpdated(_mrows, _hrows, _brows, StickerPack(), false); rowsUpdated(_mrows, _hrows, _brows, Stickers::Pack(), false);
return; return;
} }
@ -147,7 +147,7 @@ void FieldAutocomplete::updateFiltered(bool resetScroll) {
internal::MentionRows mrows; internal::MentionRows mrows;
internal::HashtagRows hrows; internal::HashtagRows hrows;
internal::BotCommandRows brows; internal::BotCommandRows brows;
StickerPack srows; Stickers::Pack srows;
if (_emoji) { if (_emoji) {
srows = Stickers::GetListByEmoji(_emoji); srows = Stickers::GetListByEmoji(_emoji);
} else if (_type == Type::Mentions) { } else if (_type == Type::Mentions) {
@ -330,7 +330,7 @@ void FieldAutocomplete::updateFiltered(bool resetScroll) {
_inner->setRecentInlineBotsInRows(recentInlineBots); _inner->setRecentInlineBotsInRows(recentInlineBots);
} }
void FieldAutocomplete::rowsUpdated(const internal::MentionRows &mrows, const internal::HashtagRows &hrows, const internal::BotCommandRows &brows, const StickerPack &srows, bool resetScroll) { void FieldAutocomplete::rowsUpdated(const internal::MentionRows &mrows, const internal::HashtagRows &hrows, const internal::BotCommandRows &brows, const Stickers::Pack &srows, bool resetScroll) {
if (mrows.isEmpty() && hrows.isEmpty() && brows.isEmpty() && srows.isEmpty()) { if (mrows.isEmpty() && hrows.isEmpty() && brows.isEmpty() && srows.isEmpty()) {
if (!isHidden()) { if (!isHidden()) {
hideAnimated(); hideAnimated();
@ -508,7 +508,7 @@ FieldAutocomplete::~FieldAutocomplete() {
namespace internal { namespace internal {
FieldAutocompleteInner::FieldAutocompleteInner(FieldAutocomplete *parent, MentionRows *mrows, HashtagRows *hrows, BotCommandRows *brows, StickerPack *srows) FieldAutocompleteInner::FieldAutocompleteInner(FieldAutocomplete *parent, MentionRows *mrows, HashtagRows *hrows, BotCommandRows *brows, Stickers::Pack *srows)
: _parent(parent) : _parent(parent)
, _mrows(mrows) , _mrows(mrows)
, _hrows(hrows) , _hrows(hrows)

View File

@ -21,6 +21,7 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org
#pragma once #pragma once
#include "ui/twidget.h" #include "ui/twidget.h"
#include "chat_helpers/stickers.h"
namespace Ui { namespace Ui {
class ScrollArea; class ScrollArea;
@ -104,9 +105,9 @@ private:
internal::MentionRows _mrows; internal::MentionRows _mrows;
internal::HashtagRows _hrows; internal::HashtagRows _hrows;
internal::BotCommandRows _brows; internal::BotCommandRows _brows;
StickerPack _srows; Stickers::Pack _srows;
void rowsUpdated(const internal::MentionRows &mrows, const internal::HashtagRows &hrows, const internal::BotCommandRows &brows, const StickerPack &srows, bool resetScroll); void rowsUpdated(const internal::MentionRows &mrows, const internal::HashtagRows &hrows, const internal::BotCommandRows &brows, const Stickers::Pack &srows, bool resetScroll);
object_ptr<Ui::ScrollArea> _scroll; object_ptr<Ui::ScrollArea> _scroll;
QPointer<internal::FieldAutocompleteInner> _inner; QPointer<internal::FieldAutocompleteInner> _inner;
@ -141,7 +142,7 @@ class FieldAutocompleteInner final : public TWidget, private base::Subscriber {
Q_OBJECT Q_OBJECT
public: public:
FieldAutocompleteInner(FieldAutocomplete *parent, MentionRows *mrows, HashtagRows *hrows, BotCommandRows *brows, StickerPack *srows); FieldAutocompleteInner(FieldAutocomplete *parent, MentionRows *mrows, HashtagRows *hrows, BotCommandRows *brows, Stickers::Pack *srows);
void clearSel(bool hidden = false); void clearSel(bool hidden = false);
bool moveSel(int key); bool moveSel(int key);
@ -179,7 +180,7 @@ private:
MentionRows *_mrows; MentionRows *_mrows;
HashtagRows *_hrows; HashtagRows *_hrows;
BotCommandRows *_brows; BotCommandRows *_brows;
StickerPack *_srows; Stickers::Pack *_srows;
int32 _stickersPerRow, _recentInlineBotsInRows; int32 _stickersPerRow, _recentInlineBotsInRows;
int32 _sel, _down; int32 _sel, _down;
bool _mouseSel; bool _mouseSel;

View File

@ -122,7 +122,10 @@ void GifsListWidget::Footer::processPanelHideFinished() {
//_field->setText(QString()); //_field->setText(QString());
} }
GifsListWidget::GifsListWidget(QWidget *parent, not_null<Window::Controller*> controller) : Inner(parent, controller) GifsListWidget::GifsListWidget(
QWidget *parent,
not_null<Window::Controller*> controller)
: Inner(parent, controller)
, _section(Section::Gifs) { , _section(Section::Gifs) {
updateSize(); updateSize();
@ -138,9 +141,10 @@ GifsListWidget::GifsListWidget(QWidget *parent, not_null<Window::Controller*> co
_inlineRequestTimer.setSingleShot(true); _inlineRequestTimer.setSingleShot(true);
connect(&_inlineRequestTimer, &QTimer::timeout, this, [this] { sendInlineRequest(); }); connect(&_inlineRequestTimer, &QTimer::timeout, this, [this] { sendInlineRequest(); });
subscribe(Auth().data().savedGifsUpdated(), [this] { Auth().data().savedGifsUpdated()
refreshSavedGifs(); | rpl::start_with_next([this] {
}); refreshSavedGifs();
}, lifetime());
subscribe(Auth().downloaderTaskFinished(), [this] { subscribe(Auth().downloaderTaskFinished(), [this] {
update(); update();
}); });
@ -459,7 +463,7 @@ void GifsListWidget::refreshSavedGifs() {
if (_section == Section::Gifs) { if (_section == Section::Gifs) {
clearInlineRows(false); clearInlineRows(false);
auto &saved = cSavedGifs(); auto &saved = Auth().data().savedGifs();
if (!saved.isEmpty()) { if (!saved.isEmpty()) {
_rows.reserve(saved.size()); _rows.reserve(saved.size());
auto row = Row(); auto row = Row();

View File

@ -40,7 +40,11 @@ class Controller;
namespace ChatHelpers { namespace ChatHelpers {
class GifsListWidget : public TabbedSelector::Inner, public InlineBots::Layout::Context, private base::Subscriber, private MTP::Sender { class GifsListWidget
: public TabbedSelector::Inner
, public InlineBots::Layout::Context
, private base::Subscriber
, private MTP::Sender {
Q_OBJECT Q_OBJECT
public: public:

View File

@ -32,16 +32,10 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org
#include "styles/style_chat_helpers.h" #include "styles/style_chat_helpers.h"
namespace Stickers { namespace Stickers {
namespace {
constexpr int kReadFeaturedSetsTimeoutMs = 1000;
QPointer<internal::FeaturedReader> FeaturedReaderInstance;
} // namespace
void ApplyArchivedResult(const MTPDmessages_stickerSetInstallResultArchive &d) { void ApplyArchivedResult(const MTPDmessages_stickerSetInstallResultArchive &d) {
auto &v = d.vsets.v; auto &v = d.vsets.v;
auto &order = Global::RefStickerSetsOrder(); auto &order = Auth().data().stickerSetsOrderRef();
Order archived; Order archived;
archived.reserve(v.size()); archived.reserve(v.size());
QMap<uint64, uint64> setsToRequest; QMap<uint64, uint64> setsToRequest;
@ -89,13 +83,13 @@ void ApplyArchivedResult(const MTPDmessages_stickerSetInstallResultArchive &d) {
Ui::Toast::Show(toast); Ui::Toast::Show(toast);
// Ui::show(Box<StickersBox>(archived), LayerOption::KeepOther); // Ui::show(Box<StickersBox>(archived), LayerOption::KeepOther);
Auth().data().stickersUpdated().notify(true); Auth().data().markStickersUpdated();
} }
// For testing: Just apply random subset or your sticker sets as archived. // For testing: Just apply random subset or your sticker sets as archived.
bool ApplyArchivedResultFake() { bool ApplyArchivedResultFake() {
auto sets = QVector<MTPStickerSetCovered>(); auto sets = QVector<MTPStickerSetCovered>();
for (auto &set : Global::RefStickerSets()) { for (auto &set : Auth().data().stickerSetsRef()) {
if ((set.flags & MTPDstickerSet::Flag::f_installed) && !(set.flags & MTPDstickerSet_ClientFlag::f_special)) { if ((set.flags & MTPDstickerSet::Flag::f_installed) && !(set.flags & MTPDstickerSet_ClientFlag::f_special)) {
if (rand_value<uint32>() % 128 < 64) { if (rand_value<uint32>() % 128 < 64) {
auto data = MTP_stickerSet(MTP_flags(set.flags | MTPDstickerSet::Flag::f_archived), MTP_long(set.id), MTP_long(set.access), MTP_string(set.title), MTP_string(set.shortName), MTP_int(set.count), MTP_int(set.hash)); auto data = MTP_stickerSet(MTP_flags(set.flags | MTPDstickerSet::Flag::f_archived), MTP_long(set.id), MTP_long(set.access), MTP_string(set.title), MTP_string(set.shortName), MTP_int(set.count), MTP_int(set.hash));
@ -110,7 +104,7 @@ bool ApplyArchivedResultFake() {
} }
void InstallLocally(uint64 setId) { void InstallLocally(uint64 setId) {
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
auto it = sets.find(setId); auto it = sets.find(setId);
if (it == sets.end()) { if (it == sets.end()) {
return; return;
@ -121,7 +115,7 @@ void InstallLocally(uint64 setId) {
it->flags |= MTPDstickerSet::Flag::f_installed; it->flags |= MTPDstickerSet::Flag::f_installed;
auto changedFlags = flags ^ it->flags; auto changedFlags = flags ^ it->flags;
auto &order = Global::RefStickerSetsOrder(); auto &order = Auth().data().stickerSetsOrderRef();
int insertAtIndex = 0, currentIndex = order.indexOf(setId); int insertAtIndex = 0, currentIndex = order.indexOf(setId);
if (currentIndex != insertAtIndex) { if (currentIndex != insertAtIndex) {
if (currentIndex > 0) { if (currentIndex > 0) {
@ -143,17 +137,17 @@ void InstallLocally(uint64 setId) {
Local::writeInstalledStickers(); Local::writeInstalledStickers();
if (changedFlags & MTPDstickerSet_ClientFlag::f_unread) Local::writeFeaturedStickers(); if (changedFlags & MTPDstickerSet_ClientFlag::f_unread) Local::writeFeaturedStickers();
if (changedFlags & MTPDstickerSet::Flag::f_archived) { if (changedFlags & MTPDstickerSet::Flag::f_archived) {
auto index = Global::RefArchivedStickerSetsOrder().indexOf(setId); auto index = Auth().data().archivedStickerSetsOrderRef().indexOf(setId);
if (index >= 0) { if (index >= 0) {
Global::RefArchivedStickerSetsOrder().removeAt(index); Auth().data().archivedStickerSetsOrderRef().removeAt(index);
Local::writeArchivedStickers(); Local::writeArchivedStickers();
} }
} }
Auth().data().stickersUpdated().notify(true); Auth().data().markStickersUpdated();
} }
void UndoInstallLocally(uint64 setId) { void UndoInstallLocally(uint64 setId) {
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
auto it = sets.find(setId); auto it = sets.find(setId);
if (it == sets.end()) { if (it == sets.end()) {
return; return;
@ -161,34 +155,23 @@ void UndoInstallLocally(uint64 setId) {
it->flags &= ~MTPDstickerSet::Flag::f_installed; it->flags &= ~MTPDstickerSet::Flag::f_installed;
auto &order = Global::RefStickerSetsOrder(); auto &order = Auth().data().stickerSetsOrderRef();
int currentIndex = order.indexOf(setId); int currentIndex = order.indexOf(setId);
if (currentIndex >= 0) { if (currentIndex >= 0) {
order.removeAt(currentIndex); order.removeAt(currentIndex);
} }
Local::writeInstalledStickers(); Local::writeInstalledStickers();
Auth().data().stickersUpdated().notify(true); Auth().data().markStickersUpdated();
Ui::show( Ui::show(
Box<InformBox>(lang(lng_stickers_not_found)), Box<InformBox>(lang(lng_stickers_not_found)),
LayerOption::KeepOther); LayerOption::KeepOther);
} }
void MarkFeaturedAsRead(uint64 setId) {
if (!FeaturedReaderInstance) {
if (auto main = App::main()) {
FeaturedReaderInstance = object_ptr<internal::FeaturedReader>(main);
} else {
return;
}
}
FeaturedReaderInstance->scheduleRead(setId);
}
bool IsFaved(not_null<DocumentData*> document) { bool IsFaved(not_null<DocumentData*> document) {
auto it = Global::StickerSets().constFind(FavedSetId); auto it = Auth().data().stickerSets().constFind(FavedSetId);
return (it != Global::StickerSets().cend()) && it->stickers.contains(document); return (it != Auth().data().stickerSets().cend()) && it->stickers.contains(document);
} }
void CheckFavedLimit(Set &set) { void CheckFavedLimit(Set &set) {
@ -242,7 +225,7 @@ void MoveFavedToFront(Set &set, int index) {
void RequestSetToPushFaved(not_null<DocumentData*> document); void RequestSetToPushFaved(not_null<DocumentData*> document);
void SetIsFaved(not_null<DocumentData*> document, base::optional<std::vector<not_null<EmojiPtr>>> emojiList = base::none) { void SetIsFaved(not_null<DocumentData*> document, base::optional<std::vector<not_null<EmojiPtr>>> emojiList = base::none) {
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
auto it = sets.find(FavedSetId); auto it = sets.find(FavedSetId);
if (it == sets.end()) { if (it == sets.end()) {
it = sets.insert(FavedSetId, Set(FavedSetId, 0, Lang::Hard::FavedSetTitle(), QString(), 0, 0, MTPDstickerSet_ClientFlag::f_special | 0)); it = sets.insert(FavedSetId, Set(FavedSetId, 0, Lang::Hard::FavedSetTitle(), QString(), 0, 0, MTPDstickerSet_ClientFlag::f_special | 0));
@ -262,7 +245,7 @@ void SetIsFaved(not_null<DocumentData*> document, base::optional<std::vector<not
return; return;
} }
Local::writeFavedStickers(); Local::writeFavedStickers();
Auth().data().stickersUpdated().notify(true); Auth().data().markStickersUpdated();
Auth().api().stickerSetInstalled(FavedSetId); Auth().api().stickerSetInstalled(FavedSetId);
} }
@ -305,7 +288,7 @@ void RequestSetToPushFaved(not_null<DocumentData*> document) {
} }
void SetIsNotFaved(not_null<DocumentData*> document) { void SetIsNotFaved(not_null<DocumentData*> document) {
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
auto it = sets.find(FavedSetId); auto it = sets.find(FavedSetId);
if (it == sets.end()) { if (it == sets.end()) {
return; return;
@ -330,7 +313,7 @@ void SetIsNotFaved(not_null<DocumentData*> document) {
sets.erase(it); sets.erase(it);
} }
Local::writeFavedStickers(); Local::writeFavedStickers();
Auth().data().stickersUpdated().notify(true); Auth().data().markStickersUpdated();
} }
void SetFaved(not_null<DocumentData*> document, bool faved) { void SetFaved(not_null<DocumentData*> document, bool faved) {
@ -342,10 +325,10 @@ void SetFaved(not_null<DocumentData*> document, bool faved) {
} }
void SetsReceived(const QVector<MTPStickerSet> &data, int32 hash) { void SetsReceived(const QVector<MTPStickerSet> &data, int32 hash) {
auto &setsOrder = Global::RefStickerSetsOrder(); auto &setsOrder = Auth().data().stickerSetsOrderRef();
setsOrder.clear(); setsOrder.clear();
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
QMap<uint64, uint64> setsToRequest; QMap<uint64, uint64> setsToRequest;
for (auto &set : sets) { for (auto &set : sets) {
if (!(set.flags & MTPDstickerSet::Flag::f_archived)) { if (!(set.flags & MTPDstickerSet::Flag::f_archived)) {
@ -402,10 +385,10 @@ void SetsReceived(const QVector<MTPStickerSet> &data, int32 hash) {
LOG(("API Error: received stickers hash %1 while counted hash is %2").arg(hash).arg(Local::countStickersHash())); LOG(("API Error: received stickers hash %1 while counted hash is %2").arg(hash).arg(Local::countStickersHash()));
} }
Auth().data().stickersUpdated().notify(true); Auth().data().markStickersUpdated();
} }
void SetPackAndEmoji(Set &set, StickerPack &&pack, const QVector<MTPStickerPack> &packs) { void SetPackAndEmoji(Set &set, Pack &&pack, const QVector<MTPStickerPack> &packs) {
set.stickers = std::move(pack); set.stickers = std::move(pack);
set.emoji.clear(); set.emoji.clear();
for_const (auto &mtpPack, packs) { for_const (auto &mtpPack, packs) {
@ -415,7 +398,7 @@ void SetPackAndEmoji(Set &set, StickerPack &&pack, const QVector<MTPStickerPack>
emoji = emoji->original(); emoji = emoji->original();
auto &stickers = pack.vdocuments.v; auto &stickers = pack.vdocuments.v;
auto p = StickerPack(); auto p = Pack();
p.reserve(stickers.size()); p.reserve(stickers.size());
for (auto j = 0, c = stickers.size(); j != c; ++j) { for (auto j = 0, c = stickers.size(); j != c; ++j) {
auto document = App::document(stickers[j].v); auto document = App::document(stickers[j].v);
@ -429,7 +412,7 @@ void SetPackAndEmoji(Set &set, StickerPack &&pack, const QVector<MTPStickerPack>
} }
void SpecialSetReceived(uint64 setId, const QString &setTitle, const QVector<MTPDocument> &items, int32 hash, const QVector<MTPStickerPack> &packs) { void SpecialSetReceived(uint64 setId, const QString &setTitle, const QVector<MTPDocument> &items, int32 hash, const QVector<MTPStickerPack> &packs) {
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
auto it = sets.find(setId); auto it = sets.find(setId);
auto &d_docs = items; auto &d_docs = items;
@ -446,7 +429,7 @@ void SpecialSetReceived(uint64 setId, const QString &setTitle, const QVector<MTP
it->hash = hash; it->hash = hash;
auto custom = sets.find(CustomSetId); auto custom = sets.find(CustomSetId);
auto pack = StickerPack(); auto pack = Pack();
pack.reserve(d_docs.size()); pack.reserve(d_docs.size());
for_const (auto &mtpDocument, d_docs) { for_const (auto &mtpDocument, d_docs) {
auto document = App::feedDocument(mtpDocument); auto document = App::feedDocument(mtpDocument);
@ -503,7 +486,7 @@ void SpecialSetReceived(uint64 setId, const QString &setTitle, const QVector<MTP
default: Unexpected("setId in SpecialSetReceived()"); default: Unexpected("setId in SpecialSetReceived()");
} }
Auth().data().stickersUpdated().notify(true); Auth().data().markStickersUpdated();
} }
void FeaturedSetsReceived(const QVector<MTPStickerSetCovered> &data, const QVector<MTPlong> &unread, int32 hash) { void FeaturedSetsReceived(const QVector<MTPStickerSetCovered> &data, const QVector<MTPlong> &unread, int32 hash) {
@ -512,10 +495,10 @@ void FeaturedSetsReceived(const QVector<MTPStickerSetCovered> &data, const QVect
unreadMap.insert(unreadSetId.v); unreadMap.insert(unreadSetId.v);
} }
auto &setsOrder = Global::RefFeaturedStickerSetsOrder(); auto &setsOrder = Auth().data().featuredStickerSetsOrderRef();
setsOrder.clear(); setsOrder.clear();
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
QMap<uint64, uint64> setsToRequest; QMap<uint64, uint64> setsToRequest;
for (auto &set : sets) { for (auto &set : sets) {
set.flags &= ~MTPDstickerSet_ClientFlag::f_featured; // mark for removing set.flags &= ~MTPDstickerSet_ClientFlag::f_featured; // mark for removing
@ -587,10 +570,7 @@ void FeaturedSetsReceived(const QVector<MTPStickerSetCovered> &data, const QVect
it = sets.erase(it); it = sets.erase(it);
} }
} }
if (Global::FeaturedStickerSetsUnreadCount() != unreadCount) { Auth().data().setFeaturedStickerSetsUnreadCount(unreadCount);
Global::SetFeaturedStickerSetsUnreadCount(unreadCount);
Global::RefFeaturedStickerSetsUnreadCountChanged().notify();
}
if (Local::countFeaturedStickersHash() != hash) { if (Local::countFeaturedStickersHash() != hash) {
LOG(("API Error: received featured stickers hash %1 while counted hash is %2").arg(hash).arg(Local::countFeaturedStickersHash())); LOG(("API Error: received featured stickers hash %1 while counted hash is %2").arg(hash).arg(Local::countFeaturedStickersHash()));
@ -606,11 +586,11 @@ void FeaturedSetsReceived(const QVector<MTPStickerSetCovered> &data, const QVect
Local::writeFeaturedStickers(); Local::writeFeaturedStickers();
Auth().data().stickersUpdated().notify(true); Auth().data().markStickersUpdated();
} }
void GifsReceived(const QVector<MTPDocument> &items, int32 hash) { void GifsReceived(const QVector<MTPDocument> &items, int32 hash) {
auto &saved = cRefSavedGifs(); auto &saved = Auth().data().savedGifsRef();
saved.clear(); saved.clear();
saved.reserve(items.size()); saved.reserve(items.size());
@ -629,16 +609,16 @@ void GifsReceived(const QVector<MTPDocument> &items, int32 hash) {
Local::writeSavedGifs(); Local::writeSavedGifs();
Auth().data().savedGifsUpdated().notify(); Auth().data().markSavedGifsUpdated();
} }
StickerPack GetListByEmoji(not_null<EmojiPtr> emoji) { Pack GetListByEmoji(not_null<EmojiPtr> emoji) {
auto original = emoji->original(); auto original = emoji->original();
auto result = StickerPack(); auto result = Pack();
auto setsToRequest = QMap<uint64, uint64>(); auto setsToRequest = QMap<uint64, uint64>();
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
auto faved = StickerPack(); auto faved = Pack();
auto favedIt = sets.find(Stickers::FavedSetId); auto favedIt = sets.find(Stickers::FavedSetId);
if (favedIt != sets.cend()) { if (favedIt != sets.cend()) {
auto i = favedIt->emoji.constFind(original); auto i = favedIt->emoji.constFind(original);
@ -647,7 +627,7 @@ StickerPack GetListByEmoji(not_null<EmojiPtr> emoji) {
result = faved; result = faved;
} }
} }
auto &order = Global::StickerSetsOrder(); auto &order = Auth().data().stickerSetsOrder();
for (auto i = 0, l = order.size(); i != l; ++i) { for (auto i = 0, l = order.size(); i != l; ++i) {
auto it = sets.find(order[i]); auto it = sets.find(order[i]);
if (it != sets.cend()) { if (it != sets.cend()) {
@ -683,7 +663,7 @@ base::optional<std::vector<not_null<EmojiPtr>>> GetEmojiListFromSet(
if (inputSet.type() != mtpc_inputStickerSetID) { if (inputSet.type() != mtpc_inputStickerSetID) {
return base::none; return base::none;
} }
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
auto it = sets.constFind(inputSet.c_inputStickerSetID().vid.v); auto it = sets.constFind(inputSet.c_inputStickerSetID().vid.v);
if (it == sets.cend()) { if (it == sets.cend()) {
return base::none; return base::none;
@ -703,7 +683,7 @@ base::optional<std::vector<not_null<EmojiPtr>>> GetEmojiListFromSet(
} }
Set *FeedSet(const MTPDstickerSet &set) { Set *FeedSet(const MTPDstickerSet &set) {
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
auto it = sets.find(set.vid.v); auto it = sets.find(set.vid.v);
auto title = GetSetTitle(set); auto title = GetSetTitle(set);
auto flags = MTPDstickerSet::Flags(0); auto flags = MTPDstickerSet::Flags(0);
@ -724,13 +704,13 @@ Set *FeedSet(const MTPDstickerSet &set) {
} }
auto changedFlags = (flags ^ it->flags); auto changedFlags = (flags ^ it->flags);
if (changedFlags & MTPDstickerSet::Flag::f_archived) { if (changedFlags & MTPDstickerSet::Flag::f_archived) {
auto index = Global::ArchivedStickerSetsOrder().indexOf(it->id); auto index = Auth().data().archivedStickerSetsOrder().indexOf(it->id);
if (it->flags & MTPDstickerSet::Flag::f_archived) { if (it->flags & MTPDstickerSet::Flag::f_archived) {
if (index < 0) { if (index < 0) {
Global::RefArchivedStickerSetsOrder().push_front(it->id); Auth().data().archivedStickerSetsOrderRef().push_front(it->id);
} }
} else if (index >= 0) { } else if (index >= 0) {
Global::RefArchivedStickerSetsOrder().removeAt(index); Auth().data().archivedStickerSetsOrderRef().removeAt(index);
} }
} }
return &it.value(); return &it.value();
@ -744,11 +724,11 @@ Set *FeedSetFull(const MTPmessages_StickerSet &data) {
set->flags &= ~MTPDstickerSet_ClientFlag::f_not_loaded; set->flags &= ~MTPDstickerSet_ClientFlag::f_not_loaded;
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
auto &d_docs = d.vdocuments.v; auto &d_docs = d.vdocuments.v;
auto custom = sets.find(Stickers::CustomSetId); auto custom = sets.find(Stickers::CustomSetId);
auto pack = StickerPack(); auto pack = Pack();
pack.reserve(d_docs.size()); pack.reserve(d_docs.size());
for (auto i = 0, l = d_docs.size(); i != l; ++i) { for (auto i = 0, l = d_docs.size(); i != l; ++i) {
auto doc = App::feedDocument(d_docs.at(i)); auto doc = App::feedDocument(d_docs.at(i));
@ -779,8 +759,8 @@ Set *FeedSetFull(const MTPmessages_StickerSet &data) {
} }
if (pack.isEmpty()) { if (pack.isEmpty()) {
int removeIndex = Global::StickerSetsOrder().indexOf(set->id); int removeIndex = Auth().data().stickerSetsOrder().indexOf(set->id);
if (removeIndex >= 0) Global::RefStickerSetsOrder().removeAt(removeIndex); if (removeIndex >= 0) Auth().data().stickerSetsOrderRef().removeAt(removeIndex);
sets.remove(set->id); sets.remove(set->id);
set = nullptr; set = nullptr;
} else { } else {
@ -795,7 +775,7 @@ Set *FeedSetFull(const MTPmessages_StickerSet &data) {
emoji = emoji->original(); emoji = emoji->original();
auto &stickers = pack.vdocuments.v; auto &stickers = pack.vdocuments.v;
StickerPack p; Pack p;
p.reserve(stickers.size()); p.reserve(stickers.size());
for (auto j = 0, c = stickers.size(); j != c; ++j) { for (auto j = 0, c = stickers.size(); j != c; ++j) {
auto doc = App::document(stickers[j].v); auto doc = App::document(stickers[j].v);
@ -823,7 +803,7 @@ Set *FeedSetFull(const MTPmessages_StickerSet &data) {
} }
} }
Auth().data().stickersUpdated().notify(true); Auth().data().markStickersUpdated();
return set; return set;
} }
@ -836,51 +816,4 @@ QString GetSetTitle(const MTPDstickerSet &s) {
return title; return title;
} }
namespace internal {
FeaturedReader::FeaturedReader(QObject *parent) : QObject(parent)
, _timer(this) {
_timer->setTimeoutHandler([this] { readSets(); });
}
void FeaturedReader::scheduleRead(uint64 setId) {
if (!_setIds.contains(setId)) {
_setIds.insert(setId);
_timer->start(kReadFeaturedSetsTimeoutMs);
}
}
void FeaturedReader::readSets() {
auto &sets = Global::RefStickerSets();
auto count = Global::FeaturedStickerSetsUnreadCount();
QVector<MTPlong> wrappedIds;
wrappedIds.reserve(_setIds.size());
for_const (auto setId, _setIds) {
auto it = sets.find(setId);
if (it != sets.cend()) {
it->flags &= ~MTPDstickerSet_ClientFlag::f_unread;
wrappedIds.append(MTP_long(setId));
if (count) {
--count;
}
}
}
_setIds.clear();
if (!wrappedIds.empty()) {
request(MTPmessages_ReadFeaturedStickers(MTP_vector<MTPlong>(wrappedIds))).done([](const MTPBool &result) {
Local::writeFeaturedStickers();
if (AuthSession::Exists()) {
Auth().data().stickersUpdated().notify(true);
}
}).send();
if (Global::FeaturedStickerSetsUnreadCount() != count) {
Global::SetFeaturedStickerSetsUnreadCount(count);
Global::RefFeaturedStickerSetsUnreadCountChanged().notify();
}
}
}
} // namespace internal
} // namespace Stickers } // namespace Stickers

View File

@ -24,13 +24,52 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org
namespace Stickers { namespace Stickers {
constexpr auto DefaultSetId = 0; // for backward compatibility
constexpr auto CustomSetId = 0xFFFFFFFFFFFFFFFFULL;
constexpr auto RecentSetId = 0xFFFFFFFFFFFFFFFEULL; // for emoji/stickers panel, should not appear in Sets
constexpr auto NoneSetId = 0xFFFFFFFFFFFFFFFDULL; // for emoji/stickers panel, should not appear in Sets
constexpr auto CloudRecentSetId = 0xFFFFFFFFFFFFFFFCULL; // for cloud-stored recent stickers
constexpr auto FeaturedSetId = 0xFFFFFFFFFFFFFFFBULL; // for emoji/stickers panel, should not appear in Sets
constexpr auto FavedSetId = 0xFFFFFFFFFFFFFFFAULL; // for cloud-stored faved stickers
constexpr auto MegagroupSetId = 0xFFFFFFFFFFFFFFEFULL; // for setting up megagroup sticker set
using Order = QList<uint64>;
using SavedGifs = QVector<DocumentData*>;
using Pack = QVector<DocumentData*>;
using ByEmojiMap = QMap<EmojiPtr, Pack>;
struct Set {
Set(uint64 id, uint64 access, const QString &title, const QString &shortName, int32 count, int32 hash, MTPDstickerSet::Flags flags)
: id(id)
, access(access)
, title(title)
, shortName(shortName)
, count(count)
, hash(hash)
, flags(flags) {
}
uint64 id, access;
QString title, shortName;
int32 count, hash;
MTPDstickerSet::Flags flags;
Pack stickers;
ByEmojiMap emoji;
};
using Sets = QMap<uint64, Set>;
inline MTPInputStickerSet inputSetId(const Set &set) {
if (set.id && set.access) {
return MTP_inputStickerSetID(MTP_long(set.id), MTP_long(set.access));
}
return MTP_inputStickerSetShortName(MTP_string(set.shortName));
}
constexpr auto kPanelPerRow = 5; constexpr auto kPanelPerRow = 5;
void ApplyArchivedResult(const MTPDmessages_stickerSetInstallResultArchive &d); void ApplyArchivedResult(const MTPDmessages_stickerSetInstallResultArchive &d);
bool ApplyArchivedResultFake(); // For testing. bool ApplyArchivedResultFake(); // For testing.
void InstallLocally(uint64 setId); void InstallLocally(uint64 setId);
void UndoInstallLocally(uint64 setId); void UndoInstallLocally(uint64 setId);
void MarkFeaturedAsRead(uint64 setId);
bool IsFaved(not_null<DocumentData*> document); bool IsFaved(not_null<DocumentData*> document);
void SetFaved(not_null<DocumentData*> document, bool faved); void SetFaved(not_null<DocumentData*> document, bool faved);
@ -39,7 +78,7 @@ void SpecialSetReceived(uint64 setId, const QString &setTitle, const QVector<MTP
void FeaturedSetsReceived(const QVector<MTPStickerSetCovered> &data, const QVector<MTPlong> &unread, int32 hash); void FeaturedSetsReceived(const QVector<MTPStickerSetCovered> &data, const QVector<MTPlong> &unread, int32 hash);
void GifsReceived(const QVector<MTPDocument> &items, int32 hash); void GifsReceived(const QVector<MTPDocument> &items, int32 hash);
StickerPack GetListByEmoji(not_null<EmojiPtr> emoji); Pack GetListByEmoji(not_null<EmojiPtr> emoji);
base::optional<std::vector<not_null<EmojiPtr>>> GetEmojiListFromSet( base::optional<std::vector<not_null<EmojiPtr>>> GetEmojiListFromSet(
not_null<DocumentData*> document); not_null<DocumentData*> document);
@ -48,20 +87,4 @@ Set *FeedSetFull(const MTPmessages_StickerSet &data);
QString GetSetTitle(const MTPDstickerSet &s); QString GetSetTitle(const MTPDstickerSet &s);
namespace internal {
class FeaturedReader : public QObject, private MTP::Sender {
public:
FeaturedReader(QObject *parent);
void scheduleRead(uint64 setId);
private:
void readSets();
object_ptr<SingleTimer> _timer;
OrderedSet<uint64> _setIds;
};
} // namespace internal
} // namespace Stickers } // namespace Stickers

View File

@ -398,7 +398,7 @@ void StickersListWidget::Footer::paintStickerSettingsIcon(Painter &p) const {
} }
void StickersListWidget::Footer::paintFeaturedStickerSetsBadge(Painter &p, int iconLeft) const { void StickersListWidget::Footer::paintFeaturedStickerSetsBadge(Painter &p, int iconLeft) const {
if (auto unread = Global::FeaturedStickerSetsUnreadCount()) { if (auto unread = Auth().data().featuredStickerSetsUnreadCount()) {
Dialogs::Layout::UnreadBadgeStyle unreadSt; Dialogs::Layout::UnreadBadgeStyle unreadSt;
unreadSt.sizeId = Dialogs::Layout::UnreadBadgeInStickersPanel; unreadSt.sizeId = Dialogs::Layout::UnreadBadgeInStickersPanel;
unreadSt.size = st::stickersSettingsUnreadSize; unreadSt.size = st::stickersSettingsUnreadSize;
@ -502,7 +502,7 @@ void StickersListWidget::readVisibleSets() {
} }
} }
if (loaded == count) { if (loaded == count) {
Stickers::MarkFeaturedAsRead(set.id); Auth().api().readFeaturedSetDelayed(set.id);
} }
} }
} }
@ -1049,7 +1049,7 @@ void StickersListWidget::removeRecentSticker(int section, int index) {
break; break;
} }
} }
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
auto it = sets.find(Stickers::CustomSetId); auto it = sets.find(Stickers::CustomSetId);
if (it != sets.cend()) { if (it != sets.cend()) {
for (int i = 0, l = it->stickers.size(); i < l; ++i) { for (int i = 0, l = it->stickers.size(); i < l; ++i) {
@ -1135,20 +1135,20 @@ void StickersListWidget::refreshStickers() {
_mySets.clear(); _mySets.clear();
_favedStickersMap.clear(); _favedStickersMap.clear();
_mySets.reserve(Global::StickerSetsOrder().size() + 3); _mySets.reserve(Auth().data().stickerSetsOrder().size() + 3);
refreshFavedStickers(); refreshFavedStickers();
refreshRecentStickers(false); refreshRecentStickers(false);
refreshMegagroupStickers(GroupStickersPlace::Visible); refreshMegagroupStickers(GroupStickersPlace::Visible);
for_const (auto setId, Global::StickerSetsOrder()) { for_const (auto setId, Auth().data().stickerSetsOrder()) {
appendSet(_mySets, setId, AppendSkip::Archived); appendSet(_mySets, setId, AppendSkip::Archived);
} }
refreshMegagroupStickers(GroupStickersPlace::Hidden); refreshMegagroupStickers(GroupStickersPlace::Hidden);
_featuredSets.clear(); _featuredSets.clear();
_featuredSets.reserve(Global::FeaturedStickerSetsOrder().size()); _featuredSets.reserve(Auth().data().featuredStickerSetsOrder().size());
for_const (auto setId, Global::FeaturedStickerSetsOrder()) { for_const (auto setId, Auth().data().featuredStickerSetsOrder()) {
appendSet(_featuredSets, setId, AppendSkip::Installed); appendSet(_featuredSets, setId, AppendSkip::Installed);
} }
@ -1203,7 +1203,7 @@ uint64 StickersListWidget::currentSet(int yOffset) const {
} }
void StickersListWidget::appendSet(Sets &to, uint64 setId, AppendSkip skip) { void StickersListWidget::appendSet(Sets &to, uint64 setId, AppendSkip skip) {
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
auto it = sets.constFind(setId); auto it = sets.constFind(setId);
if (it == sets.cend() || it->stickers.isEmpty()) return; if (it == sets.cend() || it->stickers.isEmpty()) return;
if ((skip == AppendSkip::Archived) && (it->flags & MTPDstickerSet::Flag::f_archived)) return; if ((skip == AppendSkip::Archived) && (it->flags & MTPDstickerSet::Flag::f_archived)) return;
@ -1228,12 +1228,12 @@ void StickersListWidget::refreshRecent() {
void StickersListWidget::refreshRecentStickers(bool performResize) { void StickersListWidget::refreshRecentStickers(bool performResize) {
_custom.clear(); _custom.clear();
clearSelection(); clearSelection();
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
auto &recent = cGetRecentStickers(); auto &recent = cGetRecentStickers();
auto customIt = sets.constFind(Stickers::CustomSetId); auto customIt = sets.constFind(Stickers::CustomSetId);
auto cloudIt = sets.constFind(Stickers::CloudRecentSetId); auto cloudIt = sets.constFind(Stickers::CloudRecentSetId);
StickerPack recentPack; Stickers::Pack recentPack;
int customCnt = (customIt == sets.cend()) ? 0 : customIt->stickers.size(); int customCnt = (customIt == sets.cend()) ? 0 : customIt->stickers.size();
int cloudCnt = (cloudIt == sets.cend()) ? 0 : cloudIt->stickers.size(); int cloudCnt = (cloudIt == sets.cend()) ? 0 : cloudIt->stickers.size();
recentPack.reserve(cloudCnt + recent.size() + customCnt); recentPack.reserve(cloudCnt + recent.size() + customCnt);
@ -1285,7 +1285,7 @@ void StickersListWidget::refreshRecentStickers(bool performResize) {
void StickersListWidget::refreshFavedStickers() { void StickersListWidget::refreshFavedStickers() {
clearSelection(); clearSelection();
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
auto it = sets.constFind(Stickers::FavedSetId); auto it = sets.constFind(Stickers::FavedSetId);
if (it == sets.cend() || it->stickers.isEmpty()) { if (it == sets.cend() || it->stickers.isEmpty()) {
return; return;
@ -1324,7 +1324,7 @@ void StickersListWidget::refreshMegagroupStickers(GroupStickersPlace place) {
} }
if (_megagroupSet->mgInfo->stickerSet.type() == mtpc_inputStickerSetID) { if (_megagroupSet->mgInfo->stickerSet.type() == mtpc_inputStickerSetID) {
auto &set = _megagroupSet->mgInfo->stickerSet.c_inputStickerSetID(); auto &set = _megagroupSet->mgInfo->stickerSet.c_inputStickerSetID();
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
auto it = sets.constFind(set.vid.v); auto it = sets.constFind(set.vid.v);
if (it != sets.cend()) { if (it != sets.cend()) {
auto isInstalled = (it->flags & MTPDstickerSet::Flag::f_installed) auto isInstalled = (it->flags & MTPDstickerSet::Flag::f_installed)
@ -1350,7 +1350,7 @@ void StickersListWidget::refreshMegagroupStickers(GroupStickersPlace place) {
void StickersListWidget::fillIcons(QList<StickerIcon> &icons) { void StickersListWidget::fillIcons(QList<StickerIcon> &icons) {
icons.clear(); icons.clear();
icons.reserve(_mySets.size() + 1); icons.reserve(_mySets.size() + 1);
if (Global::FeaturedStickerSetsUnreadCount() && !_featuredSets.isEmpty()) { if (Auth().data().featuredStickerSetsUnreadCount() && !_featuredSets.isEmpty()) {
icons.push_back(StickerIcon(Stickers::FeaturedSetId)); icons.push_back(StickerIcon(Stickers::FeaturedSetId));
} }
@ -1384,7 +1384,7 @@ void StickersListWidget::fillIcons(QList<StickerIcon> &icons) {
icons.push_back(StickerIcon(_mySets[i].id, s, pixw, pixh)); icons.push_back(StickerIcon(_mySets[i].id, s, pixw, pixh));
} }
if (!Global::FeaturedStickerSetsUnreadCount() && !_featuredSets.isEmpty()) { if (!Auth().data().featuredStickerSetsUnreadCount() && !_featuredSets.isEmpty()) {
icons.push_back(StickerIcon(Stickers::FeaturedSetId)); icons.push_back(StickerIcon(Stickers::FeaturedSetId));
} }
} }
@ -1623,7 +1623,7 @@ void StickersListWidget::displaySet(uint64 setId) {
return; return;
} }
} }
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
auto it = sets.constFind(setId); auto it = sets.constFind(setId);
if (it != sets.cend()) { if (it != sets.cend()) {
_displayingSetId = setId; _displayingSetId = setId;
@ -1638,7 +1638,7 @@ void StickersListWidget::displaySet(uint64 setId) {
} }
void StickersListWidget::installSet(uint64 setId) { void StickersListWidget::installSet(uint64 setId) {
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
auto it = sets.constFind(setId); auto it = sets.constFind(setId);
if (it != sets.cend()) { if (it != sets.cend()) {
request(MTPmessages_InstallStickerSet(Stickers::inputSetId(*it), MTP_bool(false))).done([this](const MTPmessages_StickerSetInstallResult &result) { request(MTPmessages_InstallStickerSet(Stickers::inputSetId(*it), MTP_bool(false))).done([this](const MTPmessages_StickerSetInstallResult &result) {
@ -1678,14 +1678,14 @@ void StickersListWidget::removeMegagroupSet(bool locally) {
} }
void StickersListWidget::removeSet(uint64 setId) { void StickersListWidget::removeSet(uint64 setId) {
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
auto it = sets.constFind(setId); auto it = sets.constFind(setId);
if (it != sets.cend()) { if (it != sets.cend()) {
_removingSetId = it->id; _removingSetId = it->id;
auto text = lng_stickers_remove_pack(lt_sticker_pack, it->title); auto text = lng_stickers_remove_pack(lt_sticker_pack, it->title);
Ui::show(Box<ConfirmBox>(text, lang(lng_box_remove), base::lambda_guarded(this, [this] { Ui::show(Box<ConfirmBox>(text, lang(lng_box_remove), base::lambda_guarded(this, [this] {
Ui::hideLayer(); Ui::hideLayer();
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
auto it = sets.find(_removingSetId); auto it = sets.find(_removingSetId);
if (it != sets.cend()) { if (it != sets.cend()) {
if (it->id && it->access) { if (it->id && it->access) {
@ -1707,8 +1707,8 @@ void StickersListWidget::removeSet(uint64 setId) {
if (!(it->flags & MTPDstickerSet_ClientFlag::f_featured) && !(it->flags & MTPDstickerSet_ClientFlag::f_special)) { if (!(it->flags & MTPDstickerSet_ClientFlag::f_featured) && !(it->flags & MTPDstickerSet_ClientFlag::f_special)) {
sets.erase(it); sets.erase(it);
} }
int removeIndex = Global::StickerSetsOrder().indexOf(_removingSetId); int removeIndex = Auth().data().stickerSetsOrder().indexOf(_removingSetId);
if (removeIndex >= 0) Global::RefStickerSetsOrder().removeAt(removeIndex); if (removeIndex >= 0) Auth().data().stickerSetsOrderRef().removeAt(removeIndex);
refreshStickers(); refreshStickers();
Local::writeInstalledStickers(); Local::writeInstalledStickers();
if (writeRecent) Local::writeUserSettings(); if (writeRecent) Local::writeUserSettings();

View File

@ -35,7 +35,10 @@ namespace ChatHelpers {
struct StickerIcon; struct StickerIcon;
class StickersListWidget : public TabbedSelector::Inner, private base::Subscriber, private MTP::Sender { class StickersListWidget
: public TabbedSelector::Inner
, private base::Subscriber
, private MTP::Sender {
Q_OBJECT Q_OBJECT
public: public:
@ -135,12 +138,12 @@ private:
}; };
struct Set { struct Set {
Set(uint64 id, MTPDstickerSet::Flags flags, const QString &title, int32 hoversSize, const StickerPack &pack = StickerPack()) : id(id), flags(flags), title(title), pack(pack) { Set(uint64 id, MTPDstickerSet::Flags flags, const QString &title, int32 hoversSize, const Stickers::Pack &pack = Stickers::Pack()) : id(id), flags(flags), title(title), pack(pack) {
} }
uint64 id; uint64 id;
MTPDstickerSet::Flags flags; MTPDstickerSet::Flags flags;
QString title; QString title;
StickerPack pack; Stickers::Pack pack;
QSharedPointer<Ui::RippleAnimation> ripple; QSharedPointer<Ui::RippleAnimation> ripple;
}; };
using Sets = QList<Set>; using Sets = QList<Set>;

View File

@ -698,7 +698,10 @@ void TabbedSelector::scrollToY(int y) {
_topShadow->update(); _topShadow->update();
} }
TabbedSelector::Inner::Inner(QWidget *parent, not_null<Window::Controller*> controller) : TWidget(parent) TabbedSelector::Inner::Inner(
QWidget *parent,
not_null<Window::Controller*> controller)
: RpWidget(parent)
, _controller(controller) { , _controller(controller) {
} }

View File

@ -206,7 +206,7 @@ private:
}; };
class TabbedSelector::Inner : public TWidget { class TabbedSelector::Inner : public Ui::RpWidget {
Q_OBJECT Q_OBJECT
public: public:

View File

@ -137,12 +137,12 @@ QString saveFileName(const QString &title, const QString &filter, const QString
bool StickerData::setInstalled() const { bool StickerData::setInstalled() const {
switch (set.type()) { switch (set.type()) {
case mtpc_inputStickerSetID: { case mtpc_inputStickerSetID: {
auto it = Global::StickerSets().constFind(set.c_inputStickerSetID().vid.v); auto it = Auth().data().stickerSets().constFind(set.c_inputStickerSetID().vid.v);
return (it != Global::StickerSets().cend()) && !(it->flags & MTPDstickerSet::Flag::f_archived) && (it->flags & MTPDstickerSet::Flag::f_installed); return (it != Auth().data().stickerSets().cend()) && !(it->flags & MTPDstickerSet::Flag::f_archived) && (it->flags & MTPDstickerSet::Flag::f_installed);
} break; } break;
case mtpc_inputStickerSetShortName: { case mtpc_inputStickerSetShortName: {
auto name = qs(set.c_inputStickerSetShortName().vshort_name).toLower(); auto name = qs(set.c_inputStickerSetShortName().vshort_name).toLower();
for (auto it = Global::StickerSets().cbegin(), e = Global::StickerSets().cend(); it != e; ++it) { for (auto it = Auth().data().stickerSets().cbegin(), e = Auth().data().stickerSets().cend(); it != e; ++it) {
if (it->shortName.toLower() == name) { if (it->shortName.toLower() == name) {
return !(it->flags & MTPDstickerSet::Flag::f_archived) && (it->flags & MTPDstickerSet::Flag::f_installed); return !(it->flags & MTPDstickerSet::Flag::f_archived) && (it->flags & MTPDstickerSet::Flag::f_installed);
} }

View File

@ -309,46 +309,6 @@ enum Flags {
}; };
} // namespace DebugLogging } // namespace DebugLogging
namespace Stickers {
constexpr auto DefaultSetId = 0; // for backward compatibility
constexpr auto CustomSetId = 0xFFFFFFFFFFFFFFFFULL;
constexpr auto RecentSetId = 0xFFFFFFFFFFFFFFFEULL; // for emoji/stickers panel, should not appear in Sets
constexpr auto NoneSetId = 0xFFFFFFFFFFFFFFFDULL; // for emoji/stickers panel, should not appear in Sets
constexpr auto CloudRecentSetId = 0xFFFFFFFFFFFFFFFCULL; // for cloud-stored recent stickers
constexpr auto FeaturedSetId = 0xFFFFFFFFFFFFFFFBULL; // for emoji/stickers panel, should not appear in Sets
constexpr auto FavedSetId = 0xFFFFFFFFFFFFFFFAULL; // for cloud-stored faved stickers
constexpr auto MegagroupSetId = 0xFFFFFFFFFFFFFFEFULL; // for setting up megagroup sticker set
struct Set {
Set(uint64 id, uint64 access, const QString &title, const QString &shortName, int32 count, int32 hash, MTPDstickerSet::Flags flags)
: id(id)
, access(access)
, title(title)
, shortName(shortName)
, count(count)
, hash(hash)
, flags(flags) {
}
uint64 id, access;
QString title, shortName;
int32 count, hash;
MTPDstickerSet::Flags flags;
StickerPack stickers;
StickersByEmojiMap emoji;
};
using Sets = QMap<uint64, Set>;
using Order = QList<uint64>;
inline MTPInputStickerSet inputSetId(const Set &set) {
if (set.id && set.access) {
return MTP_inputStickerSetID(MTP_long(set.id), MTP_long(set.access));
}
return MTP_inputStickerSetShortName(MTP_string(set.shortName));
}
} // namespace Stickers
namespace Global { namespace Global {
bool started(); bool started();
@ -414,17 +374,6 @@ DeclareVar(HiddenPinnedMessagesMap, HiddenPinnedMessages);
typedef OrderedSet<HistoryItem*> PendingItemsMap; typedef OrderedSet<HistoryItem*> PendingItemsMap;
DeclareRefVar(PendingItemsMap, PendingRepaintItems); DeclareRefVar(PendingItemsMap, PendingRepaintItems);
DeclareVar(Stickers::Sets, StickerSets);
DeclareVar(Stickers::Order, StickerSetsOrder);
DeclareVar(TimeMs, LastStickersUpdate);
DeclareVar(TimeMs, LastRecentStickersUpdate);
DeclareVar(TimeMs, LastFavedStickersUpdate);
DeclareVar(Stickers::Order, FeaturedStickerSetsOrder);
DeclareVar(int, FeaturedStickerSetsUnreadCount);
DeclareRefVar(base::Observable<void>, FeaturedStickerSetsUnreadCountChanged);
DeclareVar(TimeMs, LastFeaturedStickersUpdate);
DeclareVar(Stickers::Order, ArchivedStickerSetsOrder);
typedef QMap<uint64, QPixmap> CircleMasksMap; typedef QMap<uint64, QPixmap> CircleMasksMap;
DeclareRefVar(CircleMasksMap, CircleMasks); DeclareRefVar(CircleMasksMap, CircleMasks);

View File

@ -971,12 +971,13 @@ int HistoryWidget::itemTopForHighlight(not_null<HistoryItem*> item) const {
} }
void HistoryWidget::start() { void HistoryWidget::start() {
subscribe(Auth().data().stickersUpdated(), [this] { Auth().data().stickersUpdated()
_tabbedSelector->refreshStickers(); | rpl::start_with_next([this] {
updateStickersByEmoji(); _tabbedSelector->refreshStickers();
}); updateStickersByEmoji();
}, lifetime());
updateRecentStickers(); updateRecentStickers();
Auth().data().savedGifsUpdated().notify(); Auth().data().markSavedGifsUpdated();
subscribe(Auth().api().fullPeerUpdated(), [this](PeerData *peer) { subscribe(Auth().api().fullPeerUpdated(), [this](PeerData *peer) {
fullPeerUpdated(peer); fullPeerUpdated(peer);
}); });
@ -1473,7 +1474,7 @@ bool HistoryWidget::cmd_previous_chat() {
} }
void HistoryWidget::saveGif(DocumentData *doc) { void HistoryWidget::saveGif(DocumentData *doc) {
if (doc->isGifv() && cSavedGifs().indexOf(doc) != 0) { if (doc->isGifv() && Auth().data().savedGifs().indexOf(doc) != 0) {
MTPInputDocument mtpInput = doc->mtpInput(); MTPInputDocument mtpInput = doc->mtpInput();
if (mtpInput.type() != mtpc_inputDocumentEmpty) { if (mtpInput.type() != mtpc_inputDocumentEmpty) {
MTP::send(MTPmessages_SaveGif(mtpInput, MTP_bool(false)), rpcDone(&HistoryWidget::saveGifDone, doc)); MTP::send(MTPmessages_SaveGif(mtpInput, MTP_bool(false)), rpcDone(&HistoryWidget::saveGifDone, doc));

View File

@ -124,14 +124,14 @@ void Gif::setPosition(int32 position) {
} }
void DeleteSavedGifClickHandler::onClickImpl() const { void DeleteSavedGifClickHandler::onClickImpl() const {
auto index = cSavedGifs().indexOf(_data); auto index = Auth().data().savedGifs().indexOf(_data);
if (index >= 0) { if (index >= 0) {
cRefSavedGifs().remove(index); Auth().data().savedGifsRef().remove(index);
Local::writeSavedGifs(); Local::writeSavedGifs();
MTP::send(MTPmessages_SaveGif(_data->mtpInput(), MTP_bool(true))); MTP::send(MTPmessages_SaveGif(_data->mtpInput(), MTP_bool(true)));
} }
Auth().data().savedGifsUpdated().notify(); Auth().data().markSavedGifsUpdated();
} }
void Gif::paint(Painter &p, const QRect &clip, const PaintContext *context) const { void Gif::paint(Painter &p, const QRect &clip, const PaintContext *context) const {

View File

@ -4714,7 +4714,7 @@ void MainWidget::incrementSticker(DocumentData *sticker) {
if (sticker->sticker()->set.type() == mtpc_inputStickerSetEmpty) return; if (sticker->sticker()->set.type() == mtpc_inputStickerSetEmpty) return;
bool writeRecentStickers = false; bool writeRecentStickers = false;
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
auto it = sets.find(Stickers::CloudRecentSetId); auto it = sets.find(Stickers::CloudRecentSetId);
if (it == sets.cend()) { if (it == sets.cend()) {
if (it == sets.cend()) { if (it == sets.cend()) {
@ -5703,7 +5703,7 @@ void MainWidget::feedUpdate(const MTPUpdate &update) {
if (set.vset.type() == mtpc_stickerSet) { if (set.vset.type() == mtpc_stickerSet) {
auto &s = set.vset.c_stickerSet(); auto &s = set.vset.c_stickerSet();
if (!s.is_masks()) { if (!s.is_masks()) {
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
auto it = sets.find(s.vid.v); auto it = sets.find(s.vid.v);
if (it == sets.cend()) { if (it == sets.cend()) {
it = sets.insert(s.vid.v, Stickers::Set(s.vid.v, s.vaccess_hash.v, Stickers::GetSetTitle(s), qs(s.vshort_name), s.vcount.v, s.vhash.v, s.vflags.v | MTPDstickerSet::Flag::f_installed)); it = sets.insert(s.vid.v, Stickers::Set(s.vid.v, s.vaccess_hash.v, Stickers::GetSetTitle(s), qs(s.vshort_name), s.vcount.v, s.vhash.v, s.vflags.v | MTPDstickerSet::Flag::f_installed));
@ -5736,7 +5736,7 @@ void MainWidget::feedUpdate(const MTPUpdate &update) {
emoji = emoji->original(); emoji = emoji->original();
auto &stickers = pack.vdocuments.v; auto &stickers = pack.vdocuments.v;
StickerPack p; Stickers::Pack p;
p.reserve(stickers.size()); p.reserve(stickers.size());
for (auto j = 0, c = stickers.size(); j != c; ++j) { for (auto j = 0, c = stickers.size(); j != c; ++j) {
auto doc = App::document(stickers[j].v); auto doc = App::document(stickers[j].v);
@ -5748,7 +5748,7 @@ void MainWidget::feedUpdate(const MTPUpdate &update) {
} }
} }
auto &order(Global::RefStickerSetsOrder()); auto &order = Auth().data().stickerSetsOrderRef();
int32 insertAtIndex = 0, currentIndex = order.indexOf(s.vid.v); int32 insertAtIndex = 0, currentIndex = order.indexOf(s.vid.v);
if (currentIndex != insertAtIndex) { if (currentIndex != insertAtIndex) {
if (currentIndex > 0) { if (currentIndex > 0) {
@ -5769,7 +5769,7 @@ void MainWidget::feedUpdate(const MTPUpdate &update) {
} }
Local::writeInstalledStickers(); Local::writeInstalledStickers();
if (writeArchived) Local::writeArchivedStickers(); if (writeArchived) Local::writeArchivedStickers();
Auth().data().stickersUpdated().notify(true); Auth().data().markStickersUpdated();
} }
} }
} }
@ -5779,7 +5779,7 @@ void MainWidget::feedUpdate(const MTPUpdate &update) {
auto &d = update.c_updateStickerSetsOrder(); auto &d = update.c_updateStickerSetsOrder();
if (!d.is_masks()) { if (!d.is_masks()) {
auto &order = d.vorder.v; auto &order = d.vorder.v;
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
Stickers::Order result; Stickers::Order result;
for (int i = 0, l = order.size(); i < l; ++i) { for (int i = 0, l = order.size(); i < l; ++i) {
if (sets.constFind(order.at(i).v) == sets.cend()) { if (sets.constFind(order.at(i).v) == sets.cend()) {
@ -5787,29 +5787,29 @@ void MainWidget::feedUpdate(const MTPUpdate &update) {
} }
result.push_back(order.at(i).v); result.push_back(order.at(i).v);
} }
if (result.size() != Global::StickerSetsOrder().size() || result.size() != order.size()) { if (result.size() != Auth().data().stickerSetsOrder().size() || result.size() != order.size()) {
Global::SetLastStickersUpdate(0); Auth().data().setLastStickersUpdate(0);
Auth().api().updateStickers(); Auth().api().updateStickers();
} else { } else {
Global::SetStickerSetsOrder(result); Auth().data().stickerSetsOrderRef() = std::move(result);
Local::writeInstalledStickers(); Local::writeInstalledStickers();
Auth().data().stickersUpdated().notify(true); Auth().data().markStickersUpdated();
} }
} }
} break; } break;
case mtpc_updateStickerSets: { case mtpc_updateStickerSets: {
Global::SetLastStickersUpdate(0); Auth().data().setLastStickersUpdate(0);
Auth().api().updateStickers(); Auth().api().updateStickers();
} break; } break;
case mtpc_updateRecentStickers: { case mtpc_updateRecentStickers: {
Global::SetLastRecentStickersUpdate(0); Auth().data().setLastRecentStickersUpdate(0);
Auth().api().updateStickers(); Auth().api().updateStickers();
} break; } break;
case mtpc_updateFavedStickers: { case mtpc_updateFavedStickers: {
Global::SetLastFavedStickersUpdate(0); Auth().data().setLastFavedStickersUpdate(0);
Auth().api().updateStickers(); Auth().api().updateStickers();
} break; } break;
@ -5817,13 +5817,13 @@ void MainWidget::feedUpdate(const MTPUpdate &update) {
// We read some of the featured stickers, perhaps not all of them. // We read some of the featured stickers, perhaps not all of them.
// Here we don't know what featured sticker sets were read, so we // Here we don't know what featured sticker sets were read, so we
// request all of them once again. // request all of them once again.
Global::SetLastFeaturedStickersUpdate(0); Auth().data().setLastFeaturedStickersUpdate(0);
Auth().api().updateStickers(); Auth().api().updateStickers();
} break; } break;
////// Cloud saved GIFs ////// Cloud saved GIFs
case mtpc_updateSavedGifs: { case mtpc_updateSavedGifs: {
cSetLastSavedGifsUpdate(0); Auth().data().setLastSavedGifsUpdate(0);
Auth().api().updateStickers(); Auth().api().updateStickers();
} break; } break;

View File

@ -78,9 +78,6 @@ EmojiColorVariants gEmojiVariants;
RecentStickerPreload gRecentStickersPreload; RecentStickerPreload gRecentStickersPreload;
RecentStickerPack gRecentStickers; RecentStickerPack gRecentStickers;
SavedGifs gSavedGifs;
TimeMs gLastSavedGifsUpdate = 0;
RecentHashtagPack gRecentWriteHashtags, gRecentSearchHashtags; RecentHashtagPack gRecentWriteHashtags, gRecentSearchHashtags;
RecentInlineBots gRecentInlineBots; RecentInlineBots gRecentInlineBots;

View File

@ -168,7 +168,6 @@ DeclareSetting(RecentEmojiPreload, RecentEmojiPreload);
DeclareRefSetting(EmojiColorVariants, EmojiVariants); DeclareRefSetting(EmojiColorVariants, EmojiVariants);
class DocumentData; class DocumentData;
typedef QVector<DocumentData*> StickerPack;
typedef QList<QPair<DocumentData*, int16> > RecentStickerPackOld; typedef QList<QPair<DocumentData*, int16> > RecentStickerPackOld;
typedef QVector<QPair<uint64, ushort> > RecentStickerPreload; typedef QVector<QPair<uint64, ushort> > RecentStickerPreload;
@ -178,12 +177,6 @@ DeclareRefSetting(RecentStickerPack, RecentStickers);
RecentStickerPack &cGetRecentStickers(); RecentStickerPack &cGetRecentStickers();
typedef QMap<EmojiPtr, StickerPack> StickersByEmojiMap;
typedef QVector<DocumentData*> SavedGifs;
DeclareRefSetting(SavedGifs, SavedGifs);
DeclareSetting(TimeMs, LastSavedGifsUpdate);
typedef QList<QPair<QString, ushort> > RecentHashtagPack; typedef QList<QPair<QString, ushort> > RecentHashtagPack;
DeclareRefSetting(RecentHashtagPack, RecentWriteHashtags); DeclareRefSetting(RecentHashtagPack, RecentWriteHashtags);
DeclareSetting(RecentHashtagPack, RecentSearchHashtags); DeclareSetting(RecentHashtagPack, RecentSearchHashtags);

View File

@ -3198,7 +3198,7 @@ void _writeStickerSet(QDataStream &stream, const Stickers::Set &set) {
} }
stream << quint64(set.id) << quint64(set.access) << set.title << set.shortName << qint32(set.stickers.size()) << qint32(set.hash) << qint32(set.flags); stream << quint64(set.id) << quint64(set.access) << set.title << set.shortName << qint32(set.stickers.size()) << qint32(set.hash) << qint32(set.flags);
for (StickerPack::const_iterator j = set.stickers.cbegin(), e = set.stickers.cend(); j != e; ++j) { for (auto j = set.stickers.cbegin(), e = set.stickers.cend(); j != e; ++j) {
Serialize::Document::writeToStream(stream, *j); Serialize::Document::writeToStream(stream, *j);
} }
@ -3226,7 +3226,7 @@ template <typename CheckSet>
void _writeStickerSets(FileKey &stickersKey, CheckSet checkSet, const Stickers::Order &order) { void _writeStickerSets(FileKey &stickersKey, CheckSet checkSet, const Stickers::Order &order) {
if (!_working()) return; if (!_working()) return;
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
if (sets.isEmpty()) { if (sets.isEmpty()) {
if (stickersKey) { if (stickersKey) {
clearKey(stickersKey); clearKey(stickersKey);
@ -3304,7 +3304,7 @@ void _readStickerSets(FileKey &stickersKey, Stickers::Order *outOrder = nullptr,
bool readingInstalled = (readingFlags == MTPDstickerSet::Flag::f_installed); bool readingInstalled = (readingFlags == MTPDstickerSet::Flag::f_installed);
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
if (outOrder) outOrder->clear(); if (outOrder) outOrder->clear();
quint32 cnt; quint32 cnt;
@ -3406,7 +3406,7 @@ void _readStickerSets(FileKey &stickersKey, Stickers::Order *outOrder = nullptr,
QString emojiString; QString emojiString;
qint32 stickersCount; qint32 stickersCount;
stickers.stream >> emojiString >> stickersCount; stickers.stream >> emojiString >> stickersCount;
StickerPack pack; Stickers::Pack pack;
pack.reserve(stickersCount); pack.reserve(stickersCount);
for (int32 k = 0; k < stickersCount; ++k) { for (int32 k = 0; k < stickersCount; ++k) {
quint64 id; quint64 id;
@ -3460,7 +3460,7 @@ void writeInstalledStickers() {
return StickerSetCheckResult::Skip; return StickerSetCheckResult::Skip;
} }
return StickerSetCheckResult::Write; return StickerSetCheckResult::Write;
}, Global::StickerSetsOrder()); }, Auth().data().stickerSetsOrder());
} }
void writeFeaturedStickers() { void writeFeaturedStickers() {
@ -3479,7 +3479,7 @@ void writeFeaturedStickers() {
return StickerSetCheckResult::Skip; return StickerSetCheckResult::Skip;
} }
return StickerSetCheckResult::Write; return StickerSetCheckResult::Write;
}, Global::FeaturedStickerSetsOrder()); }, Auth().data().featuredStickerSetsOrder());
} }
void writeRecentStickers() { void writeRecentStickers() {
@ -3512,7 +3512,7 @@ void writeArchivedStickers() {
return StickerSetCheckResult::Skip; return StickerSetCheckResult::Skip;
} }
return StickerSetCheckResult::Write; return StickerSetCheckResult::Write;
}, Global::ArchivedStickerSetsOrder()); }, Auth().data().archivedStickerSetsOrder());
} }
void importOldRecentStickers() { void importOldRecentStickers() {
@ -3526,10 +3526,10 @@ void importOldRecentStickers() {
return; return;
} }
auto &sets = Global::RefStickerSets(); auto &sets = Auth().data().stickerSetsRef();
sets.clear(); sets.clear();
auto &order = Global::RefStickerSetsOrder(); auto &order = Auth().data().stickerSetsOrderRef();
order.clear(); order.clear();
auto &recent = cRefRecentStickers(); auto &recent = cRefRecentStickers();
@ -3596,25 +3596,22 @@ void readInstalledStickers() {
return importOldRecentStickers(); return importOldRecentStickers();
} }
Global::RefStickerSets().clear(); Auth().data().stickerSetsRef().clear();
_readStickerSets(_installedStickersKey, &Global::RefStickerSetsOrder(), MTPDstickerSet::Flag::f_installed); _readStickerSets(_installedStickersKey, &Auth().data().stickerSetsOrderRef(), MTPDstickerSet::Flag::f_installed);
} }
void readFeaturedStickers() { void readFeaturedStickers() {
_readStickerSets(_featuredStickersKey, &Global::RefFeaturedStickerSetsOrder(), MTPDstickerSet::Flags() | MTPDstickerSet_ClientFlag::f_featured); _readStickerSets(_featuredStickersKey, &Auth().data().featuredStickerSetsOrderRef(), MTPDstickerSet::Flags() | MTPDstickerSet_ClientFlag::f_featured);
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
int unreadCount = 0; int unreadCount = 0;
for_const (auto setId, Global::FeaturedStickerSetsOrder()) { for_const (auto setId, Auth().data().featuredStickerSetsOrder()) {
auto it = sets.constFind(setId); auto it = sets.constFind(setId);
if (it != sets.cend() && (it->flags & MTPDstickerSet_ClientFlag::f_unread)) { if (it != sets.cend() && (it->flags & MTPDstickerSet_ClientFlag::f_unread)) {
++unreadCount; ++unreadCount;
} }
} }
if (Global::FeaturedStickerSetsUnreadCount() != unreadCount) { Auth().data().setFeaturedStickerSetsUnreadCount(unreadCount);
Global::SetFeaturedStickerSetsUnreadCount(unreadCount);
Global::RefFeaturedStickerSetsUnreadCountChanged().notify();
}
} }
void readRecentStickers() { void readRecentStickers() {
@ -3628,7 +3625,7 @@ void readFavedStickers() {
void readArchivedStickers() { void readArchivedStickers() {
static bool archivedStickersRead = false; static bool archivedStickersRead = false;
if (!archivedStickersRead) { if (!archivedStickersRead) {
_readStickerSets(_archivedStickersKey, &Global::RefArchivedStickerSetsOrder()); _readStickerSets(_archivedStickersKey, &Auth().data().archivedStickerSetsOrderRef());
archivedStickersRead = true; archivedStickersRead = true;
} }
} }
@ -3644,7 +3641,7 @@ int32 countDocumentVectorHash(const QVector<DocumentData*> vector) {
} }
int32 countSpecialStickerSetHash(uint64 setId) { int32 countSpecialStickerSetHash(uint64 setId) {
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
auto it = sets.constFind(setId); auto it = sets.constFind(setId);
if (it != sets.cend()) { if (it != sets.cend()) {
return countDocumentVectorHash(it->stickers); return countDocumentVectorHash(it->stickers);
@ -3655,8 +3652,8 @@ int32 countSpecialStickerSetHash(uint64 setId) {
int32 countStickersHash(bool checkOutdatedInfo) { int32 countStickersHash(bool checkOutdatedInfo) {
uint32 acc = 0; uint32 acc = 0;
bool foundOutdated = false; bool foundOutdated = false;
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
auto &order = Global::StickerSetsOrder(); auto &order = Auth().data().stickerSetsOrder();
for (auto i = order.cbegin(), e = order.cend(); i != e; ++i) { for (auto i = order.cbegin(), e = order.cend(); i != e; ++i) {
auto j = sets.constFind(*i); auto j = sets.constFind(*i);
if (j != sets.cend()) { if (j != sets.cend()) {
@ -3681,8 +3678,8 @@ int32 countFavedStickersHash() {
int32 countFeaturedStickersHash() { int32 countFeaturedStickersHash() {
uint32 acc = 0; uint32 acc = 0;
auto &sets = Global::StickerSets(); auto &sets = Auth().data().stickerSets();
auto &featured = Global::FeaturedStickerSetsOrder(); auto &featured = Auth().data().featuredStickerSetsOrder();
for_const (auto setId, featured) { for_const (auto setId, featured) {
acc = (acc * 20261) + uint32(setId >> 32); acc = (acc * 20261) + uint32(setId >> 32);
acc = (acc * 20261) + uint32(setId & 0xFFFFFFFF); acc = (acc * 20261) + uint32(setId & 0xFFFFFFFF);
@ -3696,13 +3693,13 @@ int32 countFeaturedStickersHash() {
} }
int32 countSavedGifsHash() { int32 countSavedGifsHash() {
return countDocumentVectorHash(cSavedGifs()); return countDocumentVectorHash(Auth().data().savedGifs());
} }
void writeSavedGifs() { void writeSavedGifs() {
if (!_working()) return; if (!_working()) return;
auto &saved = cSavedGifs(); auto &saved = Auth().data().savedGifs();
if (saved.isEmpty()) { if (saved.isEmpty()) {
if (_savedGifsKey) { if (_savedGifsKey) {
clearKey(_savedGifsKey); clearKey(_savedGifsKey);
@ -3742,7 +3739,7 @@ void readSavedGifs() {
return; return;
} }
SavedGifs &saved(cRefSavedGifs()); auto &saved = Auth().data().savedGifsRef();
saved.clear(); saved.clear();
quint32 cnt; quint32 cnt;

View File

@ -21,6 +21,7 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org
#include "storage/serialize_document.h" #include "storage/serialize_document.h"
#include "storage/serialize_common.h" #include "storage/serialize_common.h"
#include "chat_helpers/stickers.h"
namespace { namespace {

View File

@ -3632,8 +3632,8 @@ void MaskedInputField::keyPressEvent(QKeyEvent *e) {
QLineEdit::keyPressEvent(e); QLineEdit::keyPressEvent(e);
} }
QString newText(text()); auto newText = text();
int32 newCursor(cursorPosition()); auto newCursor = cursorPosition();
if (wasText == newText && wasCursor == newCursor) { // call correct manually if (wasText == newText && wasCursor == newCursor) { // call correct manually
correctValue(wasText, wasCursor, newText, newCursor); correctValue(wasText, wasCursor, newText, newCursor);
_oldtext = newText; _oldtext = newText;
@ -3700,7 +3700,11 @@ void CountryCodeInput::codeSelected(const QString &code) {
emit changed(); emit changed();
} }
void CountryCodeInput::correctValue(const QString &was, int32 wasCursor, QString &now, int32 &nowCursor) { void CountryCodeInput::correctValue(
const QString &was,
int wasCursor,
QString &now,
int &nowCursor) {
QString newText, addToNumber; QString newText, addToNumber;
int oldPos(nowCursor), newPos(-1), oldLen(now.length()), start = 0, digits = 5; int oldPos(nowCursor), newPos(-1), oldLen(now.length()), start = 0, digits = 5;
newText.reserve(oldLen + 1); newText.reserve(oldLen + 1);
@ -3767,7 +3771,11 @@ void PhonePartInput::keyPressEvent(QKeyEvent *e) {
} }
} }
void PhonePartInput::correctValue(const QString &was, int32 wasCursor, QString &now, int32 &nowCursor) { void PhonePartInput::correctValue(
const QString &was,
int wasCursor,
QString &now,
int &nowCursor) {
QString newText; QString newText;
int oldPos(nowCursor), newPos(-1), oldLen(now.length()), digitCount = 0; int oldPos(nowCursor), newPos(-1), oldLen(now.length()), digitCount = 0;
for (int i = 0; i < oldLen; ++i) { for (int i = 0; i < oldLen; ++i) {
@ -3875,7 +3883,11 @@ PortInput::PortInput(QWidget *parent, const style::InputField &st, base::lambda<
} }
} }
void PortInput::correctValue(const QString &was, int32 wasCursor, QString &now, int32 &nowCursor) { void PortInput::correctValue(
const QString &was,
int wasCursor,
QString &now,
int &nowCursor) {
QString newText; QString newText;
newText.reserve(now.size()); newText.reserve(now.size());
auto newPos = nowCursor; auto newPos = nowCursor;
@ -3916,7 +3928,11 @@ void UsernameInput::paintAdditionalPlaceholder(Painter &p, TimeMs ms) {
} }
} }
void UsernameInput::correctValue(const QString &was, int32 wasCursor, QString &now, int32 &nowCursor) { void UsernameInput::correctValue(
const QString &was,
int wasCursor,
QString &now,
int &nowCursor) {
auto newPos = nowCursor; auto newPos = nowCursor;
auto from = 0, len = now.size(); auto from = 0, len = now.size();
for (; from < len; ++from) { for (; from < len; ++from) {
@ -3982,7 +3998,11 @@ void PhoneInput::paintAdditionalPlaceholder(Painter &p, TimeMs ms) {
} }
} }
void PhoneInput::correctValue(const QString &was, int32 wasCursor, QString &now, int32 &nowCursor) { void PhoneInput::correctValue(
const QString &was,
int wasCursor,
QString &now,
int &nowCursor) {
auto digits = now; auto digits = now;
digits.replace(QRegularExpression(qsl("[^\\d]")), QString()); digits.replace(QRegularExpression(qsl("[^\\d]")), QString());
_pattern = phoneNumberParse(digits); _pattern = phoneNumberParse(digits);

View File

@ -142,7 +142,10 @@ protected:
void dropEvent(QDropEvent *e) override; void dropEvent(QDropEvent *e) override;
void contextMenuEvent(QContextMenuEvent *e) override; void contextMenuEvent(QContextMenuEvent *e) override;
virtual void correctValue(const QString &was, QString &now, TagList &nowTags) { virtual void correctValue(
const QString &was,
QString &now,
TagList &nowTags) {
} }
void insertEmoji(EmojiPtr emoji, QTextCursor c); void insertEmoji(EmojiPtr emoji, QTextCursor c);
@ -755,7 +758,11 @@ protected:
void contextMenuEvent(QContextMenuEvent *e) override; void contextMenuEvent(QContextMenuEvent *e) override;
void inputMethodEvent(QInputMethodEvent *e) override; void inputMethodEvent(QInputMethodEvent *e) override;
virtual void correctValue(const QString &was, int wasCursor, QString &now, int &nowCursor) { virtual void correctValue(
const QString &was,
int wasCursor,
QString &now,
int &nowCursor) {
} }
void setCorrectedText(QString &now, int &nowCursor, const QString &newText, int newPos); void setCorrectedText(QString &now, int &nowCursor, const QString &newText, int newPos);
@ -832,7 +839,11 @@ signals:
void addedToNumber(const QString &added); void addedToNumber(const QString &added);
protected: protected:
void correctValue(const QString &was, int wasCursor, QString &now, int &nowCursor) override; void correctValue(
const QString &was,
int wasCursor,
QString &now,
int &nowCursor) override;
private: private:
bool _nosignal; bool _nosignal;
@ -855,7 +866,11 @@ signals:
protected: protected:
void keyPressEvent(QKeyEvent *e) override; void keyPressEvent(QKeyEvent *e) override;
void correctValue(const QString &was, int wasCursor, QString &now, int &nowCursor) override; void correctValue(
const QString &was,
int wasCursor,
QString &now,
int &nowCursor) override;
void paintAdditionalPlaceholder(Painter &p, TimeMs ms) override; void paintAdditionalPlaceholder(Painter &p, TimeMs ms) override;
private: private:
@ -875,7 +890,11 @@ public:
PortInput(QWidget *parent, const style::InputField &st, base::lambda<QString()> placeholderFactory, const QString &val); PortInput(QWidget *parent, const style::InputField &st, base::lambda<QString()> placeholderFactory, const QString &val);
protected: protected:
void correctValue(const QString &was, int wasCursor, QString &now, int &nowCursor) override; void correctValue(
const QString &was,
int wasCursor,
QString &now,
int &nowCursor) override;
}; };
@ -886,7 +905,11 @@ public:
void setLinkPlaceholder(const QString &placeholder); void setLinkPlaceholder(const QString &placeholder);
protected: protected:
void correctValue(const QString &was, int wasCursor, QString &now, int &nowCursor) override; void correctValue(
const QString &was,
int wasCursor,
QString &now,
int &nowCursor) override;
void paintAdditionalPlaceholder(Painter &p, TimeMs ms) override; void paintAdditionalPlaceholder(Painter &p, TimeMs ms) override;
private: private:
@ -903,7 +926,11 @@ public:
protected: protected:
void focusInEvent(QFocusEvent *e) override; void focusInEvent(QFocusEvent *e) override;
void correctValue(const QString &was, int wasCursor, QString &now, int &nowCursor) override; void correctValue(
const QString &was,
int wasCursor,
QString &now,
int &nowCursor) override;
void paintAdditionalPlaceholder(Painter &p, TimeMs ms) override; void paintAdditionalPlaceholder(Painter &p, TimeMs ms) override;
private: private: