Track and show "too early" gift transfer/resell.

This commit is contained in:
John Preston 2025-05-01 11:00:53 +04:00
parent 3e538b732a
commit 68b3d75705
8 changed files with 81 additions and 11 deletions

View file

@ -3644,6 +3644,8 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
"lng_gift_resale_symbols#one" = "{count} Symbol";
"lng_gift_resale_symbols#other" = "{count} Symbols";
"lng_gift_resale_early" = "You will be able to resell this gift in {duration}.";
"lng_gift_transfer_early" = "You will be able to transfer this gift in {duration}.";
"lng_gift_resale_transfer_early_title" = "Try Later";
"lng_accounts_limit_title" = "Limit Reached";
"lng_accounts_limit1#one" = "You have reached the limit of **{count}** connected account.";

View file

@ -886,6 +886,8 @@ std::optional<Data::SavedStarGift> FromTL(
} else if (const auto unique = parsed->unique.get()) {
unique->starsForTransfer = data.vtransfer_stars().value_or(-1);
unique->exportAt = data.vcan_export_at().value_or_empty();
unique->canTransferAt = data.vcan_transfer_at().value_or_empty();
unique->canResellAt = data.vcan_resell_at().value_or_empty();
}
using Id = Data::SavedStarGiftId;
const auto hasUnique = parsed->unique != nullptr;

View file

@ -18,7 +18,6 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "boxes/peers/replace_boost_box.h" // BoostsForGift.
#include "boxes/premium_preview_box.h" // ShowPremiumPreviewBox.
#include "boxes/star_gift_box.h" // ShowStarGiftBox.
#include "boxes/transfer_gift_box.h" // ShowTransferGiftBox.
#include "core/ui_integration.h"
#include "data/data_boosts.h"
#include "data/data_changes.h"

View file

@ -2705,6 +2705,9 @@ void SendGiftBox(
const auto star = std::get_if<GiftTypeStars>(&descriptor);
const auto unique = star ? star->info.unique : nullptr;
if (unique && star->mine && !peer->isSelf()) {
if (ShowTransferGiftLater(window->uiShow(), unique)) {
return;
}
const auto done = [=] {
window->session().credits().load(true);
window->showPeerHistory(peer);
@ -4321,15 +4324,9 @@ void UpdateGiftSellPrice(
const auto type = error.type();
if (type.startsWith(earlyPrefix)) {
const auto seconds = type.mid(earlyPrefix.size()).toInt();
const auto days = seconds / 86400;
const auto hours = seconds / 3600;
const auto minutes = std::max(seconds / 60, 1);
show->showToast(
tr::lng_gift_resale_early(tr::now, lt_duration, days
? tr::lng_days(tr::now, lt_count, days)
: hours
? tr::lng_hours(tr::now, lt_count, hours)
: tr::lng_minutes(tr::now, lt_count, minutes)));
const auto newAvailableAt = base::unixtime::now() + seconds;
unique->canResellAt = newAvailableAt;
ShowResaleGiftLater(show, unique);
} else {
show->showToast(type);
}
@ -4341,6 +4338,9 @@ void ShowUniqueGiftSellBox(
std::shared_ptr<Data::UniqueGift> unique,
Data::SavedStarGiftId savedId,
Settings::GiftWearBoxStyleOverride st) {
if (ShowResaleGiftLater(show, unique)) {
return;
}
show->show(Box([=](not_null<Ui::GenericBox*> box) {
box->setTitle(tr::lng_gift_sell_title());
box->setStyle(st.box ? *st.box : st::upgradeGiftBox);

View file

@ -25,6 +25,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "ui/boxes/confirm_box.h"
#include "ui/layers/generic_box.h"
#include "ui/text/text_utilities.h"
#include "ui/toast/toast.h"
#include "ui/basic_click_handlers.h"
#include "ui/empty_userpic.h"
#include "ui/painter.h"
@ -460,7 +461,16 @@ void TransferGift(
formDone(Payments::CheckoutResult::Paid, &result);
}).fail([=](const MTP::Error &error) {
formDone(Payments::CheckoutResult::Failed, nullptr);
if (const auto strong = weak.get()) {
const auto earlyPrefix = u"STARGIFT_TRANSFER_TOO_EARLY_"_q;
const auto type = error.type();
if (type.startsWith(earlyPrefix)) {
const auto seconds = type.mid(earlyPrefix.size()).toInt();
const auto newAvailableAt = base::unixtime::now() + seconds;
gift->canTransferAt = newAvailableAt;
if (const auto strong = weak.get()) {
ShowTransferGiftLater(strong->uiShow(), gift);
}
} else if (const auto strong = weak.get()) {
strong->showToast(error.type());
}
}).send();
@ -580,6 +590,9 @@ void ShowTransferGiftBox(
not_null<Window::SessionController*> window,
std::shared_ptr<Data::UniqueGift> gift,
Data::SavedStarGiftId savedId) {
if (ShowTransferGiftLater(window->uiShow(), gift)) {
return;
}
auto controller = std::make_unique<Controller>(
window,
gift,
@ -671,3 +684,46 @@ void ShowBuyResaleGiftBox(
});
}));
}
bool ShowResaleGiftLater(
std::shared_ptr<ChatHelpers::Show> show,
std::shared_ptr<Data::UniqueGift> gift) {
const auto now = base::unixtime::now();
if (gift->canResellAt <= now) {
return false;
}
const auto seconds = gift->canResellAt - now;
const auto days = seconds / 86400;
const auto hours = seconds / 3600;
const auto minutes = std::max(seconds / 60, 1);
show->showToast({
.title = tr::lng_gift_resale_transfer_early_title(tr::now),
.text = { tr::lng_gift_resale_early(tr::now, lt_duration, days
? tr::lng_days(tr::now, lt_count, days)
: hours
? tr::lng_hours(tr::now, lt_count, hours)
: tr::lng_minutes(tr::now, lt_count, minutes)) },
});
return true;
}
bool ShowTransferGiftLater(
std::shared_ptr<ChatHelpers::Show> show,
std::shared_ptr<Data::UniqueGift> gift) {
const auto seconds = gift->canTransferAt - base::unixtime::now();
if (seconds <= 0) {
return false;
}
const auto days = seconds / 86400;
const auto hours = seconds / 3600;
const auto minutes = std::max(seconds / 60, 1);
show->showToast({
.title = tr::lng_gift_resale_transfer_early_title(tr::now),
.text = { tr::lng_gift_transfer_early(tr::now, lt_duration, days
? tr::lng_days(tr::now, lt_count, days)
: hours
? tr::lng_hours(tr::now, lt_count, hours)
: tr::lng_minutes(tr::now, lt_count, minutes)) },
});
return true;
}

View file

@ -37,3 +37,10 @@ void ShowBuyResaleGiftBox(
std::shared_ptr<Data::UniqueGift> gift,
not_null<PeerData*> to,
Fn<void()> closeParentBox);
bool ShowResaleGiftLater(
std::shared_ptr<ChatHelpers::Show> show,
std::shared_ptr<Data::UniqueGift> gift);
bool ShowTransferGiftLater(
std::shared_ptr<ChatHelpers::Show> show,
std::shared_ptr<Data::UniqueGift> gift);

View file

@ -48,6 +48,8 @@ struct UniqueGift {
int starsForTransfer = -1;
int starsForResale = -1;
TimeId exportAt = 0;
TimeId canTransferAt = 0;
TimeId canResellAt = 0;
UniqueGiftModel model;
UniqueGiftPattern pattern;
UniqueGiftBackdrop backdrop;

View file

@ -6024,6 +6024,8 @@ void HistoryItem::applyAction(const MTPMessageAction &action) {
unique->starsForTransfer
= data.vtransfer_stars().value_or(-1);
unique->exportAt = data.vcan_export_at().value_or_empty();
unique->canTransferAt = data.vcan_transfer_at().value_or_empty();
unique->canResellAt = data.vcan_resell_at().value_or_empty();
}
}
_media = std::make_unique<Data::MediaGiftBox>(