ZaStoGram_desktop/Telegram/SourceFiles/boxes/about_box.cpp
loop-uh 5f69581fec Say which ZaStoGram build you are actually running
The side menu called the app Telegram Desktop and showed only the base
version number, so an installed dev build looked exactly like the stable
release it was built from. It now names ZaStoGram and carries the
pre-release number CI built it as.
2026-07-27 23:26:02 +03:00

318 lines
8.2 KiB
C++

/*
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 "boxes/about_box.h"
#include "base/platform/base_platform_info.h"
#include "core/application.h"
#include "core/file_utilities.h"
#include "core/update_checker.h"
#include "core/version.h"
#include "core/zsg_build.h"
#include "lang/lang_keys.h"
#include "ui/boxes/confirm_box.h"
#include "ui/painter.h"
#include "ui/rect.h"
#include "ui/text/text_utilities.h"
#include "ui/vertical_list.h"
#include "ui/widgets/buttons.h"
#include "ui/wrap/vertical_layout.h"
#include "styles/style_layers.h"
#include "styles/style_boxes.h"
#include "styles/style_channel_earn.h"
#include "styles/style_chat.h"
#include "styles/style_dialogs.h"
#include "styles/style_menu_icons.h"
#include "styles/style_premium.h"
#include "styles/style_settings.h"
#include <QtGui/QGuiApplication>
#include <QtGui/QClipboard>
namespace {
rpl::producer<TextWithEntities> Text1() {
return tr::lng_about_text1(
lt_api_link,
tr::lng_about_text1_api(tr::url(u"https://core.telegram.org/api"_q)),
tr::marked);
}
rpl::producer<TextWithEntities> Text2() {
return tr::lng_about_text2(
lt_gpl_link,
rpl::single(tr::link(
"GNU GPL",
"https://github.com/telegramdesktop/tdesktop/blob/master/LICENSE")),
lt_github_link,
rpl::single(tr::link(
"GitHub",
"https://github.com/telegramdesktop/tdesktop")),
tr::marked);
}
rpl::producer<TextWithEntities> Text3() {
return tr::lng_about_text3(
lt_faq_link,
tr::lng_about_text3_faq(tr::url(telegramFaqLink())),
tr::marked);
}
} // namespace
void AboutBox(not_null<Ui::GenericBox*> box) {
box->setTitle(AppName.utf16());
auto layout = box->verticalLayout();
const auto version = layout->add(
object_ptr<Ui::LinkButton>(
box,
tr::lng_about_version(
tr::now,
lt_version,
currentVersionText()),
st::aboutVersionLink),
QMargins(
st::boxRowPadding.left(),
-st::lineWidth * 3,
st::boxRowPadding.right(),
st::boxRowPadding.bottom()));
version->setClickedCallback([=] {
if (cRealAlphaVersion()) {
auto url = u"https://tdesktop.com/"_q;
if (Platform::IsWindows32Bit()) {
url += u"win/%1.zip"_q;
} else if (Platform::IsWindows64Bit()) {
url += u"win64/%1.zip"_q;
} else if (Platform::IsWindowsARM64()) {
url += u"winarm/%1.zip"_q;
} else if (Platform::IsMac()) {
url += u"mac/%1.zip"_q;
} else if (Platform::IsLinux()) {
url += u"linux/%1.tar.xz"_q;
} else {
Unexpected("Platform value.");
}
url = url.arg(u"talpha%1_%2"_q
.arg(cRealAlphaVersion())
.arg(Core::countAlphaVersionSignature(cRealAlphaVersion())));
QGuiApplication::clipboard()->setText(url);
box->getDelegate()->show(
Ui::MakeInformBox(
"The link to the current private alpha "
"version of Telegram Desktop was copied "
"to the clipboard."));
} else {
File::OpenUrl(Core::App().changelogLink());
}
});
Ui::AddSkip(layout, st::aboutTopSkip);
const auto addText = [&](rpl::producer<TextWithEntities> text) {
const auto label = layout->add(
object_ptr<Ui::FlatLabel>(box, std::move(text), st::aboutLabel),
st::boxRowPadding);
label->setLinksTrusted();
Ui::AddSkip(layout, st::aboutSkip);
};
addText(Text1());
addText(Text2());
addText(Text3());
box->addButton(tr::lng_close(), [=] { box->closeBox(); });
box->setWidth(st::aboutWidth);
}
QString telegramFaqLink() {
const auto result = u"https://telegram.org/faq"_q;
const auto langpacked = [&](const char *language) {
return result + '/' + language;
};
const auto current = Lang::Id();
for (const auto language : { "de", "es", "it", "ko" }) {
if (current.startsWith(QLatin1String(language))) {
return langpacked(language);
}
}
if (current.startsWith(u"pt-br"_q)) {
return langpacked("br");
}
return result;
}
QString currentVersionText() {
auto result = QString::fromLatin1(AppVersionStr);
if (cAlphaVersion()) {
result += u" alpha %1"_q.arg(cAlphaVersion() % 1000);
} else if (AppBetaVersion) {
result += " beta";
}
if (!ZsgBuildId.empty()) {
result += u" (%1)"_q.arg(ZsgBuildId.utf16());
}
if (Platform::IsWindows64Bit()) {
result += " x64";
} else if (Platform::IsWindowsARM64()) {
result += " arm64";
}
#ifdef _DEBUG
result += " DEBUG";
#endif
return result;
}
void ArchiveHintBox(
not_null<Ui::GenericBox*> box,
bool unarchiveOnNewMessage,
Fn<void()> onUnarchive) {
box->setNoContentMargin(true);
const auto content = box->verticalLayout().get();
Ui::AddSkip(content);
Ui::AddSkip(content);
Ui::AddSkip(content);
{
const auto &icon = st::dialogsArchiveUserpic;
const auto rect = Rect(icon.size() * 2);
auto owned = object_ptr<Ui::RpWidget>(content);
owned->resize(rect.size());
owned->setNaturalWidth(rect.width());
const auto widget = box->addRow(std::move(owned), style::al_top);
widget->paintRequest(
) | rpl::on_next([=] {
auto p = Painter(widget);
auto hq = PainterHighQualityEnabler(p);
p.setPen(Qt::NoPen);
p.setBrush(st::activeButtonBg);
p.drawEllipse(rect);
icon.paintInCenter(p, rect);
}, widget->lifetime());
}
Ui::AddSkip(content);
Ui::AddSkip(content);
box->addRow(
object_ptr<Ui::FlatLabel>(
content,
tr::lng_archive_hint_title(),
st::boxTitle),
style::al_top);
Ui::AddSkip(content);
Ui::AddSkip(content);
{
const auto label = box->addRow(
object_ptr<Ui::FlatLabel>(
content,
(unarchiveOnNewMessage
? tr::lng_archive_hint_about_unmuted
: tr::lng_archive_hint_about)(
lt_link,
tr::lng_archive_hint_about_link(
lt_emoji,
rpl::single(
Ui::Text::IconEmoji(&st::textMoreIconEmoji)),
tr::rich
) | rpl::map([](TextWithEntities text) {
return tr::link(std::move(text), 1);
}),
tr::rich),
st::channelEarnHistoryRecipientLabel));
label->resizeToWidth(box->width()
- rect::m::sum::h(st::boxRowPadding));
label->setLink(
1,
std::make_shared<GenericClickHandler>([=](ClickContext context) {
if (context.button == Qt::LeftButton) {
onUnarchive();
}
}));
}
Ui::AddSkip(content);
Ui::AddSkip(content);
Ui::AddSkip(content);
Ui::AddSkip(content);
{
const auto padding = QMargins(
st::settingsButton.padding.left(),
st::boxRowPadding.top(),
st::boxRowPadding.right(),
st::boxRowPadding.bottom());
const auto addEntry = [&](
rpl::producer<QString> title,
rpl::producer<QString> about,
const style::icon &icon) {
const auto top = content->add(
object_ptr<Ui::FlatLabel>(
content,
std::move(title),
st::channelEarnSemiboldLabel),
padding);
Ui::AddSkip(content, st::channelEarnHistoryThreeSkip);
content->add(
object_ptr<Ui::FlatLabel>(
content,
std::move(about),
st::channelEarnHistoryRecipientLabel),
padding);
const auto left = Ui::CreateChild<Ui::RpWidget>(
box->verticalLayout().get());
left->paintRequest(
) | rpl::on_next([=] {
auto p = Painter(left);
icon.paint(p, 0, 0, left->width());
}, left->lifetime());
left->resize(icon.size());
top->geometryValue(
) | rpl::on_next([=](const QRect &g) {
left->moveToLeft(
(g.left() - left->width()) / 2,
g.top() + st::channelEarnHistoryThreeSkip);
}, left->lifetime());
};
addEntry(
tr::lng_archive_hint_section_1(),
tr::lng_archive_hint_section_1_info(),
st::menuIconArchive);
Ui::AddSkip(content);
Ui::AddSkip(content);
addEntry(
tr::lng_archive_hint_section_2(),
tr::lng_archive_hint_section_2_info(),
st::menuIconStealth);
Ui::AddSkip(content);
Ui::AddSkip(content);
addEntry(
tr::lng_archive_hint_section_3(),
tr::lng_archive_hint_section_3_info(),
st::menuIconStoriesSavedSection);
Ui::AddSkip(content);
Ui::AddSkip(content);
}
Ui::AddSkip(content);
Ui::AddSkip(content);
Ui::AddSkip(content);
{
const auto &st = st::premiumPreviewDoubledLimitsBox;
box->setStyle(st);
auto button = object_ptr<Ui::RoundButton>(
box,
tr::lng_archive_hint_button(),
st::defaultActiveButton);
button->resizeToWidth(box->width()
- st.buttonPadding.left()
- st.buttonPadding.left());
button->setClickedCallback([=] { box->closeBox(); });
box->addButton(std::move(button));
}
}