tdesktop/Telegram/SourceFiles/settings/settings_main.cpp

706 lines
20 KiB
C++
Raw Normal View History

2018-09-05 19:05:49 +00:00
/*
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 "settings/settings_main.h"
#include "settings/settings_common.h"
2018-09-06 13:48:01 +00:00
#include "settings/settings_codes.h"
#include "settings/settings_chat.h"
#include "settings/settings_information.h"
#include "settings/settings_notifications.h"
#include "settings/settings_privacy_security.h"
#include "settings/settings_advanced.h"
#include "settings/settings_folders.h"
#include "settings/settings_calls.h"
#include "settings/settings_power_saving.h"
#include "settings/settings_premium.h"
2023-01-05 10:48:46 +00:00
#include "settings/settings_scale_preview.h"
2018-09-05 21:01:50 +00:00
#include "boxes/language_box.h"
2022-02-08 17:25:24 +00:00
#include "boxes/username_box.h"
#include "boxes/about_box.h"
#include "ui/basic_click_handlers.h"
2022-12-19 11:48:24 +00:00
#include "ui/boxes/confirm_box.h"
#include "ui/controls/userpic_button.h"
2018-09-05 19:05:49 +00:00
#include "ui/wrap/vertical_layout.h"
2020-03-24 07:26:08 +00:00
#include "ui/wrap/slide_wrap.h"
2022-02-08 17:25:24 +00:00
#include "ui/wrap/padding_wrap.h"
2018-09-05 21:01:50 +00:00
#include "ui/widgets/labels.h"
2023-01-05 10:48:46 +00:00
#include "ui/widgets/continuous_sliders.h"
#include "ui/widgets/buttons.h"
2022-02-08 17:25:24 +00:00
#include "ui/text/text_utilities.h"
#include "ui/toast/toast.h"
#include "info/profile/info_profile_badge.h"
#include "info/profile/info_profile_emoji_status_panel.h"
#include "data/data_user.h"
2019-01-18 12:27:37 +00:00
#include "data/data_session.h"
2019-09-03 15:24:51 +00:00
#include "data/data_cloud_themes.h"
2020-03-18 10:07:11 +00:00
#include "data/data_chat_filters.h"
2022-06-14 05:00:47 +00:00
#include "data/data_peer_values.h" // Data::AmPremiumValue
2018-09-05 19:05:49 +00:00
#include "lang/lang_keys.h"
2020-09-30 09:11:44 +00:00
#include "lang/lang_instance.h"
2018-09-05 21:01:50 +00:00
#include "storage/localstorage.h"
2019-07-24 11:45:24 +00:00
#include "main/main_session.h"
#include "main/main_session_settings.h"
2020-03-18 10:07:11 +00:00
#include "main/main_account.h"
#include "main/main_app_config.h"
#include "apiwrap.h"
2022-02-08 17:25:24 +00:00
#include "api/api_peer_photo.h"
#include "api/api_cloud_password.h"
2020-07-03 16:53:24 +00:00
#include "api/api_global_privacy.h"
#include "api/api_sensitive_content.h"
2022-05-31 17:11:59 +00:00
#include "api/api_premium.h"
2022-02-08 17:25:24 +00:00
#include "info/profile/info_profile_values.h"
#include "window/window_controller.h"
2019-07-24 11:13:51 +00:00
#include "window/window_session_controller.h"
#include "core/file_utilities.h"
#include "core/application.h"
2019-09-26 10:55:35 +00:00
#include "base/call_delayed.h"
2022-02-08 17:25:24 +00:00
#include "base/platform/base_platform_info.h"
2018-09-05 19:05:49 +00:00
#include "styles/style_settings.h"
2022-02-08 17:25:24 +00:00
#include "styles/style_boxes.h"
#include "styles/style_info.h"
#include <QtGui/QGuiApplication>
#include <QtGui/QClipboard>
2023-02-13 10:12:50 +00:00
#include <QtGui/QWindow>
2018-09-05 19:05:49 +00:00
namespace Settings {
2022-02-08 17:25:24 +00:00
namespace {
class Cover final : public Ui::FixedHeightWidget {
public:
Cover(
QWidget *parent,
not_null<Window::SessionController*> controller,
not_null<UserData*> user);
~Cover();
private:
void setupChildGeometry();
void initViewers();
void refreshStatusText();
void refreshNameGeometry(int newWidth);
void refreshPhoneGeometry(int newWidth);
void refreshUsernameGeometry(int newWidth);
const not_null<Window::SessionController*> _controller;
const not_null<UserData*> _user;
Info::Profile::EmojiStatusPanel _emojiStatusPanel;
Info::Profile::Badge _badge;
2022-02-08 17:25:24 +00:00
object_ptr<Ui::UserpicButton> _userpic;
object_ptr<Ui::FlatLabel> _name = { nullptr };
object_ptr<Ui::FlatLabel> _phone = { nullptr };
object_ptr<Ui::FlatLabel> _username = { nullptr };
};
Cover::Cover(
QWidget *parent,
not_null<Window::SessionController*> controller,
not_null<UserData*> user)
: FixedHeightWidget(
parent,
st::settingsPhotoTop
2022-10-14 16:53:06 +00:00
+ st::infoProfileCover.photo.size.height()
2022-02-08 17:25:24 +00:00
+ st::settingsPhotoBottom)
, _controller(controller)
, _user(user)
, _badge(
this,
st::infoPeerBadge,
user,
&_emojiStatusPanel,
[=] {
return controller->isGifPausedAtLeastFor(
Window::GifPauseReason::Layer);
},
0, // customStatusLoopsLimit
Info::Profile::BadgeType::Premium)
2022-02-08 17:25:24 +00:00
, _userpic(
this,
controller,
_user,
Ui::UserpicButton::Role::OpenPhoto,
Ui::UserpicButton::Source::PeerPhoto,
2022-10-14 16:53:06 +00:00
st::infoProfileCover.photo)
, _name(this, st::infoProfileCover.name)
2022-02-08 17:25:24 +00:00
, _phone(this, st::defaultFlatLabel)
2022-10-14 16:53:06 +00:00
, _username(this, st::infoProfileMegagroupCover.status) {
2022-02-08 17:25:24 +00:00
_user->updateFull();
_name->setSelectable(true);
_name->setContextCopyText(tr::lng_profile_copy_fullname(tr::now));
_phone->setSelectable(true);
_phone->setContextCopyText(tr::lng_profile_copy_phone(tr::now));
2022-02-08 17:25:24 +00:00
initViewers();
setupChildGeometry();
_userpic->switchChangePhotoOverlay(_user->isSelf(), [=](
Ui::UserpicButton::ChosenImage chosen) {
auto &image = chosen.image;
_userpic->showCustom(base::duplicate(image));
_user->session().api().peerPhoto().upload(
_user,
{
std::move(image),
chosen.markup.documentId,
chosen.markup.colors,
});
});
2022-06-14 05:00:47 +00:00
_badge.setPremiumClickCallback([=] {
_emojiStatusPanel.show(
_controller,
_badge.widget(),
_badge.sizeTag());
});
_badge.updated() | rpl::start_with_next([=] {
refreshNameGeometry(width());
}, _name->lifetime());
2022-02-08 17:25:24 +00:00
}
Cover::~Cover() = default;
void Cover::setupChildGeometry() {
using namespace rpl::mappers;
widthValue(
) | rpl::start_with_next([=](int newWidth) {
_userpic->moveToLeft(
st::settingsPhotoLeft,
st::settingsPhotoTop,
newWidth);
refreshNameGeometry(newWidth);
refreshPhoneGeometry(newWidth);
refreshUsernameGeometry(newWidth);
}, lifetime());
}
void Cover::initViewers() {
Info::Profile::NameValue(
_user
2022-09-27 12:05:47 +00:00
) | rpl::start_with_next([=](const QString &name) {
_name->setText(name);
2022-02-08 17:25:24 +00:00
refreshNameGeometry(width());
}, lifetime());
Info::Profile::PhoneValue(
_user
) | rpl::start_with_next([=](const TextWithEntities &value) {
_phone->setText(value.text);
refreshPhoneGeometry(width());
}, lifetime());
Info::Profile::UsernameValue(
_user
) | rpl::start_with_next([=](const TextWithEntities &value) {
_username->setMarkedText(Ui::Text::Link(value.text.isEmpty()
? tr::lng_settings_username_add(tr::now)
: value.text));
refreshUsernameGeometry(width());
}, lifetime());
_username->overrideLinkClickHandler([=] {
2022-02-08 17:25:24 +00:00
const auto username = _user->userName();
if (username.isEmpty()) {
2022-10-11 18:10:15 +00:00
_controller->show(Box(UsernamesBox, &_user->session()));
2022-02-08 17:25:24 +00:00
} else {
QGuiApplication::clipboard()->setText(
_user->session().createInternalLinkFull(username));
Ui::Toast::Show(
Window::Show(_controller).toastParent(),
tr::lng_username_copied(tr::now));
2022-02-08 17:25:24 +00:00
}
});
}
void Cover::refreshNameGeometry(int newWidth) {
const auto nameLeft = st::settingsNameLeft;
const auto nameTop = st::settingsNameTop;
auto nameWidth = newWidth
2022-06-14 05:00:47 +00:00
- nameLeft
2022-10-14 16:53:06 +00:00
- st::infoProfileCover.rightSkip;
if (const auto width = _badge.widget() ? _badge.widget()->width() : 0) {
nameWidth -= st::infoVerifiedCheckPosition.x() + width;
}
2022-02-08 17:25:24 +00:00
_name->resizeToNaturalWidth(nameWidth);
_name->moveToLeft(nameLeft, nameTop, newWidth);
const auto badgeLeft = nameLeft + _name->width();
const auto badgeTop = nameTop;
const auto badgeBottom = nameTop + _name->height();
_badge.move(badgeLeft, badgeTop, badgeBottom);
2022-02-08 17:25:24 +00:00
}
void Cover::refreshPhoneGeometry(int newWidth) {
const auto phoneLeft = st::settingsPhoneLeft;
const auto phoneTop = st::settingsPhoneTop;
2022-10-14 16:53:06 +00:00
const auto phoneWidth = newWidth
- phoneLeft
- st::infoProfileCover.rightSkip;
2022-02-08 17:25:24 +00:00
_phone->resizeToWidth(phoneWidth);
_phone->moveToLeft(phoneLeft, phoneTop, newWidth);
}
void Cover::refreshUsernameGeometry(int newWidth) {
const auto usernameLeft = st::settingsUsernameLeft;
const auto usernameTop = st::settingsUsernameTop;
2022-10-14 16:53:06 +00:00
const auto usernameRight = st::infoProfileCover.rightSkip;
2022-02-08 17:25:24 +00:00
const auto usernameWidth = newWidth - usernameLeft - usernameRight;
_username->resizeToWidth(usernameWidth);
_username->moveToLeft(usernameLeft, usernameTop, newWidth);
}
} // namespace
2018-09-05 21:01:50 +00:00
void SetupPowerSavingButton(
not_null<Window::Controller*> window,
not_null<Ui::VerticalLayout*> container) {
const auto button = AddButton(
container,
tr::lng_settings_power_menu(),
st::settingsButton,
{ &st::settingsIconBattery, kIconDarkOrange });
button->setClickedCallback([=] {
window->show(Box(PowerSavingBox));
});
}
2018-09-17 10:52:34 +00:00
void SetupLanguageButton(
not_null<Window::Controller*> window,
2018-09-17 10:52:34 +00:00
not_null<Ui::VerticalLayout*> container,
bool icon) {
2018-09-07 09:40:25 +00:00
const auto button = AddButtonWithLabel(
2018-09-05 21:01:50 +00:00
container,
2019-06-18 12:16:43 +00:00
tr::lng_settings_language(),
2019-06-19 11:22:25 +00:00
rpl::single(
2020-09-30 09:11:44 +00:00
Lang::GetInstance().id()
2019-06-19 11:22:25 +00:00
) | rpl::then(
2020-09-30 09:11:44 +00:00
Lang::GetInstance().idChanges()
) | rpl::map([] { return Lang::GetInstance().nativeName(); }),
icon ? st::settingsButton : st::settingsButtonNoIcon,
{ icon ? &st::settingsIconLanguage : nullptr, kIconLightBlue });
2018-11-21 10:09:46 +00:00
const auto guard = Ui::CreateChild<base::binary_guard>(button.get());
2018-09-05 21:01:50 +00:00
button->addClickHandler([=] {
const auto m = button->clickModifiers();
if ((m & Qt::ShiftModifier) && (m & Qt::AltModifier)) {
2022-11-29 21:46:36 +00:00
Lang::CurrentCloudManager().switchToLanguage({ u"#custom"_q });
} else {
*guard = LanguageBox::Show(window->sessionController());
}
2018-09-05 21:01:50 +00:00
});
}
void SetupSections(
2019-07-24 14:00:30 +00:00
not_null<Window::SessionController*> controller,
not_null<Ui::VerticalLayout*> container,
Fn<void(Type)> showOther) {
AddDivider(container);
AddSkip(container);
const auto addSection = [&](
2019-06-18 12:16:43 +00:00
rpl::producer<QString> label,
Type type,
IconDescriptor &&descriptor) {
2018-09-07 09:40:25 +00:00
AddButton(
container,
2019-06-18 12:16:43 +00:00
std::move(label),
st::settingsButton,
std::move(descriptor)
)->addClickHandler([=] {
if (type == PremiumId()) {
controller->setPremiumRef("settings");
}
showOther(type);
});
};
2019-07-24 14:00:30 +00:00
if (controller->session().supportMode()) {
SetupSupport(controller, container);
AddDivider(container);
AddSkip(container);
} else {
addSection(
2019-06-18 12:16:43 +00:00
tr::lng_settings_information(),
Information::Id(),
{ &st::settingsIconAccount, kIconLightOrange });
}
addSection(
2019-06-18 12:16:43 +00:00
tr::lng_settings_section_notify(),
Notifications::Id(),
{ &st::settingsIconNotifications, kIconRed });
addSection(
2019-06-18 12:16:43 +00:00
tr::lng_settings_section_privacy(),
PrivacySecurity::Id(),
{ &st::settingsIconLock, kIconGreen });
addSection(
2019-06-18 12:16:43 +00:00
tr::lng_settings_section_chat_settings(),
Chat::Id(),
{ &st::settingsIconChat, kIconLightBlue });
2020-03-24 07:26:08 +00:00
const auto preload = [=] {
controller->session().data().chatsFilters().requestSuggested();
};
2020-03-24 07:26:08 +00:00
const auto account = &controller->session().account();
const auto slided = container->add(
object_ptr<Ui::SlideWrap<Ui::SettingsButton>>(
container,
CreateButton(
container,
tr::lng_settings_section_filters(),
st::settingsButton,
{ &st::settingsIconFolders, kIconDarkBlue }))
)->setDuration(0);
if (controller->session().data().chatsFilters().has()
|| controller->session().settings().dialogsFiltersEnabled()) {
2020-03-24 07:26:08 +00:00
slided->show(anim::type::instant);
preload();
2020-03-24 07:26:08 +00:00
} else {
const auto enabled = [=] {
const auto result = account->appConfig().get<bool>(
2020-03-24 07:26:08 +00:00
"dialog_filters_enabled",
false);
if (result) {
preload();
}
return result;
};
const auto preloadIfEnabled = [=](bool enabled) {
if (enabled) {
preload();
}
2020-03-24 07:26:08 +00:00
};
slided->toggleOn(
rpl::single(rpl::empty) | rpl::then(
2020-03-24 07:26:08 +00:00
account->appConfig().refreshed()
) | rpl::map(
enabled
) | rpl::before_next(preloadIfEnabled));
2020-03-18 10:07:11 +00:00
}
2020-03-24 07:26:08 +00:00
slided->entity()->setClickedCallback([=] {
showOther(Folders::Id());
2020-03-24 07:26:08 +00:00
});
2018-09-13 20:09:26 +00:00
addSection(
2019-06-18 12:16:43 +00:00
tr::lng_settings_advanced(),
Advanced::Id(),
{ &st::settingsIconGeneral, kIconPurple });
addSection(
tr::lng_settings_section_call_settings(),
Calls::Id(),
{ &st::settingsIconCalls, kIconGreen });
SetupPowerSavingButton(&controller->window(), container);
SetupLanguageButton(&controller->window(), container);
2022-06-07 07:27:06 +00:00
if (controller->session().premiumPossible()) {
AddSkip(container);
AddDivider(container);
AddSkip(container);
const auto icon = &st::settingsPremiumIconStar;
auto gradient = QLinearGradient(
0,
icon->height(),
icon->width() + icon->width() / 3,
0 - icon->height() / 3);
gradient.setStops(QGradientStops{
{ 0.0, st::premiumButtonBg1->c },
{ 1.0, st::premiumButtonBg3->c },
});
addSection(
tr::lng_premium_summary_title(),
PremiumId(),
{ .icon = icon, .backgroundBrush = QBrush(gradient) });
}
AddSkip(container);
}
2018-09-11 18:07:04 +00:00
bool HasInterfaceScale() {
return true;
2018-09-11 18:07:04 +00:00
}
void SetupInterfaceScale(
not_null<Window::Controller*> window,
2018-09-11 18:07:04 +00:00
not_null<Ui::VerticalLayout*> container,
bool icon) {
if (!HasInterfaceScale()) {
2018-09-05 21:01:50 +00:00
return;
}
2018-11-21 10:09:46 +00:00
const auto toggled = Ui::CreateChild<rpl::event_stream<bool>>(
container.get());
2018-09-05 21:01:50 +00:00
2019-09-13 10:24:06 +00:00
const auto switched = (cConfigScale() == style::kScaleAuto);
2018-09-07 09:40:25 +00:00
const auto button = AddButton(
2018-09-05 21:01:50 +00:00
container,
2019-06-18 12:16:43 +00:00
tr::lng_settings_default_scale(),
icon ? st::settingsButton : st::settingsButtonNoIcon,
{ icon ? &st::settingsIconInterfaceScale : nullptr, kIconLightOrange }
)->toggleOn(toggled->events_starting_with_copy(switched));
2018-09-05 21:01:50 +00:00
2023-01-05 10:48:46 +00:00
const auto ratio = style::DevicePixelRatio();
const auto scaleMin = style::kScaleMin;
const auto scaleMax = style::MaxScaleForRatio(ratio);
2023-01-05 10:48:46 +00:00
const auto scaleConfig = cConfigScale();
const auto step = 5;
Assert(!((scaleMax - scaleMin) % step));
auto values = std::vector<int>();
for (auto i = scaleMin; i != scaleMax; i += step) {
values.push_back(i);
if (scaleConfig > i && scaleConfig < i + step) {
values.push_back(scaleConfig);
}
2023-01-05 10:48:46 +00:00
}
values.push_back(scaleMax);
const auto valuesCount = int(values.size());
2023-01-05 10:48:46 +00:00
const auto valueFromScale = [=](int scale) {
scale = cEvalScale(scale);
auto result = 0;
2023-01-05 10:48:46 +00:00
for (const auto value : values) {
if (scale == value) {
break;
}
++result;
}
2023-01-05 10:48:46 +00:00
return ((result == valuesCount) ? (result - 1) : result)
/ float64(valuesCount - 1);
};
2023-01-05 10:48:46 +00:00
auto sliderWithLabel = MakeSliderWithLabel(
container,
st::settingsScale,
st::settingsScaleLabel,
st::normalFont->spacew * 2,
st::settingsScaleLabel.style.font->width("300%"));
container->add(
std::move(sliderWithLabel.widget),
icon ? st::settingsScalePadding : st::settingsBigScalePadding);
const auto slider = sliderWithLabel.slider;
const auto label = sliderWithLabel.label;
const auto updateLabel = [=](int scale) {
const auto labelText = [&](int scale) {
if constexpr (Platform::IsMac()) {
return QString::number(scale) + '%';
} else {
const auto handle = window->widget()->windowHandle();
const auto ratio = handle->devicePixelRatio();
return QString::number(base::SafeRound(scale * ratio)) + '%';
2023-01-05 10:48:46 +00:00
}
};
label->setText(labelText(cEvalScale(scale)));
};
updateLabel(cConfigScale());
const auto inSetScale = container->lifetime().make_state<bool>();
const auto setScale = [=](int scale, const auto &repeatSetScale) -> void {
if (*inSetScale) {
return;
}
2018-09-05 21:01:50 +00:00
*inSetScale = true;
const auto guard = gsl::finally([=] { *inSetScale = false; });
2023-01-05 10:48:46 +00:00
updateLabel(scale);
2019-09-13 10:24:06 +00:00
toggled->fire(scale == style::kScaleAuto);
2023-01-05 10:48:46 +00:00
slider->setValue(valueFromScale(scale));
if (cEvalScale(scale) != cEvalScale(cConfigScale())) {
2018-09-05 21:01:50 +00:00
const auto confirmed = crl::guard(button, [=] {
cSetConfigScale(scale);
2018-09-05 21:01:50 +00:00
Local::writeSettings();
Core::Restart();
2018-09-05 21:01:50 +00:00
});
2022-03-01 13:15:23 +00:00
const auto cancelled = crl::guard(button, [=](Fn<void()> close) {
2019-09-26 10:55:35 +00:00
base::call_delayed(
2018-09-05 21:01:50 +00:00
st::defaultSettingsSlider.duration,
button,
[=] { repeatSetScale(cConfigScale(), repeatSetScale); });
2022-03-01 13:15:23 +00:00
close();
2018-09-05 21:01:50 +00:00
});
window->show(Ui::MakeConfirmBox({
.text = tr::lng_settings_need_restart(),
.confirmed = confirmed,
.cancelled = cancelled,
.confirmText = tr::lng_settings_restart_now(),
}));
} else if (scale != cConfigScale()) {
2018-09-05 21:01:50 +00:00
cSetConfigScale(scale);
Local::writeSettings();
}
};
2023-01-05 10:48:46 +00:00
const auto shown = container->lifetime().make_state<bool>();
const auto togglePreview = SetupScalePreview(window, slider);
const auto toggleForScale = [=](int scale) {
scale = cEvalScale(scale);
const auto show = *shown
? ScalePreviewShow::Update
: ScalePreviewShow::Show;
*shown = true;
for (auto i = 0; i != valuesCount; ++i) {
if (values[i] <= scale
&& (i + 1 == valuesCount || values[i + 1] > scale)) {
const auto x = (slider->width() * i) / (valuesCount - 1);
togglePreview(show, scale, x);
2023-01-05 10:48:46 +00:00
return;
}
}
togglePreview(show, scale, slider->width() / 2);
2018-09-05 21:01:50 +00:00
};
2023-01-05 10:48:46 +00:00
const auto toggleHidePreview = [=] {
togglePreview(ScalePreviewShow::Hide, 0, 0);
*shown = false;
2018-09-05 21:01:50 +00:00
};
2023-01-05 10:48:46 +00:00
slider->setPseudoDiscrete(
valuesCount,
[=](int index) { return values[index]; },
cConfigScale(),
[=](int scale) { updateLabel(scale); toggleForScale(scale); },
[=](int scale) { toggleHidePreview(); setScale(scale, setScale); });
button->toggledValue(
) | rpl::map([](bool checked) {
2019-09-13 10:24:06 +00:00
return checked ? style::kScaleAuto : cEvalScale(cConfigScale());
}) | rpl::start_with_next([=](int scale) {
setScale(scale, setScale);
}, button->lifetime());
if (!icon) {
AddSkip(container, st::settingsThumbSkip);
}
2018-09-05 21:01:50 +00:00
}
void OpenFaq() {
File::OpenUrl(telegramFaqLink());
}
2018-09-11 18:07:04 +00:00
void SetupFaq(not_null<Ui::VerticalLayout*> container, bool icon) {
2018-09-07 09:40:25 +00:00
AddButton(
container,
2019-06-18 12:16:43 +00:00
tr::lng_settings_faq(),
icon ? st::settingsButton : st::settingsButtonNoIcon,
{ icon ? &st::settingsIconFaq : nullptr, kIconLightBlue }
)->addClickHandler(OpenFaq);
2018-09-11 18:07:04 +00:00
}
2019-07-24 14:00:30 +00:00
void SetupHelp(
not_null<Window::SessionController*> controller,
not_null<Ui::VerticalLayout*> container) {
2018-09-11 18:07:04 +00:00
AddDivider(container);
AddSkip(container);
SetupFaq(container);
AddButton(
container,
2022-02-27 13:32:36 +00:00
tr::lng_settings_features(),
st::settingsButton,
{ &st::settingsIconTips, kIconLightOrange }
)->setClickedCallback([=] {
UrlClickHandler::Open(tr::lng_telegram_features_url(tr::now));
});
2019-07-24 14:00:30 +00:00
const auto button = AddButton(
container,
tr::lng_settings_ask_question(),
st::settingsButton,
{ &st::settingsIconAskQuestion, kIconGreen });
2019-09-03 15:24:51 +00:00
const auto requestId = button->lifetime().make_state<mtpRequestId>();
button->lifetime().add([=] {
if (*requestId) {
controller->session().api().request(*requestId).cancel();
}
});
2019-07-24 14:00:30 +00:00
button->addClickHandler([=] {
const auto sure = crl::guard(button, [=] {
2019-09-03 15:24:51 +00:00
if (*requestId) {
return;
}
*requestId = controller->session().api().request(
MTPhelp_GetSupport()
).done([=](const MTPhelp_Support &result) {
*requestId = 0;
result.match([&](const MTPDhelp_support &data) {
auto &owner = controller->session().data();
if (const auto user = owner.processUser(data.vuser())) {
2022-11-30 12:55:51 +00:00
controller->showPeerHistory(user);
2019-09-03 15:24:51 +00:00
}
});
}).fail([=] {
2019-09-03 15:24:51 +00:00
*requestId = 0;
}).send();
2019-07-24 14:00:30 +00:00
});
auto box = Ui::MakeConfirmBox({
.text = tr::lng_settings_ask_sure(),
.confirmed = sure,
.cancelled = OpenFaq,
.confirmText = tr::lng_settings_ask_ok(),
.cancelText = tr::lng_settings_faq_button(),
.strictCancel = true,
});
controller->show(std::move(box));
2019-07-24 14:00:30 +00:00
});
}
2018-09-05 19:39:35 +00:00
Main::Main(
QWidget *parent,
2019-07-24 14:00:30 +00:00
not_null<Window::SessionController*> controller)
2018-09-05 19:05:49 +00:00
: Section(parent)
2019-07-24 14:00:30 +00:00
, _controller(controller) {
2018-09-05 19:39:35 +00:00
setupContent(controller);
_controller->session().api().premium().reload();
2018-09-05 19:05:49 +00:00
}
rpl::producer<QString> Main::title() {
return tr::lng_menu_settings();
}
2018-09-06 13:48:01 +00:00
void Main::keyPressEvent(QKeyEvent *e) {
2020-03-26 10:29:27 +00:00
crl::on_main(this, [=, text = e->text()]{
CodesFeedString(_controller, text);
});
2018-09-06 13:48:01 +00:00
return Section::keyPressEvent(e);
}
void Main::setupContent(not_null<Window::SessionController*> controller) {
2018-09-05 19:05:49 +00:00
const auto content = Ui::CreateChild<Ui::VerticalLayout>(this);
content->add(object_ptr<Cover>(
2018-09-05 19:39:35 +00:00
content,
2022-02-08 17:25:24 +00:00
controller,
controller->session().user()));
2018-09-05 19:39:35 +00:00
2019-07-24 14:00:30 +00:00
SetupSections(controller, content, [=](Type type) {
_showOther.fire_copy(type);
});
2018-09-11 18:07:04 +00:00
if (HasInterfaceScale()) {
AddDivider(content);
AddSkip(content);
SetupInterfaceScale(&controller->window(), content);
2018-09-11 18:07:04 +00:00
AddSkip(content);
}
2019-07-24 14:00:30 +00:00
SetupHelp(controller, content);
2018-09-05 21:01:50 +00:00
Ui::ResizeFitChild(this, content);
// If we load this in advance it won't jump when we open its' section.
controller->session().api().cloudPassword().reload();
2019-07-24 11:13:51 +00:00
controller->session().api().reloadContactSignupSilent();
2020-07-03 16:53:24 +00:00
controller->session().api().sensitiveContent().reload();
controller->session().api().globalPrivacy().reload();
2019-09-03 15:24:51 +00:00
controller->session().data().cloudThemes().refresh();
2018-09-05 21:01:50 +00:00
}
2018-09-05 19:05:49 +00:00
rpl::producer<Type> Main::sectionShowOther() {
return _showOther.events();
}
} // namespace Settings