diff --git a/Telegram/CMakeLists.txt b/Telegram/CMakeLists.txt
index 028979462b..24b7ed6722 100644
--- a/Telegram/CMakeLists.txt
+++ b/Telegram/CMakeLists.txt
@@ -688,6 +688,8 @@ PRIVATE
dialogs/dialogs_search_from_controllers.h
dialogs/dialogs_search_tags.cpp
dialogs/dialogs_search_tags.h
+ dialogs/dialogs_swipe_action.cpp
+ dialogs/dialogs_swipe_action.h
dialogs/dialogs_widget.cpp
dialogs/dialogs_widget.h
editor/color_picker.cpp
diff --git a/Telegram/Resources/animations/swipe_action/archive.tgs b/Telegram/Resources/animations/swipe_action/archive.tgs
new file mode 100644
index 0000000000..73e049e69c
Binary files /dev/null and b/Telegram/Resources/animations/swipe_action/archive.tgs differ
diff --git a/Telegram/Resources/animations/swipe_action/delete.tgs b/Telegram/Resources/animations/swipe_action/delete.tgs
new file mode 100644
index 0000000000..daa3a01626
Binary files /dev/null and b/Telegram/Resources/animations/swipe_action/delete.tgs differ
diff --git a/Telegram/Resources/animations/swipe_action/disabled.tgs b/Telegram/Resources/animations/swipe_action/disabled.tgs
new file mode 100644
index 0000000000..a4fb31cb25
Binary files /dev/null and b/Telegram/Resources/animations/swipe_action/disabled.tgs differ
diff --git a/Telegram/Resources/animations/swipe_action/mute.tgs b/Telegram/Resources/animations/swipe_action/mute.tgs
new file mode 100644
index 0000000000..97d7bbf68c
Binary files /dev/null and b/Telegram/Resources/animations/swipe_action/mute.tgs differ
diff --git a/Telegram/Resources/animations/swipe_action/pin.tgs b/Telegram/Resources/animations/swipe_action/pin.tgs
new file mode 100644
index 0000000000..5fbeedbc4f
Binary files /dev/null and b/Telegram/Resources/animations/swipe_action/pin.tgs differ
diff --git a/Telegram/Resources/animations/swipe_action/read.tgs b/Telegram/Resources/animations/swipe_action/read.tgs
new file mode 100644
index 0000000000..59b258677c
Binary files /dev/null and b/Telegram/Resources/animations/swipe_action/read.tgs differ
diff --git a/Telegram/Resources/animations/swipe_action/unarchive.tgs b/Telegram/Resources/animations/swipe_action/unarchive.tgs
new file mode 100644
index 0000000000..f8a4f2108f
Binary files /dev/null and b/Telegram/Resources/animations/swipe_action/unarchive.tgs differ
diff --git a/Telegram/Resources/animations/swipe_action/unmute.tgs b/Telegram/Resources/animations/swipe_action/unmute.tgs
new file mode 100644
index 0000000000..563749f53f
Binary files /dev/null and b/Telegram/Resources/animations/swipe_action/unmute.tgs differ
diff --git a/Telegram/Resources/animations/swipe_action/unpin.tgs b/Telegram/Resources/animations/swipe_action/unpin.tgs
new file mode 100644
index 0000000000..8e96e36ec9
Binary files /dev/null and b/Telegram/Resources/animations/swipe_action/unpin.tgs differ
diff --git a/Telegram/Resources/animations/swipe_action/unread.tgs b/Telegram/Resources/animations/swipe_action/unread.tgs
new file mode 100644
index 0000000000..97ce96a05f
Binary files /dev/null and b/Telegram/Resources/animations/swipe_action/unread.tgs differ
diff --git a/Telegram/Resources/langs/lang.strings b/Telegram/Resources/langs/lang.strings
index af2a2d6abd..7de5a48e25 100644
--- a/Telegram/Resources/langs/lang.strings
+++ b/Telegram/Resources/langs/lang.strings
@@ -1180,6 +1180,17 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
"lng_settings_restart_now" = "Restart";
"lng_settings_restart_later" = "Later";
+"lng_settings_swipe_mute" = "Mute";
+"lng_settings_swipe_unmute" = "Unmute";
+"lng_settings_swipe_pin" = "Pin";
+"lng_settings_swipe_unpin" = "Unpin";
+"lng_settings_swipe_read" = "Read";
+"lng_settings_swipe_unread" = "Unread";
+"lng_settings_swipe_archive" = "Archive";
+"lng_settings_swipe_unarchive" = "Unarchive";
+"lng_settings_swipe_delete" = "Delete";
+"lng_settings_swipe_disabled" = "Change folder";
+
"lng_sessions_header" = "This device";
"lng_sessions_other_header" = "Active Devices";
"lng_sessions_other_desc" = "You can log in to Telegram from other mobile, tablet and desktop devices, using the same phone number. All your data will be instantly synchronized.";
diff --git a/Telegram/Resources/qrc/telegram/animations.qrc b/Telegram/Resources/qrc/telegram/animations.qrc
index e66d847b6a..871ff80878 100644
--- a/Telegram/Resources/qrc/telegram/animations.qrc
+++ b/Telegram/Resources/qrc/telegram/animations.qrc
@@ -49,5 +49,16 @@
../../animations/star_reaction/effect1.tgs
../../animations/star_reaction/effect2.tgs
../../animations/star_reaction/effect3.tgs
+
+ ../../animations/swipe_action/archive.tgs
+ ../../animations/swipe_action/unarchive.tgs
+ ../../animations/swipe_action/delete.tgs
+ ../../animations/swipe_action/disabled.tgs
+ ../../animations/swipe_action/mute.tgs
+ ../../animations/swipe_action/unmute.tgs
+ ../../animations/swipe_action/pin.tgs
+ ../../animations/swipe_action/unpin.tgs
+ ../../animations/swipe_action/read.tgs
+ ../../animations/swipe_action/unread.tgs
diff --git a/Telegram/SourceFiles/dialogs/dialogs.style b/Telegram/SourceFiles/dialogs/dialogs.style
index 4027da23ee..2d4d01fda5 100644
--- a/Telegram/SourceFiles/dialogs/dialogs.style
+++ b/Telegram/SourceFiles/dialogs/dialogs.style
@@ -789,3 +789,5 @@ dialogsPopularAppsPadding: margins(10px, 8px, 10px, 12px);
dialogsPopularAppsAbout: FlatLabel(boxDividerLabel) {
minWidth: 128px;
}
+
+dialogsSwipeActionSize: 20px;
diff --git a/Telegram/SourceFiles/dialogs/dialogs_inner_widget.cpp b/Telegram/SourceFiles/dialogs/dialogs_inner_widget.cpp
index 5836207a1f..9b1492e9a2 100644
--- a/Telegram/SourceFiles/dialogs/dialogs_inner_widget.cpp
+++ b/Telegram/SourceFiles/dialogs/dialogs_inner_widget.cpp
@@ -54,6 +54,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "base/unixtime.h"
#include "base/options.h"
#include "lang/lang_keys.h"
+#include "lottie/lottie_icon.h"
#include "mainwindow.h"
#include "mainwidget.h"
#include "storage/storage_account.h"
@@ -808,6 +809,7 @@ void InnerWidget::paintEvent(QPaintEvent *e) {
const auto ms = crl::now();
const auto childListShown = _childListShown.current();
auto context = Ui::PaintContext{
+ .swipeContext = _swipeContext,
.st = _st,
.topicJumpCache = _topicJumpCache.get(),
.folder = _openedFolder,
@@ -4992,4 +4994,74 @@ rpl::producer InnerWidget::openBotMainAppRequests() const {
return _openBotMainAppRequests.events();
}
+void InnerWidget::setSwipeContextData(Ui::Controls::SwipeContextData data) {
+ _swipeContext.data = std::move(data);
+ if (_swipeContext.data.msgBareId) {
+ constexpr auto kStartAnimateThreshold = 0.32;
+ constexpr auto kResetAnimateThreshold = 0.24;
+ if (_swipeContext.data.ratio > kStartAnimateThreshold) {
+ if (_swipeContext.icon
+ && !_swipeContext.icon->frameIndex()
+ && !_swipeContext.icon->animating()) {
+ _swipeContext.icon->animate(
+ [=] { update(); },
+ 0,
+ _swipeContext.icon->framesCount());
+ }
+ } else if (_swipeContext.data.ratio < kResetAnimateThreshold) {
+ if (_swipeContext.icon && _swipeContext.icon->frameIndex()) {
+ _swipeContext.icon->jumpTo(0, [=] { update(); });
+ }
+ }
+ update();
+ }
+}
+
+int64 InnerWidget::calcSwipeKey(int top) {
+ top -= dialogsOffset();
+ for (auto it = _shownList->begin(); it != _shownList->end(); ++it) {
+ const auto row = it->get();
+ const auto from = row->top();
+ const auto to = from + row->height();
+ if (top >= from && top < to) {
+ if (const auto peer = row->key().peer()) {
+ return peer->id.value;
+ }
+ return 0;
+ }
+ }
+ return 0;
+}
+
+void InnerWidget::prepareSwipeAction(
+ int64 key,
+ Dialogs::Ui::SwipeDialogAction action) {
+ if (key) {
+ auto name = (action == Dialogs::Ui::SwipeDialogAction::Mute)
+ ? u"swipe_mute"_q
+ : (action == Dialogs::Ui::SwipeDialogAction::Pin)
+ ? u"swipe_pin"_q
+ : (action == Dialogs::Ui::SwipeDialogAction::Read)
+ ? u"swipe_read"_q
+ : (action == Dialogs::Ui::SwipeDialogAction::Archive)
+ ? u"swipe_archive"_q
+ : (action == Dialogs::Ui::SwipeDialogAction::Delete)
+ ? u"swipe_delete"_q
+ : u"swipe_disabled"_q;
+ _swipeLottieIcon = Lottie::MakeIcon({
+ .name = std::move(name),
+ .sizeOverride = Size(st::dialogsSwipeActionSize),
+ });
+ _swipeContext.icon = _swipeLottieIcon.get();
+ _swipeContext.action = action;
+ } else {
+ if (_swipeContext.icon) {
+ _swipeContext = {};
+ }
+ if (_swipeLottieIcon) {
+ _swipeLottieIcon.reset();
+ }
+ }
+}
+
} // namespace Dialogs
diff --git a/Telegram/SourceFiles/dialogs/dialogs_inner_widget.h b/Telegram/SourceFiles/dialogs/dialogs_inner_widget.h
index 2500f43d1f..846feac821 100644
--- a/Telegram/SourceFiles/dialogs/dialogs_inner_widget.h
+++ b/Telegram/SourceFiles/dialogs/dialogs_inner_widget.h
@@ -11,6 +11,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "base/object_ptr.h"
#include "base/timer.h"
#include "dialogs/dialogs_key.h"
+#include "dialogs/ui/dialogs_swipe_context.h"
#include "data/data_messages.h"
#include "ui/dragging_scroll_manager.h"
#include "ui/effects/animations.h"
@@ -25,6 +26,10 @@ namespace MTP {
class Error;
} // namespace MTP
+namespace Lottie {
+class Icon;
+} // namespace Lottie
+
namespace Main {
class Session;
} // namespace Main
@@ -34,6 +39,9 @@ class IconButton;
class PopupMenu;
class FlatLabel;
struct ScrollToRequest;
+namespace Controls {
+enum class SwipeDialogAction;
+} // namespace Controls
} // namespace Ui
namespace Window {
@@ -208,6 +216,10 @@ public:
[[nodiscard]] rpl::producer openBotMainAppRequests() const;
+ void setSwipeContextData(Ui::Controls::SwipeContextData data);
+ [[nodiscard]] int64 calcSwipeKey(int top);
+ void prepareSwipeAction(int64 key, Dialogs::Ui::SwipeDialogAction);
+
protected:
void visibleTopBottomUpdated(
int visibleTop,
@@ -611,6 +623,9 @@ private:
rpl::event_stream<> _refreshHashtagsRequests;
rpl::event_stream _openBotMainAppRequests;
+ Dialogs::Ui::SwipeContext _swipeContext;
+ std::unique_ptr _swipeLottieIcon = nullptr;
+
RowDescriptor _chatPreviewRow;
bool _chatPreviewScheduled = false;
std::optional _chatPreviewTouchGlobal;
diff --git a/Telegram/SourceFiles/dialogs/dialogs_swipe_action.cpp b/Telegram/SourceFiles/dialogs/dialogs_swipe_action.cpp
new file mode 100644
index 0000000000..90ed1fc032
--- /dev/null
+++ b/Telegram/SourceFiles/dialogs/dialogs_swipe_action.cpp
@@ -0,0 +1,29 @@
+/*
+This file is part of Telegram Desktop,
+the official desktop application for the Telegram messaging service.
+
+For license and copyright information please follow this link:
+https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
+*/
+#include "dialogs/dialogs_swipe_action.h"
+
+#include "dialogs/ui/dialogs_swipe_context.h"
+#include "data/data_peer.h"
+#include "data/data_session.h"
+#include "history/history.h"
+#include "main/main_session.h"
+#include "menu/menu_mute.h"
+
+namespace Dialogs {
+
+void PerformSwipeDialogAction(
+ not_null peer,
+ Ui::SwipeDialogAction action) {
+ if (action == Dialogs::Ui::SwipeDialogAction::Mute) {
+ const auto history = peer->owner().history(peer);
+ MuteMenu::ThreadDescriptor(history).updateMutePeriod(
+ std::numeric_limits::max());
+ }
+}
+
+} // namespace Dialogs
diff --git a/Telegram/SourceFiles/dialogs/dialogs_swipe_action.h b/Telegram/SourceFiles/dialogs/dialogs_swipe_action.h
new file mode 100644
index 0000000000..9dca99277c
--- /dev/null
+++ b/Telegram/SourceFiles/dialogs/dialogs_swipe_action.h
@@ -0,0 +1,22 @@
+/*
+This file is part of Telegram Desktop,
+the official desktop application for the Telegram messaging service.
+
+For license and copyright information please follow this link:
+https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
+*/
+#pragma once
+
+class PeerData;
+
+namespace Dialogs::Ui {
+enum class SwipeDialogAction;
+} // namespace Dialogs::Ui
+
+namespace Dialogs {
+
+void PerformSwipeDialogAction(
+ not_null peer,
+ Ui::SwipeDialogAction action);
+
+} // namespace Dialogs
diff --git a/Telegram/SourceFiles/dialogs/dialogs_widget.cpp b/Telegram/SourceFiles/dialogs/dialogs_widget.cpp
index 83ab9665e9..b00963bc91 100644
--- a/Telegram/SourceFiles/dialogs/dialogs_widget.cpp
+++ b/Telegram/SourceFiles/dialogs/dialogs_widget.cpp
@@ -7,6 +7,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
*/
#include "dialogs/dialogs_widget.h"
+#include "base/call_delayed.h"
#include "base/qt/qt_key_modifiers.h"
#include "base/options.h"
#include "dialogs/ui/chat_search_in.h"
@@ -15,6 +16,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "dialogs/ui/dialogs_suggestions.h"
#include "dialogs/dialogs_inner_widget.h"
#include "dialogs/dialogs_search_from_controllers.h"
+#include "dialogs/dialogs_swipe_action.h"
#include "dialogs/dialogs_key.h"
#include "history/history.h"
#include "history/history_item.h"
@@ -688,32 +690,64 @@ void Widget::setupSwipeBack() {
Ui::Controls::SetupSwipeHandler(_inner, _scroll.data(), [=](
Ui::Controls::SwipeContextData data) {
if (data.translation != 0) {
- if (!_swipeBackData.callback) {
- _swipeBackData = Ui::Controls::SetupSwipeBack(
- this,
- []() -> std::pair {
- return {
- st::historyForwardChooseBg->c,
- st::historyForwardChooseFg->c,
- };
- },
- _swipeBackMirrored,
- _swipeBackIconMirrored);
+ if (data.translation < 0) {
+ if (_inner) {
+ _inner->setSwipeContextData(std::move(data));
+ }
+ } else {
+ if (!_swipeBackData.callback) {
+ _swipeBackData = Ui::Controls::SetupSwipeBack(
+ this,
+ []() -> std::pair {
+ return {
+ st::historyForwardChooseBg->c,
+ st::historyForwardChooseFg->c,
+ };
+ },
+ _swipeBackMirrored,
+ _swipeBackIconMirrored);
+ }
+ _swipeBackData.callback(data);
}
- _swipeBackData.callback(data);
return;
} else {
if (_swipeBackData.lifetime) {
_swipeBackData = {};
}
+ if (_inner) {
+ _inner->setSwipeContextData({});
+ _inner->update();
+ }
}
- }, [=](int, Qt::LayoutDirection direction) {
+ }, [=](int top, Qt::LayoutDirection direction) {
_swipeBackIconMirrored = false;
_swipeBackMirrored = false;
if (_childListShown.current()) {
return Ui::Controls::SwipeHandlerFinishData();
}
const auto isRightToLeft = direction == Qt::RightToLeft;
+ if (!isRightToLeft && _inner) {
+ if (const auto key = _inner->calcSwipeKey(top)) {
+ const auto action = Dialogs::Ui::SwipeDialogAction::Mute;
+ _inner->prepareSwipeAction(key, action);
+ return Ui::Controls::SwipeHandlerFinishData{
+ .callback = [=, session = &session()] {
+ auto callback = [=, peerId = PeerId(key)] {
+ const auto peer = session->data().peer(peerId);
+ PerformSwipeDialogAction(peer, action);
+ };
+ base::call_delayed(
+ st::slideWrapDuration,
+ session,
+ std::move(callback));
+ },
+ .msgBareId = key,
+ .speedRatio = 1.,
+ .reachRatioDuration = crl::time(st::slideWrapDuration),
+ .provideReachOutRatio = true,
+ };
+ }
+ }
if (controller()->openedFolder().current()) {
if (!isRightToLeft) {
return Ui::Controls::SwipeHandlerFinishData();
diff --git a/Telegram/SourceFiles/dialogs/ui/dialogs_layout.cpp b/Telegram/SourceFiles/dialogs/ui/dialogs_layout.cpp
index 39a8e3826c..ebde34c6a5 100644
--- a/Telegram/SourceFiles/dialogs/ui/dialogs_layout.cpp
+++ b/Telegram/SourceFiles/dialogs/ui/dialogs_layout.cpp
@@ -28,12 +28,15 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "history/history_unread_things.h"
#include "history/view/history_view_item_preview.h"
#include "history/view/history_view_send_action.h"
+#include "lang/lang_instance.h"
#include "lang/lang_keys.h"
+#include "lottie/lottie_icon.h"
#include "main/main_session.h"
#include "storage/localstorage.h"
#include "support/support_helper.h"
#include "ui/empty_userpic.h"
#include "ui/painter.h"
+#include "ui/rect.h"
#include "ui/power_saving.h"
#include "ui/text/format_values.h"
#include "ui/text/text_options.h"
@@ -66,6 +69,54 @@ const auto kPsaBadgePrefix = "cloud_lng_badge_psa_";
return !history->isForum();
}
+[[nodiscard]] QString SwipeActionText(Dialogs::Ui::SwipeDialogAction type) {
+ return (type == Dialogs::Ui::SwipeDialogAction::Archive)
+ ? tr::lng_settings_swipe_archive(tr::now)
+ : (type == Dialogs::Ui::SwipeDialogAction::Delete)
+ ? tr::lng_settings_swipe_delete(tr::now)
+ : (type == Dialogs::Ui::SwipeDialogAction::Read)
+ ? tr::lng_settings_swipe_read(tr::now)
+ : (type == Dialogs::Ui::SwipeDialogAction::Pin)
+ ? tr::lng_settings_swipe_pin(tr::now)
+ : tr::lng_settings_swipe_mute(tr::now);
+}
+
+const style::font &SwipeActionFont(
+ Dialogs::Ui::SwipeDialogAction action,
+ int availableWidth) {
+ struct Entry final {
+ Dialogs::Ui::SwipeDialogAction action;
+ QString langId;
+ style::font font;
+ };
+ static auto Fonts = std::vector();
+ for (auto &entry : Fonts) {
+ if (entry.action == action) {
+ if (entry.langId == Lang::GetInstance().id()) {
+ return entry.font;
+ }
+ }
+ }
+ constexpr auto kNormalFontSize = 13;
+ constexpr auto kMinFontSize = 5;
+ for (auto i = kNormalFontSize; i >= kMinFontSize; --i) {
+ auto font = style::font(
+ style::ConvertScale(i, style::Scale()),
+ st::semiboldFont->flags(),
+ st::semiboldFont->family());
+ if (font->width(SwipeActionText(action)) <= availableWidth
+ || i == kMinFontSize) {
+ Fonts.emplace_back(Entry{
+ .action = action,
+ .langId = Lang::GetInstance().id(),
+ .font = std::move(font),
+ });
+ return Fonts.back().font;
+ }
+ }
+ Unexpected("SwipeActionFont: can't find font.");
+}
+
void PaintRowTopRight(
QPainter &p,
const QString &text,
@@ -344,11 +395,25 @@ void PaintRow(
draft = nullptr;
}
+ const auto history = entry->asHistory();
+ const auto thread = entry->asThread();
+ const auto sublist = entry->asSublist();
+
auto bg = context.active
? st::dialogsBgActive
: context.selected
? st::dialogsBgOver
: context.currentBg;
+ auto swipeTranslation = 0;
+ if (history
+ && history->peer->id.value == context.swipeContext.data.msgBareId) {
+ if (context.swipeContext.data.translation != 0) {
+ swipeTranslation = context.swipeContext.data.translation * -2;
+ }
+ }
+ if (swipeTranslation) {
+ p.translate(-swipeTranslation, 0);
+ }
p.fillRect(geometry, bg);
if (!(flags & Flag::TopicJumpRipple)) {
auto ripple = context.active
@@ -357,10 +422,6 @@ void PaintRow(
row->paintRipple(p, 0, 0, context.width, &ripple->c);
}
- const auto history = entry->asHistory();
- const auto thread = entry->asThread();
- const auto sublist = entry->asSublist();
-
if (flags & Flag::SavedMessages) {
EmptyUserpic::PaintSavedMessages(
p,
@@ -821,6 +882,54 @@ void PaintRow(
+ (tag->width() / style::DevicePixelRatio());
}
}
+ if (swipeTranslation) {
+ p.translate(swipeTranslation, 0);
+ const auto swipeActionRect = QRect(
+ geometry.x() + geometry.width() - swipeTranslation,
+ geometry.y(),
+ swipeTranslation,
+ geometry.height());
+ p.setClipRegion(swipeActionRect);
+ p.fillRect(swipeActionRect, st::attentionButtonFg);
+ if (context.swipeContext.data.reachRatio) {
+ p.setPen(Qt::NoPen);
+ p.setBrush(st::windowBgActive);
+ const auto r = swipeTranslation
+ * context.swipeContext.data.reachRatio;
+ const auto offset = st::dialogsSwipeActionSize
+ + st::dialogsSwipeActionSize / 2.;
+ p.drawEllipse(QPointF(geometry.width() - offset, offset), r, r);
+ }
+ const auto iconOffset = (geometry.height()
+ - st::dialogsSwipeActionSize) / 2;
+ const auto topTranslation = iconOffset / 2.;
+ p.translate(0, -topTranslation);
+ if (context.swipeContext.icon) {
+ context.swipeContext.icon->paint(
+ p,
+ rect::right(geometry)
+ - iconOffset
+ - st::dialogsSwipeActionSize,
+ iconOffset,
+ st::premiumButtonFg->c);
+ }
+ {
+ p.setPen(st::premiumButtonFg);
+ p.setBrush(Qt::NoBrush);
+ const auto left = rect::right(geometry)
+ - iconOffset * 2
+ - st::dialogsSwipeActionSize;
+ const auto availableWidth = geometry.width() - left;
+ p.setFont(
+ SwipeActionFont(context.swipeContext.action, availableWidth));
+ p.drawText(
+ QRect(left, 0, availableWidth, geometry.height()),
+ SwipeActionText(context.swipeContext.action),
+ style::al_bottom);
+ }
+ p.translate(0, topTranslation);
+ p.setClipRegion(QRegion());
+ }
}
} // namespace
diff --git a/Telegram/SourceFiles/dialogs/ui/dialogs_layout.h b/Telegram/SourceFiles/dialogs/ui/dialogs_layout.h
index e014e657f5..9b905eac82 100644
--- a/Telegram/SourceFiles/dialogs/ui/dialogs_layout.h
+++ b/Telegram/SourceFiles/dialogs/ui/dialogs_layout.h
@@ -7,6 +7,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
*/
#pragma once
+#include "dialogs/ui/dialogs_swipe_context.h"
#include "ui/cached_round_corners.h"
namespace style {
@@ -18,9 +19,6 @@ namespace st {
extern const style::DialogRow &defaultDialogRow;
} // namespace st
-namespace Ui {
-} // namespace Ui
-
namespace Data {
class Forum;
class Folder;
@@ -57,6 +55,7 @@ struct TopicJumpCache {
struct PaintContext {
RightButton *rightButton = nullptr;
std::vector *chatsFilterTags = nullptr;
+ SwipeContext swipeContext;
not_null st;
TopicJumpCache *topicJumpCache = nullptr;
Data::Folder *folder = nullptr;
diff --git a/Telegram/SourceFiles/dialogs/ui/dialogs_swipe_context.h b/Telegram/SourceFiles/dialogs/ui/dialogs_swipe_context.h
new file mode 100644
index 0000000000..bbfc81d018
--- /dev/null
+++ b/Telegram/SourceFiles/dialogs/ui/dialogs_swipe_context.h
@@ -0,0 +1,35 @@
+/*
+This file is part of Telegram Desktop,
+the official desktop application for the Telegram messaging service.
+
+For license and copyright information please follow this link:
+https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
+*/
+#pragma once
+
+#include "ui/controls/swipe_handler_data.h"
+
+namespace Lottie {
+class Icon;
+} // namespace Lottie
+
+namespace Dialogs::Ui {
+
+using namespace ::Ui;
+
+enum class SwipeDialogAction {
+ Mute,
+ Pin,
+ Read,
+ Archive,
+ Delete,
+ Disabled,
+};
+
+struct SwipeContext {
+ ::Ui::Controls::SwipeContextData data;
+ Lottie::Icon *icon = nullptr;
+ SwipeDialogAction action;
+};
+
+} // namespace Dialogs::Ui
diff --git a/Telegram/cmake/td_ui.cmake b/Telegram/cmake/td_ui.cmake
index 321fcbdbc9..1e66b314a3 100644
--- a/Telegram/cmake/td_ui.cmake
+++ b/Telegram/cmake/td_ui.cmake
@@ -103,6 +103,7 @@ PRIVATE
dialogs/ui/chat_search_in.h
dialogs/ui/dialogs_stories_list.cpp
dialogs/ui/dialogs_stories_list.h
+ dialogs/ui/dialogs_swipe_context.h
dialogs/ui/top_peers_strip.cpp
dialogs/ui/top_peers_strip.h