feat: add message shot toggle for top-right badges

This commit is contained in:
Ireina
2026-04-02 21:40:15 +08:00
committed by AlexeyZavar
parent fc5bfeaee1
commit a33c3d8602
7 changed files with 111 additions and 3 deletions
+1
View File
@@ -8314,6 +8314,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
"ayu_MessageShotShowBackground" = "Show background";
"ayu_MessageShotShowDate" = "Show date";
"ayu_MessageShotShowReactions" = "Show reactions";
"ayu_MessageShotShowHeaderDecorations" = "Show header decorations";
"ayu_MessageShotShowColorfulReplies" = "Show colorful replies";
"ayu_MessageShotRevealSpoilers" = "Reveal spoilers";
"ayu_SendAsSticker" = "Send as Sticker";
@@ -242,6 +242,12 @@ void MessageShotSettings::setShowReactions(bool val) {
AyuSettings::save();
}
void MessageShotSettings::setShowHeaderDecorations(bool val) {
if (_showHeaderDecorations.current() == val) return;
_showHeaderDecorations = val;
AyuSettings::save();
}
void MessageShotSettings::setShowColorfulReplies(bool val) {
if (_showColorfulReplies.current() == val) return;
_showColorfulReplies = val;
@@ -318,6 +324,7 @@ void to_json(nlohmann::json &j, const MessageShotSettings &s) {
{"showBackground", s._showBackground.current()},
{"showDate", s._showDate.current()},
{"showReactions", s._showReactions.current()},
{"showHeaderDecorations", s._showHeaderDecorations.current()},
{"showColorfulReplies", s._showColorfulReplies.current()},
{"revealSpoilers", s._revealSpoilers.current()},
{"embeddedThemeType", s._embeddedThemeType.current()},
@@ -334,6 +341,7 @@ void from_json(const nlohmann::json &j, MessageShotSettings &s) {
s._showBackground = j.value("showBackground", true);
s._showDate = j.value("showDate", false);
s._showReactions = j.value("showReactions", false);
s._showHeaderDecorations = j.value("showHeaderDecorations", true);
s._showColorfulReplies = j.value("showColorfulReplies", true);
s._revealSpoilers = j.value("revealSpoilers", true);
s._embeddedThemeType = j.value("embeddedThemeType", j.value("themeType", -1));
+3
View File
@@ -186,6 +186,7 @@ public:
[[nodiscard]] bool showBackground() const { return _showBackground.current(); }
[[nodiscard]] bool showDate() const { return _showDate.current(); }
[[nodiscard]] bool showReactions() const { return _showReactions.current(); }
[[nodiscard]] bool showHeaderDecorations() const { return _showHeaderDecorations.current(); }
[[nodiscard]] bool showColorfulReplies() const { return _showColorfulReplies.current(); }
[[nodiscard]] bool revealSpoilers() const { return _revealSpoilers.current(); }
[[nodiscard]] int embeddedThemeType() const { return _embeddedThemeType.current(); }
@@ -199,6 +200,7 @@ public:
void setShowBackground(bool val);
void setShowDate(bool val);
void setShowReactions(bool val);
void setShowHeaderDecorations(bool val);
void setShowColorfulReplies(bool val);
void setRevealSpoilers(bool val);
@@ -217,6 +219,7 @@ private:
rpl::variable<bool> _showBackground = true;
rpl::variable<bool> _showDate = false;
rpl::variable<bool> _showReactions = false;
rpl::variable<bool> _showHeaderDecorations = true;
rpl::variable<bool> _showColorfulReplies = true;
rpl::variable<bool> _revealSpoilers = true;
@@ -63,7 +63,9 @@ bool ignoreRender(RenderPart part) {
const auto &s = AyuSettings::getInstance().messageShotSettings();
return isTakingShot()
&& ((part == RenderPart::Date && !s.showDate())
|| (part == RenderPart::Reactions && !s.showReactions()));
|| (part == RenderPart::Reactions && !s.showReactions())
|| (part == RenderPart::HeaderDecorations
&& !s.showHeaderDecorations()));
}
bool isTakingShot() {
@@ -26,6 +26,7 @@ enum RenderPart
{
Date,
Reactions,
HeaderDecorations,
};
void setShotConfig(ShotConfig &config);
@@ -12,7 +12,12 @@
#include "ayu/ui/components/image_view.h"
#include "ayu/utils/telegram_helpers.h"
#include "boxes/abstract_box.h"
#include "data/data_chat.h"
#include "data/data_channel.h"
#include "data/data_todo_list.h"
#include "data/data_user.h"
#include "history/history.h"
#include "history/history_item_components.h"
#include "history/history_item.h"
#include "main/main_session.h"
#include "settings/settings_common.h"
@@ -87,6 +92,7 @@ void MessageShotBox::setupContent() {
auto hasReactions = false;
auto hasReplies = false;
auto hasHeaderDecorations = false;
auto hasSpoilers = false;
for (const auto &item : _config.messages) {
if (!hasReactions && !item->reactions().empty()) {
@@ -129,7 +135,70 @@ void MessageShotBox::setupContent() {
}
}
}
if (hasReactions && hasReplies && hasSpoilers) {
if (!hasHeaderDecorations) {
const auto drawChannelBadge = [&] {
if (item->isDiscussionPost()) {
return true;
} else if (item->author()->isMegagroup()) {
if (const auto signedInfo = item->Get<HistoryMessageSigned>()) {
if (!signedInfo->viaBusinessBot) {
return false;
}
}
}
return item->history()->peer->isMegagroup()
&& item->author()->isChannel()
&& !item->out();
}();
auto badgeText = QString();
if (item->isDiscussionPost()) {
badgeText = tr::lng_channel_badge(tr::now);
} else if (item->author()->isMegagroup()) {
if (const auto signedInfo = item->Get<HistoryMessageSigned>()) {
if (!signedInfo->viaBusinessBot) {
badgeText = signedInfo->author;
}
}
} else if (drawChannelBadge) {
badgeText = tr::lng_channel_badge(tr::now);
} else if (const auto chat = item->history()->peer->asChat()) {
if (const auto user = item->author()->asUser()) {
const auto rank = chat->memberRanks.find(peerToUser(user->id));
if (rank != chat->memberRanks.end()) {
badgeText = rank->second;
}
}
} else if (const auto channel = item->history()->peer->asMegagroup()) {
if (const auto user = item->author()->asUser()) {
const auto info = channel->mgInfo.get();
const auto userId = peerToUser(user->id);
const auto isCreator = info && (info->creator == user);
const auto isAdmin = info && info->admins.contains(userId);
if (isCreator || isAdmin) {
const auto rank = info->memberRanks.find(userId);
if (rank != info->memberRanks.end()
&& !rank->second.isEmpty()) {
badgeText = rank->second;
} else if (isCreator) {
badgeText = tr::lng_owner_badge(tr::now);
} else {
badgeText = tr::lng_admin_badge(tr::now);
}
} else {
badgeText = item->fromRank();
}
}
}
hasHeaderDecorations = drawChannelBadge
|| !badgeText.isEmpty()
|| (item->boostsApplied() > 0);
}
if (hasReactions
&& hasReplies
&& hasHeaderDecorations
&& hasSpoilers) {
break;
}
}
@@ -270,6 +339,23 @@ void MessageShotBox::setupContent() {
content->lifetime());
}
if (hasHeaderDecorations) {
latestToggle = AddButtonWithIcon(
content,
tr::ayu_MessageShotShowHeaderDecorations(),
st::settingsButtonNoIcon
);
latestToggle->toggleOn(rpl::single(shotSettings.showHeaderDecorations())
)->toggledValue(
) | rpl::skip(1) | on_next(
[=](bool enabled)
{
AyuSettings::getInstance().messageShotSettings().setShowHeaderDecorations(enabled);
updatePreview();
},
content->lifetime());
}
if (hasReplies) {
latestToggle = AddButtonWithIcon(
content,
@@ -409,7 +409,14 @@ void Message::refreshRightBadge() {
if (const auto badge = Get<RightBadge>(); badge && badge->overridden) {
return;
}
if (hasOutLayout()) {
if (hasOutLayout() && !AyuFeatures::MessageShot::isTakingShot()) {
if (Has<RightBadge>()) {
RemoveComponents(RightBadge::Bit());
}
return;
}
if (AyuFeatures::MessageShot::ignoreRender(
AyuFeatures::MessageShot::RenderPart::HeaderDecorations)) {
if (Has<RightBadge>()) {
RemoveComponents(RightBadge::Bit());
}