mirror of
https://github.com/AyuGram/AyuGramDesktop.git
synced 2025-06-06 15:13:57 +02:00
Show chat intro in an empty chat.
This commit is contained in:
parent
7f4d13c54a
commit
85554d19e4
12 changed files with 194 additions and 293 deletions
|
@ -2302,7 +2302,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
"lng_chat_intro_title" = "Intro";
|
"lng_chat_intro_title" = "Intro";
|
||||||
"lng_chat_intro_subtitle" = "Customize your intro";
|
"lng_chat_intro_subtitle" = "Customize your intro";
|
||||||
"lng_chat_intro_default_title" = "No messages here yet...";
|
"lng_chat_intro_default_title" = "No messages here yet...";
|
||||||
"lng_chat_intro_default_message" = "Send a message or tap on the greeting below";
|
"lng_chat_intro_default_message" = "Send a message or click on the greeting below";
|
||||||
"lng_chat_intro_enter_title" = "Enter Title";
|
"lng_chat_intro_enter_title" = "Enter Title";
|
||||||
"lng_chat_intro_enter_message" = "Enter Message";
|
"lng_chat_intro_enter_message" = "Enter Message";
|
||||||
"lng_chat_intro_choose_sticker" = "Choose Sticker";
|
"lng_chat_intro_choose_sticker" = "Choose Sticker";
|
||||||
|
|
|
@ -153,8 +153,10 @@ BusinessRecipients FromMTP(
|
||||||
}
|
}
|
||||||
|
|
||||||
BusinessDetails FromMTP(
|
BusinessDetails FromMTP(
|
||||||
|
not_null<Session*> owner,
|
||||||
const tl::conditional<MTPBusinessWorkHours> &hours,
|
const tl::conditional<MTPBusinessWorkHours> &hours,
|
||||||
const tl::conditional<MTPBusinessLocation> &location) {
|
const tl::conditional<MTPBusinessLocation> &location,
|
||||||
|
const tl::conditional<MTPBusinessIntro> &intro) {
|
||||||
auto result = BusinessDetails();
|
auto result = BusinessDetails();
|
||||||
if (hours) {
|
if (hours) {
|
||||||
const auto &data = hours->data();
|
const auto &data = hours->data();
|
||||||
|
@ -179,6 +181,17 @@ BusinessDetails FromMTP(
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if (intro) {
|
||||||
|
const auto &data = intro->data();
|
||||||
|
result.intro.title = qs(data.vtitle());
|
||||||
|
result.intro.description = qs(data.vdescription());
|
||||||
|
if (const auto document = data.vsticker()) {
|
||||||
|
result.intro.sticker = owner->processDocument(*document);
|
||||||
|
if (!result.intro.sticker->sticker()) {
|
||||||
|
result.intro.sticker = nullptr;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -334,22 +347,4 @@ WorkingIntervals ReplaceDayIntervals(
|
||||||
return result.normalized();
|
return result.normalized();
|
||||||
}
|
}
|
||||||
|
|
||||||
ChatIntro FromMTP(
|
|
||||||
not_null<Session*> owner,
|
|
||||||
const tl::conditional<MTPBusinessIntro> &intro) {
|
|
||||||
auto result = ChatIntro();
|
|
||||||
if (intro) {
|
|
||||||
const auto &data = intro->data();
|
|
||||||
result.title = qs(data.vtitle());
|
|
||||||
result.description = qs(data.vdescription());
|
|
||||||
if (const auto document = data.vsticker()) {
|
|
||||||
result.sticker = owner->processDocument(*document);
|
|
||||||
if (!result.sticker->sticker()) {
|
|
||||||
result.sticker = nullptr;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace Data
|
} // namespace Data
|
||||||
|
|
|
@ -182,12 +182,27 @@ struct BusinessLocation {
|
||||||
const BusinessLocation &b) = default;
|
const BusinessLocation &b) = default;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct ChatIntro {
|
||||||
|
QString title;
|
||||||
|
QString description;
|
||||||
|
DocumentData *sticker = nullptr;
|
||||||
|
|
||||||
|
explicit operator bool() const {
|
||||||
|
return !title.isEmpty() || !description.isEmpty();
|
||||||
|
}
|
||||||
|
|
||||||
|
friend inline bool operator==(
|
||||||
|
const ChatIntro &a,
|
||||||
|
const ChatIntro &b) = default;
|
||||||
|
};
|
||||||
|
|
||||||
struct BusinessDetails {
|
struct BusinessDetails {
|
||||||
WorkingHours hours;
|
WorkingHours hours;
|
||||||
BusinessLocation location;
|
BusinessLocation location;
|
||||||
|
ChatIntro intro;
|
||||||
|
|
||||||
explicit operator bool() const {
|
explicit operator bool() const {
|
||||||
return hours || location;
|
return hours || location || intro;
|
||||||
}
|
}
|
||||||
|
|
||||||
friend inline bool operator==(
|
friend inline bool operator==(
|
||||||
|
@ -196,8 +211,10 @@ struct BusinessDetails {
|
||||||
};
|
};
|
||||||
|
|
||||||
[[nodiscard]] BusinessDetails FromMTP(
|
[[nodiscard]] BusinessDetails FromMTP(
|
||||||
|
not_null<Session*> owner,
|
||||||
const tl::conditional<MTPBusinessWorkHours> &hours,
|
const tl::conditional<MTPBusinessWorkHours> &hours,
|
||||||
const tl::conditional<MTPBusinessLocation> &location);
|
const tl::conditional<MTPBusinessLocation> &location,
|
||||||
|
const tl::conditional<MTPBusinessIntro> &intro);
|
||||||
|
|
||||||
enum class AwayScheduleType : uchar {
|
enum class AwayScheduleType : uchar {
|
||||||
Never = 0,
|
Never = 0,
|
||||||
|
@ -252,22 +269,4 @@ struct GreetingSettings {
|
||||||
not_null<Session*> owner,
|
not_null<Session*> owner,
|
||||||
const tl::conditional<MTPBusinessGreetingMessage> &message);
|
const tl::conditional<MTPBusinessGreetingMessage> &message);
|
||||||
|
|
||||||
struct ChatIntro {
|
|
||||||
QString title;
|
|
||||||
QString description;
|
|
||||||
DocumentData *sticker = nullptr;
|
|
||||||
|
|
||||||
explicit operator bool() const {
|
|
||||||
return !title.isEmpty() || !description.isEmpty();
|
|
||||||
}
|
|
||||||
|
|
||||||
friend inline bool operator==(
|
|
||||||
const ChatIntro &a,
|
|
||||||
const ChatIntro &b) = default;
|
|
||||||
};
|
|
||||||
|
|
||||||
[[nodiscard]] ChatIntro FromMTP(
|
|
||||||
not_null<Session*> owner,
|
|
||||||
const tl::conditional<MTPBusinessIntro> &intro);
|
|
||||||
|
|
||||||
} // namespace Data
|
} // namespace Data
|
||||||
|
|
|
@ -96,6 +96,40 @@ void BusinessInfo::saveWorkingHours(
|
||||||
session->user()->setBusinessDetails(std::move(details));
|
session->user()->setBusinessDetails(std::move(details));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void BusinessInfo::saveChatIntro(ChatIntro data, Fn<void(QString)> fail) {
|
||||||
|
const auto session = &_owner->session();
|
||||||
|
auto details = session->user()->businessDetails();
|
||||||
|
const auto &was = details.intro;
|
||||||
|
if (was == data) {
|
||||||
|
return;
|
||||||
|
} else {
|
||||||
|
const auto session = &_owner->session();
|
||||||
|
using Flag = MTPaccount_UpdateBusinessIntro::Flag;
|
||||||
|
session->api().request(MTPaccount_UpdateBusinessIntro(
|
||||||
|
MTP_flags(data ? Flag::f_intro : Flag()),
|
||||||
|
MTP_inputBusinessIntro(
|
||||||
|
MTP_flags(data.sticker
|
||||||
|
? MTPDinputBusinessIntro::Flag::f_sticker
|
||||||
|
: MTPDinputBusinessIntro::Flag()),
|
||||||
|
MTP_string(data.title),
|
||||||
|
MTP_string(data.description),
|
||||||
|
(data.sticker
|
||||||
|
? data.sticker->mtpInput()
|
||||||
|
: MTP_inputDocumentEmpty()))
|
||||||
|
)).fail([=](const MTP::Error &error) {
|
||||||
|
auto details = session->user()->businessDetails();
|
||||||
|
details.intro = was;
|
||||||
|
session->user()->setBusinessDetails(std::move(details));
|
||||||
|
if (fail) {
|
||||||
|
fail(error.type());
|
||||||
|
}
|
||||||
|
}).send();
|
||||||
|
}
|
||||||
|
|
||||||
|
details.intro = std::move(data);
|
||||||
|
session->user()->setBusinessDetails(std::move(details));
|
||||||
|
}
|
||||||
|
|
||||||
void BusinessInfo::applyAwaySettings(AwaySettings data) {
|
void BusinessInfo::applyAwaySettings(AwaySettings data) {
|
||||||
if (_awaySettings == data) {
|
if (_awaySettings == data) {
|
||||||
return;
|
return;
|
||||||
|
@ -184,54 +218,6 @@ rpl::producer<> BusinessInfo::greetingSettingsChanged() const {
|
||||||
return _greetingSettingsChanged.events();
|
return _greetingSettingsChanged.events();
|
||||||
}
|
}
|
||||||
|
|
||||||
void BusinessInfo::saveChatIntro(ChatIntro data, Fn<void(QString)> fail) {
|
|
||||||
const auto &was = _chatIntro;
|
|
||||||
if (was == data) {
|
|
||||||
return;
|
|
||||||
} else {
|
|
||||||
const auto session = &_owner->session();
|
|
||||||
using Flag = MTPaccount_UpdateBusinessIntro::Flag;
|
|
||||||
session->api().request(MTPaccount_UpdateBusinessIntro(
|
|
||||||
MTP_flags(data ? Flag::f_intro : Flag()),
|
|
||||||
MTP_inputBusinessIntro(
|
|
||||||
MTP_flags(data.sticker ? MTPDinputBusinessIntro::Flag::f_sticker : MTPDinputBusinessIntro::Flag()),
|
|
||||||
MTP_string(data.title),
|
|
||||||
MTP_string(data.description),
|
|
||||||
(data.sticker
|
|
||||||
? data.sticker->mtpInput()
|
|
||||||
: MTP_inputDocumentEmpty()))
|
|
||||||
)).fail([=](const MTP::Error &error) {
|
|
||||||
_chatIntro = was;
|
|
||||||
_chatIntroChanged.fire({});
|
|
||||||
if (fail) {
|
|
||||||
fail(error.type());
|
|
||||||
}
|
|
||||||
}).send();
|
|
||||||
}
|
|
||||||
_chatIntro = std::move(data);
|
|
||||||
_chatIntroChanged.fire({});
|
|
||||||
}
|
|
||||||
|
|
||||||
void BusinessInfo::applyChatIntro(ChatIntro data) {
|
|
||||||
if (_chatIntro == data) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
_chatIntro = data;
|
|
||||||
_chatIntroChanged.fire({});
|
|
||||||
}
|
|
||||||
|
|
||||||
ChatIntro BusinessInfo::chatIntro() const {
|
|
||||||
return _chatIntro.value_or(ChatIntro());
|
|
||||||
}
|
|
||||||
|
|
||||||
bool BusinessInfo::chatIntroLoaded() const {
|
|
||||||
return _chatIntro.has_value();
|
|
||||||
}
|
|
||||||
|
|
||||||
rpl::producer<> BusinessInfo::chatIntroChanged() const {
|
|
||||||
return _chatIntroChanged.events();
|
|
||||||
}
|
|
||||||
|
|
||||||
void BusinessInfo::preload() {
|
void BusinessInfo::preload() {
|
||||||
preloadTimezones();
|
preloadTimezones();
|
||||||
}
|
}
|
||||||
|
|
|
@ -21,6 +21,7 @@ public:
|
||||||
void preload();
|
void preload();
|
||||||
|
|
||||||
void saveWorkingHours(WorkingHours data, Fn<void(QString)> fail);
|
void saveWorkingHours(WorkingHours data, Fn<void(QString)> fail);
|
||||||
|
void saveChatIntro(ChatIntro data, Fn<void(QString)> fail);
|
||||||
|
|
||||||
void saveAwaySettings(AwaySettings data, Fn<void(QString)> fail);
|
void saveAwaySettings(AwaySettings data, Fn<void(QString)> fail);
|
||||||
void applyAwaySettings(AwaySettings data);
|
void applyAwaySettings(AwaySettings data);
|
||||||
|
@ -36,12 +37,6 @@ public:
|
||||||
[[nodiscard]] bool greetingSettingsLoaded() const;
|
[[nodiscard]] bool greetingSettingsLoaded() const;
|
||||||
[[nodiscard]] rpl::producer<> greetingSettingsChanged() const;
|
[[nodiscard]] rpl::producer<> greetingSettingsChanged() const;
|
||||||
|
|
||||||
void saveChatIntro(ChatIntro data, Fn<void(QString)> fail);
|
|
||||||
void applyChatIntro(ChatIntro data);
|
|
||||||
[[nodiscard]] ChatIntro chatIntro() const;
|
|
||||||
[[nodiscard]] bool chatIntroLoaded() const;
|
|
||||||
[[nodiscard]] rpl::producer<> chatIntroChanged() const;
|
|
||||||
|
|
||||||
void preloadTimezones();
|
void preloadTimezones();
|
||||||
[[nodiscard]] bool timezonesLoaded() const;
|
[[nodiscard]] bool timezonesLoaded() const;
|
||||||
[[nodiscard]] rpl::producer<Timezones> timezonesValue() const;
|
[[nodiscard]] rpl::producer<Timezones> timezonesValue() const;
|
||||||
|
@ -57,9 +52,6 @@ private:
|
||||||
std::optional<GreetingSettings> _greetingSettings;
|
std::optional<GreetingSettings> _greetingSettings;
|
||||||
rpl::event_stream<> _greetingSettingsChanged;
|
rpl::event_stream<> _greetingSettingsChanged;
|
||||||
|
|
||||||
std::optional<ChatIntro> _chatIntro;
|
|
||||||
rpl::event_stream<> _chatIntroChanged;
|
|
||||||
|
|
||||||
mtpRequestId _timezonesRequestId = 0;
|
mtpRequestId _timezonesRequestId = 0;
|
||||||
int32 _timezonesHash = 0;
|
int32 _timezonesHash = 0;
|
||||||
|
|
||||||
|
|
|
@ -594,15 +594,15 @@ void ApplyUserUpdate(not_null<UserData*> user, const MTPDuserFull &update) {
|
||||||
}
|
}
|
||||||
|
|
||||||
user->setBusinessDetails(FromMTP(
|
user->setBusinessDetails(FromMTP(
|
||||||
|
&user->owner(),
|
||||||
update.vbusiness_work_hours(),
|
update.vbusiness_work_hours(),
|
||||||
update.vbusiness_location()));
|
update.vbusiness_location(),
|
||||||
|
update.vbusiness_intro()));
|
||||||
if (user->isSelf()) {
|
if (user->isSelf()) {
|
||||||
user->owner().businessInfo().applyAwaySettings(
|
user->owner().businessInfo().applyAwaySettings(
|
||||||
FromMTP(&user->owner(), update.vbusiness_away_message()));
|
FromMTP(&user->owner(), update.vbusiness_away_message()));
|
||||||
user->owner().businessInfo().applyGreetingSettings(
|
user->owner().businessInfo().applyGreetingSettings(
|
||||||
FromMTP(&user->owner(), update.vbusiness_greeting_message()));
|
FromMTP(&user->owner(), update.vbusiness_greeting_message()));
|
||||||
user->owner().businessInfo().applyChatIntro(
|
|
||||||
FromMTP(&user->owner(), update.vbusiness_intro()));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
user->owner().stories().apply(user, update.vstories());
|
user->owner().stories().apply(user, update.vstories());
|
||||||
|
|
|
@ -502,7 +502,7 @@ void Stickers::undoInstallLocally(uint64 setId) {
|
||||||
Ui::LayerOption::KeepOther);
|
Ui::LayerOption::KeepOther);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Stickers::isFaved(not_null<const DocumentData*> document) {
|
bool Stickers::isFaved(not_null<const DocumentData*> document) const {
|
||||||
const auto &sets = this->sets();
|
const auto &sets = this->sets();
|
||||||
const auto it = sets.find(FavedSetId);
|
const auto it = sets.find(FavedSetId);
|
||||||
if (it == sets.cend()) {
|
if (it == sets.cend()) {
|
||||||
|
|
|
@ -80,13 +80,13 @@ public:
|
||||||
|
|
||||||
void incrementSticker(not_null<DocumentData*> document);
|
void incrementSticker(not_null<DocumentData*> document);
|
||||||
|
|
||||||
bool updateNeeded(crl::time now) const {
|
[[nodiscard]] bool updateNeeded(crl::time now) const {
|
||||||
return updateNeeded(_lastUpdate, now);
|
return updateNeeded(_lastUpdate, now);
|
||||||
}
|
}
|
||||||
void setLastUpdate(crl::time update) {
|
void setLastUpdate(crl::time update) {
|
||||||
_lastUpdate = update;
|
_lastUpdate = update;
|
||||||
}
|
}
|
||||||
bool recentUpdateNeeded(crl::time now) const {
|
[[nodiscard]] bool recentUpdateNeeded(crl::time now) const {
|
||||||
return updateNeeded(_lastRecentUpdate, now);
|
return updateNeeded(_lastRecentUpdate, now);
|
||||||
}
|
}
|
||||||
void setLastRecentUpdate(crl::time update) {
|
void setLastRecentUpdate(crl::time update) {
|
||||||
|
@ -95,19 +95,19 @@ public:
|
||||||
}
|
}
|
||||||
_lastRecentUpdate = update;
|
_lastRecentUpdate = update;
|
||||||
}
|
}
|
||||||
bool masksUpdateNeeded(crl::time now) const {
|
[[nodiscard]] bool masksUpdateNeeded(crl::time now) const {
|
||||||
return updateNeeded(_lastMasksUpdate, now);
|
return updateNeeded(_lastMasksUpdate, now);
|
||||||
}
|
}
|
||||||
void setLastMasksUpdate(crl::time update) {
|
void setLastMasksUpdate(crl::time update) {
|
||||||
_lastMasksUpdate = update;
|
_lastMasksUpdate = update;
|
||||||
}
|
}
|
||||||
bool emojiUpdateNeeded(crl::time now) const {
|
[[nodiscard]] bool emojiUpdateNeeded(crl::time now) const {
|
||||||
return updateNeeded(_lastEmojiUpdate, now);
|
return updateNeeded(_lastEmojiUpdate, now);
|
||||||
}
|
}
|
||||||
void setLastEmojiUpdate(crl::time update) {
|
void setLastEmojiUpdate(crl::time update) {
|
||||||
_lastEmojiUpdate = update;
|
_lastEmojiUpdate = update;
|
||||||
}
|
}
|
||||||
bool recentAttachedUpdateNeeded(crl::time now) const {
|
[[nodiscard]] bool recentAttachedUpdateNeeded(crl::time now) const {
|
||||||
return updateNeeded(_lastRecentAttachedUpdate, now);
|
return updateNeeded(_lastRecentAttachedUpdate, now);
|
||||||
}
|
}
|
||||||
void setLastRecentAttachedUpdate(crl::time update) {
|
void setLastRecentAttachedUpdate(crl::time update) {
|
||||||
|
@ -116,31 +116,31 @@ public:
|
||||||
}
|
}
|
||||||
_lastRecentAttachedUpdate = update;
|
_lastRecentAttachedUpdate = update;
|
||||||
}
|
}
|
||||||
bool favedUpdateNeeded(crl::time now) const {
|
[[nodiscard]] bool favedUpdateNeeded(crl::time now) const {
|
||||||
return updateNeeded(_lastFavedUpdate, now);
|
return updateNeeded(_lastFavedUpdate, now);
|
||||||
}
|
}
|
||||||
void setLastFavedUpdate(crl::time update) {
|
void setLastFavedUpdate(crl::time update) {
|
||||||
_lastFavedUpdate = update;
|
_lastFavedUpdate = update;
|
||||||
}
|
}
|
||||||
bool featuredUpdateNeeded(crl::time now) const {
|
[[nodiscard]] bool featuredUpdateNeeded(crl::time now) const {
|
||||||
return updateNeeded(_lastFeaturedUpdate, now);
|
return updateNeeded(_lastFeaturedUpdate, now);
|
||||||
}
|
}
|
||||||
void setLastFeaturedUpdate(crl::time update) {
|
void setLastFeaturedUpdate(crl::time update) {
|
||||||
_lastFeaturedUpdate = update;
|
_lastFeaturedUpdate = update;
|
||||||
}
|
}
|
||||||
bool featuredEmojiUpdateNeeded(crl::time now) const {
|
[[nodiscard]] bool featuredEmojiUpdateNeeded(crl::time now) const {
|
||||||
return updateNeeded(_lastFeaturedEmojiUpdate, now);
|
return updateNeeded(_lastFeaturedEmojiUpdate, now);
|
||||||
}
|
}
|
||||||
void setLastFeaturedEmojiUpdate(crl::time update) {
|
void setLastFeaturedEmojiUpdate(crl::time update) {
|
||||||
_lastFeaturedEmojiUpdate = update;
|
_lastFeaturedEmojiUpdate = update;
|
||||||
}
|
}
|
||||||
bool savedGifsUpdateNeeded(crl::time now) const {
|
[[nodiscard]] bool savedGifsUpdateNeeded(crl::time now) const {
|
||||||
return updateNeeded(_lastSavedGifsUpdate, now);
|
return updateNeeded(_lastSavedGifsUpdate, now);
|
||||||
}
|
}
|
||||||
void setLastSavedGifsUpdate(crl::time update) {
|
void setLastSavedGifsUpdate(crl::time update) {
|
||||||
_lastSavedGifsUpdate = update;
|
_lastSavedGifsUpdate = update;
|
||||||
}
|
}
|
||||||
int featuredSetsUnreadCount() const {
|
[[nodiscard]] int featuredSetsUnreadCount() const {
|
||||||
return _featuredSetsUnreadCount.current();
|
return _featuredSetsUnreadCount.current();
|
||||||
}
|
}
|
||||||
void setFeaturedSetsUnreadCount(int count) {
|
void setFeaturedSetsUnreadCount(int count) {
|
||||||
|
@ -149,58 +149,58 @@ public:
|
||||||
[[nodiscard]] rpl::producer<int> featuredSetsUnreadCountValue() const {
|
[[nodiscard]] rpl::producer<int> featuredSetsUnreadCountValue() const {
|
||||||
return _featuredSetsUnreadCount.value();
|
return _featuredSetsUnreadCount.value();
|
||||||
}
|
}
|
||||||
const StickersSets &sets() const {
|
[[nodiscard]] const StickersSets &sets() const {
|
||||||
return _sets;
|
return _sets;
|
||||||
}
|
}
|
||||||
StickersSets &setsRef() {
|
[[nodiscard]] StickersSets &setsRef() {
|
||||||
return _sets;
|
return _sets;
|
||||||
}
|
}
|
||||||
const StickersSetsOrder &setsOrder() const {
|
[[nodiscard]] const StickersSetsOrder &setsOrder() const {
|
||||||
return _setsOrder;
|
return _setsOrder;
|
||||||
}
|
}
|
||||||
StickersSetsOrder &setsOrderRef() {
|
[[nodiscard]] StickersSetsOrder &setsOrderRef() {
|
||||||
return _setsOrder;
|
return _setsOrder;
|
||||||
}
|
}
|
||||||
const StickersSetsOrder &maskSetsOrder() const {
|
[[nodiscard]] const StickersSetsOrder &maskSetsOrder() const {
|
||||||
return _maskSetsOrder;
|
return _maskSetsOrder;
|
||||||
}
|
}
|
||||||
StickersSetsOrder &maskSetsOrderRef() {
|
[[nodiscard]] StickersSetsOrder &maskSetsOrderRef() {
|
||||||
return _maskSetsOrder;
|
return _maskSetsOrder;
|
||||||
}
|
}
|
||||||
const StickersSetsOrder &emojiSetsOrder() const {
|
[[nodiscard]] const StickersSetsOrder &emojiSetsOrder() const {
|
||||||
return _emojiSetsOrder;
|
return _emojiSetsOrder;
|
||||||
}
|
}
|
||||||
StickersSetsOrder &emojiSetsOrderRef() {
|
[[nodiscard]] StickersSetsOrder &emojiSetsOrderRef() {
|
||||||
return _emojiSetsOrder;
|
return _emojiSetsOrder;
|
||||||
}
|
}
|
||||||
const StickersSetsOrder &featuredSetsOrder() const {
|
[[nodiscard]] const StickersSetsOrder &featuredSetsOrder() const {
|
||||||
return _featuredSetsOrder;
|
return _featuredSetsOrder;
|
||||||
}
|
}
|
||||||
StickersSetsOrder &featuredSetsOrderRef() {
|
[[nodiscard]] StickersSetsOrder &featuredSetsOrderRef() {
|
||||||
return _featuredSetsOrder;
|
return _featuredSetsOrder;
|
||||||
}
|
}
|
||||||
const StickersSetsOrder &featuredEmojiSetsOrder() const {
|
[[nodiscard]] const StickersSetsOrder &featuredEmojiSetsOrder() const {
|
||||||
return _featuredEmojiSetsOrder;
|
return _featuredEmojiSetsOrder;
|
||||||
}
|
}
|
||||||
StickersSetsOrder &featuredEmojiSetsOrderRef() {
|
[[nodiscard]] StickersSetsOrder &featuredEmojiSetsOrderRef() {
|
||||||
return _featuredEmojiSetsOrder;
|
return _featuredEmojiSetsOrder;
|
||||||
}
|
}
|
||||||
const StickersSetsOrder &archivedSetsOrder() const {
|
[[nodiscard]] const StickersSetsOrder &archivedSetsOrder() const {
|
||||||
return _archivedSetsOrder;
|
return _archivedSetsOrder;
|
||||||
}
|
}
|
||||||
StickersSetsOrder &archivedSetsOrderRef() {
|
[[nodiscard]] StickersSetsOrder &archivedSetsOrderRef() {
|
||||||
return _archivedSetsOrder;
|
return _archivedSetsOrder;
|
||||||
}
|
}
|
||||||
const StickersSetsOrder &archivedMaskSetsOrder() const {
|
[[nodiscard]] const StickersSetsOrder &archivedMaskSetsOrder() const {
|
||||||
return _archivedMaskSetsOrder;
|
return _archivedMaskSetsOrder;
|
||||||
}
|
}
|
||||||
StickersSetsOrder &archivedMaskSetsOrderRef() {
|
[[nodiscard]] StickersSetsOrder &archivedMaskSetsOrderRef() {
|
||||||
return _archivedMaskSetsOrder;
|
return _archivedMaskSetsOrder;
|
||||||
}
|
}
|
||||||
const SavedGifs &savedGifs() const {
|
[[nodiscard]] const SavedGifs &savedGifs() const {
|
||||||
return _savedGifs;
|
return _savedGifs;
|
||||||
}
|
}
|
||||||
SavedGifs &savedGifsRef() {
|
[[nodiscard]] SavedGifs &savedGifsRef() {
|
||||||
return _savedGifs;
|
return _savedGifs;
|
||||||
}
|
}
|
||||||
void removeFromRecentSet(not_null<DocumentData*> document);
|
void removeFromRecentSet(not_null<DocumentData*> document);
|
||||||
|
@ -214,7 +214,7 @@ public:
|
||||||
const MTPDmessages_stickerSetInstallResultArchive &d);
|
const MTPDmessages_stickerSetInstallResultArchive &d);
|
||||||
void installLocally(uint64 setId);
|
void installLocally(uint64 setId);
|
||||||
void undoInstallLocally(uint64 setId);
|
void undoInstallLocally(uint64 setId);
|
||||||
bool isFaved(not_null<const DocumentData*> document);
|
[[nodiscard]] bool isFaved(not_null<const DocumentData*> document) const;
|
||||||
void setFaved(
|
void setFaved(
|
||||||
std::shared_ptr<ChatHelpers::Show> show,
|
std::shared_ptr<ChatHelpers::Show> show,
|
||||||
not_null<DocumentData*> document,
|
not_null<DocumentData*> document,
|
||||||
|
@ -235,12 +235,12 @@ public:
|
||||||
const MTPmessages_FeaturedStickers &result);
|
const MTPmessages_FeaturedStickers &result);
|
||||||
void gifsReceived(const QVector<MTPDocument> &items, uint64 hash);
|
void gifsReceived(const QVector<MTPDocument> &items, uint64 hash);
|
||||||
|
|
||||||
std::vector<not_null<DocumentData*>> getListByEmoji(
|
[[nodiscard]] std::vector<not_null<DocumentData*>> getListByEmoji(
|
||||||
std::vector<EmojiPtr> emoji,
|
std::vector<EmojiPtr> emoji,
|
||||||
uint64 seed,
|
uint64 seed,
|
||||||
bool forceAllResults = false);
|
bool forceAllResults = false);
|
||||||
std::optional<std::vector<not_null<EmojiPtr>>> getEmojiListFromSet(
|
[[nodiscard]] auto getEmojiListFromSet(not_null<DocumentData*> document)
|
||||||
not_null<DocumentData*> document);
|
-> std::optional<std::vector<not_null<EmojiPtr>>>;
|
||||||
|
|
||||||
not_null<StickersSet*> feedSet(const MTPStickerSet &data);
|
not_null<StickersSet*> feedSet(const MTPStickerSet &data);
|
||||||
not_null<StickersSet*> feedSet(const MTPStickerSetCovered &data);
|
not_null<StickersSet*> feedSet(const MTPStickerSetCovered &data);
|
||||||
|
@ -254,15 +254,14 @@ public:
|
||||||
const QVector<MTPDocument> &documents);
|
const QVector<MTPDocument> &documents);
|
||||||
void newSetReceived(const MTPDmessages_stickerSet &set);
|
void newSetReceived(const MTPDmessages_stickerSet &set);
|
||||||
|
|
||||||
QString getSetTitle(const MTPDstickerSet &s);
|
[[nodiscard]] QString getSetTitle(const MTPDstickerSet &s);
|
||||||
|
|
||||||
RecentStickerPack &getRecentPack() const;
|
[[nodiscard]] RecentStickerPack &getRecentPack() const;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
bool updateNeeded(crl::time lastUpdate, crl::time now) const {
|
[[nodiscard]] bool updateNeeded(crl::time last, crl::time now) const {
|
||||||
constexpr auto kUpdateTimeout = crl::time(3600'000);
|
constexpr auto kUpdateTimeout = crl::time(3600'000);
|
||||||
return (lastUpdate == 0)
|
return (last == 0) || (now >= last + kUpdateTimeout);
|
||||||
|| (now >= lastUpdate + kUpdateTimeout);
|
|
||||||
}
|
}
|
||||||
void checkFavedLimit(
|
void checkFavedLimit(
|
||||||
StickersSet &set,
|
StickersSet &set,
|
||||||
|
|
|
@ -4072,7 +4072,7 @@ void HistoryInner::refreshAboutView() {
|
||||||
_history->delegateMixin()->delegate());
|
_history->delegateMixin()->delegate());
|
||||||
}
|
}
|
||||||
if (!info->inited) {
|
if (!info->inited) {
|
||||||
session().api().requestFullPeer(_peer);
|
session().api().requestFullPeer(user);
|
||||||
}
|
}
|
||||||
} else if (user->meRequiresPremiumToWrite()
|
} else if (user->meRequiresPremiumToWrite()
|
||||||
&& !user->session().premium()
|
&& !user->session().premium()
|
||||||
|
@ -4082,8 +4082,15 @@ void HistoryInner::refreshAboutView() {
|
||||||
_history,
|
_history,
|
||||||
_history->delegateMixin()->delegate());
|
_history->delegateMixin()->delegate());
|
||||||
}
|
}
|
||||||
} else {
|
} else if (!historyHeight()) {
|
||||||
_aboutView = nullptr;
|
if (!_aboutView) {
|
||||||
|
_aboutView = std::make_unique<HistoryView::AboutView>(
|
||||||
|
_history,
|
||||||
|
_history->delegateMixin()->delegate());
|
||||||
|
}
|
||||||
|
if (!user->isFullLoaded()) {
|
||||||
|
session().api().requestFullPeer(user);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,6 +7,9 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
*/
|
*/
|
||||||
#include "history/view/history_view_about_view.h"
|
#include "history/view/history_view_about_view.h"
|
||||||
|
|
||||||
|
#include "api/api_premium.h"
|
||||||
|
#include "apiwrap.h"
|
||||||
|
#include "base/random.h"
|
||||||
#include "chat_helpers/stickers_lottie.h"
|
#include "chat_helpers/stickers_lottie.h"
|
||||||
#include "core/click_handler_types.h"
|
#include "core/click_handler_types.h"
|
||||||
#include "data/business/data_business_common.h"
|
#include "data/business/data_business_common.h"
|
||||||
|
@ -70,47 +73,11 @@ private:
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
class ChatIntroBox final : public ServiceBoxContent {
|
|
||||||
public:
|
|
||||||
ChatIntroBox(not_null<Element*> parent, Data::ChatIntro data);
|
|
||||||
~ChatIntroBox();
|
|
||||||
|
|
||||||
int width() override;
|
|
||||||
int top() override;
|
|
||||||
QSize size() override;
|
|
||||||
QString title() override;
|
|
||||||
TextWithEntities subtitle() override;
|
|
||||||
int buttonSkip() override;
|
|
||||||
rpl::producer<QString> button() override;
|
|
||||||
void draw(
|
|
||||||
Painter &p,
|
|
||||||
const PaintContext &context,
|
|
||||||
const QRect &geometry) override;
|
|
||||||
ClickHandlerPtr createViewLink() override;
|
|
||||||
|
|
||||||
bool hideServiceText() override {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
void stickerClearLoopPlayed() override;
|
|
||||||
std::unique_ptr<StickerPlayer> stickerTakePlayer(
|
|
||||||
not_null<DocumentData*> data,
|
|
||||||
const Lottie::ColorReplacements *replacements) override;
|
|
||||||
|
|
||||||
bool hasHeavyPart() override;
|
|
||||||
void unloadHeavyPart() override;
|
|
||||||
|
|
||||||
private:
|
|
||||||
const not_null<Element*> _parent;
|
|
||||||
const Data::ChatIntro _data;
|
|
||||||
mutable std::optional<Sticker> _sticker;
|
|
||||||
|
|
||||||
};
|
|
||||||
|
|
||||||
auto GenerateChatIntro(
|
auto GenerateChatIntro(
|
||||||
not_null<Element*> parent,
|
not_null<Element*> parent,
|
||||||
Element *replacing,
|
Element *replacing,
|
||||||
const Data::ChatIntro &data)
|
const Data::ChatIntro &data,
|
||||||
|
Fn<void(not_null<DocumentData*>)> helloChosen)
|
||||||
-> Fn<void(Fn<void(std::unique_ptr<MediaInBubble::Part>)>)> {
|
-> Fn<void(Fn<void(std::unique_ptr<MediaInBubble::Part>)>)> {
|
||||||
return [=](Fn<void(std::unique_ptr<MediaInBubble::Part>)> push) {
|
return [=](Fn<void(std::unique_ptr<MediaInBubble::Part>)> push) {
|
||||||
auto pushText = [&](
|
auto pushText = [&](
|
||||||
|
@ -137,8 +104,19 @@ auto GenerateChatIntro(
|
||||||
: st::chatIntroMargin);
|
: st::chatIntroMargin);
|
||||||
const auto sticker = [=] {
|
const auto sticker = [=] {
|
||||||
using Tag = ChatHelpers::StickerLottieSize;
|
using Tag = ChatHelpers::StickerLottieSize;
|
||||||
|
auto sticker = data.sticker;
|
||||||
|
if (!sticker) {
|
||||||
|
const auto api = &parent->history()->session().api();
|
||||||
|
const auto &list = api->premium().helloStickers();
|
||||||
|
if (!list.empty()) {
|
||||||
|
sticker = list[base::RandomIndex(list.size())];
|
||||||
|
if (helloChosen) {
|
||||||
|
helloChosen(sticker);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
return StickerInBubblePart::Data{
|
return StickerInBubblePart::Data{
|
||||||
.sticker = data.sticker,
|
.sticker = sticker,
|
||||||
.size = st::chatIntroStickerSize,
|
.size = st::chatIntroStickerSize,
|
||||||
.cacheTag = Tag::ChatIntroHelloSticker,
|
.cacheTag = Tag::ChatIntroHelloSticker,
|
||||||
};
|
};
|
||||||
|
@ -220,96 +198,6 @@ bool PremiumRequiredBox::hasHeavyPart() {
|
||||||
void PremiumRequiredBox::unloadHeavyPart() {
|
void PremiumRequiredBox::unloadHeavyPart() {
|
||||||
}
|
}
|
||||||
|
|
||||||
ChatIntroBox::ChatIntroBox(not_null<Element*> parent, Data::ChatIntro data)
|
|
||||||
: _parent(parent)
|
|
||||||
, _data(data) {
|
|
||||||
if (const auto document = data.sticker) {
|
|
||||||
if (const auto sticker = document->sticker()) {
|
|
||||||
const auto skipPremiumEffect = true;
|
|
||||||
_sticker.emplace(_parent, document, skipPremiumEffect, _parent);
|
|
||||||
_sticker->initSize(st::chatIntroStickerSize);
|
|
||||||
_sticker->setCustomCachingTag(
|
|
||||||
ChatHelpers::StickerLottieSize::ChatIntroHelloSticker);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
ChatIntroBox::~ChatIntroBox() = default;
|
|
||||||
|
|
||||||
int ChatIntroBox::width() {
|
|
||||||
return st::chatIntroWidth;
|
|
||||||
}
|
|
||||||
|
|
||||||
int ChatIntroBox::top() {
|
|
||||||
return st::msgServiceGiftBoxButtonMargins.top();
|
|
||||||
}
|
|
||||||
|
|
||||||
QSize ChatIntroBox::size() {
|
|
||||||
return { st::msgServicePhotoWidth, st::msgServicePhotoWidth };
|
|
||||||
}
|
|
||||||
|
|
||||||
QString ChatIntroBox::title() {
|
|
||||||
return _data ? _data.title : tr::lng_chat_intro_default_title(tr::now);
|
|
||||||
}
|
|
||||||
|
|
||||||
int ChatIntroBox::buttonSkip() {
|
|
||||||
return st::storyMentionButtonSkip;
|
|
||||||
}
|
|
||||||
|
|
||||||
rpl::producer<QString> ChatIntroBox::button() {
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
TextWithEntities ChatIntroBox::subtitle() {
|
|
||||||
return {
|
|
||||||
(_data
|
|
||||||
? _data.description
|
|
||||||
: tr::lng_chat_intro_default_message(tr::now))
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
ClickHandlerPtr ChatIntroBox::createViewLink() {
|
|
||||||
return std::make_shared<LambdaClickHandler>([=](ClickContext context) {
|
|
||||||
const auto my = context.other.value<ClickHandlerContext>();
|
|
||||||
if (const auto controller = my.sessionWindow.get()) {
|
|
||||||
Settings::ShowPremium(controller, u"require_premium"_q);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
void ChatIntroBox::draw(
|
|
||||||
Painter &p,
|
|
||||||
const PaintContext &context,
|
|
||||||
const QRect &geometry) {
|
|
||||||
if (_sticker) {
|
|
||||||
_sticker->draw(p, context, geometry);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void ChatIntroBox::stickerClearLoopPlayed() {
|
|
||||||
if (_sticker) {
|
|
||||||
_sticker->stickerClearLoopPlayed();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
std::unique_ptr<StickerPlayer> ChatIntroBox::stickerTakePlayer(
|
|
||||||
not_null<DocumentData*> data,
|
|
||||||
const Lottie::ColorReplacements *replacements) {
|
|
||||||
return _sticker
|
|
||||||
? _sticker->stickerTakePlayer(data, replacements)
|
|
||||||
: nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool ChatIntroBox::hasHeavyPart() {
|
|
||||||
return _sticker && _sticker->hasHeavyPart();
|
|
||||||
}
|
|
||||||
|
|
||||||
void ChatIntroBox::unloadHeavyPart() {
|
|
||||||
if (_sticker) {
|
|
||||||
_sticker->unloadHeavyPart();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
|
||||||
AboutView::AboutView(
|
AboutView::AboutView(
|
||||||
|
@ -339,21 +227,22 @@ HistoryItem *AboutView::item() const {
|
||||||
}
|
}
|
||||||
|
|
||||||
bool AboutView::refresh() {
|
bool AboutView::refresh() {
|
||||||
const auto bot = _history->peer->asUser();
|
const auto user = _history->peer->asUser();
|
||||||
const auto info = bot ? bot->botInfo.get() : nullptr;
|
const auto info = user ? user->botInfo.get() : nullptr;
|
||||||
if (!info) {
|
if (!info) {
|
||||||
if (bot
|
if (user && _history->isDisplayedEmpty()) {
|
||||||
&& bot->meRequiresPremiumToWrite()
|
|
||||||
&& !bot->session().premium()
|
|
||||||
&& _history->isDisplayedEmpty()) {
|
|
||||||
if (_item) {
|
if (_item) {
|
||||||
return false;
|
return false;
|
||||||
|
} else if (user->meRequiresPremiumToWrite()
|
||||||
|
&& !user->session().premium()) {
|
||||||
|
setItem(makePremiumRequired(), nullptr);
|
||||||
|
} else {
|
||||||
|
makeIntro(user);
|
||||||
}
|
}
|
||||||
_item = makePremiumRequired();
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if (_item) {
|
if (_item) {
|
||||||
_item = {};
|
setItem({}, nullptr);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
_version = 0;
|
_version = 0;
|
||||||
|
@ -364,10 +253,14 @@ bool AboutView::refresh() {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
_version = version;
|
_version = version;
|
||||||
_item = makeAboutBot(info);
|
setItem(makeAboutBot(info), nullptr);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void AboutView::makeIntro(not_null<UserData*> user) {
|
||||||
|
make(user->businessDetails().intro);
|
||||||
|
}
|
||||||
|
|
||||||
void AboutView::make(Data::ChatIntro data) {
|
void AboutView::make(Data::ChatIntro data) {
|
||||||
const auto item = _history->makeMessage({
|
const auto item = _history->makeMessage({
|
||||||
.id = _history->nextNonHistoryEntryId(),
|
.id = _history->nextNonHistoryEntryId(),
|
||||||
|
@ -377,31 +270,58 @@ void AboutView::make(Data::ChatIntro data) {
|
||||||
.from = _history->peer->id,
|
.from = _history->peer->id,
|
||||||
}, PreparedServiceText{ { } });
|
}, PreparedServiceText{ { } });
|
||||||
|
|
||||||
|
if (data.sticker) {
|
||||||
|
_helloChosen = nullptr;
|
||||||
|
} else if (_helloChosen) {
|
||||||
|
data.sticker = _helloChosen;
|
||||||
|
}
|
||||||
|
|
||||||
auto owned = AdminLog::OwnedItem(_delegate, item);
|
auto owned = AdminLog::OwnedItem(_delegate, item);
|
||||||
|
const auto helloChosen = [=](not_null<DocumentData*> sticker) {
|
||||||
|
setHelloChosen(sticker);
|
||||||
|
};
|
||||||
owned->overrideMedia(std::make_unique<HistoryView::MediaInBubble>(
|
owned->overrideMedia(std::make_unique<HistoryView::MediaInBubble>(
|
||||||
owned.get(),
|
owned.get(),
|
||||||
GenerateChatIntro(owned.get(), _item.get(), data),
|
GenerateChatIntro(owned.get(), _item.get(), data, helloChosen),
|
||||||
HistoryView::MediaInBubbleDescriptor{
|
HistoryView::MediaInBubbleDescriptor{
|
||||||
.maxWidth = st::chatIntroWidth,
|
.maxWidth = st::chatIntroWidth,
|
||||||
.service = true,
|
.service = true,
|
||||||
.hideServiceText = true,
|
.hideServiceText = true,
|
||||||
}));
|
}));
|
||||||
|
if (!data.sticker && _helloChosen) {
|
||||||
|
data.sticker = _helloChosen;
|
||||||
|
}
|
||||||
setItem(std::move(owned), data.sticker);
|
setItem(std::move(owned), data.sticker);
|
||||||
}
|
}
|
||||||
|
|
||||||
void AboutView::setItem(AdminLog::OwnedItem item, DocumentData *sticker) {
|
void AboutView::toggleStickerRegistered(bool registered) {
|
||||||
if (const auto was = _item ? _item->data().get() : nullptr) {
|
if (const auto item = _item ? _item->data().get() : nullptr) {
|
||||||
if (_sticker) {
|
if (_sticker) {
|
||||||
was->history()->owner().unregisterDocumentItem(_sticker, was);
|
const auto owner = &item->history()->owner();
|
||||||
|
if (registered) {
|
||||||
|
owner->registerDocumentItem(_sticker, item);
|
||||||
|
} else {
|
||||||
|
owner->unregisterDocumentItem(_sticker, item);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
if (!registered) {
|
||||||
|
_sticker = nullptr;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void AboutView::setHelloChosen(not_null<DocumentData*> sticker) {
|
||||||
|
_helloChosen = sticker;
|
||||||
|
toggleStickerRegistered(false);
|
||||||
|
_sticker = sticker;
|
||||||
|
toggleStickerRegistered(true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void AboutView::setItem(AdminLog::OwnedItem item, DocumentData *sticker) {
|
||||||
|
toggleStickerRegistered(false);
|
||||||
_item = std::move(item);
|
_item = std::move(item);
|
||||||
_sticker = sticker;
|
_sticker = sticker;
|
||||||
if (const auto now = _item ? _item->data().get() : nullptr) {
|
toggleStickerRegistered(true);
|
||||||
if (_sticker) {
|
|
||||||
now->history()->owner().registerDocumentItem(_sticker, now);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
AdminLog::OwnedItem AboutView::makeAboutBot(not_null<BotInfo*> info) {
|
AdminLog::OwnedItem AboutView::makeAboutBot(not_null<BotInfo*> info) {
|
||||||
|
|
|
@ -36,11 +36,15 @@ public:
|
||||||
private:
|
private:
|
||||||
[[nodiscard]] AdminLog::OwnedItem makeAboutBot(not_null<BotInfo*> info);
|
[[nodiscard]] AdminLog::OwnedItem makeAboutBot(not_null<BotInfo*> info);
|
||||||
[[nodiscard]] AdminLog::OwnedItem makePremiumRequired();
|
[[nodiscard]] AdminLog::OwnedItem makePremiumRequired();
|
||||||
|
void makeIntro(not_null<UserData*> user);
|
||||||
void setItem(AdminLog::OwnedItem item, DocumentData *sticker);
|
void setItem(AdminLog::OwnedItem item, DocumentData *sticker);
|
||||||
|
void setHelloChosen(not_null<DocumentData*> sticker);
|
||||||
|
void toggleStickerRegistered(bool registered);
|
||||||
|
|
||||||
const not_null<History*> _history;
|
const not_null<History*> _history;
|
||||||
const not_null<ElementDelegate*> _delegate;
|
const not_null<ElementDelegate*> _delegate;
|
||||||
AdminLog::OwnedItem _item;
|
AdminLog::OwnedItem _item;
|
||||||
|
DocumentData *_helloChosen = nullptr;
|
||||||
DocumentData *_sticker = nullptr;
|
DocumentData *_sticker = nullptr;
|
||||||
int _version = 0;
|
int _version = 0;
|
||||||
|
|
||||||
|
|
|
@ -17,6 +17,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "data/data_document.h"
|
#include "data/data_document.h"
|
||||||
#include "data/data_document_media.h"
|
#include "data/data_document_media.h"
|
||||||
#include "data/data_session.h"
|
#include "data/data_session.h"
|
||||||
|
#include "data/data_user.h"
|
||||||
#include "history/view/media/history_view_media_common.h"
|
#include "history/view/media/history_view_media_common.h"
|
||||||
#include "history/view/media/history_view_sticker_player.h"
|
#include "history/view/media/history_view_sticker_player.h"
|
||||||
#include "history/view/history_view_about_view.h"
|
#include "history/view/history_view_about_view.h"
|
||||||
|
@ -564,10 +565,8 @@ void ChatIntro::setupContent(
|
||||||
|
|
||||||
const auto content = Ui::CreateChild<Ui::VerticalLayout>(this);
|
const auto content = Ui::CreateChild<Ui::VerticalLayout>(this);
|
||||||
const auto session = &controller->session();
|
const auto session = &controller->session();
|
||||||
const auto info = &session->data().businessInfo();
|
_intro = controller->session().user()->businessDetails().intro;
|
||||||
const auto current = info->chatIntro();
|
|
||||||
|
|
||||||
_intro = info->chatIntro();
|
|
||||||
const auto change = [=](Fn<void(Data::ChatIntro &)> modify) {
|
const auto change = [=](Fn<void(Data::ChatIntro &)> modify) {
|
||||||
auto intro = _intro.current();
|
auto intro = _intro.current();
|
||||||
modify(intro);
|
modify(intro);
|
||||||
|
@ -584,12 +583,12 @@ void ChatIntro::setupContent(
|
||||||
const auto title = AddPartInput(
|
const auto title = AddPartInput(
|
||||||
content,
|
content,
|
||||||
tr::lng_chat_intro_enter_title(),
|
tr::lng_chat_intro_enter_title(),
|
||||||
current.title,
|
_intro.current().title,
|
||||||
PartLimit(session, u"intro_title_length_limit"_q, 32));
|
PartLimit(session, u"intro_title_length_limit"_q, 32));
|
||||||
const auto description = AddPartInput(
|
const auto description = AddPartInput(
|
||||||
content,
|
content,
|
||||||
tr::lng_chat_intro_enter_message(),
|
tr::lng_chat_intro_enter_message(),
|
||||||
current.description,
|
_intro.current().description,
|
||||||
PartLimit(session, u"intro_description_length_limit"_q, 70));
|
PartLimit(session, u"intro_description_length_limit"_q, 70));
|
||||||
content->add(CreateIntroStickerButton(
|
content->add(CreateIntroStickerButton(
|
||||||
content,
|
content,
|
||||||
|
|
Loading…
Add table
Reference in a new issue