diff --git a/.efrocachemap b/.efrocachemap index a9052269..564cbb66 100644 --- a/.efrocachemap +++ b/.efrocachemap @@ -420,20 +420,20 @@ "assets/build/ba_data/audio/zoeOw.ogg": "https://files.ballistica.net/cache/ba1/04/0a/c4f7d2794b018593ab0b2bcb07f0", "assets/build/ba_data/audio/zoePickup01.ogg": "https://files.ballistica.net/cache/ba1/06/4d/18777c9a2eb2207a2891a2837a70", "assets/build/ba_data/audio/zoeScream01.ogg": "https://files.ballistica.net/cache/ba1/81/90/23ab1ecc8c55267bd904a9c05344", - "assets/build/ba_data/data/langdata.json": "https://files.ballistica.net/cache/ba1/cd/7a/dcf7f0f9436884167abdcb126716", + "assets/build/ba_data/data/langdata.json": "https://files.ballistica.net/cache/ba1/f7/81/01515c4bef514f45bfe3b8e6566b", "assets/build/ba_data/data/languages/arabic.json": "https://files.ballistica.net/cache/ba1/a9/3c/63857b3f5f943205d7a5d8f8e476", "assets/build/ba_data/data/languages/belarussian.json": "https://files.ballistica.net/cache/ba1/49/5f/b29bb65369040892fe6601801637", "assets/build/ba_data/data/languages/chinese.json": "https://files.ballistica.net/cache/ba1/ea/14/6485c200c717f82cca7c01dee0b3", - "assets/build/ba_data/data/languages/chinesetraditional.json": "https://files.ballistica.net/cache/ba1/a0/ca/b4e3c4ea2c76e462b7e657b2b1c2", + "assets/build/ba_data/data/languages/chinesetraditional.json": "https://files.ballistica.net/cache/ba1/1d/a0/c2b68a77207c0fed98d7cec3b22f", "assets/build/ba_data/data/languages/croatian.json": "https://files.ballistica.net/cache/ba1/bb/9c/360fc084e6254a087096993af219", "assets/build/ba_data/data/languages/czech.json": "https://files.ballistica.net/cache/ba1/dd/5a/14ca3ebb92a802315921e2b2b215", "assets/build/ba_data/data/languages/danish.json": "https://files.ballistica.net/cache/ba1/3f/46/e4da3c1d2b0ebf916df55c608b28", "assets/build/ba_data/data/languages/dutch.json": "https://files.ballistica.net/cache/ba1/d1/07/37b7adc3dbec7328d26c5325f212", - "assets/build/ba_data/data/languages/english.json": "https://files.ballistica.net/cache/ba1/8b/c6/3fbabe88f18df228f6f2984201a5", + "assets/build/ba_data/data/languages/english.json": "https://files.ballistica.net/cache/ba1/56/1f/fe2912d87b3af510469dc40bdf85", "assets/build/ba_data/data/languages/esperanto.json": "https://files.ballistica.net/cache/ba1/6e/fd/685a4e1da031474d47a1d9eb2731", "assets/build/ba_data/data/languages/french.json": "https://files.ballistica.net/cache/ba1/0d/ae/d2df1bf3c2157b4b5302df54622f", - "assets/build/ba_data/data/languages/german.json": "https://files.ballistica.net/cache/ba1/ef/92/4a602f11f6dd3d0310ce98cd5538", - "assets/build/ba_data/data/languages/gibberish.json": "https://files.ballistica.net/cache/ba1/cb/10/5d94df639e3e0cb405711e1b907f", + "assets/build/ba_data/data/languages/german.json": "https://files.ballistica.net/cache/ba1/fe/33/cead18bf921903f8c6d922017892", + "assets/build/ba_data/data/languages/gibberish.json": "https://files.ballistica.net/cache/ba1/57/7d/e79791913a06c9c15fec75138e6a", "assets/build/ba_data/data/languages/greek.json": "https://files.ballistica.net/cache/ba1/17/78/3fd0dca40e632ce53d03a944e7fa", "assets/build/ba_data/data/languages/hindi.json": "https://files.ballistica.net/cache/ba1/11/56/ed2b07866104596338f7ce582d64", "assets/build/ba_data/data/languages/hungarian.json": "https://files.ballistica.net/cache/ba1/87/2d/027aa239eb66ea8f496562f4fd83", @@ -3927,16 +3927,16 @@ "assets/build/windows/Win32/ucrtbased.dll": "https://files.ballistica.net/cache/ba1/b5/85/f8b6d0558ddb87267f34254b1450", "assets/build/windows/Win32/vc_redist.x86.exe": "https://files.ballistica.net/cache/ba1/1c/e1/4a1a2eddda2f4aebd5f8b64ab08e", "assets/build/windows/Win32/vcruntime140d.dll": "https://files.ballistica.net/cache/ba1/50/8d/bc2600ac9491f1b14d659709451f", - "build/prefab/linux-server/debug/dist/ballisticacore_headless": "https://files.ballistica.net/cache/ba1/41/b4/93f8ac61e4b0fad27790b896a79c", - "build/prefab/linux-server/release/dist/ballisticacore_headless": "https://files.ballistica.net/cache/ba1/b9/fe/9e8a1711d318c8f446ce42e2c8b4", - "build/prefab/linux/debug/ballisticacore": "https://files.ballistica.net/cache/ba1/8d/47/ca91d44facaca3201e8b82f487ed", - "build/prefab/linux/release/ballisticacore": "https://files.ballistica.net/cache/ba1/64/bc/97857879f57276567e99db0351dc", - "build/prefab/mac-server/debug/dist/ballisticacore_headless": "https://files.ballistica.net/cache/ba1/d9/b4/0415d8af3e4904c640991ddd16f9", - "build/prefab/mac-server/release/dist/ballisticacore_headless": "https://files.ballistica.net/cache/ba1/d3/86/aa9ca99515ffa5676c960245659f", - "build/prefab/mac/debug/ballisticacore": "https://files.ballistica.net/cache/ba1/a7/22/1fdd6e64721676f8c40fdf8b3e16", - "build/prefab/mac/release/ballisticacore": "https://files.ballistica.net/cache/ba1/ce/aa/17c53dbb9513d5ef3b8c0ccde6cf", - "build/prefab/windows-server/debug/dist/ballisticacore_headless.exe": "https://files.ballistica.net/cache/ba1/d5/3b/4e1fc9281cad80d6cbb5aca74761", - "build/prefab/windows-server/release/dist/ballisticacore_headless.exe": "https://files.ballistica.net/cache/ba1/3c/79/f6476677ef525451a18c18f120d3", - "build/prefab/windows/debug/BallisticaCore.exe": "https://files.ballistica.net/cache/ba1/63/50/b120c428fc03a18adf24c0363985", - "build/prefab/windows/release/BallisticaCore.exe": "https://files.ballistica.net/cache/ba1/c8/1d/a5f65b32cd9a0fac2415b61d6875" + "build/prefab/linux-server/debug/dist/ballisticacore_headless": "https://files.ballistica.net/cache/ba1/ee/45/cade5b2fd62b09a51257941c7533", + "build/prefab/linux-server/release/dist/ballisticacore_headless": "https://files.ballistica.net/cache/ba1/1b/8f/ff4979b5192a38ef1b2ef0ef0875", + "build/prefab/linux/debug/ballisticacore": "https://files.ballistica.net/cache/ba1/5a/2a/ef6ffc7421f21c196872ffa43101", + "build/prefab/linux/release/ballisticacore": "https://files.ballistica.net/cache/ba1/08/3b/c5cbdf8034bc872f1aa622a64b58", + "build/prefab/mac-server/debug/dist/ballisticacore_headless": "https://files.ballistica.net/cache/ba1/eb/44/cfded3124db547b6a99aa8d7a947", + "build/prefab/mac-server/release/dist/ballisticacore_headless": "https://files.ballistica.net/cache/ba1/30/d6/5d712b546730fed241aa3f5e5498", + "build/prefab/mac/debug/ballisticacore": "https://files.ballistica.net/cache/ba1/69/d3/7af0c2b55abfa753dd148f7199d9", + "build/prefab/mac/release/ballisticacore": "https://files.ballistica.net/cache/ba1/88/16/70cd1b7b50578910267f91d563aa", + "build/prefab/windows-server/debug/dist/ballisticacore_headless.exe": "https://files.ballistica.net/cache/ba1/d3/a8/1e79f6258790a886ef14d4df5dd5", + "build/prefab/windows-server/release/dist/ballisticacore_headless.exe": "https://files.ballistica.net/cache/ba1/b8/a7/9cb20c8a6cb09880e2cfbbf427cf", + "build/prefab/windows/debug/BallisticaCore.exe": "https://files.ballistica.net/cache/ba1/ab/14/6173a6f6b7588a335f96e8f1f240", + "build/prefab/windows/release/BallisticaCore.exe": "https://files.ballistica.net/cache/ba1/7e/38/cfc24fc3e5e53ffedde3b372eef8" } \ No newline at end of file diff --git a/.idea/dictionaries/ericf.xml b/.idea/dictionaries/ericf.xml index f280d478..4d9e7d52 100644 --- a/.idea/dictionaries/ericf.xml +++ b/.idea/dictionaries/ericf.xml @@ -29,8 +29,8 @@ achname achs acinstance - ack ack'ed + ack acked acks acnt @@ -149,8 +149,8 @@ bacommon badguy bafoundation - ballistica ballistica's + ballistica ballisticacore ballisticacorecb bamaster @@ -586,6 +586,7 @@ endmessage endparen endtime + englishkeyboard ensurepip entitylist entrynew @@ -779,8 +780,8 @@ gamedata gameinstance gamemap - gamepad gamepad's + gamepad gamepadadvanced gamepads gamepadselect @@ -1019,6 +1020,7 @@ jsonstrbase jsontools jsonutils + kbclass kbytecount keepaway keeprefs @@ -1149,8 +1151,8 @@ lsqlite lssl lstart - lstr lstr's + lstr lstrs lsval ltex @@ -1771,8 +1773,8 @@ sessionname sessionplayer sessionplayers - sessionteam sessionteam's + sessionteam sessionteams sessiontype setactivity @@ -2098,8 +2100,8 @@ txtw typeargs typecheck - typechecker typechecker's + typechecker typedval typeshed typestr diff --git a/assets/.asset_manifest_public.json b/assets/.asset_manifest_public.json index ecfa5dee..cb611882 100644 --- a/assets/.asset_manifest_public.json +++ b/assets/.asset_manifest_public.json @@ -1,5 +1,4 @@ [ - "ba_data/python/__pycache__/keyboards.cpython-38.opt-1.pyc", "ba_data/python/ba/__init__.py", "ba_data/python/ba/__pycache__/__init__.cpython-38.opt-1.pyc", "ba_data/python/ba/__pycache__/_account.cpython-38.opt-1.pyc", @@ -240,6 +239,10 @@ "ba_data/python/bastd/game/targetpractice.py", "ba_data/python/bastd/game/thelaststand.py", "ba_data/python/bastd/gameutils.py", + "ba_data/python/bastd/keyboard/__init__.py", + "ba_data/python/bastd/keyboard/__pycache__/__init__.cpython-38.opt-1.pyc", + "ba_data/python/bastd/keyboard/__pycache__/englishkeyboard.cpython-38.opt-1.pyc", + "ba_data/python/bastd/keyboard/englishkeyboard.py", "ba_data/python/bastd/mainmenu.py", "ba_data/python/bastd/mapdata/__init__.py", "ba_data/python/bastd/mapdata/__pycache__/__init__.cpython-38.opt-1.pyc", @@ -500,7 +503,6 @@ "ba_data/python/efro/json.py", "ba_data/python/efro/terminal.py", "ba_data/python/efro/util.py", - "ba_data/python/keyboards.py", "server/__pycache__/ballisticacore_server.cpython-38.opt-1.pyc", "server/ballisticacore_server.py" ] \ No newline at end of file diff --git a/assets/Makefile b/assets/Makefile index 31bfb63c..ab0997b1 100644 --- a/assets/Makefile +++ b/assets/Makefile @@ -263,6 +263,8 @@ SCRIPT_TARGETS_PY_PUBLIC = \ build/ba_data/python/bastd/game/targetpractice.py \ build/ba_data/python/bastd/game/thelaststand.py \ build/ba_data/python/bastd/gameutils.py \ + build/ba_data/python/bastd/keyboard/__init__.py \ + build/ba_data/python/bastd/keyboard/englishkeyboard.py \ build/ba_data/python/bastd/mainmenu.py \ build/ba_data/python/bastd/mapdata/__init__.py \ build/ba_data/python/bastd/mapdata/big_g.py \ @@ -381,7 +383,6 @@ SCRIPT_TARGETS_PY_PUBLIC = \ build/ba_data/python/bastd/ui/trophies.py \ build/ba_data/python/bastd/ui/url.py \ build/ba_data/python/bastd/ui/watch.py \ - build/ba_data/python/keyboards.py \ build/server/ballisticacore_server.py SCRIPT_TARGETS_PYC_PUBLIC = \ @@ -499,6 +500,8 @@ SCRIPT_TARGETS_PYC_PUBLIC = \ build/ba_data/python/bastd/game/__pycache__/targetpractice.cpython-38.opt-1.pyc \ build/ba_data/python/bastd/game/__pycache__/thelaststand.cpython-38.opt-1.pyc \ build/ba_data/python/bastd/__pycache__/gameutils.cpython-38.opt-1.pyc \ + build/ba_data/python/bastd/keyboard/__pycache__/__init__.cpython-38.opt-1.pyc \ + build/ba_data/python/bastd/keyboard/__pycache__/englishkeyboard.cpython-38.opt-1.pyc \ build/ba_data/python/bastd/__pycache__/mainmenu.cpython-38.opt-1.pyc \ build/ba_data/python/bastd/mapdata/__pycache__/__init__.cpython-38.opt-1.pyc \ build/ba_data/python/bastd/mapdata/__pycache__/big_g.cpython-38.opt-1.pyc \ @@ -617,7 +620,6 @@ SCRIPT_TARGETS_PYC_PUBLIC = \ build/ba_data/python/bastd/ui/__pycache__/trophies.cpython-38.opt-1.pyc \ build/ba_data/python/bastd/ui/__pycache__/url.cpython-38.opt-1.pyc \ build/ba_data/python/bastd/ui/__pycache__/watch.cpython-38.opt-1.pyc \ - build/ba_data/python/__pycache__/keyboards.cpython-38.opt-1.pyc \ build/server/__pycache__/ballisticacore_server.cpython-38.opt-1.pyc # Rule to copy src asset scripts to dst. diff --git a/assets/src/ba_data/python/ba/__init__.py b/assets/src/ba_data/python/ba/__init__.py index a511f9c1..808338ed 100644 --- a/assets/src/ba_data/python/ba/__init__.py +++ b/assets/src/ba_data/python/ba/__init__.py @@ -77,7 +77,7 @@ from ba._campaign import Campaign from ba._gameutils import (GameTip, animate, animate_array, show_damage_count, timestring, cameraflash) from ba._general import (WeakCall, Call, existing, Existable, - verify_object_death, storagename) + verify_object_death, storagename, getclass) from ba._keyboard import Keyboard from ba._level import Level from ba._lobby import Lobby, Chooser diff --git a/assets/src/ba_data/python/ba/_meta.py b/assets/src/ba_data/python/ba/_meta.py index 9e97ec9e..3e3a8055 100644 --- a/assets/src/ba_data/python/ba/_meta.py +++ b/assets/src/ba_data/python/ba/_meta.py @@ -379,13 +379,13 @@ def get_scan_results() -> ScanResults: def get_game_types() -> List[Type[ba.GameActivity]]: """Return available game types.""" - from ba import _general - from ba import _gameactivity + from ba._general import getclass + from ba._gameactivity import GameActivity gameclassnames = get_scan_results().games gameclasses = [] for gameclassname in gameclassnames: try: - cls = _general.getclass(gameclassname, _gameactivity.GameActivity) + cls = getclass(gameclassname, GameActivity) gameclasses.append(cls) except Exception: from ba import _error diff --git a/assets/src/ba_data/python/bastd/keyboard/__init__.py b/assets/src/ba_data/python/bastd/keyboard/__init__.py new file mode 100644 index 00000000..32622553 --- /dev/null +++ b/assets/src/ba_data/python/bastd/keyboard/__init__.py @@ -0,0 +1,20 @@ +# Copyright (c) 2011-2020 Eric Froemling +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +# SOFTWARE. +# ----------------------------------------------------------------------------- diff --git a/assets/src/ba_data/python/keyboards.py b/assets/src/ba_data/python/bastd/keyboard/englishkeyboard.py similarity index 100% rename from assets/src/ba_data/python/keyboards.py rename to assets/src/ba_data/python/bastd/keyboard/englishkeyboard.py diff --git a/assets/src/ba_data/python/bastd/ui/onscreenkeyboard.py b/assets/src/ba_data/python/bastd/ui/onscreenkeyboard.py index 53ab84c2..17a7899a 100644 --- a/assets/src/ba_data/python/bastd/ui/onscreenkeyboard.py +++ b/assets/src/ba_data/python/bastd/ui/onscreenkeyboard.py @@ -228,12 +228,19 @@ class OnScreenKeyboardWindow(ba.Window): color=key_color_dark, label=ba.Lstr(resource='spaceKeyText'), on_activate_call=ba.Call(self._type_char, ' ')) - ba.textwidget(parent=self._root_widget, - h_align='center', - position=(210, v - 70), - size=(key_width * 6.1, key_height + 15), - text='Double press space to change keyboard', - scale=0.75) + + # Show change instructions only if we have more than one + # keyboard option. + if (ba.app.metascan is not None + and len(ba.app.metascan.keyboards) > 1): + ba.textwidget( + parent=self._root_widget, + h_align='center', + position=(210, v - 70), + size=(key_width * 6.1, key_height + 15), + text=ba.Lstr( + resource='keyboardChangeInstructionsText'), + scale=0.75) btn2 = self._space_button btn3 = self._emoji_button ba.widget(edit=btn1, right_widget=btn2, left_widget=btn3) @@ -250,12 +257,9 @@ class OnScreenKeyboardWindow(ba.Window): def _get_keyboard(self) -> ba.Keyboard: assert ba.app.metascan is not None - path = ba.app.metascan.keyboards[self._keyboard_index] - classname = path.split('.')[-1] - module = path[:-len(classname) - 1] - keyboard = getattr(__import__(module), classname)() - assert isinstance(keyboard, ba.Keyboard) - return keyboard + classname = ba.app.metascan.keyboards[self._keyboard_index] + kbclass = ba.getclass(classname, ba.Keyboard) + return kbclass() def _refresh(self) -> None: chars: Optional[List[str]] = None @@ -325,9 +329,11 @@ class OnScreenKeyboardWindow(ba.Window): self._load_keyboard() if len(ba.app.metascan.keyboards) < 2: ba.playsound(ba.getsound('error')) - ba.screenmessage('No other keyboards available', color=(1, 0, 0)) + ba.screenmessage(ba.Lstr(resource='keyboardNoOthersAvailableText'), + color=(1, 0, 0)) else: - ba.screenmessage(f'Switching keyboard to "{self._keyboard.name}"', + ba.screenmessage(ba.Lstr(resource='keyboardSwitchText', + subs=[('${NAME}', self._keyboard.name)]), color=(0, 1, 0)) def _shift(self) -> None: @@ -360,13 +366,13 @@ class OnScreenKeyboardWindow(ba.Window): return self._last_space_press = ba.time(ba.TimeType.REAL) - # operate in unicode so we don't do anything funky like chop utf-8 - # chars in half + # Operate in unicode so we don't do anything funky like chop utf-8 + # chars in half. txt = cast(str, ba.textwidget(query=self._text_field)) txt += char ba.textwidget(edit=self._text_field, text=txt) - # if we were caps, - # go back only if not Shift is pressed twice + + # If we were caps, go back only if not Shift is pressed twice. if self._mode == 'caps' and not self._double_press_shift: self._mode = 'normal' self._refresh() diff --git a/docs/ba_module.md b/docs/ba_module.md index d2f091d9..0550db84 100644 --- a/docs/ba_module.md +++ b/docs/ba_module.md @@ -85,6 +85,7 @@
  • ba.charstr()
  • ba.do_once()
  • ba.get_valid_languages()
  • +
  • ba.getclass()
  • ba.is_browser_likely_available()
  • ba.is_point_in_box()
  • ba.log()
  • @@ -6283,6 +6284,17 @@ Activity has since been created or is transitioning in. If there is no current Activity, raises a ba.ActivityNotFoundError. If doraise is False, None will be returned instead in that case.

    +
    +

    ba.getclass()

    +

    getclass(name: str, subclassof: Type[T]) -> Type[T]

    + +

    Given a full class name such as foo.bar.MyClass, return the class.

    + +

    Category: General Utility Functions

    + +

    The class will be checked to make sure it is a subclass of the provided +'subclassof' class, and a TypeError will be raised if not.

    +

    ba.getcollidemodel()

    getcollidemodel(name: str) -> ba.CollideModel