fix: crash & badges position with avatarCorners

This commit is contained in:
AlexeyZavar
2026-03-18 14:00:47 +03:00
parent 7868e5e905
commit 96231c217c
5 changed files with 71 additions and 49 deletions
@@ -11,6 +11,7 @@
#include "media/streaming/media_streaming_common.h"
#include "ui/image/image_prepare.h"
#include "ui/style/style_core.h"
#include "base/algorithm.h"
#include <QRectF>
@@ -88,6 +89,15 @@ QPointF OnlineBadgePosition(int photoSize, double badgeSize, double stroke) {
return QPointF(pos, pos);
}
QRect OnlineBadgeRect(int photoSize, int badgeSize, int stroke) {
const auto pos = OnlineBadgePosition(photoSize, badgeSize, stroke);
return QRect(
int(base::SafeRound(pos.x())),
int(base::SafeRound(pos.y())),
badgeSize,
badgeSize);
}
void ApplyFrameRounding(
::Media::Streaming::FrameRequest &request,
std::array<QImage, 4> &cornersCache,
@@ -8,6 +8,8 @@
#include "ui/userpic_view.h"
#include <QRect>
namespace Media::Streaming { struct FrameRequest; }
namespace AyuUserpic {
@@ -23,6 +25,10 @@ void PaintShape(QPainter &p, int x, int y, int size);
void PaintShape(QPainter &p, const QRectF &rect);
[[nodiscard]] QPointF OnlineBadgePosition(int photoSize, double badgeSize, double stroke = 0);
[[nodiscard]] QRect OnlineBadgeRect(
int photoSize,
int badgeSize,
int stroke = 0);
void ApplyFrameRounding(
::Media::Streaming::FrameRequest &request,
@@ -994,25 +994,20 @@ static bool prependPseudoReplyImpl(
QString()
});
auto accessHash = uint64(0);
if (const auto user = from->asUser()) {
accessHash = user->accessHash();
} else if (const auto channel = from->asChannel()) {
accessHash = channel->accessHash();
}
if (const auto accessHash = user->accessHash()) {
const auto mentionData = QStringLiteral("%1.%2:%3")
.arg(user->id.value)
.arg(accessHash)
.arg(session->userId().bare);
if (accessHash != 0) {
const auto mentionData = QStringLiteral("%1.%2:%3")
.arg(from->id.value)
.arg(accessHash)
.arg(session->userId().bare);
newEntities.push_back(EntityInText{
EntityType::MentionName,
0,
nameLength,
mentionData
});
newEntities.push_back(EntityInText{
EntityType::MentionName,
0,
nameLength,
mentionData
});
}
}
}
@@ -93,6 +93,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include <QtCore/QMimeData>
// AyuGram includes
#include "ayu/ui/ayu_userpic.h"
#include "ayu/utils/telegram_helpers.h"
#include "styles/style_ayu_icons.h"
@@ -5419,14 +5420,10 @@ void InnerWidget::repaintDialogRowCornerStatus(not_null<History*> history) {
? st::dialogsOnlineBadgeSize
: st::dialogsCallBadgeSize;
const auto stroke = st::dialogsOnlineBadgeStroke;
const auto skip = user
? st::dialogsOnlineBadgeSkip
: st::dialogsCallBadgeSkip;
const auto updateRect = QRect(
_st->photoSize - skip.x() - size,
_st->photoSize - skip.y() - size,
const auto updateRect = AyuUserpic::OnlineBadgeRect(
_st->photoSize,
size,
size
stroke
).marginsAdded(
{ stroke, stroke, stroke, stroke }
).translated(
+39 -25
View File
@@ -115,7 +115,8 @@ constexpr auto kBlurRadius = 24;
[[nodiscard]] QImage CornerBadgeTTL(
not_null<PeerData*> peer,
Ui::PeerUserpicView &view,
int photoSize) {
int photoSize,
QColor background) {
const auto ttl = peer->messagesTTL();
if (!ttl) {
return QImage();
@@ -124,8 +125,21 @@ constexpr auto kBlurRadius = 24;
const auto fullSize = photoSize;
const auto partRect = CornerBadgeTTLRect(fullSize);
const auto &partSize = partRect.width();
auto source = PeerData::GenerateUserpicImage(peer, view, fullSize * ratio);
if (source.hasAlphaChannel()) {
auto flattened = QImage(
source.size(),
QImage::Format_ARGB32_Premultiplied);
flattened.setDevicePixelRatio(source.devicePixelRatio());
flattened.fill(background);
{
auto painter = QPainter(&flattened);
painter.drawImage(0, 0, source);
}
source = std::move(flattened);
}
auto result = Images::Circle(BlurredDarkenedPart(
PeerData::GenerateUserpicImage(peer, view, fullSize * ratio, 0),
std::move(source),
QRect(
partRect.topLeft() * ratio,
QSize(partSize, partSize) * ratio)));
@@ -169,13 +183,7 @@ constexpr auto kBlurRadius = 24;
} // namespace
QRect CornerBadgeTTLRect(int photoSize) {
const auto &partSize = st::dialogsTTLBadgeSize;
const auto pos = AyuUserpic::OnlineBadgePosition(photoSize, partSize);
return QRect(
int(pos.x()),
int(pos.y()),
partSize,
partSize);
return AyuUserpic::OnlineBadgeRect(photoSize, st::dialogsTTLBadgeSize);
}
QImage BlurredDarkenedPart(QImage image, QRect part) {
@@ -520,7 +528,11 @@ void Row::PaintCornerBadgeFrame(
if (const auto p = manager.progressForLayer(kBottomLayer); p > 0.) {
const auto size = photoSize;
if (data->cacheTTL.isNull() && peer && peer->messagesTTL()) {
data->cacheTTL = CornerBadgeTTL(peer, view, size);
data->cacheTTL = CornerBadgeTTL(
peer,
view,
size,
(context.active ? st::dialogsBgActive : st::dialogsBg)->c);
}
q.setOpacity(p);
const auto point = CornerBadgeTTLRect(size).topLeft();
@@ -542,9 +554,6 @@ void Row::PaintCornerBadgeFrame(
? st::dialogsOnlineBadgeSize
: st::dialogsCallBadgeSize;
const auto stroke = st::dialogsOnlineBadgeStroke;
const auto skip = online
? st::dialogsOnlineBadgeSkip
: st::dialogsCallBadgeSkip;
const auto shrink = (size / 2) * (1. - topLayerProgress);
auto pen = QPen(Qt::transparent);
@@ -553,13 +562,13 @@ void Row::PaintCornerBadgeFrame(
q.setBrush(data->active
? st::dialogsOnlineBadgeFgActive
: st::dialogsOnlineBadgeFg);
const auto badge = AyuUserpic::OnlineBadgePosition(photoSize, size, stroke);
q.drawEllipse(QRectF(
badge.x(),
badge.y(),
size,
size
).marginsRemoved({ shrink, shrink, shrink, shrink }));
const auto badge = AyuUserpic::OnlineBadgeRect(photoSize, size, stroke);
q.drawEllipse(QRectF(badge).marginsRemoved({
shrink,
shrink,
shrink,
shrink,
}));
}
void Row::paintUserpic(
@@ -640,16 +649,17 @@ void Row::paintUserpic(
const auto paletteVersionReal = style::PaletteVersion();
const auto paletteVersion = (paletteVersionReal & ((1 << 17) - 1));
const auto active = context.active ? 1 : 0;
const auto activeChanged = (_cornerBadgeUserpic->active != active);
const auto keyChanged = (_cornerBadgeUserpic->key != key)
|| (_cornerBadgeUserpic->paletteVersion != paletteVersion);
if (keyChanged) {
if (keyChanged || activeChanged) {
_cornerBadgeUserpic->cacheTTL = QImage();
}
const auto subscribed = Data::ChannelHasSubscriptionUntilDate(
peer ? peer->asChannel() : nullptr);
if (keyChanged
|| !_cornerBadgeUserpic->layersManager.isFinished()
|| _cornerBadgeUserpic->active != active
|| activeChanged
|| _cornerBadgeUserpic->frameIndex != frameIndex
|| _cornerBadgeUserpic->storiesCount != storiesCount
|| _cornerBadgeUserpic->storiesUnreadCount != storiesUnreadCount
@@ -686,14 +696,18 @@ void Row::paintUserpic(
? st::dialogsBgActive
: st::dialogsBg;
const auto size = st::dialogsCallBadgeSize;
const auto skip = st::dialogsCallBadgeSkip;
const auto stroke = st::dialogsOnlineBadgeStroke;
const auto badge = AyuUserpic::OnlineBadgeRect(
context.st->photoSize,
size,
stroke);
p.setOpacity(
_cornerBadgeUserpic->layersManager.progressForLayer(kTopLayer));
p.translate(context.st->padding.left(), context.st->padding.top());
actionPainter->paintSpeaking(
p,
context.st->photoSize - skip.x() - size,
context.st->photoSize - skip.y() - size,
badge.x(),
badge.y(),
context.width,
bg,
context.now);