vh-bombsquad-modded-server-.../dist/ba_data/python/bastd/ui/appinvite.py
2024-06-06 19:50:58 +05:30

449 lines
15 KiB
Python

# Released under the MIT License. See LICENSE for details.
#
"""UI functionality related to inviting people to try the game."""
from __future__ import annotations
import copy
import time
from typing import TYPE_CHECKING
import ba
import ba.internal
if TYPE_CHECKING:
from typing import Any
class AppInviteWindow(ba.Window):
"""Window for showing different ways to invite people to try the game."""
def __init__(self) -> None:
ba.set_analytics_screen('AppInviteWindow')
self._data: dict[str, Any] | None = None
self._width = 650
self._height = 400
uiscale = ba.app.ui.uiscale
super().__init__(
root_widget=ba.containerwidget(
size=(self._width, self._height),
transition='in_scale',
scale=(
1.8
if uiscale is ba.UIScale.SMALL
else 1.35
if uiscale is ba.UIScale.MEDIUM
else 1.0
),
)
)
self._cancel_button = ba.buttonwidget(
parent=self._root_widget,
scale=0.8,
position=(60, self._height - 50),
size=(50, 50),
label='',
on_activate_call=self.close,
autoselect=True,
color=(0.4, 0.4, 0.6),
icon=ba.gettexture('crossOut'),
iconscale=1.2,
)
ba.containerwidget(
edit=self._root_widget, cancel_button=self._cancel_button
)
ba.textwidget(
parent=self._root_widget,
size=(0, 0),
position=(self._width * 0.5, self._height * 0.5 + 110),
autoselect=True,
scale=0.8,
maxwidth=self._width * 0.9,
h_align='center',
v_align='center',
color=(0.3, 0.8, 0.3),
flatness=1.0,
text=ba.Lstr(
resource='gatherWindow.earnTicketsForRecommendingAmountText',
fallback_resource=(
'gatherWindow.earnTicketsForRecommendingText'
),
subs=[
(
'${COUNT}',
str(
ba.internal.get_v1_account_misc_read_val(
'friendTryTickets', 300
)
),
),
(
'${YOU_COUNT}',
str(
ba.internal.get_v1_account_misc_read_val(
'friendTryAwardTickets', 100
)
),
),
],
),
)
or_text = (
ba.Lstr(resource='orText', subs=[('${A}', ''), ('${B}', '')])
.evaluate()
.strip()
)
ba.buttonwidget(
parent=self._root_widget,
size=(250, 150),
position=(self._width * 0.5 - 125, self._height * 0.5 - 80),
autoselect=True,
button_type='square',
label=ba.Lstr(resource='gatherWindow.inviteFriendsText'),
on_activate_call=ba.WeakCall(self._google_invites),
)
ba.textwidget(
parent=self._root_widget,
size=(0, 0),
position=(self._width * 0.5, self._height * 0.5 - 94),
autoselect=True,
scale=0.9,
h_align='center',
v_align='center',
color=(0.5, 0.5, 0.5),
flatness=1.0,
text=or_text,
)
ba.buttonwidget(
parent=self._root_widget,
size=(180, 50),
position=(self._width * 0.5 - 90, self._height * 0.5 - 170),
autoselect=True,
color=(0.5, 0.5, 0.6),
textcolor=(0.7, 0.7, 0.8),
text_scale=0.8,
label=ba.Lstr(resource='gatherWindow.appInviteSendACodeText'),
on_activate_call=ba.WeakCall(self._send_code),
)
# kick off a transaction to get our code
ba.internal.add_transaction(
{
'type': 'FRIEND_PROMO_CODE_REQUEST',
'ali': False,
'expire_time': time.time() + 20,
},
callback=ba.WeakCall(self._on_code_result),
)
ba.internal.run_transactions()
def _on_code_result(self, result: dict[str, Any] | None) -> None:
if result is not None:
self._data = result
def _send_code(self) -> None:
handle_app_invites_press(force_code=True)
def _google_invites(self) -> None:
if self._data is None:
ba.screenmessage(
ba.Lstr(resource='getTicketsWindow.unavailableTemporarilyText'),
color=(1, 0, 0),
)
ba.playsound(ba.getsound('error'))
return
if ba.internal.get_v1_account_state() == 'signed_in':
ba.set_analytics_screen('App Invite UI')
ba.internal.show_app_invite(
ba.Lstr(
resource='gatherWindow.appInviteTitleText',
subs=[('${APP_NAME}', ba.Lstr(resource='titleText'))],
).evaluate(),
ba.Lstr(
resource='gatherWindow.appInviteMessageText',
subs=[
('${COUNT}', str(self._data['tickets'])),
(
'${NAME}',
ba.internal.get_v1_account_name().split()[0],
),
('${APP_NAME}', ba.Lstr(resource='titleText')),
],
).evaluate(),
self._data['code'],
)
else:
ba.playsound(ba.getsound('error'))
def close(self) -> None:
"""Close the window."""
ba.containerwidget(edit=self._root_widget, transition='out_scale')
class ShowFriendCodeWindow(ba.Window):
"""Window showing a code for sharing with friends."""
def __init__(self, data: dict[str, Any]):
from ba.internal import is_browser_likely_available
ba.set_analytics_screen('Friend Promo Code')
self._width = 650
self._height = 400
uiscale = ba.app.ui.uiscale
super().__init__(
root_widget=ba.containerwidget(
size=(self._width, self._height),
color=(0.45, 0.63, 0.15),
transition='in_scale',
scale=(
1.7
if uiscale is ba.UIScale.SMALL
else 1.35
if uiscale is ba.UIScale.MEDIUM
else 1.0
),
)
)
self._data = copy.deepcopy(data)
ba.playsound(ba.getsound('cashRegister'))
ba.playsound(ba.getsound('swish'))
self._cancel_button = ba.buttonwidget(
parent=self._root_widget,
scale=0.7,
position=(50, self._height - 50),
size=(60, 60),
label='',
on_activate_call=self.close,
autoselect=True,
color=(0.45, 0.63, 0.15),
icon=ba.gettexture('crossOut'),
iconscale=1.2,
)
ba.containerwidget(
edit=self._root_widget, cancel_button=self._cancel_button
)
ba.textwidget(
parent=self._root_widget,
position=(self._width * 0.5, self._height * 0.8),
size=(0, 0),
color=ba.app.ui.infotextcolor,
scale=1.0,
flatness=1.0,
h_align='center',
v_align='center',
text=ba.Lstr(resource='gatherWindow.shareThisCodeWithFriendsText'),
maxwidth=self._width * 0.85,
)
ba.textwidget(
parent=self._root_widget,
position=(self._width * 0.5, self._height * 0.645),
size=(0, 0),
color=(1.0, 3.0, 1.0),
scale=2.0,
h_align='center',
v_align='center',
text=data['code'],
maxwidth=self._width * 0.85,
)
award_str: str | ba.Lstr | None
if self._data['awardTickets'] != 0:
award_str = ba.Lstr(
resource='gatherWindow.friendPromoCodeAwardText',
subs=[('${COUNT}', str(self._data['awardTickets']))],
)
else:
award_str = ''
ba.textwidget(
parent=self._root_widget,
position=(self._width * 0.5, self._height * 0.37),
size=(0, 0),
color=ba.app.ui.infotextcolor,
scale=1.0,
flatness=1.0,
h_align='center',
v_align='center',
text=ba.Lstr(
value='${A}\n${B}\n${C}\n${D}',
subs=[
(
'${A}',
ba.Lstr(
resource=(
'gatherWindow.friendPromoCodeRedeemLongText'
),
subs=[
('${COUNT}', str(self._data['tickets'])),
(
'${MAX_USES}',
str(self._data['usesRemaining']),
),
],
),
),
(
'${B}',
ba.Lstr(
resource=(
'gatherWindow.friendPromoCodeWhereToEnterText'
)
),
),
('${C}', award_str),
(
'${D}',
ba.Lstr(
resource='gatherWindow.friendPromoCodeExpireText',
subs=[
(
'${EXPIRE_HOURS}',
str(self._data['expireHours']),
)
],
),
),
],
),
maxwidth=self._width * 0.9,
max_height=self._height * 0.35,
)
if is_browser_likely_available():
xoffs = 0
ba.buttonwidget(
parent=self._root_widget,
size=(200, 40),
position=(self._width * 0.5 - 100 + xoffs, 39),
autoselect=True,
label=ba.Lstr(resource='gatherWindow.emailItText'),
on_activate_call=ba.WeakCall(self._email),
)
def _google_invites(self) -> None:
ba.set_analytics_screen('App Invite UI')
ba.internal.show_app_invite(
ba.Lstr(
resource='gatherWindow.appInviteTitleText',
subs=[('${APP_NAME}', ba.Lstr(resource='titleText'))],
).evaluate(),
ba.Lstr(
resource='gatherWindow.appInviteMessageText',
subs=[
('${COUNT}', str(self._data['tickets'])),
('${NAME}', ba.internal.get_v1_account_name().split()[0]),
('${APP_NAME}', ba.Lstr(resource='titleText')),
],
).evaluate(),
self._data['code'],
)
def _email(self) -> None:
import urllib.parse
# If somehow we got signed out.
if ba.internal.get_v1_account_state() != 'signed_in':
ba.screenmessage(
ba.Lstr(resource='notSignedInText'), color=(1, 0, 0)
)
ba.playsound(ba.getsound('error'))
return
ba.set_analytics_screen('Email Friend Code')
subject = (
ba.Lstr(resource='gatherWindow.friendHasSentPromoCodeText')
.evaluate()
.replace('${NAME}', ba.internal.get_v1_account_name())
.replace('${APP_NAME}', ba.Lstr(resource='titleText').evaluate())
.replace('${COUNT}', str(self._data['tickets']))
)
body = (
ba.Lstr(resource='gatherWindow.youHaveBeenSentAPromoCodeText')
.evaluate()
.replace('${APP_NAME}', ba.Lstr(resource='titleText').evaluate())
+ '\n\n'
+ str(self._data['code'])
+ '\n\n'
)
body += (
(
ba.Lstr(resource='gatherWindow.friendPromoCodeRedeemShortText')
.evaluate()
.replace('${COUNT}', str(self._data['tickets']))
)
+ '\n\n'
+ ba.Lstr(resource='gatherWindow.friendPromoCodeInstructionsText')
.evaluate()
.replace('${APP_NAME}', ba.Lstr(resource='titleText').evaluate())
+ '\n'
+ ba.Lstr(resource='gatherWindow.friendPromoCodeExpireText')
.evaluate()
.replace('${EXPIRE_HOURS}', str(self._data['expireHours']))
+ '\n'
+ ba.Lstr(resource='enjoyText').evaluate()
)
ba.open_url(
'mailto:?subject='
+ urllib.parse.quote(subject)
+ '&body='
+ urllib.parse.quote(body)
)
def close(self) -> None:
"""Close the window."""
ba.containerwidget(edit=self._root_widget, transition='out_scale')
def handle_app_invites_press(force_code: bool = False) -> None:
"""(internal)"""
app = ba.app
do_app_invites = (
app.platform == 'android'
and app.subplatform == 'google'
and ba.internal.get_v1_account_misc_read_val('enableAppInvites', False)
and not app.on_tv
)
# Update: google's app invites are deprecated.
do_app_invites = False
if force_code:
do_app_invites = False
# FIXME: Should update this to grab a code before showing the invite UI.
if do_app_invites:
AppInviteWindow()
else:
ba.screenmessage(
ba.Lstr(resource='gatherWindow.requestingAPromoCodeText'),
color=(0, 1, 0),
)
def handle_result(result: dict[str, Any] | None) -> None:
with ba.Context('ui'):
if result is None:
ba.screenmessage(
ba.Lstr(resource='errorText'), color=(1, 0, 0)
)
ba.playsound(ba.getsound('error'))
else:
ShowFriendCodeWindow(result)
ba.internal.add_transaction(
{
'type': 'FRIEND_PROMO_CODE_REQUEST',
'ali': False,
'expire_time': time.time() + 10,
},
callback=handle_result,
)
ba.internal.run_transactions()