mirror of
https://github.com/AyuGram/AyuGramDesktop.git
synced 2025-04-14 05:07:10 +02:00
Allow editing charge-for-message privacy.
This commit is contained in:
parent
909b01241b
commit
f2aa3afbbb
8 changed files with 327 additions and 42 deletions
|
@ -1218,6 +1218,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
"lng_edit_privacy_contacts" = "My contacts";
|
||||
"lng_edit_privacy_close_friends" = "Close friends";
|
||||
"lng_edit_privacy_contacts_and_premium" = "Contacts & Premium";
|
||||
"lng_edit_privacy_paid" = "Paid";
|
||||
"lng_edit_privacy_contacts_and_miniapps" = "Contacts & Mini Apps";
|
||||
"lng_edit_privacy_nobody" = "Nobody";
|
||||
"lng_edit_privacy_premium" = "Premium users";
|
||||
|
@ -1356,6 +1357,13 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
"lng_messages_privacy_premium_about" = "Subscribe now to change this setting and get access to other exclusive features of Telegram Premium.";
|
||||
"lng_messages_privacy_premium" = "Only subscribers of {link} can select this option.";
|
||||
"lng_messages_privacy_premium_link" = "Telegram Premium";
|
||||
"lng_messages_privacy_charge" = "Charge for messages";
|
||||
"lng_messages_privacy_charge_about" = "Charge a fee for messages from people outside your contacts or those you haven't messaged first.";
|
||||
"lng_messages_privacy_price" = "Set your price per message";
|
||||
"lng_messages_privacy_price_about" = "You will receive {percent} of the selected fee ({amount}) for each incoming message.";
|
||||
"lng_messages_privacy_exceptions" = "Exceptions";
|
||||
"lng_messages_privacy_remove_fee" = "Remove Fee";
|
||||
"lng_messages_privacy_remove_about" = "Add users or entire groups who won't be charged for sending messages to you.";
|
||||
|
||||
"lng_self_destruct_title" = "Account self-destruction";
|
||||
"lng_self_destruct_description" = "If you don't come online at least once within this period, your account will be deleted along with all groups, messages and contacts.";
|
||||
|
@ -2158,6 +2166,10 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
"lng_action_boost_apply#other" = "{from} boosted the group {count} times";
|
||||
"lng_action_set_chat_intro" = "{from} added the message below for all empty chats. How?";
|
||||
"lng_action_payment_refunded" = "{peer} refunded {amount}";
|
||||
"lng_action_paid_message_sent#one" = "You paid {count} Star to send a message";
|
||||
"lng_action_paid_message_sent#other" = "You paid {count} Stars to send a message";
|
||||
"lng_action_paid_message_got#one" = "You received {count} Star from {name}";
|
||||
"lng_action_paid_message_got#other" = "You received {count} Stars from {name}";
|
||||
|
||||
"lng_similar_channels_title" = "Similar channels";
|
||||
"lng_similar_channels_view_all" = "View all";
|
||||
|
@ -4798,6 +4810,10 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
"lng_rights_boosts_no_restrict" = "Do not restrict boosters";
|
||||
"lng_rights_boosts_about" = "Turn this on to always allow users who boosted your group to send messages and media.";
|
||||
"lng_rights_boosts_about_on" = "Choose how many boosts a user must give to the group to bypass restrictions on sending messages.";
|
||||
"lng_rights_charge_stars" = "Charge Stars for Messages";
|
||||
"lng_rights_charge_stars_about" = "If you turn this on, regular members of the group will have to pay Stars to send messages.";
|
||||
"lng_rights_charge_price" = "Set price per message";
|
||||
"lng_rights_charge_price_about" = "Your group will receive {percent} of the selected fee ({amount}) for each incoming message.";
|
||||
|
||||
"lng_slowmode_enabled" = "Slow Mode is active.\nYou can send your next message in {left}.";
|
||||
"lng_slowmode_no_many" = "Slow mode is enabled. You can't send more than one message at a time.";
|
||||
|
@ -4805,6 +4821,24 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
"lng_slowmode_seconds#one" = "{count} second";
|
||||
"lng_slowmode_seconds#other" = "{count} seconds";
|
||||
|
||||
"lng_payment_for_message#one" = "Pay {star}{count} for 1 Message";
|
||||
"lng_payment_for_message#other" = "Pay {star}{count} for 1 Message";
|
||||
"lng_payment_confirm_title" = "Confirm payment";
|
||||
"lng_payment_confirm_text#one" = "{name} charges **{count}** Star per message.";
|
||||
"lng_payment_confirm_text#other" = "{name} charges **{count}** Stars per message.";
|
||||
"lng_payment_confirm_sure#one" = "Would you like to pay **{count}** Star to send one message?";
|
||||
"lng_payment_confirm_sure#other" = "Would you like to pay **{count}** Stars to send one message?";
|
||||
"lng_payment_confirm_dont_ask" = "Don't ask me again";
|
||||
"lng_payment_confirm_button" = "Pay for 1 Message";
|
||||
"lng_payment_bar_text#one" = "{name} must pay {star}{count} for each message to you.";
|
||||
"lng_payment_bar_text#other" = "{name} must pay {star}{count} for each message to you.";
|
||||
"lng_payment_bar_button" = "Remove Fee";
|
||||
"lng_payment_refund_title" = "Remove Fee";
|
||||
"lng_payment_refund_text" = "Are you sure you want to allow {name} to message you for free?";
|
||||
"lng_payment_refund_also#one" = "Refund already paid {count} Star";
|
||||
"lng_payment_refund_also#other" = "Refund already paid {count} Stars";
|
||||
"lng_payment_refund_confirm" = "Confirm";
|
||||
|
||||
"lng_rights_gigagroup_title" = "Broadcast group";
|
||||
"lng_rights_gigagroup_convert" = "Convert to Broadcast Group";
|
||||
"lng_rights_gigagroup_about" = "Broadcast groups can have over 200,000 members, but only admins can send messages in them.";
|
||||
|
|
|
@ -114,7 +114,8 @@ void GlobalPrivacy::updateHideReadTime(bool hide) {
|
|||
archiveAndMuteCurrent(),
|
||||
unarchiveOnNewMessageCurrent(),
|
||||
hide,
|
||||
newRequirePremiumCurrent());
|
||||
newRequirePremiumCurrent(),
|
||||
newChargeStarsCurrent());
|
||||
}
|
||||
|
||||
bool GlobalPrivacy::hideReadTimeCurrent() const {
|
||||
|
@ -125,14 +126,6 @@ rpl::producer<bool> GlobalPrivacy::hideReadTime() const {
|
|||
return _hideReadTime.value();
|
||||
}
|
||||
|
||||
void GlobalPrivacy::updateNewRequirePremium(bool value) {
|
||||
update(
|
||||
archiveAndMuteCurrent(),
|
||||
unarchiveOnNewMessageCurrent(),
|
||||
hideReadTimeCurrent(),
|
||||
value);
|
||||
}
|
||||
|
||||
bool GlobalPrivacy::newRequirePremiumCurrent() const {
|
||||
return _newRequirePremium.current();
|
||||
}
|
||||
|
@ -141,6 +134,25 @@ rpl::producer<bool> GlobalPrivacy::newRequirePremium() const {
|
|||
return _newRequirePremium.value();
|
||||
}
|
||||
|
||||
int GlobalPrivacy::newChargeStarsCurrent() const {
|
||||
return _newChargeStars.current();
|
||||
}
|
||||
|
||||
rpl::producer<int> GlobalPrivacy::newChargeStars() const {
|
||||
return _newChargeStars.value();
|
||||
}
|
||||
|
||||
void GlobalPrivacy::updateMessagesPrivacy(
|
||||
bool requirePremium,
|
||||
int chargeStars) {
|
||||
update(
|
||||
archiveAndMuteCurrent(),
|
||||
unarchiveOnNewMessageCurrent(),
|
||||
hideReadTimeCurrent(),
|
||||
requirePremium,
|
||||
chargeStars);
|
||||
}
|
||||
|
||||
void GlobalPrivacy::loadPaidReactionShownPeer() {
|
||||
if (_paidReactionShownPeerLoaded) {
|
||||
return;
|
||||
|
@ -169,7 +181,8 @@ void GlobalPrivacy::updateArchiveAndMute(bool value) {
|
|||
value,
|
||||
unarchiveOnNewMessageCurrent(),
|
||||
hideReadTimeCurrent(),
|
||||
newRequirePremiumCurrent());
|
||||
newRequirePremiumCurrent(),
|
||||
newChargeStarsCurrent());
|
||||
}
|
||||
|
||||
void GlobalPrivacy::updateUnarchiveOnNewMessage(
|
||||
|
@ -178,14 +191,16 @@ void GlobalPrivacy::updateUnarchiveOnNewMessage(
|
|||
archiveAndMuteCurrent(),
|
||||
value,
|
||||
hideReadTimeCurrent(),
|
||||
newRequirePremiumCurrent());
|
||||
newRequirePremiumCurrent(),
|
||||
newChargeStarsCurrent());
|
||||
}
|
||||
|
||||
void GlobalPrivacy::update(
|
||||
bool archiveAndMute,
|
||||
UnarchiveOnNewMessage unarchiveOnNewMessage,
|
||||
bool hideReadTime,
|
||||
bool newRequirePremium) {
|
||||
bool newRequirePremium,
|
||||
int newChargeStars) {
|
||||
using Flag = MTPDglobalPrivacySettings::Flag;
|
||||
|
||||
_api.request(_requestId).cancel();
|
||||
|
@ -204,38 +219,44 @@ void GlobalPrivacy::update(
|
|||
| (hideReadTime ? Flag::f_hide_read_marks : Flag())
|
||||
| ((newRequirePremium && newRequirePremiumAllowed)
|
||||
? Flag::f_new_noncontact_peers_require_premium
|
||||
: Flag());
|
||||
auto nonContactPaidStars = int64(0);
|
||||
: Flag())
|
||||
| Flag::f_noncontact_peers_paid_stars;
|
||||
_requestId = _api.request(MTPaccount_SetGlobalPrivacySettings(
|
||||
MTP_globalPrivacySettings(
|
||||
MTP_flags(flags),
|
||||
MTP_long(nonContactPaidStars))
|
||||
MTP_long(newChargeStars))
|
||||
)).done([=](const MTPGlobalPrivacySettings &result) {
|
||||
_requestId = 0;
|
||||
apply(result);
|
||||
}).fail([=](const MTP::Error &error) {
|
||||
_requestId = 0;
|
||||
if (error.type() == u"PREMIUM_ACCOUNT_REQUIRED"_q) {
|
||||
update(archiveAndMute, unarchiveOnNewMessage, hideReadTime, {});
|
||||
update(
|
||||
archiveAndMute,
|
||||
unarchiveOnNewMessage,
|
||||
hideReadTime,
|
||||
false,
|
||||
0);
|
||||
}
|
||||
}).send();
|
||||
_archiveAndMute = archiveAndMute;
|
||||
_unarchiveOnNewMessage = unarchiveOnNewMessage;
|
||||
_hideReadTime = hideReadTime;
|
||||
_newRequirePremium = newRequirePremium;
|
||||
_newChargeStars = newChargeStars;
|
||||
}
|
||||
|
||||
void GlobalPrivacy::apply(const MTPGlobalPrivacySettings &data) {
|
||||
data.match([&](const MTPDglobalPrivacySettings &data) {
|
||||
_archiveAndMute = data.is_archive_and_mute_new_noncontact_peers();
|
||||
_unarchiveOnNewMessage = data.is_keep_archived_unmuted()
|
||||
? UnarchiveOnNewMessage::None
|
||||
: data.is_keep_archived_folders()
|
||||
? UnarchiveOnNewMessage::NotInFoldersUnmuted
|
||||
: UnarchiveOnNewMessage::AnyUnmuted;
|
||||
_hideReadTime = data.is_hide_read_marks();
|
||||
_newRequirePremium = data.is_new_noncontact_peers_require_premium();
|
||||
});
|
||||
void GlobalPrivacy::apply(const MTPGlobalPrivacySettings &settings) {
|
||||
const auto &data = settings.data();
|
||||
_archiveAndMute = data.is_archive_and_mute_new_noncontact_peers();
|
||||
_unarchiveOnNewMessage = data.is_keep_archived_unmuted()
|
||||
? UnarchiveOnNewMessage::None
|
||||
: data.is_keep_archived_folders()
|
||||
? UnarchiveOnNewMessage::NotInFoldersUnmuted
|
||||
: UnarchiveOnNewMessage::AnyUnmuted;
|
||||
_hideReadTime = data.is_hide_read_marks();
|
||||
_newRequirePremium = data.is_new_noncontact_peers_require_premium();
|
||||
_newChargeStars = data.vnoncontact_peers_paid_stars().value_or_empty();
|
||||
}
|
||||
|
||||
} // namespace Api
|
||||
|
|
|
@ -49,23 +49,28 @@ public:
|
|||
[[nodiscard]] bool hideReadTimeCurrent() const;
|
||||
[[nodiscard]] rpl::producer<bool> hideReadTime() const;
|
||||
|
||||
void updateNewRequirePremium(bool value);
|
||||
[[nodiscard]] bool newRequirePremiumCurrent() const;
|
||||
[[nodiscard]] rpl::producer<bool> newRequirePremium() const;
|
||||
|
||||
[[nodiscard]] int newChargeStarsCurrent() const;
|
||||
[[nodiscard]] rpl::producer<int> newChargeStars() const;
|
||||
|
||||
void updateMessagesPrivacy(bool requirePremium, int chargeStars);
|
||||
|
||||
void loadPaidReactionShownPeer();
|
||||
void updatePaidReactionShownPeer(PeerId shownPeer);
|
||||
[[nodiscard]] PeerId paidReactionShownPeerCurrent() const;
|
||||
[[nodiscard]] rpl::producer<PeerId> paidReactionShownPeer() const;
|
||||
|
||||
private:
|
||||
void apply(const MTPGlobalPrivacySettings &data);
|
||||
void apply(const MTPGlobalPrivacySettings &settings);
|
||||
|
||||
void update(
|
||||
bool archiveAndMute,
|
||||
UnarchiveOnNewMessage unarchiveOnNewMessage,
|
||||
bool hideReadTime,
|
||||
bool newRequirePremium);
|
||||
bool newRequirePremium,
|
||||
int newChargeStars);
|
||||
|
||||
const not_null<Main::Session*> _session;
|
||||
MTP::Sender _api;
|
||||
|
@ -76,6 +81,7 @@ private:
|
|||
rpl::variable<bool> _showArchiveAndMute = false;
|
||||
rpl::variable<bool> _hideReadTime = false;
|
||||
rpl::variable<bool> _newRequirePremium = false;
|
||||
rpl::variable<int> _newChargeStars = 0;
|
||||
rpl::variable<PeerId> _paidReactionShownPeer = false;
|
||||
std::vector<Fn<void()>> _callbacks;
|
||||
bool _paidReactionShownPeerLoaded = false;
|
||||
|
|
|
@ -12,7 +12,9 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
#include "ui/effects/premium_graphics.h"
|
||||
#include "ui/layers/generic_box.h"
|
||||
#include "ui/widgets/checkbox.h"
|
||||
#include "ui/widgets/continuous_sliders.h"
|
||||
#include "ui/widgets/shadow.h"
|
||||
#include "ui/text/format_values.h"
|
||||
#include "ui/text/text_utilities.h"
|
||||
#include "ui/toast/toast.h"
|
||||
#include "ui/wrap/slide_wrap.h"
|
||||
|
@ -42,6 +44,10 @@ namespace {
|
|||
|
||||
constexpr auto kPremiumsRowId = PeerId(FakeChatId(BareId(1))).value;
|
||||
constexpr auto kMiniAppsRowId = PeerId(FakeChatId(BareId(2))).value;
|
||||
constexpr auto kGetPercent = 85;
|
||||
constexpr auto kStarsMin = 10;
|
||||
constexpr auto kStarsMax = 9000;
|
||||
constexpr auto kDefaultChargeStars = 200;
|
||||
|
||||
using Exceptions = Api::UserPrivacy::Exceptions;
|
||||
|
||||
|
@ -452,6 +458,109 @@ auto PrivacyExceptionsBoxController::createRow(not_null<History*> history)
|
|||
return result;
|
||||
}
|
||||
|
||||
[[nodiscard]] object_ptr<Ui::RpWidget> MakeChargeStarsSlider(
|
||||
QWidget *parent,
|
||||
not_null<const style::MediaSlider*> sliderStyle,
|
||||
not_null<const style::FlatLabel*> labelStyle,
|
||||
int valuesCount,
|
||||
Fn<int(int)> valueByIndex,
|
||||
int value,
|
||||
Fn<void(int)> valueProgress,
|
||||
Fn<void(int)> valueFinished) {
|
||||
auto result = object_ptr<Ui::VerticalLayout>(parent);
|
||||
const auto raw = result.data();
|
||||
|
||||
const auto labels = raw->add(object_ptr<Ui::RpWidget>(raw));
|
||||
const auto min = Ui::CreateChild<Ui::FlatLabel>(
|
||||
raw,
|
||||
QString::number(kStarsMin),
|
||||
*labelStyle);
|
||||
const auto max = Ui::CreateChild<Ui::FlatLabel>(
|
||||
raw,
|
||||
QString::number(kStarsMax),
|
||||
*labelStyle);
|
||||
const auto current = Ui::CreateChild<Ui::FlatLabel>(
|
||||
raw,
|
||||
QString::number(value),
|
||||
*labelStyle);
|
||||
min->setTextColorOverride(st::windowSubTextFg->c);
|
||||
max->setTextColorOverride(st::windowSubTextFg->c);
|
||||
const auto slider = raw->add(object_ptr<Ui::MediaSliderWheelless>(
|
||||
raw,
|
||||
*sliderStyle));
|
||||
labels->resize(
|
||||
labels->width(),
|
||||
current->height() + st::defaultVerticalListSkip);
|
||||
struct State {
|
||||
int indexMin = 0;
|
||||
int index = 0;
|
||||
};
|
||||
const auto state = raw->lifetime().make_state<State>();
|
||||
const auto updateByIndex = [=] {
|
||||
const auto outer = labels->width();
|
||||
const auto minWidth = min->width();
|
||||
const auto maxWidth = max->width();
|
||||
const auto currentWidth = current->width();
|
||||
if (minWidth + maxWidth + currentWidth > outer) {
|
||||
return;
|
||||
}
|
||||
|
||||
min->moveToLeft(0, 0, outer);
|
||||
max->moveToRight(0, 0, outer);
|
||||
current->moveToLeft((outer - current->width()) / 2, 0, outer);
|
||||
};
|
||||
const auto updateByValue = [=](int value) {
|
||||
current->setText(
|
||||
tr::lng_action_gift_for_stars(tr::now, lt_count, value));
|
||||
|
||||
state->index = 0;
|
||||
auto maxIndex = valuesCount - 1;
|
||||
while (state->index < maxIndex) {
|
||||
const auto mid = (state->index + maxIndex) / 2;
|
||||
const auto midValue = valueByIndex(mid);
|
||||
if (midValue == value) {
|
||||
state->index = mid;
|
||||
break;
|
||||
} else if (midValue < value) {
|
||||
state->index = mid + 1;
|
||||
} else {
|
||||
maxIndex = mid - 1;
|
||||
}
|
||||
}
|
||||
updateByIndex();
|
||||
};
|
||||
const auto progress = [=](int value) {
|
||||
updateByValue(value);
|
||||
valueProgress(value);
|
||||
};
|
||||
const auto finished = [=](int value) {
|
||||
updateByValue(value);
|
||||
valueFinished(value);
|
||||
};
|
||||
style::PaletteChanged() | rpl::start_with_next([=] {
|
||||
min->setTextColorOverride(st::windowSubTextFg->c);
|
||||
max->setTextColorOverride(st::windowSubTextFg->c);
|
||||
}, raw->lifetime());
|
||||
updateByValue(value);
|
||||
state->indexMin = 0;
|
||||
|
||||
slider->setPseudoDiscrete(
|
||||
valuesCount,
|
||||
valueByIndex,
|
||||
value,
|
||||
progress,
|
||||
finished,
|
||||
state->indexMin);
|
||||
slider->resize(slider->width(), sliderStyle->seekSize.height());
|
||||
|
||||
raw->widthValue() | rpl::start_with_next([=](int width) {
|
||||
labels->resizeToWidth(width);
|
||||
updateByIndex();
|
||||
}, slider->lifetime());
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
bool EditPrivacyController::hasOption(Option option) const {
|
||||
|
@ -812,6 +921,7 @@ void EditMessagesPrivacyBox(
|
|||
|
||||
constexpr auto kOptionAll = 0;
|
||||
constexpr auto kOptionPremium = 1;
|
||||
constexpr auto kOptionCharge = 2;
|
||||
|
||||
const auto allowed = [=] {
|
||||
return controller->session().premium()
|
||||
|
@ -824,7 +934,11 @@ void EditMessagesPrivacyBox(
|
|||
Ui::AddSkip(inner, st::messagePrivacyTopSkip);
|
||||
Ui::AddSubsectionTitle(inner, tr::lng_messages_privacy_subtitle());
|
||||
const auto group = std::make_shared<Ui::RadiobuttonGroup>(
|
||||
privacy->newRequirePremiumCurrent() ? kOptionPremium : kOptionAll);
|
||||
(privacy->newRequirePremiumCurrent()
|
||||
? kOptionPremium
|
||||
: privacy->newChargeStarsCurrent()
|
||||
? kOptionCharge
|
||||
: kOptionAll));
|
||||
inner->add(
|
||||
object_ptr<Ui::Radiobutton>(
|
||||
inner,
|
||||
|
@ -846,6 +960,107 @@ void EditMessagesPrivacyBox(
|
|||
0,
|
||||
st::messagePrivacyBottomSkip));
|
||||
|
||||
Ui::AddDividerText(inner, tr::lng_messages_privacy_about());
|
||||
|
||||
const auto charged = inner->add(
|
||||
object_ptr<Ui::Radiobutton>(
|
||||
inner,
|
||||
group,
|
||||
kOptionCharge,
|
||||
tr::lng_messages_privacy_charge(tr::now),
|
||||
st::messagePrivacyCheck),
|
||||
st::settingsSendTypePadding + style::margins(
|
||||
0,
|
||||
st::messagePrivacyBottomSkip,
|
||||
0,
|
||||
st::messagePrivacyBottomSkip));
|
||||
|
||||
Ui::AddDividerText(inner, tr::lng_messages_privacy_charge_about());
|
||||
|
||||
const auto chargeWrap = inner->add(
|
||||
object_ptr<Ui::SlideWrap<Ui::VerticalLayout>>(
|
||||
inner,
|
||||
object_ptr<Ui::VerticalLayout>(inner)));
|
||||
const auto chargeInner = chargeWrap->entity();
|
||||
|
||||
Ui::AddSkip(chargeInner);
|
||||
Ui::AddSubsectionTitle(chargeInner, tr::lng_messages_privacy_price());
|
||||
|
||||
struct State {
|
||||
rpl::variable<int> stars;
|
||||
};
|
||||
const auto state = std::make_shared<State>();
|
||||
const auto savedValue = privacy->newChargeStarsCurrent();
|
||||
const auto chargeStars = savedValue ? savedValue : kDefaultChargeStars;
|
||||
state->stars = chargeStars;
|
||||
|
||||
auto values = std::vector<int>();
|
||||
if (chargeStars < kStarsMin) {
|
||||
values.push_back(chargeStars);
|
||||
}
|
||||
for (auto i = kStarsMin; i < 100; ++i) {
|
||||
values.push_back(i);
|
||||
}
|
||||
for (auto i = 100; i < 1000; i += 10) {
|
||||
if (i < chargeStars + 10 && chargeStars < i) {
|
||||
values.push_back(chargeStars);
|
||||
}
|
||||
values.push_back(i);
|
||||
}
|
||||
for (auto i = 1000; i < kStarsMax + 1; i += 100) {
|
||||
if (i < chargeStars + 100 && chargeStars < i) {
|
||||
values.push_back(chargeStars);
|
||||
}
|
||||
values.push_back(i);
|
||||
}
|
||||
const auto valuesCount = int(values.size());
|
||||
const auto setStars = [=](int value) {
|
||||
state->stars = value;
|
||||
};
|
||||
chargeInner->add(
|
||||
MakeChargeStarsSlider(
|
||||
chargeInner,
|
||||
&st::settingsScale,
|
||||
&st::settingsScaleLabel,
|
||||
valuesCount,
|
||||
[=](int index) { return values[index]; },
|
||||
chargeStars,
|
||||
setStars,
|
||||
setStars),
|
||||
st::boxRowPadding);
|
||||
Ui::AddSkip(chargeInner);
|
||||
|
||||
auto dollars = state->stars.value() | rpl::map([=](int stars) {
|
||||
const auto ratio = controller->session().appConfig().get<float64>(
|
||||
u"stars_usd_withdraw_rate_x1000"_q,
|
||||
1200);
|
||||
const auto dollars = int(base::SafeRound(stars * (ratio / 1000.)));
|
||||
return '~' + Ui::FillAmountAndCurrency(dollars, u"USD"_q);
|
||||
});
|
||||
Ui::AddDividerText(
|
||||
chargeInner,
|
||||
tr::lng_messages_privacy_price_about(
|
||||
lt_percent,
|
||||
rpl::single(QString::number(kGetPercent) + '%'),
|
||||
lt_amount,
|
||||
std::move(dollars)));
|
||||
|
||||
Ui::AddSkip(chargeInner);
|
||||
Ui::AddSubsectionTitle(
|
||||
chargeInner,
|
||||
tr::lng_messages_privacy_exceptions());
|
||||
const auto exceptions = Settings::AddButtonWithLabel(
|
||||
chargeInner,
|
||||
tr::lng_messages_privacy_remove_fee(),
|
||||
rpl::single(u""_q),
|
||||
st::settingsButtonNoIcon);
|
||||
Ui::AddSkip(chargeInner);
|
||||
Ui::AddDividerText(chargeInner, tr::lng_messages_privacy_remove_about());
|
||||
|
||||
using namespace rpl::mappers;
|
||||
chargeWrap->toggleOn(group->value() | rpl::map(_1 == kOptionCharge));
|
||||
chargeWrap->finishAnimating();
|
||||
|
||||
using WeakToast = base::weak_ptr<Ui::Toast::Instance>;
|
||||
const auto toast = std::make_shared<WeakToast>();
|
||||
const auto showToast = [=] {
|
||||
|
@ -875,19 +1090,18 @@ void EditMessagesPrivacyBox(
|
|||
}),
|
||||
});
|
||||
};
|
||||
|
||||
if (!allowed()) {
|
||||
CreateRadiobuttonLock(restricted, st::messagePrivacyCheck);
|
||||
CreateRadiobuttonLock(charged, st::messagePrivacyCheck);
|
||||
|
||||
group->setChangedCallback([=](int value) {
|
||||
if (value == kOptionPremium) {
|
||||
if (value == kOptionPremium || value == kOptionCharge) {
|
||||
group->setValue(kOptionAll);
|
||||
showToast();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
Ui::AddDividerText(inner, tr::lng_messages_privacy_about());
|
||||
if (!allowed()) {
|
||||
Ui::AddSkip(inner);
|
||||
Settings::AddButtonWithIcon(
|
||||
inner,
|
||||
|
@ -907,8 +1121,12 @@ void EditMessagesPrivacyBox(
|
|||
} else {
|
||||
box->addButton(tr::lng_settings_save(), [=] {
|
||||
if (allowed()) {
|
||||
privacy->updateNewRequirePremium(
|
||||
group->current() == kOptionPremium);
|
||||
const auto value = group->current();
|
||||
const auto premiumRequired = (value == kOptionPremium);
|
||||
const auto chargeStars = (value == kOptionCharge)
|
||||
? state->stars.current()
|
||||
: 0;
|
||||
privacy->updateMessagesPrivacy(premiumRequired, chargeStars);
|
||||
box->closeBox();
|
||||
} else {
|
||||
showToast();
|
||||
|
|
|
@ -610,7 +610,6 @@ void UserData::setCallsStatus(CallsStatus callsStatus) {
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
Data::Birthday UserData::birthday() const {
|
||||
return _birthday;
|
||||
}
|
||||
|
|
|
@ -630,7 +630,7 @@ void Widget::fillTopBarMenu(const Ui::Menu::MenuCallback &addAction) {
|
|||
});
|
||||
}, filter.skipUnique ? nullptr : &st::mediaPlayerMenuCheck);
|
||||
|
||||
if (_inner->peer()->canManageGifts() && _inner->peer()->isChannel()) {
|
||||
if (_inner->peer()->canManageGifts()) {
|
||||
addAction({ .isSeparator = true });
|
||||
|
||||
addAction(tr::lng_peer_gifts_filter_saved(tr::now), [=] {
|
||||
|
|
|
@ -535,6 +535,7 @@ inputPrivacyKeyVoiceMessages#aee69d68 = InputPrivacyKey;
|
|||
inputPrivacyKeyAbout#3823cc40 = InputPrivacyKey;
|
||||
inputPrivacyKeyBirthday#d65a11cc = InputPrivacyKey;
|
||||
inputPrivacyKeyStarGiftsAutoSave#e1732341 = InputPrivacyKey;
|
||||
inputPrivacyKeyNoPaidMessages#bdc597b4 = InputPrivacyKey;
|
||||
|
||||
privacyKeyStatusTimestamp#bc2eab30 = PrivacyKey;
|
||||
privacyKeyChatInvite#500e6dfa = PrivacyKey;
|
||||
|
|
|
@ -356,10 +356,16 @@ void AddMessagesPrivacyButton(
|
|||
not_null<Ui::VerticalLayout*> container) {
|
||||
const auto session = &controller->session();
|
||||
const auto privacy = &session->api().globalPrivacy();
|
||||
auto label = rpl::conditional(
|
||||
auto label = rpl::combine(
|
||||
privacy->newRequirePremium(),
|
||||
tr::lng_edit_privacy_contacts_and_premium(),
|
||||
tr::lng_edit_privacy_everyone());
|
||||
privacy->newChargeStars()
|
||||
) | rpl::map([=](bool requirePremium, int chargeStars) {
|
||||
return chargeStars
|
||||
? tr::lng_edit_privacy_paid()
|
||||
: requirePremium
|
||||
? tr::lng_edit_privacy_contacts_and_premium()
|
||||
: tr::lng_edit_privacy_everyone();
|
||||
}) | rpl::flatten_latest();
|
||||
const auto &st = st::settingsButtonNoIcon;
|
||||
const auto button = AddButtonWithLabel(
|
||||
container,
|
||||
|
|
Loading…
Add table
Reference in a new issue