2
0
mirror of https://github.com/telegramdesktop/tdesktop synced 2025-08-29 05:29:23 +00:00

Improve Ctrl+Tab switch design.

This commit is contained in:
John Preston 2025-08-21 18:04:19 +04:00
parent 0d8065fc1f
commit fe26594f12
4 changed files with 63 additions and 16 deletions

View File

@ -333,11 +333,22 @@ maxWidthSharedMediaWindow: 419px;
chatSwitchMargins: margins(16px, 16px, 16px, 16px); chatSwitchMargins: margins(16px, 16px, 16px, 16px);
chatSwitchPadding: margins(12px, 12px, 12px, 12px); chatSwitchPadding: margins(12px, 12px, 12px, 12px);
chatSwitchSize: size(72px, 72px); chatSwitchSize: size(72px, 104px);
chatSwitchUserpic: UserpicButton(defaultUserpicButton) { chatSwitchUserpic: UserpicButton(defaultUserpicButton) {
size: size(56px, 56px); size: size(56px, 56px);
photoSize: 56px; photoSize: 56px;
} }
chatSwitchUserpicTop: 8px;
chatSwitchNameLabel: FlatLabel(defaultFlatLabel) {
style: TextStyle(defaultTextStyle) {
font: font(11px);
}
align: align(top);
minWidth: 56px;
maxHeight: 36px;
}
chatSwitchNameSkip: 6px;
chatSwitchSelectLine: 3px;
// Windows specific // Windows specific

View File

@ -11,14 +11,21 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "data/components/recent_peers.h" #include "data/components/recent_peers.h"
#include "data/data_thread.h" #include "data/data_thread.h"
#include "main/main_session.h" #include "main/main_session.h"
#include "ui/widgets/labels.h"
#include "ui/widgets/shadow.h" #include "ui/widgets/shadow.h"
#include "ui/controls/userpic_button.h" #include "ui/controls/userpic_button.h"
#include "ui/painter.h"
#include "ui/rp_widget.h" #include "ui/rp_widget.h"
#include "styles/style_layers.h" #include "styles/style_layers.h"
#include "styles/style_window.h" #include "styles/style_window.h"
namespace Window { namespace Window {
struct ChatSwitchProcess::Entry {
not_null<Ui::AbstractButton*> button;
Ui::Animations::Simple overAnimation;
};
ChatSwitchProcess::ChatSwitchProcess( ChatSwitchProcess::ChatSwitchProcess(
not_null<Ui::RpWidget*> geometry, not_null<Ui::RpWidget*> geometry,
not_null<Main::Session*> session, not_null<Main::Session*> session,
@ -27,8 +34,7 @@ ChatSwitchProcess::ChatSwitchProcess(
, _widget(std::make_unique<Ui::RpWidget>( , _widget(std::make_unique<Ui::RpWidget>(
geometry->parentWidget() ? geometry->parentWidget() : geometry)) geometry->parentWidget() ? geometry->parentWidget() : geometry))
, _view(Ui::CreateChild<Ui::RpWidget>(_widget.get()))\ , _view(Ui::CreateChild<Ui::RpWidget>(_widget.get()))\
, _bg(st::boxRadius, st::boxBg) , _bg(st::boxRadius, st::boxBg) {
, _over(st::boxRadius, st::windowBgOver) {
setupWidget(geometry); setupWidget(geometry);
setupContent(opened); setupContent(opened);
setupView(); setupView();
@ -76,11 +82,19 @@ void ChatSwitchProcess::setSelected(int index) {
return; return;
} }
if (_selected >= 0) { if (_selected >= 0) {
_entries[_selected].button->update(); auto &entry = _entries[_selected];
const auto raw = entry.button.get();
entry.overAnimation.start([=] {
raw->update();
}, 1., 0., st::slideWrapDuration);
} }
_selected = index; _selected = index;
if (_selected >= 0) { if (_selected >= 0) {
_entries[_selected].button->update(); auto &entry = _entries[_selected];
const auto raw = entry.button.get();
entry.overAnimation.start([=] {
raw->update();
}, 0., 1., st::slideWrapDuration);
} }
} }
@ -119,9 +133,19 @@ void ChatSwitchProcess::setupContent(Data::Thread *opened) {
const auto button = Ui::CreateChild<Ui::AbstractButton>(_view.get()); const auto button = Ui::CreateChild<Ui::AbstractButton>(_view.get());
button->resize(st::chatSwitchSize); button->resize(st::chatSwitchSize);
button->paintRequest() | rpl::start_with_next([=] { button->paintRequest() | rpl::start_with_next([=] {
if (index == _selected) { const auto selection = _entries[index].overAnimation.value(
(index == _selected) ? 1. : 0.);
if (selection > 0.) {
auto p = QPainter(button); auto p = QPainter(button);
_over.paint(p, button->rect()); auto hq = PainterHighQualityEnabler(p);
const auto radius = st::boxRadius;
const auto line = st::chatSwitchSelectLine;
auto pen = st::defaultRoundCheckbox.bgActive->p;
pen.setWidthF(line * selection);
p.setPen(pen);
const auto r = QRectF(button->rect()).marginsRemoved(
{ line / 2., line / 2., line / 2., line / 2. });
p.drawRoundedRect(r, radius, radius);
} }
}, button->lifetime()); }, button->lifetime());
button->setClickedCallback([=] { button->setClickedCallback([=] {
@ -141,9 +165,24 @@ void ChatSwitchProcess::setupContent(Data::Thread *opened) {
userpic->show(); userpic->show();
userpic->move( userpic->move(
((button->width() - userpic->width()) / 2), ((button->width() - userpic->width()) / 2),
((button->height() - userpic->height()) / 2)); st::chatSwitchUserpicTop);
userpic->setAttribute(Qt::WA_TransparentForMouseEvents); userpic->setAttribute(Qt::WA_TransparentForMouseEvents);
const auto label = Ui::CreateChild<Ui::FlatLabel>(
button,
thread->chatListName(),
st::chatSwitchNameLabel);
label->setBreakEverywhere(true);
label->show();
label->resizeToNaturalWidth(
button->width() - 2 * st::chatSwitchNameSkip);
label->move(
(button->width() - label->width()) / 2,
(button->height()
+ userpic->y()
+ userpic->height()
- label->height()) / 2);
_entries.push_back({ .button = button }); _entries.push_back({ .button = button });
++index; ++index;

View File

@ -46,9 +46,8 @@ public:
[[nodiscard]] rpl::lifetime &lifetime(); [[nodiscard]] rpl::lifetime &lifetime();
private: private:
struct Entry { struct Entry;
not_null<Ui::AbstractButton*> button;
};
void setupWidget(not_null<Ui::RpWidget*> geometry); void setupWidget(not_null<Ui::RpWidget*> geometry);
void setupContent(Data::Thread *opened); void setupContent(Data::Thread *opened);
void setupView(); void setupView();
@ -65,7 +64,6 @@ private:
QRect _outer; QRect _outer;
QRect _inner; QRect _inner;
Ui::RoundRect _bg; Ui::RoundRect _bg;
Ui::RoundRect _over;
std::vector<not_null<Data::Thread*>> _list; std::vector<not_null<Data::Thread*>> _list;
std::vector<Entry> _entries; std::vector<Entry> _entries;

View File

@ -2067,10 +2067,9 @@ void SessionController::setActiveChatEntry(Dialogs::RowDescriptor row) {
{ anim::type::normal, anim::activation::background }); { anim::type::normal, anim::activation::background });
}, _activeHistoryLifetime); }, _activeHistoryLifetime);
} }
}
if (const auto thread = row.key.thread()) { if (const auto thread = row.key.thread()) {
session().recentPeers().chatOpenPush(thread); session().recentPeers().chatOpenPush(thread);
}
} }
if (session().supportMode()) { if (session().supportMode()) {
pushToChatEntryHistory(row); pushToChatEntryHistory(row);