Add messageAnimatedEmoji.
This commit is contained in:
parent
77158cd7a5
commit
ffe03ecb10
@ -1707,6 +1707,9 @@ messageVenue venue:venue = MessageContent;
|
||||
//@description A message with a user contact @contact The contact description
|
||||
messageContact contact:contact = MessageContent;
|
||||
|
||||
//@description A message with an animated emoji @sticker The animated sticker with the emoji animation @emoji The corresponding emoji
|
||||
messageAnimatedEmoji sticker:sticker emoji:string = MessageContent;
|
||||
|
||||
//@description A dice message. The dice value is randomly generated by the server
|
||||
//@initial_state The animated stickers with the initial dice animation; may be null if unknown. updateMessageContent will be sent when the sticker became known
|
||||
//@final_state The animated stickers with the final dice animation; may be null if unknown. updateMessageContent will be sent when the sticker became known
|
||||
|
@ -1360,6 +1360,7 @@ void StickersManager::load_special_sticker_set_by_type(const SpecialStickerSetTy
|
||||
}
|
||||
|
||||
void StickersManager::load_special_sticker_set(SpecialStickerSet &sticker_set) {
|
||||
CHECK(!td_->auth_manager_->is_bot());
|
||||
if (sticker_set.is_being_loaded_) {
|
||||
return;
|
||||
}
|
||||
@ -1407,23 +1408,17 @@ void StickersManager::on_load_special_sticker_set(const SpecialStickerSetType &t
|
||||
CHECK(sticker_set->was_loaded);
|
||||
|
||||
if (type.type_ == SpecialStickerSetType::animated_emoji()) {
|
||||
for (auto sticker_it : sticker_set->sticker_emojis_map_) {
|
||||
for (auto &emoji : sticker_it.second) {
|
||||
auto it = emoji_messages_.find(emoji);
|
||||
if (it == emoji_messages_.end()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
vector<FullMessageId> full_message_ids;
|
||||
for (auto full_message_id : it->second) {
|
||||
vector<FullMessageId> full_message_ids;
|
||||
for (const auto &it : emoji_messages_) {
|
||||
if (get_animated_emoji_sticker(sticker_set, it.first).first.is_valid()) {
|
||||
for (auto full_message_id : it.second) {
|
||||
full_message_ids.push_back(full_message_id);
|
||||
}
|
||||
CHECK(!full_message_ids.empty());
|
||||
for (auto full_message_id : full_message_ids) {
|
||||
td_->messages_manager_->on_external_update_message_content(full_message_id);
|
||||
}
|
||||
}
|
||||
}
|
||||
for (auto full_message_id : full_message_ids) {
|
||||
td_->messages_manager_->on_external_update_message_content(full_message_id);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
@ -1916,8 +1911,64 @@ tl_object_ptr<td_api::stickerSetInfo> StickersManager::get_sticker_set_info_obje
|
||||
std::move(stickers));
|
||||
}
|
||||
|
||||
std::pair<FileId, int> StickersManager::get_animated_emoji_sticker(const StickerSet *sticker_set, const string &emoji) {
|
||||
auto emoji_without_modifiers = remove_emoji_modifiers(emoji).str();
|
||||
auto it = sticker_set->emoji_stickers_map_.find(emoji_without_modifiers);
|
||||
if (it == sticker_set->emoji_stickers_map_.end()) {
|
||||
return {};
|
||||
}
|
||||
|
||||
// trying to find full emoji match
|
||||
for (const auto &sticker_id : it->second) {
|
||||
auto emoji_it = sticker_set->sticker_emojis_map_.find(sticker_id);
|
||||
CHECK(emoji_it != sticker_set->sticker_emojis_map_.end());
|
||||
if (td::contains(emoji_it->second, emoji)) {
|
||||
return {sticker_id, 0};
|
||||
}
|
||||
}
|
||||
|
||||
// trying to find match without Fitzpatrick modifiers
|
||||
int modifier_id = get_fitzpatrick_modifier(emoji);
|
||||
if (modifier_id > 0) {
|
||||
for (const auto &sticker_id : it->second) {
|
||||
auto emoji_it = sticker_set->sticker_emojis_map_.find(sticker_id);
|
||||
CHECK(emoji_it != sticker_set->sticker_emojis_map_.end());
|
||||
if (td::contains(emoji_it->second, Slice(emoji).remove_suffix(4))) {
|
||||
return {sticker_id, modifier_id};
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// there is no match
|
||||
return {};
|
||||
}
|
||||
|
||||
std::pair<FileId, int> StickersManager::get_animated_emoji_sticker(const string &emoji) {
|
||||
if (td_->auth_manager_->is_bot()) {
|
||||
return {};
|
||||
}
|
||||
auto &special_sticker_set = add_special_sticker_set(SpecialStickerSetType::animated_emoji());
|
||||
if (!special_sticker_set.id_.is_valid()) {
|
||||
load_special_sticker_set(special_sticker_set);
|
||||
return {};
|
||||
}
|
||||
|
||||
auto sticker_set = get_sticker_set(special_sticker_set.id_);
|
||||
CHECK(sticker_set != nullptr);
|
||||
if (!sticker_set->was_loaded) {
|
||||
load_special_sticker_set(special_sticker_set);
|
||||
return {};
|
||||
}
|
||||
|
||||
return get_animated_emoji_sticker(sticker_set, emoji);
|
||||
}
|
||||
|
||||
td_api::object_ptr<td_api::MessageContent> StickersManager::get_message_content_animated_emoji_object(
|
||||
const string &emoji) {
|
||||
auto animated_sticker = get_animated_emoji_sticker(emoji);
|
||||
if (animated_sticker.first.is_valid()) {
|
||||
return td_api::make_object<td_api::messageAnimatedEmoji>(get_sticker_object(animated_sticker.first), emoji);
|
||||
}
|
||||
return td_api::make_object<td_api::messageText>(
|
||||
td_api::make_object<td_api::formattedText>(emoji, std::vector<td_api::object_ptr<td_api::textEntity>>()),
|
||||
nullptr);
|
||||
@ -4139,7 +4190,7 @@ int StickersManager::get_emoji_number(Slice emoji) {
|
||||
return emoji[0] - '0';
|
||||
}
|
||||
|
||||
vector<FileId> StickersManager::get_animated_emoji_stickers(const StickerSet *sticker_set, Slice emoji) const {
|
||||
vector<FileId> StickersManager::get_animated_emoji_click_stickers(const StickerSet *sticker_set, Slice emoji) const {
|
||||
vector<FileId> result;
|
||||
for (auto sticker_id : sticker_set->sticker_ids) {
|
||||
auto s = get_sticker(sticker_id);
|
||||
@ -4151,7 +4202,7 @@ vector<FileId> StickersManager::get_animated_emoji_stickers(const StickerSet *st
|
||||
if (result.empty()) {
|
||||
const static vector<string> heart_emojis{"💛", "💙", "💚", "💜", "🧡", "🖤", "🤎", "🤍"};
|
||||
if (td::contains(heart_emojis, emoji)) {
|
||||
return get_animated_emoji_stickers(sticker_set, Slice("❤"));
|
||||
return get_animated_emoji_click_stickers(sticker_set, Slice("❤"));
|
||||
}
|
||||
}
|
||||
return result;
|
||||
@ -4172,7 +4223,7 @@ void StickersManager::choose_animated_emoji_click_sticker(const StickerSet *stic
|
||||
return promise.set_value(nullptr);
|
||||
}
|
||||
|
||||
auto all_sticker_ids = get_animated_emoji_stickers(sticker_set, message_text);
|
||||
auto all_sticker_ids = get_animated_emoji_click_stickers(sticker_set, message_text);
|
||||
vector<std::pair<int, FileId>> found_stickers;
|
||||
for (auto sticker_id : all_sticker_ids) {
|
||||
auto it = sticker_set->sticker_emojis_map_.find(sticker_id);
|
||||
@ -4322,6 +4373,10 @@ bool StickersManager::is_sent_animated_emoji_click(DialogId dialog_id, Slice emo
|
||||
}
|
||||
|
||||
Status StickersManager::on_animated_emoji_message_clicked(Slice emoji, FullMessageId full_message_id, string data) {
|
||||
if (td_->auth_manager_->is_bot()) {
|
||||
return Status::OK();
|
||||
}
|
||||
|
||||
TRY_RESULT(value, json_decode(data));
|
||||
if (value.type() != JsonValue::Type::Object) {
|
||||
return Status::Error("Expected an object");
|
||||
@ -4402,7 +4457,7 @@ void StickersManager::schedule_update_animated_emoji_clicked(const StickerSet *s
|
||||
return;
|
||||
}
|
||||
|
||||
auto all_sticker_ids = get_animated_emoji_stickers(sticker_set, emoji);
|
||||
auto all_sticker_ids = get_animated_emoji_click_stickers(sticker_set, emoji);
|
||||
std::unordered_map<int, FileId> sticker_ids;
|
||||
for (auto sticker_id : all_sticker_ids) {
|
||||
auto it = sticker_set->sticker_emojis_map_.find(sticker_id);
|
||||
|
@ -603,7 +603,11 @@ class StickersManager final : public Actor {
|
||||
|
||||
static int get_emoji_number(Slice emoji);
|
||||
|
||||
vector<FileId> get_animated_emoji_stickers(const StickerSet *sticker_set, Slice emoji) const;
|
||||
static std::pair<FileId, int> get_animated_emoji_sticker(const StickerSet *sticker_set, const string &emoji);
|
||||
|
||||
std::pair<FileId, int> get_animated_emoji_sticker(const string &emoji);
|
||||
|
||||
vector<FileId> get_animated_emoji_click_stickers(const StickerSet *sticker_set, Slice emoji) const;
|
||||
|
||||
void choose_animated_emoji_click_sticker(const StickerSet *sticker_set, Slice message_text,
|
||||
FullMessageId full_message_id, double start_time,
|
||||
|
@ -839,6 +839,18 @@ bool is_emoji(Slice str) {
|
||||
return emojis.count(str) != 0;
|
||||
}
|
||||
|
||||
int get_fitzpatrick_modifier(Slice emoji) {
|
||||
if (emoji.size() < 4 || emoji[emoji.size() - 4] != '\xF0' || emoji[emoji.size() - 3] != '\x9F' ||
|
||||
emoji[emoji.size() - 2] != '\x8F') {
|
||||
return 0;
|
||||
}
|
||||
auto c = static_cast<unsigned char>(emoji.back());
|
||||
if (c < 0xBB || c > 0xBF) {
|
||||
return 0;
|
||||
}
|
||||
return (c - 0xBB) + 2;
|
||||
}
|
||||
|
||||
Slice remove_emoji_modifiers(Slice emoji) {
|
||||
static const Slice modifiers[] = {u8"\uFE0E" /* variation selector-15 */,
|
||||
u8"\uFE0F" /* variation selector-16 */,
|
||||
|
@ -14,6 +14,9 @@ namespace td {
|
||||
// checks whether the string is an emoji; variation selectors are ignored
|
||||
bool is_emoji(Slice str);
|
||||
|
||||
// checks whether emoji ends on a Fitzpatrick modifier and returns it's number or 0
|
||||
int get_fitzpatrick_modifier(Slice emoji);
|
||||
|
||||
// removes all emoji modifiers from the end of the string
|
||||
Slice remove_emoji_modifiers(Slice emoji);
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user