forked from test/mau_mau_bot
implement plurals, update de_DE translation to use plurals
This commit is contained in:
parent
c54ffd83e5
commit
6901e7f4d0
10 changed files with 410 additions and 233 deletions
58
bot.py
58
bot.py
|
@ -37,11 +37,12 @@ from utils import display_name
|
||||||
import card as c
|
import card as c
|
||||||
from errors import (NoGameInChatError, LobbyClosedError, AlreadyJoinedError,
|
from errors import (NoGameInChatError, LobbyClosedError, AlreadyJoinedError,
|
||||||
NotEnoughPlayersError, DeckEmptyError)
|
NotEnoughPlayersError, DeckEmptyError)
|
||||||
from utils import _, __, send_async, answer_async, user_locale, game_locales, \
|
from utils import send_async, answer_async, error, TIMEOUT
|
||||||
error, TIMEOUT
|
|
||||||
from shared_vars import botan, gm, updater, dispatcher
|
from shared_vars import botan, gm, updater, dispatcher
|
||||||
|
from internationalization import _, __, user_locale, game_locales
|
||||||
|
import simple_commands
|
||||||
|
import settings
|
||||||
|
|
||||||
import simple_commands, settings
|
|
||||||
from simple_commands import help
|
from simple_commands import help
|
||||||
|
|
||||||
|
|
||||||
|
@ -136,11 +137,12 @@ def leave_game(bot, update):
|
||||||
|
|
||||||
except NotEnoughPlayersError:
|
except NotEnoughPlayersError:
|
||||||
gm.end_game(chat, user)
|
gm.end_game(chat, user)
|
||||||
send_async(bot, chat.id, text=__("Game ended!", game.translate))
|
send_async(bot, chat.id, text=__("Game ended!", multi=game.translate))
|
||||||
|
|
||||||
else:
|
else:
|
||||||
send_async(bot, chat.id,
|
send_async(bot, chat.id,
|
||||||
text=__("Okay. Next Player: {name}", game.translate).format(
|
text=__("Okay. Next Player: {name}",
|
||||||
|
multi=game.translate).format(
|
||||||
name=display_name(game.current_player.user)),
|
name=display_name(game.current_player.user)),
|
||||||
reply_to_message_id=update.message.message_id)
|
reply_to_message_id=update.message.message_id)
|
||||||
|
|
||||||
|
@ -197,10 +199,11 @@ def status_update(bot, update):
|
||||||
pass
|
pass
|
||||||
except NotEnoughPlayersError:
|
except NotEnoughPlayersError:
|
||||||
gm.end_game(chat, user)
|
gm.end_game(chat, user)
|
||||||
send_async(bot, chat.id, text=__("Game ended!", game.translate))
|
send_async(bot, chat.id, text=__("Game ended!",
|
||||||
|
multi=game.translate))
|
||||||
else:
|
else:
|
||||||
send_async(bot, chat.id, text=__("Removing {name} from the game",
|
send_async(bot, chat.id, text=__("Removing {name} from the game",
|
||||||
game.translate)
|
multi=game.translate)
|
||||||
.format(name=display_name(user)))
|
.format(name=display_name(user)))
|
||||||
|
|
||||||
|
|
||||||
|
@ -236,7 +239,7 @@ def start_game(bot, update, args):
|
||||||
__("First player: {name}\n"
|
__("First player: {name}\n"
|
||||||
"Use /close to stop people from joining the game.\n"
|
"Use /close to stop people from joining the game.\n"
|
||||||
"Enable multi-translations with /enable_translations",
|
"Enable multi-translations with /enable_translations",
|
||||||
game.translate)
|
multi=game.translate)
|
||||||
.format(name=display_name(game.current_player.user)))
|
.format(name=display_name(game.current_player.user)))
|
||||||
|
|
||||||
@run_async
|
@run_async
|
||||||
|
@ -410,9 +413,12 @@ def skip_player(bot, update):
|
||||||
delta = (now - started).seconds
|
delta = (now - started).seconds
|
||||||
|
|
||||||
if delta < skipped_player.waiting_time:
|
if delta < skipped_player.waiting_time:
|
||||||
|
n = skipped_player.waiting_time - delta
|
||||||
send_async(bot, chat.id,
|
send_async(bot, chat.id,
|
||||||
text=_("Please wait {time} seconds")
|
text=_("Please wait {time} second",
|
||||||
.format(time=(skipped_player.waiting_time - delta)),
|
"Please wait {time} seconds",
|
||||||
|
n)
|
||||||
|
.format(time=n),
|
||||||
reply_to_message_id=update.message.message_id)
|
reply_to_message_id=update.message.message_id)
|
||||||
|
|
||||||
elif skipped_player.waiting_time > 0:
|
elif skipped_player.waiting_time > 0:
|
||||||
|
@ -423,11 +429,17 @@ def skip_player(bot, update):
|
||||||
except DeckEmptyError:
|
except DeckEmptyError:
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
n = skipped_player.waiting_time
|
||||||
send_async(bot, chat.id,
|
send_async(bot, chat.id,
|
||||||
text=__("Waiting time to skip this player has "
|
text=__("Waiting time to skip this player has "
|
||||||
|
"been reduced to {time} second.\n"
|
||||||
|
"Next player: {name}",
|
||||||
|
"Waiting time to skip this player has "
|
||||||
"been reduced to {time} seconds.\n"
|
"been reduced to {time} seconds.\n"
|
||||||
"Next player: {name}", game.translate)
|
"Next player: {name}",
|
||||||
.format(time=skipped_player.waiting_time,
|
n,
|
||||||
|
multi=game.translate)
|
||||||
|
.format(time=n,
|
||||||
name=display_name(next_player.user)))
|
name=display_name(next_player.user)))
|
||||||
game.turn()
|
game.turn()
|
||||||
|
|
||||||
|
@ -437,7 +449,7 @@ def skip_player(bot, update):
|
||||||
send_async(bot, chat.id,
|
send_async(bot, chat.id,
|
||||||
text=__("{name1} was skipped four times in a row "
|
text=__("{name1} was skipped four times in a row "
|
||||||
"and has been removed from the game.\n"
|
"and has been removed from the game.\n"
|
||||||
"Next player: {name2}", game.translate)
|
"Next player: {name2}", multi=game.translate)
|
||||||
.format(name1=display_name(skipped_player.user),
|
.format(name1=display_name(skipped_player.user),
|
||||||
name2=display_name(next_player.user)))
|
name2=display_name(next_player.user)))
|
||||||
|
|
||||||
|
@ -445,7 +457,7 @@ def skip_player(bot, update):
|
||||||
send_async(bot, chat.id,
|
send_async(bot, chat.id,
|
||||||
text=__("{name} was skipped four times in a row "
|
text=__("{name} was skipped four times in a row "
|
||||||
"and has been removed from the game.\n"
|
"and has been removed from the game.\n"
|
||||||
"The game ended.", game.translate)
|
"The game ended.", multi=game.translate)
|
||||||
.format(name=display_name(skipped_player.user)))
|
.format(name=display_name(skipped_player.user)))
|
||||||
|
|
||||||
gm.end_game(chat.id, skipped_player.user)
|
gm.end_game(chat.id, skipped_player.user)
|
||||||
|
@ -459,7 +471,6 @@ def reply_to_query(bot, update):
|
||||||
Builds the result list for inline queries and answers to the client.
|
Builds the result list for inline queries and answers to the client.
|
||||||
"""
|
"""
|
||||||
results = list()
|
results = list()
|
||||||
playable = list()
|
|
||||||
switch = None
|
switch = None
|
||||||
|
|
||||||
try:
|
try:
|
||||||
|
@ -476,7 +487,7 @@ def reply_to_query(bot, update):
|
||||||
elif user_id == game.current_player.user.id:
|
elif user_id == game.current_player.user.id:
|
||||||
if game.choosing_color:
|
if game.choosing_color:
|
||||||
add_choose_color(results, game)
|
add_choose_color(results, game)
|
||||||
add_other_cards(playable, player, results, game)
|
add_other_cards(player, results, game)
|
||||||
else:
|
else:
|
||||||
if not player.drew:
|
if not player.drew:
|
||||||
add_draw(player, results)
|
add_draw(player, results)
|
||||||
|
@ -541,7 +552,7 @@ def process_result(bot, update):
|
||||||
return
|
return
|
||||||
elif int(anti_cheat) != last_anti_cheat:
|
elif int(anti_cheat) != last_anti_cheat:
|
||||||
send_async(bot, chat.id,
|
send_async(bot, chat.id,
|
||||||
text=__("Cheat attempt by {name}", game.translate)
|
text=__("Cheat attempt by {name}", multi=game.translate)
|
||||||
.format(name=display_name(player.user)))
|
.format(name=display_name(player.user)))
|
||||||
return
|
return
|
||||||
elif result_id == 'call_bluff':
|
elif result_id == 'call_bluff':
|
||||||
|
@ -560,7 +571,7 @@ def process_result(bot, update):
|
||||||
|
|
||||||
if game in gm.chatid_games.get(chat.id, list()):
|
if game in gm.chatid_games.get(chat.id, list()):
|
||||||
send_async(bot, chat.id,
|
send_async(bot, chat.id,
|
||||||
text=__("Next player: {name}", game.translate)
|
text=__("Next player: {name}", multi=game.translate)
|
||||||
.format(name=display_name(game.current_player.user)))
|
.format(name=display_name(game.current_player.user)))
|
||||||
|
|
||||||
|
|
||||||
|
@ -572,7 +583,7 @@ def reset_waiting_time(bot, player):
|
||||||
player.waiting_time = 90
|
player.waiting_time = 90
|
||||||
send_async(bot, chat.id,
|
send_async(bot, chat.id,
|
||||||
text=__("Waiting time for {name} has been reset to 90 "
|
text=__("Waiting time for {name} has been reset to 90 "
|
||||||
"seconds", player.game.translate)
|
"seconds", multi=player.game.translate)
|
||||||
.format(name=display_name(player.user)))
|
.format(name=display_name(player.user)))
|
||||||
|
|
||||||
|
|
||||||
|
@ -598,7 +609,7 @@ def do_play_card(bot, player, result_id):
|
||||||
|
|
||||||
if len(player.cards) == 0:
|
if len(player.cards) == 0:
|
||||||
send_async(bot, chat.id,
|
send_async(bot, chat.id,
|
||||||
text=__("{name} won!", game.translate)
|
text=__("{name} won!", multi=game.translate)
|
||||||
.format(name=user.first_name))
|
.format(name=user.first_name))
|
||||||
|
|
||||||
if us.stats:
|
if us.stats:
|
||||||
|
@ -612,7 +623,8 @@ def do_play_card(bot, player, result_id):
|
||||||
try:
|
try:
|
||||||
gm.leave_game(user, chat)
|
gm.leave_game(user, chat)
|
||||||
except NotEnoughPlayersError:
|
except NotEnoughPlayersError:
|
||||||
send_async(bot, chat.id, text=__("Game ended!", game.translate))
|
send_async(bot, chat.id,
|
||||||
|
text=__("Game ended!", multi=game.translate))
|
||||||
|
|
||||||
us2 = UserSetting.get(id=game.current_player.user.id)
|
us2 = UserSetting.get(id=game.current_player.user.id)
|
||||||
if us2 and us2.stats:
|
if us2 and us2.stats:
|
||||||
|
@ -636,7 +648,7 @@ def do_draw(bot, player):
|
||||||
except DeckEmptyError:
|
except DeckEmptyError:
|
||||||
send_async(bot, player.game.chat.id,
|
send_async(bot, player.game.chat.id,
|
||||||
text=__("There are no more cards in the deck.",
|
text=__("There are no more cards in the deck.",
|
||||||
game.translate))
|
multi=game.translate))
|
||||||
|
|
||||||
if (game.last_card.value == c.DRAW_TWO or
|
if (game.last_card.value == c.DRAW_TWO or
|
||||||
game.last_card.special == c.DRAW_FOUR) and \
|
game.last_card.special == c.DRAW_FOUR) and \
|
||||||
|
@ -694,6 +706,8 @@ dispatcher.add_handler(CommandHandler('enable_translations',
|
||||||
dispatcher.add_handler(CommandHandler('disable_translations',
|
dispatcher.add_handler(CommandHandler('disable_translations',
|
||||||
disable_translations))
|
disable_translations))
|
||||||
dispatcher.add_handler(CommandHandler('skip', skip_player))
|
dispatcher.add_handler(CommandHandler('skip', skip_player))
|
||||||
|
simple_commands.register()
|
||||||
|
settings.register()
|
||||||
dispatcher.add_handler(MessageHandler([Filters.status_update], status_update))
|
dispatcher.add_handler(MessageHandler([Filters.status_update], status_update))
|
||||||
dispatcher.add_error_handler(error)
|
dispatcher.add_error_handler(error)
|
||||||
|
|
||||||
|
|
175
internationalization.py
Normal file
175
internationalization.py
Normal file
|
@ -0,0 +1,175 @@
|
||||||
|
#!/usr/bin/env python3
|
||||||
|
# -*- coding: utf-8 -*-
|
||||||
|
#
|
||||||
|
# Telegram bot to play UNO in group chats
|
||||||
|
# Copyright (c) 2016 Jannes Höke <uno@jhoeke.de>
|
||||||
|
#
|
||||||
|
# This program is free software: you can redistribute it and/or modify
|
||||||
|
# it under the terms of the GNU Affero General Public License as
|
||||||
|
# published by the Free Software Foundation, either version 3 of the
|
||||||
|
# License, or (at your option) any later version.
|
||||||
|
#
|
||||||
|
# This program is distributed in the hope that it will be useful,
|
||||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
# GNU Affero General Public License for more details.
|
||||||
|
#
|
||||||
|
# You should have received a copy of the GNU Affero General Public License
|
||||||
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
|
||||||
|
import gettext
|
||||||
|
from functools import wraps
|
||||||
|
import logging
|
||||||
|
|
||||||
|
from locales import available_locales
|
||||||
|
from database import db_session
|
||||||
|
from user_setting import UserSetting
|
||||||
|
from shared_vars import gm
|
||||||
|
|
||||||
|
GETTEXT_DOMAIN = 'unobot'
|
||||||
|
GETTEXT_DIR = 'locales'
|
||||||
|
|
||||||
|
|
||||||
|
class _Underscore(object):
|
||||||
|
"""Class to emulate flufl.i18n behaviour, but with plural support"""
|
||||||
|
def __init__(self):
|
||||||
|
self.translators = {
|
||||||
|
locale: gettext.GNUTranslations(
|
||||||
|
open(gettext.find(
|
||||||
|
GETTEXT_DOMAIN, GETTEXT_DIR, languages=[locale]
|
||||||
|
), 'rb')
|
||||||
|
)
|
||||||
|
for locale
|
||||||
|
in available_locales.keys()
|
||||||
|
if locale != 'en_US' # No translation file for en_US
|
||||||
|
}
|
||||||
|
self.locale_stack = list()
|
||||||
|
|
||||||
|
def push(self, locale):
|
||||||
|
self.locale_stack.append(locale)
|
||||||
|
|
||||||
|
def pop(self):
|
||||||
|
if self.locale_stack:
|
||||||
|
return self.locale_stack.pop()
|
||||||
|
else:
|
||||||
|
return None
|
||||||
|
|
||||||
|
@property
|
||||||
|
def code(self):
|
||||||
|
if self.locale_stack:
|
||||||
|
return self.locale_stack[-1]
|
||||||
|
else:
|
||||||
|
return None
|
||||||
|
|
||||||
|
def __call__(self, singular, plural=None, n=1, locale=None):
|
||||||
|
if not locale:
|
||||||
|
locale = self.locale_stack[-1]
|
||||||
|
|
||||||
|
if locale not in self.translators.keys():
|
||||||
|
if n is 1:
|
||||||
|
return singular
|
||||||
|
else:
|
||||||
|
return plural
|
||||||
|
|
||||||
|
translator = self.translators[locale]
|
||||||
|
|
||||||
|
if plural is None:
|
||||||
|
return translator.gettext(singular)
|
||||||
|
else:
|
||||||
|
return translator.ngettext(singular, plural, n)
|
||||||
|
|
||||||
|
_ = _Underscore()
|
||||||
|
|
||||||
|
|
||||||
|
def __(singular, plural=None, n=1, multi=False):
|
||||||
|
"""Translates text into all locales on the stack"""
|
||||||
|
translations = list()
|
||||||
|
|
||||||
|
if not multi:
|
||||||
|
_.push('en_US')
|
||||||
|
translations.append(_(singular))
|
||||||
|
_.pop()
|
||||||
|
|
||||||
|
else:
|
||||||
|
for locale in _.locale_stack:
|
||||||
|
translation = _(singular, plural, n, locale)
|
||||||
|
logging.info(translation)
|
||||||
|
|
||||||
|
if translation not in translations:
|
||||||
|
translations.append(translation)
|
||||||
|
|
||||||
|
return '\n'.join(translations)
|
||||||
|
|
||||||
|
|
||||||
|
def user_locale(func):
|
||||||
|
@wraps(func)
|
||||||
|
@db_session
|
||||||
|
def wrapped(bot, update, *pargs, **kwargs):
|
||||||
|
user, chat = _user_chat_from_update(update)
|
||||||
|
|
||||||
|
with db_session:
|
||||||
|
us = UserSetting.get(id=user.id)
|
||||||
|
|
||||||
|
if us:
|
||||||
|
_.push(us.lang)
|
||||||
|
else:
|
||||||
|
_.push('en_US')
|
||||||
|
|
||||||
|
result = func(bot, update, *pargs, **kwargs)
|
||||||
|
_.pop()
|
||||||
|
return result
|
||||||
|
return wrapped
|
||||||
|
|
||||||
|
|
||||||
|
def game_locales(func):
|
||||||
|
@wraps(func)
|
||||||
|
@db_session
|
||||||
|
def wrapped(bot, update, *pargs, **kwargs):
|
||||||
|
user, chat = _user_chat_from_update(update)
|
||||||
|
player = gm.player_for_user_in_chat(user, chat)
|
||||||
|
locales = list()
|
||||||
|
|
||||||
|
if player:
|
||||||
|
for player in player.game.players:
|
||||||
|
us = UserSetting.get(id=player.user.id)
|
||||||
|
|
||||||
|
if us:
|
||||||
|
loc = us.lang
|
||||||
|
else:
|
||||||
|
loc = 'en_US'
|
||||||
|
|
||||||
|
if loc in locales:
|
||||||
|
continue
|
||||||
|
|
||||||
|
_.push(loc)
|
||||||
|
locales.append(loc)
|
||||||
|
|
||||||
|
result = func(bot, update, *pargs, **kwargs)
|
||||||
|
|
||||||
|
while _.code:
|
||||||
|
_.pop()
|
||||||
|
|
||||||
|
return result
|
||||||
|
return wrapped
|
||||||
|
|
||||||
|
|
||||||
|
def _user_chat_from_update(update):
|
||||||
|
|
||||||
|
try:
|
||||||
|
user = update.message.from_user
|
||||||
|
chat = update.message.chat
|
||||||
|
except (NameError, AttributeError):
|
||||||
|
try:
|
||||||
|
user = update.inline_query.from_user
|
||||||
|
chat = gm.userid_current[user.id].game.chat
|
||||||
|
except KeyError:
|
||||||
|
chat = None
|
||||||
|
except (NameError, AttributeError):
|
||||||
|
try:
|
||||||
|
user = update.chosen_inline_result.from_user
|
||||||
|
chat = gm.userid_current[user.id].game.chat
|
||||||
|
except (NameError, AttributeError):
|
||||||
|
chat = None
|
||||||
|
|
||||||
|
return user, chat
|
|
@ -0,0 +1,21 @@
|
||||||
|
#!/usr/bin/env python3
|
||||||
|
# -*- coding: utf-8 -*-
|
||||||
|
#
|
||||||
|
# Telegram bot to play UNO in group chats
|
||||||
|
# Copyright (c) 2016 Jannes Höke <uno@jhoeke.de>
|
||||||
|
#
|
||||||
|
# This program is free software: you can redistribute it and/or modify
|
||||||
|
# it under the terms of the GNU Affero General Public License as
|
||||||
|
# published by the Free Software Foundation, either version 3 of the
|
||||||
|
# License, or (at your option) any later version.
|
||||||
|
#
|
||||||
|
# This program is distributed in the hope that it will be useful,
|
||||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
# GNU Affero General Public License for more details.
|
||||||
|
#
|
||||||
|
# You should have received a copy of the GNU Affero General Public License
|
||||||
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
|
||||||
|
from .available import available_locales
|
37
locales/available.py
Normal file
37
locales/available.py
Normal file
|
@ -0,0 +1,37 @@
|
||||||
|
#!/usr/bin/env python3
|
||||||
|
# -*- coding: utf-8 -*-
|
||||||
|
#
|
||||||
|
# Telegram bot to play UNO in group chats
|
||||||
|
# Copyright (c) 2016 Jannes Höke <uno@jhoeke.de>
|
||||||
|
#
|
||||||
|
# This program is free software: you can redistribute it and/or modify
|
||||||
|
# it under the terms of the GNU Affero General Public License as
|
||||||
|
# published by the Free Software Foundation, either version 3 of the
|
||||||
|
# License, or (at your option) any later version.
|
||||||
|
#
|
||||||
|
# This program is distributed in the hope that it will be useful,
|
||||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
# GNU Affero General Public License for more details.
|
||||||
|
#
|
||||||
|
# You should have received a copy of the GNU Affero General Public License
|
||||||
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
|
||||||
|
"""Defines a dict of all available locales to the language name"""
|
||||||
|
|
||||||
|
OFFSET = 127462 - ord('A')
|
||||||
|
|
||||||
|
|
||||||
|
def flag(code):
|
||||||
|
return chr(ord(code[0]) + OFFSET) + chr(ord(code[1]) + OFFSET)
|
||||||
|
|
||||||
|
|
||||||
|
available_locales = {'en_US': flag('US') + ' English (US)',
|
||||||
|
'de_DE': flag('DE') + ' Deutsch (DE)',
|
||||||
|
'es_ES': flag('ES') + ' Español (ES)',
|
||||||
|
'id_ID': flag('ID') + ' Bahasa Indonesia',
|
||||||
|
'it_IT': flag('IT') + ' Italiano',
|
||||||
|
'pt_BR': flag('BR') + ' Português Brasileiro',
|
||||||
|
'zh_HK': flag('HK') + ' 廣東話',
|
||||||
|
'zh_TW': flag('TW') + ' 中文(香港)'}
|
|
@ -29,7 +29,7 @@ msgstr ""
|
||||||
"MIME-Version: 1.0\n"
|
"MIME-Version: 1.0\n"
|
||||||
"Content-Type: text/plain; charset=utf-8\n"
|
"Content-Type: text/plain; charset=utf-8\n"
|
||||||
"Content-Transfer-Encoding: utf-8\n"
|
"Content-Transfer-Encoding: utf-8\n"
|
||||||
"Plural-Forms: nplurals=2; plural=(n > 1);\n"
|
"Plural-Forms: nplurals=2; plural=(n != 1);\n"
|
||||||
"X-Generator: Gtranslator 2.91.6\n"
|
"X-Generator: Gtranslator 2.91.6\n"
|
||||||
|
|
||||||
#: bot.py:60
|
#: bot.py:60
|
||||||
|
@ -229,17 +229,22 @@ msgstr "Du spielst kein Spiel in dieser Gruppe."
|
||||||
|
|
||||||
#: bot.py:400
|
#: bot.py:400
|
||||||
#, python-format
|
#, python-format
|
||||||
msgid "Please wait {time} seconds"
|
msgid "Please wait {time} second"
|
||||||
msgstr "Bitte warte {time} Sekunden"
|
msgid_plural "Please wait {time} seconds"
|
||||||
|
msgstr[0] "Bitte warte {time} Sekunde"
|
||||||
|
msgstr[1] "Bitte warte {time} Sekunden"
|
||||||
|
|
||||||
#: bot.py:413
|
#: bot.py:413
|
||||||
#, python-format
|
#, python-format
|
||||||
msgid ""
|
msgid "Waiting time to skip this player has been reduced to {time} second.\n"
|
||||||
"Waiting time to skip this player has been reduced to {time} seconds.\n"
|
|
||||||
"Next player: {name}"
|
"Next player: {name}"
|
||||||
msgstr ""
|
msgid_plural "Waiting time to skip this player has been reduced to {time} seconds.\n"
|
||||||
"Die Wartezeit um diesen Spieler zu überspringen wurde auf {time} Sekunden "
|
"Next player: {name}"
|
||||||
"reduziert.\n"
|
msgstr[0] "Die Wartezeit um diesen Spieler zu überspringen wurde auf {time} "
|
||||||
|
"Sekunde reduziert.\n"
|
||||||
|
"Nächster Spieler: {name}"
|
||||||
|
msgstr[1] "Die Wartezeit um diesen Spieler zu überspringen wurde auf {time} "
|
||||||
|
"Sekunden reduziert.\n"
|
||||||
"Nächster Spieler: {name}"
|
"Nächster Spieler: {name}"
|
||||||
|
|
||||||
#: bot.py:424
|
#: bot.py:424
|
||||||
|
@ -313,8 +318,10 @@ msgid "Choose Color"
|
||||||
msgstr "Wähle Farbe"
|
msgstr "Wähle Farbe"
|
||||||
|
|
||||||
#: results.py:56
|
#: results.py:56
|
||||||
msgid "Cards (tap for game state):"
|
msgid "Last card (tap for game state):"
|
||||||
msgstr "Karten (tippe für Spielinfo):"
|
msgid_plural "Cards (tap for game state):"
|
||||||
|
msgstr[0] "Letzte Karte (tippe für Spielinfo):"
|
||||||
|
msgstr[1] "Karten (tippe für Spielinfo):"
|
||||||
|
|
||||||
#: results.py:60 results.py:123 results.py:165
|
#: results.py:60 results.py:123 results.py:165
|
||||||
msgid "Current player: {name}"
|
msgid "Current player: {name}"
|
||||||
|
@ -325,13 +332,17 @@ msgid "Last card: {card}"
|
||||||
msgstr "Letzte Karte: {card}"
|
msgstr "Letzte Karte: {card}"
|
||||||
|
|
||||||
#: results.py:62 results.py:125 results.py:168
|
#: results.py:62 results.py:125 results.py:168
|
||||||
msgid "Players: {player_list}"
|
msgid "Player: {player_list}"
|
||||||
msgstr "Spieler: {player_list}"
|
msgid_plural "Players: {player_list}"
|
||||||
|
msgstr[0] "Spieler: {player_list}"
|
||||||
|
msgstr[1] "Spieler: {player_list}"
|
||||||
|
|
||||||
#: results.py:72
|
#: results.py:72
|
||||||
#, python-format
|
#, python-format
|
||||||
msgid "{name} ({number} cards)"
|
msgid "{name} ({number} card)"
|
||||||
msgstr "{name} ({number} Karten)"
|
msgid_plural "{name} ({number} cards)"
|
||||||
|
msgstr[0] "{name} ({number} Karte)"
|
||||||
|
msgstr[1] "{name} ({number} Karten)"
|
||||||
|
|
||||||
#: results.py:81
|
#: results.py:81
|
||||||
msgid "You are not playing"
|
msgid "You are not playing"
|
||||||
|
@ -355,11 +366,10 @@ msgstr "Starte das Spiel mit /start"
|
||||||
|
|
||||||
#: results.py:108
|
#: results.py:108
|
||||||
#, python-format
|
#, python-format
|
||||||
msgid "Drawing 1 card"
|
msgid "Drawing {number} card"
|
||||||
msgstr "Zieht 1 Karte"
|
msgid_plural "Drawing {number} cards"
|
||||||
|
msgstr[0] "Ich ziehe {number} Karte"
|
||||||
msgid "Drawing {number} cards"
|
msgstr[1] "Ich ziehe {number} Karten"
|
||||||
msgstr "Zieht {number} Karten"
|
|
||||||
|
|
||||||
#: results.py:136
|
#: results.py:136
|
||||||
msgid "Pass"
|
msgid "Pass"
|
||||||
|
@ -413,16 +423,22 @@ msgstr "Du hast die Spiel-Statistiken nicht aktiviert. Aktiviere sie, mit dem "
|
||||||
"/settings-Kommando in einem privaten Chat mit dem Bot."
|
"/settings-Kommando in einem privaten Chat mit dem Bot."
|
||||||
|
|
||||||
#: simple_commands.py
|
#: simple_commands.py
|
||||||
msgid "{number} games played"
|
msgid "{number} game played"
|
||||||
msgstr "{number} gespielte Spiele"
|
msgid_plural "{number} games played"
|
||||||
|
msgstr[0] "{number} gespieltes Spiel"
|
||||||
|
msgstr[1] "{number} gespielte Spiele"
|
||||||
|
|
||||||
#: simple_commands.py
|
#: simple_commands.py
|
||||||
msgid "{number} first places"
|
msgid "{number} first place"
|
||||||
msgstr "{number}x 1. Platz"
|
msgid_plural "{number} first places"
|
||||||
|
msgstr[0] "{number} mal 1. Platz"
|
||||||
|
msgstr[1] "{number} mal 1. Platz"
|
||||||
|
|
||||||
#: simple_commands.py
|
#: simple_commands.py
|
||||||
msgid "{number} cards played"
|
msgid "{number} card played"
|
||||||
msgstr "{number} gespielte Karten"
|
msgid_plural "{number} cards played"
|
||||||
|
msgstr[0] "{number} gespielte Karte"
|
||||||
|
msgstr[1] "{number} gespielte Karten"
|
||||||
|
|
||||||
|
|
||||||
#: utils.py
|
#: utils.py
|
||||||
|
|
|
@ -29,6 +29,7 @@ msgstr ""
|
||||||
"MIME-Version: 1.0\n"
|
"MIME-Version: 1.0\n"
|
||||||
"Content-Type: text/plain; charset=utf-8\n"
|
"Content-Type: text/plain; charset=utf-8\n"
|
||||||
"Content-Transfer-Encoding: utf-8\n"
|
"Content-Transfer-Encoding: utf-8\n"
|
||||||
|
"Plural-Forms: nplurals=2; plural=(n != 1);\n"
|
||||||
|
|
||||||
|
|
||||||
#: bot.py:60
|
#: bot.py:60
|
||||||
|
@ -184,14 +185,19 @@ msgstr ""
|
||||||
|
|
||||||
#: bot.py:400
|
#: bot.py:400
|
||||||
#, python-format
|
#, python-format
|
||||||
msgid "Please wait {time} seconds"
|
msgid "Please wait {time} second"
|
||||||
msgstr ""
|
msgid_plural "Please wait {time} seconds"
|
||||||
|
msgstr[0] ""
|
||||||
|
msgstr[1] ""
|
||||||
|
|
||||||
#: bot.py:413
|
#: bot.py:413
|
||||||
#, python-format
|
#, python-format
|
||||||
msgid "Waiting time to skip this player has been reduced to {time} seconds.\n"
|
msgid "Waiting time to skip this player has been reduced to {time} second.\n"
|
||||||
"Next player: {name}"
|
"Next player: {name}"
|
||||||
msgstr ""
|
msgid_plural "Waiting time to skip this player has been reduced to {time} seconds.\n"
|
||||||
|
"Next player: {name}"
|
||||||
|
msgstr[0] ""
|
||||||
|
msgstr[1] ""
|
||||||
|
|
||||||
#: bot.py:424
|
#: bot.py:424
|
||||||
#, python-format
|
#, python-format
|
||||||
|
@ -256,8 +262,10 @@ msgid "Choose Color"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
#: results.py:56
|
#: results.py:56
|
||||||
msgid "Cards (tap for game state):"
|
msgid "Last card (tap for game state):"
|
||||||
msgstr ""
|
msgid_plural "Cards (tap for game state):"
|
||||||
|
msgstr[0] ""
|
||||||
|
msgstr[1] ""
|
||||||
|
|
||||||
#: results.py:60 results.py:123 results.py:165
|
#: results.py:60 results.py:123 results.py:165
|
||||||
msgid "Current player: {name}"
|
msgid "Current player: {name}"
|
||||||
|
@ -268,13 +276,17 @@ msgid "Last card: {card}"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
#: results.py:62 results.py:125 results.py:168
|
#: results.py:62 results.py:125 results.py:168
|
||||||
msgid "Players: {player_list}"
|
msgid "Player: {player_list}"
|
||||||
msgstr ""
|
msgid_plural "Players: {player_list}"
|
||||||
|
msgstr[0] ""
|
||||||
|
msgstr[1] ""
|
||||||
|
|
||||||
#: results.py:72
|
#: results.py:72
|
||||||
#, python-format
|
#, python-format
|
||||||
msgid "{name} ({number} cards)"
|
msgid "{name} ({number} card)"
|
||||||
msgstr ""
|
msgid_plural "{name} ({number} cards)"
|
||||||
|
msgstr[0] ""
|
||||||
|
msgstr[1] ""
|
||||||
|
|
||||||
#: results.py:81
|
#: results.py:81
|
||||||
msgid "You are not playing"
|
msgid "You are not playing"
|
||||||
|
@ -295,11 +307,10 @@ msgstr ""
|
||||||
|
|
||||||
#: results.py:108
|
#: results.py:108
|
||||||
#, python-format
|
#, python-format
|
||||||
msgid "Drawing 1 card"
|
msgid "Drawing {number} card"
|
||||||
msgstr ""
|
msgid_plural "Drawing {number} cards"
|
||||||
|
msgstr[0] ""
|
||||||
msgid "Drawing {number} cards"
|
msgstr[1] ""
|
||||||
msgstr ""
|
|
||||||
|
|
||||||
#: results.py:136
|
#: results.py:136
|
||||||
msgid "Pass"
|
msgid "Pass"
|
||||||
|
@ -352,16 +363,22 @@ msgid "You did not enable statistics. Use /settings in "
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
#: simple_commands.py
|
#: simple_commands.py
|
||||||
msgid "{number} games played"
|
msgid "{number} game played"
|
||||||
msgstr ""
|
msgid_plural "{number} games played"
|
||||||
|
msgstr[0] ""
|
||||||
|
msgstr[1] ""
|
||||||
|
|
||||||
#: simple_commands.py
|
#: simple_commands.py
|
||||||
msgid "{number} first places"
|
msgid "{number} first place"
|
||||||
msgstr ""
|
msgid_plural "{number} first places"
|
||||||
|
msgstr[0] ""
|
||||||
|
msgstr[1] ""
|
||||||
|
|
||||||
#: simple_commands.py
|
#: simple_commands.py
|
||||||
msgid "{number} cards played"
|
msgid "{number} card played"
|
||||||
msgstr ""
|
msgid_plural "{number} cards played"
|
||||||
|
msgstr[0] ""
|
||||||
|
msgstr[1] ""
|
||||||
|
|
||||||
|
|
||||||
#: utils.py
|
#: utils.py
|
||||||
|
|
37
results.py
37
results.py
|
@ -26,8 +26,8 @@ from telegram import InlineQueryResultArticle, InputTextMessageContent, \
|
||||||
InlineQueryResultCachedSticker as Sticker
|
InlineQueryResultCachedSticker as Sticker
|
||||||
|
|
||||||
import card as c
|
import card as c
|
||||||
from utils import display_color, display_color_group, display_name, \
|
from utils import display_color, display_color_group, display_name
|
||||||
list_subtract, _, __
|
from internationalization import _, __
|
||||||
|
|
||||||
|
|
||||||
def add_choose_color(results, game):
|
def add_choose_color(results, game):
|
||||||
|
@ -44,17 +44,16 @@ def add_choose_color(results, game):
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
def add_other_cards(playable, player, results, game):
|
def add_other_cards(player, results, game):
|
||||||
"""Add hand cards when choosing colors"""
|
"""Add hand cards when choosing colors"""
|
||||||
if not playable:
|
|
||||||
playable = list()
|
|
||||||
|
|
||||||
results.append(
|
results.append(
|
||||||
InlineQueryResultArticle(
|
InlineQueryResultArticle(
|
||||||
"hand",
|
"hand",
|
||||||
title=_("Cards (tap for game state):"),
|
title=_("Card (tap for game state):",
|
||||||
description=', '.join([repr(card) for card in
|
"Cards (tap for game state):",
|
||||||
list_subtract(player.cards, playable)]),
|
len(player.cards)),
|
||||||
|
description=', '.join([repr(card) for card in player.cards]),
|
||||||
input_message_content=game_info(game)
|
input_message_content=game_info(game)
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
@ -62,7 +61,9 @@ def add_other_cards(playable, player, results, game):
|
||||||
|
|
||||||
def player_list(game):
|
def player_list(game):
|
||||||
"""Generate list of player strings"""
|
"""Generate list of player strings"""
|
||||||
return [_("{name} ({number} cards)")
|
return [_("{name} ({number} card)",
|
||||||
|
"{name} ({number} cards)",
|
||||||
|
len(player.cards))
|
||||||
.format(name=player.user.first_name, number=len(player.cards))
|
.format(name=player.user.first_name, number=len(player.cards))
|
||||||
for player in game.players]
|
for player in game.players]
|
||||||
|
|
||||||
|
@ -101,10 +102,9 @@ def add_draw(player, results):
|
||||||
Sticker(
|
Sticker(
|
||||||
"draw", sticker_file_id=c.STICKERS['option_draw'],
|
"draw", sticker_file_id=c.STICKERS['option_draw'],
|
||||||
input_message_content=
|
input_message_content=
|
||||||
InputTextMessageContent(__('Drawing 1 card', player.game.translate)
|
InputTextMessageContent(__('Drawing {number} card',
|
||||||
if n == 1 else
|
'Drawing {number} cards', n,
|
||||||
__('Drawing {number} cards',
|
multi=player.game.translate)
|
||||||
player.game.translate)
|
|
||||||
.format(number=n))
|
.format(number=n))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
@ -127,8 +127,9 @@ def add_pass(results, game):
|
||||||
results.append(
|
results.append(
|
||||||
Sticker(
|
Sticker(
|
||||||
"pass", sticker_file_id=c.STICKERS['option_pass'],
|
"pass", sticker_file_id=c.STICKERS['option_pass'],
|
||||||
input_message_content=InputTextMessageContent(__('Pass',
|
input_message_content=InputTextMessageContent(
|
||||||
game.translate))
|
__('Pass', multi=game.translate)
|
||||||
|
)
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -141,7 +142,7 @@ def add_call_bluff(results, game):
|
||||||
sticker_file_id=c.STICKERS['option_bluff'],
|
sticker_file_id=c.STICKERS['option_bluff'],
|
||||||
input_message_content=
|
input_message_content=
|
||||||
InputTextMessageContent(__("I'm calling your bluff!",
|
InputTextMessageContent(__("I'm calling your bluff!",
|
||||||
game.translate))
|
multi=game.translate))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -168,6 +169,8 @@ def game_info(game):
|
||||||
"\n" +
|
"\n" +
|
||||||
_("Last card: {card}").format(card=repr(game.last_card)) +
|
_("Last card: {card}").format(card=repr(game.last_card)) +
|
||||||
"\n" +
|
"\n" +
|
||||||
_("Players: {player_list}")
|
_("Player: {player_list}",
|
||||||
|
"Players: {player_list}",
|
||||||
|
len(players))
|
||||||
.format(player_list=" -> ".join(players))
|
.format(player_list=" -> ".join(players))
|
||||||
)
|
)
|
31
settings.py
31
settings.py
|
@ -18,31 +18,14 @@
|
||||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
|
||||||
import logging
|
|
||||||
|
|
||||||
from telegram import ReplyKeyboardMarkup, Emoji
|
from telegram import ReplyKeyboardMarkup, Emoji
|
||||||
from telegram.ext import CommandHandler, RegexHandler
|
from telegram.ext import CommandHandler, RegexHandler
|
||||||
|
|
||||||
from utils import send_async
|
from utils import send_async
|
||||||
from user_setting import UserSetting
|
from user_setting import UserSetting
|
||||||
from utils import _, user_locale
|
|
||||||
from shared_vars import dispatcher
|
from shared_vars import dispatcher
|
||||||
|
from locales import available_locales
|
||||||
OFFSET = 127462 - ord('A')
|
from internationalization import _, user_locale
|
||||||
|
|
||||||
|
|
||||||
def flag(code):
|
|
||||||
return chr(ord(code[0]) + OFFSET) + chr(ord(code[1]) + OFFSET)
|
|
||||||
|
|
||||||
|
|
||||||
available_locales = [['en_US - ' + flag('US') + ' English (US)'],
|
|
||||||
['de_DE - ' + flag('DE') + ' Deutsch (DE)'],
|
|
||||||
['es_ES - ' + flag('ES') + ' Español (ES)'],
|
|
||||||
['id_ID - ' + flag('ID') + ' Bahasa Indonesia'],
|
|
||||||
['it_IT - ' + flag('IT') + ' Italiano'],
|
|
||||||
['pt_BR - ' + flag('BR') + ' Português Brasileiro'],
|
|
||||||
['zh_HK - ' + flag('HK') + ' 廣東話'],
|
|
||||||
['zh_TW - ' + flag('TW') + ' 中文(香港)']]
|
|
||||||
|
|
||||||
|
|
||||||
@user_locale
|
@user_locale
|
||||||
|
@ -83,8 +66,11 @@ def kb_select(bot, update, groups):
|
||||||
send_async(bot, chat.id, text=_("Enabled statistics!"))
|
send_async(bot, chat.id, text=_("Enabled statistics!"))
|
||||||
|
|
||||||
elif option == Emoji.EARTH_GLOBE_EUROPE_AFRICA:
|
elif option == Emoji.EARTH_GLOBE_EUROPE_AFRICA:
|
||||||
|
kb = [[locale + ' - ' + descr]
|
||||||
|
for locale, descr
|
||||||
|
in sorted(available_locales.items())]
|
||||||
send_async(bot, chat.id, text=_("Select locale"),
|
send_async(bot, chat.id, text=_("Select locale"),
|
||||||
reply_markup=ReplyKeyboardMarkup(keyboard=available_locales,
|
reply_markup=ReplyKeyboardMarkup(keyboard=kb,
|
||||||
one_time_keyboard=True))
|
one_time_keyboard=True))
|
||||||
|
|
||||||
elif option == Emoji.CROSS_MARK:
|
elif option == Emoji.CROSS_MARK:
|
||||||
|
@ -102,9 +88,7 @@ def locale_select(bot, update, groups):
|
||||||
user = update.message.from_user
|
user = update.message.from_user
|
||||||
option = groups[0]
|
option = groups[0]
|
||||||
|
|
||||||
if option in [locale.split()[0]
|
if option in available_locales:
|
||||||
for row in available_locales
|
|
||||||
for locale in row]:
|
|
||||||
us = UserSetting.get(id=user.id)
|
us = UserSetting.get(id=user.id)
|
||||||
us.lang = option
|
us.lang = option
|
||||||
_.push(option)
|
_.push(option)
|
||||||
|
@ -112,6 +96,7 @@ def locale_select(bot, update, groups):
|
||||||
_.pop()
|
_.pop()
|
||||||
|
|
||||||
|
|
||||||
|
def register():
|
||||||
dispatcher.add_handler(CommandHandler('settings', show_settings))
|
dispatcher.add_handler(CommandHandler('settings', show_settings))
|
||||||
dispatcher.add_handler(RegexHandler('^([' + Emoji.BAR_CHART +
|
dispatcher.add_handler(RegexHandler('^([' + Emoji.BAR_CHART +
|
||||||
Emoji.EARTH_GLOBE_EUROPE_AFRICA +
|
Emoji.EARTH_GLOBE_EUROPE_AFRICA +
|
||||||
|
|
|
@ -21,8 +21,9 @@ from telegram import ParseMode
|
||||||
from telegram.ext import CommandHandler
|
from telegram.ext import CommandHandler
|
||||||
|
|
||||||
from user_setting import UserSetting
|
from user_setting import UserSetting
|
||||||
from utils import _, send_async, user_locale
|
from utils import send_async
|
||||||
from shared_vars import dispatcher
|
from shared_vars import dispatcher
|
||||||
|
from internationalization import _, user_locale
|
||||||
|
|
||||||
help_text = ("Follow these steps:\n\n"
|
help_text = ("Follow these steps:\n\n"
|
||||||
"1. Add this bot to a group\n"
|
"1. Add this bot to a group\n"
|
||||||
|
@ -101,17 +102,33 @@ def stats(bot, update):
|
||||||
"a private chat with the bot to enable them."))
|
"a private chat with the bot to enable them."))
|
||||||
else:
|
else:
|
||||||
stats_text = list()
|
stats_text = list()
|
||||||
|
|
||||||
|
n = us.games_played
|
||||||
stats_text.append(
|
stats_text.append(
|
||||||
_("{number} games played").format(number=us.games_played))
|
_("{number} game played",
|
||||||
|
"{number} games played",
|
||||||
|
n).format(number=n)
|
||||||
|
)
|
||||||
|
|
||||||
|
n = us.first_places
|
||||||
stats_text.append(
|
stats_text.append(
|
||||||
_("{number} first places").format(number=us.first_places))
|
_("{number} first places",
|
||||||
|
"{number} first places",
|
||||||
|
n).format(number=n)
|
||||||
|
)
|
||||||
|
|
||||||
|
n = us.cards_played
|
||||||
stats_text.append(
|
stats_text.append(
|
||||||
_("{number} cards played").format(number=us.cards_played))
|
_("{number} card played",
|
||||||
|
"{number} cards played",
|
||||||
|
n).format(number=n)
|
||||||
|
)
|
||||||
|
|
||||||
send_async(bot, update.message.chat_id,
|
send_async(bot, update.message.chat_id,
|
||||||
text='\n'.join(stats_text))
|
text='\n'.join(stats_text))
|
||||||
|
|
||||||
|
|
||||||
|
def register():
|
||||||
dispatcher.add_handler(CommandHandler('help', help))
|
dispatcher.add_handler(CommandHandler('help', help))
|
||||||
dispatcher.add_handler(CommandHandler('source', source))
|
dispatcher.add_handler(CommandHandler('source', source))
|
||||||
dispatcher.add_handler(CommandHandler('news', news))
|
dispatcher.add_handler(CommandHandler('news', news))
|
||||||
|
|
112
utils.py
112
utils.py
|
@ -19,52 +19,17 @@
|
||||||
|
|
||||||
|
|
||||||
import logging
|
import logging
|
||||||
from functools import wraps
|
|
||||||
|
|
||||||
from flufl.i18n import registry
|
|
||||||
from flufl.i18n import PackageStrategy
|
|
||||||
|
|
||||||
from telegram import Emoji
|
from telegram import Emoji
|
||||||
from telegram.ext.dispatcher import run_async
|
from telegram.ext.dispatcher import run_async
|
||||||
import locales
|
|
||||||
from database import db_session
|
|
||||||
from user_setting import UserSetting
|
|
||||||
from shared_vars import gm
|
|
||||||
|
|
||||||
strategy = PackageStrategy('unobot', locales)
|
from internationalization import _, __
|
||||||
application = registry.register(strategy)
|
|
||||||
_ = application._
|
|
||||||
logger = logging.getLogger(__name__)
|
logger = logging.getLogger(__name__)
|
||||||
|
|
||||||
TIMEOUT = 2.5
|
TIMEOUT = 2.5
|
||||||
|
|
||||||
|
|
||||||
def __(string, multi_translate):
|
|
||||||
"""Translates text into all locales on the stack"""
|
|
||||||
translations = list()
|
|
||||||
locales = list()
|
|
||||||
|
|
||||||
if not multi_translate:
|
|
||||||
_.push('en_US')
|
|
||||||
translations.append(_(string))
|
|
||||||
_.pop()
|
|
||||||
|
|
||||||
else:
|
|
||||||
while _.code:
|
|
||||||
translation = _(string)
|
|
||||||
|
|
||||||
if translation not in translations:
|
|
||||||
translations.append(translation)
|
|
||||||
|
|
||||||
locales.append(_.code)
|
|
||||||
_.pop()
|
|
||||||
|
|
||||||
for l in reversed(locales):
|
|
||||||
_.push(l)
|
|
||||||
|
|
||||||
return '\n'.join(translations)
|
|
||||||
|
|
||||||
|
|
||||||
def list_subtract(list1, list2):
|
def list_subtract(list1, list2):
|
||||||
""" Helper function to subtract two lists and return the sorted result """
|
""" Helper function to subtract two lists and return the sorted result """
|
||||||
list1 = list1.copy()
|
list1 = list1.copy()
|
||||||
|
@ -138,76 +103,3 @@ def answer_async(bot, *args, **kwargs):
|
||||||
bot.answerInlineQuery(*args, **kwargs)
|
bot.answerInlineQuery(*args, **kwargs)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
error(None, None, e)
|
error(None, None, e)
|
||||||
|
|
||||||
|
|
||||||
def user_locale(func):
|
|
||||||
@wraps(func)
|
|
||||||
@db_session
|
|
||||||
def wrapped(bot, update, *pargs, **kwargs):
|
|
||||||
user, chat = _user_chat_from_update(update)
|
|
||||||
|
|
||||||
with db_session:
|
|
||||||
us = UserSetting.get(id=user.id)
|
|
||||||
|
|
||||||
if us:
|
|
||||||
_.push(us.lang)
|
|
||||||
else:
|
|
||||||
_.push('en_US')
|
|
||||||
|
|
||||||
result = func(bot, update, *pargs, **kwargs)
|
|
||||||
_.pop()
|
|
||||||
return result
|
|
||||||
return wrapped
|
|
||||||
|
|
||||||
|
|
||||||
def game_locales(func):
|
|
||||||
@wraps(func)
|
|
||||||
@db_session
|
|
||||||
def wrapped(bot, update, *pargs, **kwargs):
|
|
||||||
user, chat = _user_chat_from_update(update)
|
|
||||||
player = gm.player_for_user_in_chat(user, chat)
|
|
||||||
locales = list()
|
|
||||||
|
|
||||||
if player:
|
|
||||||
for player in player.game.players:
|
|
||||||
us = UserSetting.get(id=player.user.id)
|
|
||||||
|
|
||||||
if us:
|
|
||||||
loc = us.lang
|
|
||||||
else:
|
|
||||||
loc = 'en_US'
|
|
||||||
|
|
||||||
if loc in locales:
|
|
||||||
continue
|
|
||||||
|
|
||||||
_.push(loc)
|
|
||||||
locales.append(loc)
|
|
||||||
|
|
||||||
result = func(bot, update, *pargs, **kwargs)
|
|
||||||
|
|
||||||
while _.code:
|
|
||||||
_.pop()
|
|
||||||
|
|
||||||
return result
|
|
||||||
return wrapped
|
|
||||||
|
|
||||||
|
|
||||||
def _user_chat_from_update(update):
|
|
||||||
|
|
||||||
try:
|
|
||||||
user = update.message.from_user
|
|
||||||
chat = update.message.chat
|
|
||||||
except (NameError, AttributeError):
|
|
||||||
try:
|
|
||||||
user = update.inline_query.from_user
|
|
||||||
chat = gm.userid_current[user.id].game.chat
|
|
||||||
except KeyError:
|
|
||||||
chat = None
|
|
||||||
except (NameError, AttributeError):
|
|
||||||
try:
|
|
||||||
user = update.chosen_inline_result.from_user
|
|
||||||
chat = gm.userid_current[user.id].game.chat
|
|
||||||
except (NameError, AttributeError):
|
|
||||||
chat = None
|
|
||||||
|
|
||||||
return user, chat
|
|
||||||
|
|
Loading…
Reference in a new issue