feat: icon picker
Inspired by Forkgram's icon changer Need to refactor a bit later
|
@ -50,6 +50,7 @@ If you enjoy using **AyuGram** and want to send us a tip, here's how you can do
|
|||
- [Telegram Desktop](https://github.com/telegramdesktop/tdesktop)
|
||||
- [Kotatogram](https://github.com/kotatogram/kotatogram-desktop)
|
||||
- [64Gram](https://github.com/TDesktop-x64/tdesktop)
|
||||
- [Forkgram](https://github.com/forkgram/tdesktop)
|
||||
- [SQLite](https://github.com/sqlite/sqlite)
|
||||
- [sqlite_orm](https://github.com/fnc12/sqlite_orm)
|
||||
|
||||
|
|
|
@ -106,8 +106,12 @@ PRIVATE
|
|||
ayu/utils/telegram_helpers.h
|
||||
ayu/ui/ayu_lottie.cpp
|
||||
ayu/ui/ayu_lottie.h
|
||||
ayu/ui/ayu_assets.cpp
|
||||
ayu/ui/ayu_assets.h
|
||||
ayu/ui/utils/ayu_profile_values.cpp
|
||||
ayu/ui/utils/ayu_profile_values.h
|
||||
ayu/ui/settings/icon_picker.cpp
|
||||
ayu/ui/settings/icon_picker.h
|
||||
ayu/ui/settings/settings_ayu.cpp
|
||||
ayu/ui/settings/settings_ayu.h
|
||||
ayu/ui/context_menu/context_menu.cpp
|
||||
|
@ -1514,6 +1518,8 @@ endif()
|
|||
|
||||
nice_target_sources(Telegram ${res_loc}
|
||||
PRIVATE
|
||||
qrc/ayu/ayu.qrc
|
||||
|
||||
qrc/emoji_1.qrc
|
||||
qrc/emoji_2.qrc
|
||||
qrc/emoji_3.qrc
|
||||
|
|
BIN
Telegram/Resources/art/ayu/alt/logo256.png
Normal file
After Width: | Height: | Size: 11 KiB |
BIN
Telegram/Resources/art/ayu/alt/logo256_no_margin.png
Normal file
After Width: | Height: | Size: 8.5 KiB |
BIN
Telegram/Resources/art/ayu/nothing/logo256.png
Normal file
After Width: | Height: | Size: 7 KiB |
BIN
Telegram/Resources/art/ayu/nothing/logo256_no_margin.png
Normal file
After Width: | Height: | Size: 6.9 KiB |
Before Width: | Height: | Size: 3.2 KiB After Width: | Height: | Size: 6.7 KiB |
Before Width: | Height: | Size: 6.3 KiB After Width: | Height: | Size: 12 KiB |
Before Width: | Height: | Size: 507 B After Width: | Height: | Size: 832 B |
Before Width: | Height: | Size: 921 B After Width: | Height: | Size: 1.7 KiB |
Before Width: | Height: | Size: 108 KiB After Width: | Height: | Size: 8.7 KiB |
Before Width: | Height: | Size: 6.3 KiB After Width: | Height: | Size: 12 KiB |
Before Width: | Height: | Size: 13 KiB After Width: | Height: | Size: 24 KiB |
Before Width: | Height: | Size: 921 B After Width: | Height: | Size: 1.7 KiB |
Before Width: | Height: | Size: 1.7 KiB After Width: | Height: | Size: 3.5 KiB |
Before Width: | Height: | Size: 1.3 KiB After Width: | Height: | Size: 2.6 KiB |
Before Width: | Height: | Size: 2.5 KiB After Width: | Height: | Size: 5.1 KiB |
Before Width: | Height: | Size: 13 KiB After Width: | Height: | Size: 24 KiB |
Before Width: | Height: | Size: 72 KiB After Width: | Height: | Size: 58 KiB |
Before Width: | Height: | Size: 1.7 KiB After Width: | Height: | Size: 3.5 KiB |
Before Width: | Height: | Size: 6.3 KiB After Width: | Height: | Size: 6.7 KiB |
Before Width: | Height: | Size: 72 KiB After Width: | Height: | Size: 58 KiB |
Before Width: | Height: | Size: 6.3 KiB After Width: | Height: | Size: 12 KiB |
Before Width: | Height: | Size: 6.3 KiB After Width: | Height: | Size: 9.7 KiB |
8
Telegram/Resources/qrc/ayu/ayu.qrc
Normal file
|
@ -0,0 +1,8 @@
|
|||
<RCC>
|
||||
<qresource prefix="/gui">
|
||||
<file alias="art/ayu/alt/logo256.png">../../art/ayu/alt/logo256.png</file>
|
||||
<file alias="art/ayu/alt/logo256_no_margin.png">../../art/ayu/alt/logo256_no_margin.png</file>
|
||||
<file alias="art/ayu/nothing/logo256.png">../../art/ayu/nothing/logo256.png</file>
|
||||
<file alias="art/ayu/nothing/logo256_no_margin.png">../../art/ayu/nothing/logo256_no_margin.png</file>
|
||||
</qresource>
|
||||
</RCC>
|
|
@ -229,6 +229,11 @@ namespace AyuSettings
|
|||
copyUsernameAsLink = val;
|
||||
}
|
||||
|
||||
void AyuGramSettings::set_appIcon(QString val)
|
||||
{
|
||||
appIcon = std::move(val);
|
||||
}
|
||||
|
||||
void AyuGramSettings::set_deletedMark(QString val)
|
||||
{
|
||||
deletedMark = std::move(val);
|
||||
|
|
|
@ -14,6 +14,10 @@
|
|||
|
||||
namespace AyuSettings
|
||||
{
|
||||
const auto DEFAULT_ICON = QString("default");
|
||||
const auto ALT_ICON = QString("alt");
|
||||
const auto NOTHING_ICON = QString("nothing");
|
||||
|
||||
class AyuGramSettings
|
||||
{
|
||||
public:
|
||||
|
@ -40,6 +44,7 @@ namespace AyuSettings
|
|||
copyUsernameAsLink = true;
|
||||
|
||||
// ~ Customization
|
||||
appIcon = DEFAULT_ICON;
|
||||
deletedMark = "🧹";
|
||||
editedMark = tr::lng_edited(tr::now);
|
||||
recentStickersCount = 20;
|
||||
|
@ -74,6 +79,7 @@ namespace AyuSettings
|
|||
bool disableStories;
|
||||
bool localPremium;
|
||||
bool copyUsernameAsLink;
|
||||
QString appIcon;
|
||||
QString deletedMark;
|
||||
QString editedMark;
|
||||
int recentStickersCount;
|
||||
|
@ -114,6 +120,8 @@ namespace AyuSettings
|
|||
|
||||
void set_copyUsernameAsLink(bool val);
|
||||
|
||||
void set_appIcon(QString val);
|
||||
|
||||
void set_deletedMark(QString val);
|
||||
|
||||
void set_editedMark(QString val);
|
||||
|
@ -150,6 +158,7 @@ namespace AyuSettings
|
|||
disableStories,
|
||||
localPremium,
|
||||
copyUsernameAsLink,
|
||||
appIcon,
|
||||
deletedMark,
|
||||
editedMark,
|
||||
recentStickersCount,
|
||||
|
@ -174,7 +183,6 @@ namespace AyuSettings
|
|||
|
||||
rpl::producer<int> get_showPeerIdReactive();
|
||||
|
||||
// computed fields
|
||||
bool get_ghostModeEnabled();
|
||||
|
||||
rpl::producer<bool> get_ghostModeEnabledReactive();
|
||||
|
|
89
Telegram/SourceFiles/ayu/ui/ayu_assets.cpp
Normal file
|
@ -0,0 +1,89 @@
|
|||
// This is the source code of AyuGram for Desktop.
|
||||
//
|
||||
// We do not and cannot prevent the use of our code,
|
||||
// but be respectful and credit the original author.
|
||||
//
|
||||
// Copyright @Radolyn, 2023
|
||||
|
||||
#include "ayu_assets.h"
|
||||
#include "ayu/ayu_settings.h"
|
||||
|
||||
QString LAST_LOADED_NAME;
|
||||
QImage LAST_LOADED;
|
||||
QImage LAST_LOADED_NO_MARGIN;
|
||||
|
||||
void loadIcons()
|
||||
{
|
||||
auto settings = &AyuSettings::getInstance();
|
||||
if (LAST_LOADED_NAME != settings->appIcon)
|
||||
{
|
||||
LAST_LOADED_NAME = settings->appIcon;
|
||||
if (settings->appIcon == AyuSettings::DEFAULT_ICON)
|
||||
{
|
||||
LAST_LOADED = logo();
|
||||
LAST_LOADED_NO_MARGIN = logoNoMargin();
|
||||
}
|
||||
else if (settings->appIcon == AyuSettings::ALT_ICON)
|
||||
{
|
||||
LAST_LOADED = logoAlt();
|
||||
LAST_LOADED_NO_MARGIN = logoAltNoMargin();
|
||||
}
|
||||
else if (settings->appIcon == AyuSettings::NOTHING_ICON)
|
||||
{
|
||||
LAST_LOADED = logoNothing();
|
||||
LAST_LOADED_NO_MARGIN = logoNothingNoMargin();
|
||||
}
|
||||
else
|
||||
{
|
||||
LAST_LOADED = logo();
|
||||
LAST_LOADED_NO_MARGIN = logoNoMargin();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
QImage logo()
|
||||
{
|
||||
return QImage(qsl(":/gui/art/logo_256.png"));
|
||||
}
|
||||
|
||||
QImage logoNoMargin()
|
||||
{
|
||||
return QImage(qsl(":/gui/art/logo_256_no_margin.png"));
|
||||
}
|
||||
|
||||
QImage logoAlt()
|
||||
{
|
||||
return QImage(qsl(":/gui/art/ayu/alt/logo256.png"));
|
||||
}
|
||||
|
||||
QImage logoAltNoMargin()
|
||||
{
|
||||
return QImage(qsl(":/gui/art/ayu/alt/logo256_no_margin.png"));
|
||||
}
|
||||
|
||||
QImage logoNothing()
|
||||
{
|
||||
return QImage(qsl(":/gui/art/ayu/nothing/logo256.png"));
|
||||
}
|
||||
|
||||
QImage logoNothingNoMargin()
|
||||
{
|
||||
return QImage(qsl(":/gui/art/ayu/nothing/logo256_no_margin.png"));
|
||||
}
|
||||
|
||||
QString currentAppLogoName()
|
||||
{
|
||||
return LAST_LOADED_NAME;
|
||||
}
|
||||
|
||||
QImage currentAppLogo()
|
||||
{
|
||||
loadIcons();
|
||||
return LAST_LOADED;
|
||||
}
|
||||
|
||||
QImage currentAppLogoNoMargin()
|
||||
{
|
||||
loadIcons();
|
||||
return LAST_LOADED_NO_MARGIN;
|
||||
}
|
21
Telegram/SourceFiles/ayu/ui/ayu_assets.h
Normal file
|
@ -0,0 +1,21 @@
|
|||
// This is the source code of AyuGram for Desktop.
|
||||
//
|
||||
// We do not and cannot prevent the use of our code,
|
||||
// but be respectful and credit the original author.
|
||||
//
|
||||
// Copyright @Radolyn, 2023
|
||||
|
||||
#pragma once
|
||||
|
||||
QImage logo();
|
||||
QImage logoNoMargin();
|
||||
|
||||
QImage logoAlt();
|
||||
QImage logoAltNoMargin();
|
||||
|
||||
QImage logoNothing();
|
||||
QImage logoNothingNoMargin();
|
||||
|
||||
QString currentAppLogoName();
|
||||
QImage currentAppLogo();
|
||||
QImage currentAppLogoNoMargin();
|
|
@ -1,3 +1,12 @@
|
|||
/*
|
||||
* This is the source code of AyuGram for Desktop.
|
||||
*
|
||||
* We do not and cannot prevent the use of our code,
|
||||
* but be respectful and credit the original author.
|
||||
*
|
||||
* Copyright @Radolyn, 2023
|
||||
*/
|
||||
|
||||
using "ui/colors.palette";
|
||||
using "ui/widgets/widgets.style";
|
||||
|
||||
|
|
|
@ -7,10 +7,12 @@
|
|||
|
||||
#include "ayu_lottie.h"
|
||||
|
||||
namespace AyuUi {
|
||||
std::unique_ptr<Lottie::Icon> getLottie(const QString& text) {
|
||||
namespace AyuUi
|
||||
{
|
||||
std::unique_ptr<Lottie::Icon> getLottie(const QString& text)
|
||||
{
|
||||
// todo: some kind of mapping
|
||||
// Lottie::MakeIcon({.json = QString(), .sizeOverride = {24, 24}});
|
||||
return nullptr;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -9,6 +9,7 @@
|
|||
|
||||
#include "lottie/lottie_icon.h"
|
||||
|
||||
namespace AyuUi {
|
||||
namespace AyuUi
|
||||
{
|
||||
std::unique_ptr<Lottie::Icon> getLottie(const QString& text);
|
||||
}
|
||||
|
|
14
Telegram/SourceFiles/ayu/ui/ayu_styles.style
Normal file
|
@ -0,0 +1,14 @@
|
|||
/*
|
||||
* This is the source code of AyuGram for Desktop.
|
||||
*
|
||||
* We do not and cannot prevent the use of our code,
|
||||
* but be respectful and credit the original author.
|
||||
*
|
||||
* Copyright @Radolyn, 2023
|
||||
*/
|
||||
|
||||
using "ui/basic.style";
|
||||
using "ui/colors.palette";
|
||||
using "ui/widgets/widgets.style";
|
||||
|
||||
iconPreviewStroke: activeButtonBg;
|
85
Telegram/SourceFiles/ayu/ui/settings/icon_picker.cpp
Normal file
|
@ -0,0 +1,85 @@
|
|||
// This is the source code of AyuGram for Desktop.
|
||||
//
|
||||
// We do not and cannot prevent the use of our code,
|
||||
// but be respectful and credit the original author.
|
||||
//
|
||||
// Copyright @Radolyn, 2023
|
||||
|
||||
#include "icon_picker.h"
|
||||
#include "ayu/ayu_settings.h"
|
||||
#include "core/application.h"
|
||||
#include "styles/style_layers.h"
|
||||
|
||||
#include "ayu/ui/ayu_assets.h"
|
||||
#include "main/main_domain.h"
|
||||
#include "styles/style_ayu_styles.h"
|
||||
#include "ui/painter.h"
|
||||
#include "window/main_window.h"
|
||||
|
||||
void drawIcon(QPainter& p, const QImage& icon, int offset, bool selected)
|
||||
{
|
||||
if (selected)
|
||||
{
|
||||
p.save();
|
||||
p.setPen(QPen(st::iconPreviewStroke, 2));
|
||||
p.drawEllipse(offset + 2, 2, 68, 68);
|
||||
p.restore();
|
||||
}
|
||||
|
||||
auto rect = QRect(offset + 4, 4, 64, 64);
|
||||
p.drawImage(rect, icon);
|
||||
}
|
||||
|
||||
IconPicker::IconPicker(QWidget* parent) : RpWidget(parent)
|
||||
{
|
||||
setMinimumSize(st::boxWidth, 72);
|
||||
}
|
||||
|
||||
void IconPicker::paintEvent(QPaintEvent* e)
|
||||
{
|
||||
Painter p(this);
|
||||
PainterHighQualityEnabler hq(p);
|
||||
|
||||
auto icon1 = logo().scaled(64, 64, Qt::KeepAspectRatio, Qt::SmoothTransformation);
|
||||
auto icon2 = logoAlt().scaled(64, 64, Qt::KeepAspectRatio, Qt::SmoothTransformation);
|
||||
auto icon3 = logoNothing().scaled(64, 64, Qt::KeepAspectRatio, Qt::SmoothTransformation);
|
||||
|
||||
// todo: center
|
||||
drawIcon(p, icon1, 0, currentAppLogoName() == AyuSettings::DEFAULT_ICON);
|
||||
drawIcon(p, icon2, 0 + 64 + 16, currentAppLogoName() == AyuSettings::ALT_ICON);
|
||||
drawIcon(p, icon3, 0 + 64 + 16 + 64 + 16, currentAppLogoName() == AyuSettings::NOTHING_ICON);
|
||||
}
|
||||
|
||||
void IconPicker::mousePressEvent(QMouseEvent* e)
|
||||
{
|
||||
auto settings = &AyuSettings::getInstance();
|
||||
auto changed = false;
|
||||
|
||||
auto x = e->pos().x();
|
||||
if (x <= 64 && settings->appIcon != AyuSettings::DEFAULT_ICON)
|
||||
{
|
||||
settings->set_appIcon(AyuSettings::DEFAULT_ICON);
|
||||
changed = true;
|
||||
}
|
||||
else if (x >= 64 + 16 && x <= 64 + 16 + 64 && settings->appIcon != AyuSettings::ALT_ICON)
|
||||
{
|
||||
settings->set_appIcon(AyuSettings::ALT_ICON);
|
||||
changed = true;
|
||||
}
|
||||
else if (x >= 64 + 16 + 64 + 16 && x < 64 + 16 + 64 + 16 + 64 && settings->appIcon != AyuSettings::NOTHING_ICON)
|
||||
{
|
||||
settings->set_appIcon(AyuSettings::NOTHING_ICON);
|
||||
changed = true;
|
||||
}
|
||||
|
||||
if (changed)
|
||||
{
|
||||
AyuSettings::save();
|
||||
|
||||
Window::OverrideApplicationIcon(currentAppLogo());
|
||||
Core::App().refreshApplicationIcon();
|
||||
Core::App().domain().notifyUnreadBadgeChanged();
|
||||
|
||||
repaint();
|
||||
}
|
||||
}
|
20
Telegram/SourceFiles/ayu/ui/settings/icon_picker.h
Normal file
|
@ -0,0 +1,20 @@
|
|||
// This is the source code of AyuGram for Desktop.
|
||||
//
|
||||
// We do not and cannot prevent the use of our code,
|
||||
// but be respectful and credit the original author.
|
||||
//
|
||||
// Copyright @Radolyn, 2023
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "ui/rp_widget.h"
|
||||
|
||||
class IconPicker : public Ui::RpWidget
|
||||
{
|
||||
public:
|
||||
IconPicker(QWidget* parent);
|
||||
|
||||
protected:
|
||||
void paintEvent(QPaintEvent* e) override;
|
||||
void mousePressEvent(QMouseEvent* e) override;
|
||||
};
|
|
@ -34,6 +34,7 @@
|
|||
#include "styles/style_settings.h"
|
||||
#include "styles/style_widgets.h"
|
||||
|
||||
#include "icon_picker.h"
|
||||
#include "ui/painter.h"
|
||||
#include "ui/boxes/confirm_box.h"
|
||||
#include "ui/boxes/single_choice_box.h"
|
||||
|
@ -626,6 +627,13 @@ namespace Settings
|
|||
}, container->lifetime());
|
||||
}
|
||||
|
||||
void Ayu::SetupAppIcon(not_null<Ui::VerticalLayout*> container)
|
||||
{
|
||||
container->add(
|
||||
object_ptr<IconPicker>(container),
|
||||
st::settingsSubsectionTitlePadding);
|
||||
}
|
||||
|
||||
void Ayu::SetupCustomization(not_null<Ui::VerticalLayout*> container,
|
||||
not_null<Window::SessionController*> controller)
|
||||
{
|
||||
|
@ -633,6 +641,8 @@ namespace Settings
|
|||
|
||||
AddSubsectionTitle(container, tr::ayu_CustomizationHeader());
|
||||
|
||||
SetupAppIcon(container);
|
||||
|
||||
auto btn = AddButtonWithLabel(
|
||||
container,
|
||||
tr::ayu_DeletedMarkText(),
|
||||
|
|
|
@ -44,6 +44,8 @@ namespace Settings
|
|||
|
||||
void SetupQoLToggles(not_null<Ui::VerticalLayout*> container);
|
||||
|
||||
void SetupAppIcon(not_null<Ui::VerticalLayout*> container);
|
||||
|
||||
void SetupCustomization(not_null<Ui::VerticalLayout*> container,
|
||||
not_null<Window::SessionController*> controller);
|
||||
|
||||
|
|
|
@ -24,6 +24,10 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
#include <private/qguiapplication_p.h>
|
||||
#include <private/qhighdpiscaling_p.h>
|
||||
|
||||
// AyuGram includes
|
||||
#include "ayu/ui/ayu_assets.h"
|
||||
|
||||
|
||||
namespace Platform {
|
||||
|
||||
namespace {
|
||||
|
@ -37,6 +41,12 @@ constexpr auto kTooltipDelay = crl::time(10000);
|
|||
static constexpr auto kCount = 3;
|
||||
static auto ScaledLogo = std::array<QImage, kCount>();
|
||||
static auto ScaledLogoNoMargin = std::array<QImage, kCount>();
|
||||
static auto lastUsedIcon = currentAppLogoName();
|
||||
|
||||
if (lastUsedIcon != currentAppLogoName()) {
|
||||
ScaledLogo = std::array<QImage, kCount>();
|
||||
ScaledLogoNoMargin = std::array<QImage, kCount>();
|
||||
}
|
||||
|
||||
struct Dimensions {
|
||||
int index = 0;
|
||||
|
|
|
@ -52,6 +52,10 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
|
||||
#include <kurlmimedata.h>
|
||||
|
||||
// AyuGram includes
|
||||
#include "ayu/ui/ayu_assets.h"
|
||||
|
||||
|
||||
namespace Window {
|
||||
namespace {
|
||||
|
||||
|
@ -74,14 +78,12 @@ using Core::WindowPosition;
|
|||
|
||||
} // namespace
|
||||
|
||||
const QImage &Logo() {
|
||||
static const auto result = QImage(u":/gui/art/logo_256.png"_q);
|
||||
return result;
|
||||
QImage Logo() {
|
||||
return currentAppLogo();
|
||||
}
|
||||
|
||||
const QImage &LogoNoMargin() {
|
||||
static const auto result = QImage(u":/gui/art/logo_256_no_margin.png"_q);
|
||||
return result;
|
||||
QImage LogoNoMargin() {
|
||||
return currentAppLogoNoMargin();
|
||||
}
|
||||
|
||||
void ConvertIconToBlack(QImage &image) {
|
||||
|
@ -136,16 +138,7 @@ void OverrideApplicationIcon(QImage image) {
|
|||
}
|
||||
|
||||
QIcon CreateOfficialIcon(Main::Session *session) {
|
||||
const auto support = (session && session->supportMode());
|
||||
if (!support) {
|
||||
return QIcon();
|
||||
}
|
||||
auto overriden = OverridenIcon();
|
||||
auto image = overriden.isNull()
|
||||
? Platform::DefaultApplicationIcon()
|
||||
: overriden;
|
||||
ConvertIconToBlack(image);
|
||||
return QIcon(Ui::PixmapFromImage(std::move(image)));
|
||||
return QIcon(Ui::PixmapFromImage(currentAppLogo()));
|
||||
}
|
||||
|
||||
QIcon CreateIcon(Main::Session *session, bool returnNullIfDefault) {
|
||||
|
|
|
@ -35,8 +35,8 @@ class SessionController;
|
|||
class TitleWidget;
|
||||
struct TermsLock;
|
||||
|
||||
[[nodiscard]] const QImage &Logo();
|
||||
[[nodiscard]] const QImage &LogoNoMargin();
|
||||
[[nodiscard]] QImage Logo();
|
||||
[[nodiscard]] QImage LogoNoMargin();
|
||||
void OverrideApplicationIcon(QImage image);
|
||||
[[nodiscard]] QIcon CreateIcon(
|
||||
Main::Session *session = nullptr,
|
||||
|
|
|
@ -13,6 +13,7 @@ include(cmake/generate_numbers.cmake)
|
|||
|
||||
set(style_files
|
||||
ayu/ui/ayu_icons.style
|
||||
ayu/ui/ayu_styles.style
|
||||
|
||||
ui/td_common.style
|
||||
ui/filter_icons.style
|
||||
|
|
2
cmake
|
@ -1 +1 @@
|
|||
Subproject commit bd556e2a16d34ad876054fb3ab25e83481af652a
|
||||
Subproject commit 797fa772cd95f5eb087c95e9ff619c9888ad8604
|