diff --git a/plugins/maps/forest.py b/plugins/maps/forest.py index c9f04be..4ccf2b6 100644 --- a/plugins/maps/forest.py +++ b/plugins/maps/forest.py @@ -68,10 +68,10 @@ class ForestMap(bs.Map): def on_preload(cls) -> any: data: dict[str, any] = { 'mesh': bs.getmesh('natureBackground'), - 'tex': bui.gettexture('natureBackgroundColor'), + 'tex': bs.gettexture('natureBackgroundColor'), 'collision_mesh': bs.getcollisionmesh('natureBackgroundCollide'), 'bgmesh': bs.getmesh('thePadBG'), - 'bgtex': bui.gettexture('menuBG') + 'bgtex': bs.gettexture('menuBG') } return data @@ -85,7 +85,7 @@ class ForestMap(bs.Map): attrs={ 'mesh': self.preloaddata['mesh'], 'color_texture': self.preloaddata['tex'], - 'collide_mesh': self.preloaddata['collide_mesh'], + 'collision_mesh': self.preloaddata['collision_mesh'], 'materials': [shared.footing_material] } ) diff --git a/plugins/minigames.json b/plugins/minigames.json index e803bce..e3ad092 100644 --- a/plugins/minigames.json +++ b/plugins/minigames.json @@ -77,6 +77,7 @@ } ], "versions": { + "1.0.1": null, "1.0.0": { "api_version": 7, "commit_sha": "2fda676", @@ -92,10 +93,11 @@ { "name": "JoseAng3l", "email": "", - "discord": "! JoseANG3L#0268" + "discord": "joseang3l" } ], "versions": { + "1.0.1": null, "1.0.0": { "api_version": 7, "commit_sha": "2fda676", @@ -111,10 +113,11 @@ { "name": "JoseAng3l", "email": "", - "discord": "! JoseANG3L#0268" + "discord": "joseang3l" } ], "versions": { + "1.0.1": null, "1.0.0": { "api_version": 7, "commit_sha": "2fda676", @@ -130,10 +133,11 @@ { "name": "JoseAng3l", "email": "", - "discord": "! JoseANG3L#0268" + "discord": "joseang3l" } ], "versions": { + "1.0.1": null, "1.0.0": { "api_version": 7, "commit_sha": "2fda676", @@ -149,7 +153,7 @@ { "name": "JoseAng3l", "email": "", - "discord": "! JoseANG3L#0268" + "discord": "joseang3l" } ], "versions": { @@ -178,6 +182,7 @@ } ], "versions": { + "1.1.0": null, "1.0.1": { "api_version": 7, "commit_sha": "d511c15", @@ -199,10 +204,11 @@ { "name": "Cross Joy", "email": "cross.joy.official@gmail.com", - "discord": "Cross Joy#0721" + "discord": "crossjoy" } ], "versions": { + "1.0.0": null, "2.0.0": { "api_version": 7, "commit_sha": "8b257b3", @@ -328,6 +334,7 @@ } ], "versions": { + "1.0.1": null, "1.0.0": { "api_version": 7, "commit_sha": "0841b9e", @@ -343,7 +350,7 @@ { "name": "SEBASTIAN2059", "email": "", - "discord": "SEBASTIAN2059#5751" + "discord": "sebastian2059" }, { "name": "zPanxo", @@ -373,10 +380,11 @@ { "name": "Mr.Smoothy", "email": "smoothy@bombsquad.ga", - "discord": "mr.smoothy#5824" + "discord": "mr.smoothy" } ], "versions": { + "1.0.1": null, "1.0.0": { "api_version": 7, "commit_sha": "52094fc", @@ -392,7 +400,7 @@ { "name": "Mr.Smoothy", "email": "smoothy@bombsquad.ga", - "discord": "mr.smoothy#5824" + "discord": "mr.smoothy" } ], "versions": { @@ -417,10 +425,11 @@ { "name": "Mr.Smoothy", "email": "smoothy@bombsquad.ga", - "discord": "mr.smoothy#5824" + "discord": "mr.smoothy" } ], "versions": { + "1.0.1": null, "1.0.0": { "api_version": 7, "commit_sha": "2aa1e50", @@ -436,7 +445,7 @@ { "name": "Mr.Smoothy", "email": "smoothy@bombsquad.ga", - "discord": "mr.smoothy#5824" + "discord": "mr.smoothy" } ], "versions": { @@ -455,10 +464,11 @@ { "name": "Mr.Smoothy", "email": "smoothy@bombsquad.ga", - "discord": "mr.smoothy#5824" + "discord": "mr.smoothy" } ], "versions": { + "1.0.1": null, "1.0.0": { "api_version": 7, "commit_sha": "2aa1e50", @@ -474,10 +484,11 @@ { "name": "Mr.Smoothy", "email": "smoothy@bombsquad.ga", - "discord": "mr.smoothy#5824" + "discord": "mr.smoothy" } ], "versions": { + "1.0.1": null, "1.0.0": { "api_version": 7, "commit_sha": "52094fc", @@ -534,7 +545,7 @@ { "name": "JoseAng3l", "email": "", - "discord": "! JoseANG3L#0268" + "discord": "joseang3l" } ], "versions": { @@ -588,6 +599,7 @@ } ], "versions": { + "1.0.1": null, "1.0.0": { "api_version": 7, "commit_sha": "7219487", @@ -603,10 +615,11 @@ { "name": "ThePersonMan", "email": "", - "discord": "ThePersonMan#0276" + "discord": "the.personman" } ], "versions": { + "1.0.1": null, "1.0.0": { "api_version": 7, "commit_sha": "7219487", @@ -622,10 +635,11 @@ { "name": "Dliwk", "email": "", - "discord": "Dliwk#7961" + "discord": "dliwk" } ], "versions": { + "1.0.1": null, "1.0.0": { "api_version": 7, "commit_sha": "7219487", @@ -645,6 +659,7 @@ } ], "versions": { + "1.0.1": null, "1.0.0": { "api_version": 7, "commit_sha": "7219487", @@ -660,10 +675,11 @@ { "name": "SEBASTIAN2059", "email": "", - "discord": "SEBASTIAN2059#5751" + "discord": "sebastian2059" } ], "versions": { + "1.0.1": null, "1.0.0": { "api_version": 7, "commit_sha": "7219487", @@ -698,7 +714,7 @@ { "name": "Cross Joy", "email": "cross.joy.official@gmail.com", - "discord": "Cross Joy#0721" + "discord": "crossjoy" } ], "versions": { diff --git a/plugins/minigames/air_soccer.py b/plugins/minigames/air_soccer.py index a089d95..75e9ba4 100644 --- a/plugins/minigames/air_soccer.py +++ b/plugins/minigames/air_soccer.py @@ -1,20 +1,21 @@ +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) # Released under the MIT License. See LICENSE for details. # BY Stary_Agent """Hockey game and support classes.""" -# ba_meta require api 7 +# ba_meta require api 8 # (see https://ballistica.net/wiki/meta-tag-system) from __future__ import annotations from typing import TYPE_CHECKING -import ba -import _ba -from bastd.actor.playerspaz import PlayerSpaz -from bastd.actor.scoreboard import Scoreboard -from bastd.actor.powerupbox import PowerupBoxFactory -from bastd.gameutils import SharedObjects +import babase +import bascenev1 as bs +from bascenev1lib.actor.playerspaz import PlayerSpaz +from bascenev1lib.actor.scoreboard import Scoreboard +from bascenev1lib.actor.powerupbox import PowerupBoxFactory +from bascenev1lib.gameutils import SharedObjects if TYPE_CHECKING: from typing import Any, Sequence, Dict, Type, List, Optional, Union @@ -32,13 +33,13 @@ def create_slope(self): x = 5 y = 12 for i in range(0, 10): - ba.newnode('region', attrs={'position': (x, y, -5.52), 'scale': (0.2, 0.1, 6), + bs.newnode('region', attrs={'position': (x, y, -5.52), 'scale': (0.2, 0.1, 6), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) x = x+0.3 y = y+0.1 -class Puck(ba.Actor): +class Puck(bs.Actor): """A lovely giant hockey puck.""" def __init__(self, position: Sequence[float] = (0.0, 13.0, 0.0)): @@ -53,10 +54,10 @@ class Puck(ba.Actor): assert activity is not None assert isinstance(activity, HockeyGame) pmats = [shared.object_material, activity.puck_material] - self.node = ba.newnode('prop', + self.node = bs.newnode('prop', delegate=self, attrs={ - 'model': activity.puck_model, + 'mesh': activity.puck_mesh, 'color_texture': activity.puck_tex, 'body': 'sphere', 'reflection': 'soft', @@ -67,10 +68,10 @@ class Puck(ba.Actor): 'position': self._spawn_pos, 'materials': pmats }) - ba.animate(self.node, 'model_scale', {0: 0, 0.2: 1.3, 0.26: 1}) + bs.animate(self.node, 'mesh_scale', {0: 0, 0.2: 1.3, 0.26: 1}) def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.DieMessage): + if isinstance(msg, bs.DieMessage): assert self.node self.node.delete() activity = self._activity() @@ -78,11 +79,11 @@ class Puck(ba.Actor): activity.handlemessage(PuckDiedMessage(self)) # If we go out of bounds, move back to where we started. - elif isinstance(msg, ba.OutOfBoundsMessage): + elif isinstance(msg, bs.OutOfBoundsMessage): assert self.node self.node.position = self._spawn_pos - elif isinstance(msg, ba.HitMessage): + elif isinstance(msg, bs.HitMessage): assert self.node assert msg.force_direction is not None self.node.handlemessage( @@ -103,31 +104,31 @@ class Puck(ba.Actor): super().handlemessage(msg) -class Player(ba.Player['Team']): +class Player(bs.Player['Team']): """Our player type for this game.""" -class Team(ba.Team[Player]): +class Team(bs.Team[Player]): """Our team type for this game.""" def __init__(self) -> None: self.score = 0 -# ba_meta export game -class AirSoccerGame(ba.TeamGameActivity[Player, Team]): +# ba_meta export bascenev1.GameActivity +class AirSoccerGame(bs.TeamGameActivity[Player, Team]): """Ice hockey game.""" name = 'Epic Air Soccer' description = 'Score some goals.' available_settings = [ - ba.IntSetting( + bs.IntSetting( 'Score to Win', min_value=1, default=1, increment=1, ), - ba.IntChoiceSetting( + bs.IntChoiceSetting( 'Time Limit', choices=[ ('None', 0), @@ -139,7 +140,7 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): ], default=0, ), - ba.FloatChoiceSetting( + bs.FloatChoiceSetting( 'Respawn Times', choices=[ ('Shorter', 0.1), @@ -151,14 +152,14 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): default=1.0, ), ] - default_music = ba.MusicType.HOCKEY + default_music = bs.MusicType.HOCKEY @classmethod - def supports_session_type(cls, sessiontype: Type[ba.Session]) -> bool: - return issubclass(sessiontype, ba.DualTeamSession) + def supports_session_type(cls, sessiontype: Type[bs.Session]) -> bool: + return issubclass(sessiontype, bs.DualTeamSession) @classmethod - def get_supported_maps(cls, sessiontype: Type[ba.Session]) -> List[str]: + def get_supported_maps(cls, sessiontype: Type[bs.Session]) -> List[str]: return ['Creative Thoughts'] def __init__(self, settings: dict): @@ -166,16 +167,16 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): shared = SharedObjects.get() self.slow_motion = True self._scoreboard = Scoreboard() - self._cheer_sound = ba.getsound('cheer') - self._chant_sound = ba.getsound('crowdChant') - self._foghorn_sound = ba.getsound('foghorn') - self._swipsound = ba.getsound('swip') - self._whistle_sound = ba.getsound('refWhistle') - self.puck_model = ba.getmodel('bomb') - self.puck_tex = ba.gettexture('landMine') - self.puck_scored_tex = ba.gettexture('landMineLit') - self._puck_sound = ba.getsound('metalHit') - self.puck_material = ba.Material() + self._cheer_sound = bs.getsound('cheer') + self._chant_sound = bs.getsound('crowdChant') + self._foghorn_sound = bs.getsound('foghorn') + self._swipsound = bs.getsound('swip') + self._whistle_sound = bs.getsound('refWhistle') + self.puck_mesh = bs.getmesh('bomb') + self.puck_tex = bs.gettexture('landMine') + self.puck_scored_tex = bs.gettexture('landMineLit') + self._puck_sound = bs.getsound('metalHit') + self.puck_material = bs.Material() self.puck_material.add_actions(actions=(('modify_part_collision', 'friction', 0.5))) self.puck_material.add_actions(conditions=('they_have_material', @@ -194,7 +195,7 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): shared.footing_material), actions=('impact_sound', self._puck_sound, 0.2, 5)) - self._real_wall_material = ba.Material() + self._real_wall_material = bs.Material() self._real_wall_material.add_actions( actions=( @@ -210,7 +211,7 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): ('modify_part_collision', 'physical', True) )) - self._goal_post_material = ba.Material() + self._goal_post_material = bs.Material() self._goal_post_material.add_actions( actions=( @@ -237,15 +238,15 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): conditions=('they_have_material', PowerupBoxFactory.get().powerup_material), actions=(('modify_part_collision', 'physical', False), - ('message', 'their_node', 'at_connect', ba.DieMessage()))) - self._score_region_material = ba.Material() + ('message', 'their_node', 'at_connect', bs.DieMessage()))) + self._score_region_material = bs.Material() self._score_region_material.add_actions( conditions=('they_have_material', self.puck_material), actions=(('modify_part_collision', 'collide', True), ('modify_part_collision', 'physical', False), ('call', 'at_connect', self._handle_score))) self._puck_spawn_pos: Optional[Sequence[float]] = None - self._score_regions: Optional[List[ba.NodeActor]] = None + self._score_regions: Optional[List[bs.NodeActor]] = None self._puck: Optional[Puck] = None self._score_to_win = int(settings['Score to Win']) self._time_limit = float(settings['Time Limit']) @@ -273,8 +274,8 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): defs = self.map.defs self._score_regions = [] self._score_regions.append( - ba.NodeActor( - ba.newnode('region', + bs.NodeActor( + bs.newnode('region', attrs={ 'position': (17, 14.5, -5.52), 'scale': (1, 3, 1), @@ -282,8 +283,8 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): 'materials': [self._score_region_material] }))) self._score_regions.append( - ba.NodeActor( - ba.newnode('region', + bs.NodeActor( + bs.newnode('region', attrs={ 'position': (-17, 14.5, -5.52), 'scale': (1, 3, 1), @@ -291,36 +292,36 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): 'materials': [self._score_region_material] }))) self._update_scoreboard() - ba.playsound(self._chant_sound) + self._chant_sound.play() def on_team_join(self, team: Team) -> None: self._update_scoreboard() def _handle_puck_player_collide(self) -> None: - collision = ba.getcollision() + collision = bs.getcollision() try: puck = collision.sourcenode.getdelegate(Puck, True) player = collision.opposingnode.getdelegate(PlayerSpaz, True).getplayer( Player, True) - except ba.NotFoundError: + except bs.NotFoundError: return puck.last_players_to_touch[player.team.id] = player def make_map(self): shared = SharedObjects.get() - _ba.get_foreground_host_activity()._map.leftwall.materials = [ + bs.get_foreground_host_activity()._map.leftwall.materials = [ shared.footing_material, self._real_wall_material] - _ba.get_foreground_host_activity()._map.rightwall.materials = [ + bs.get_foreground_host_activity()._map.rightwall.materials = [ shared.footing_material, self._real_wall_material] - _ba.get_foreground_host_activity()._map.topwall.materials = [ + bs.get_foreground_host_activity()._map.topwall.materials = [ shared.footing_material, self._real_wall_material] - self.floorwall = ba.newnode('region', attrs={'position': (0, 5, -5.52), 'scale': ( + self.floorwall = bs.newnode('region', attrs={'position': (0, 5, -5.52), 'scale': ( 35.4, 0.2, 2), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - ba.newnode('locator', attrs={'shape': 'box', 'position': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': ( 0, 5, -5.52), 'color': (0, 0, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (35.4, 0.2, 2)}) self.create_goal_post(-16.65, 12.69) @@ -343,9 +344,9 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): floor += "_ " shared = SharedObjects.get() step = {} - step["r"] = ba.newnode('region', attrs={'position': (x, y, -5.52), 'scale': ( + step["r"] = bs.newnode('region', attrs={'position': (x, y, -5.52), 'scale': ( 3, 0.1, 6), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - ba.newnode('locator', attrs={'shape': 'box', 'position': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': ( x, y, -5.52), 'color': (1, 1, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (3, 0.1, 2)}) return step @@ -359,10 +360,10 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): floor = "" for i in range(0, 4): floor += "_ " - ba.newnode('region', attrs={'position': (x-0.2, y, -5.52), 'scale': (1.8, 0.1, 6), + bs.newnode('region', attrs={'position': (x-0.2, y, -5.52), 'scale': (1.8, 0.1, 6), 'type': 'box', 'materials': [shared.footing_material, self._goal_post_material]}) - ba.newnode('locator', attrs={'shape': 'box', 'position': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': ( x-0.2, y, -5.52), 'color': color, 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (1.8, 0.1, 2)}) def create_vertical(self, x, y): @@ -370,9 +371,9 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): floor = "" for i in range(0, 4): floor += "|\n" - ba.newnode('region', attrs={'position': (x, y, -5.52), 'scale': (0.1, 2.8, 1), + bs.newnode('region', attrs={'position': (x, y, -5.52), 'scale': (0.1, 2.8, 1), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - ba.newnode('locator', attrs={'shape': 'box', 'position': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': ( x, y, -5.52), 'color': (1, 1, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (0.1, 2.8, 2)}) def spawn_player_spaz(self, @@ -402,7 +403,7 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): if self._puck.scored: return - region = ba.getcollision().sourcenode + region = bs.getcollision().sourcenode index = 0 for index in range(len(self._score_regions)): if region == self._score_regions[index].node: @@ -416,7 +417,7 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): # Tell all players to celebrate. for player in team.players: if player.actor: - player.actor.handlemessage(ba.CelebrateMessage(2.0)) + player.actor.handlemessage(bs.CelebrateMessage(2.0)) # If we've got the player from the scoring team that last # touched us, give them points. @@ -431,30 +432,30 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): if team.score >= self._score_to_win: self.end_game() - ba.playsound(self._foghorn_sound) - ba.playsound(self._cheer_sound) + self._foghorn_sound.play() + self._cheer_sound.play() self._puck.scored = True # Change puck texture to something cool self._puck.node.color_texture = self.puck_scored_tex # Kill the puck (it'll respawn itself shortly). - ba.timer(1.0, self._kill_puck) + bs.timer(1.0, self._kill_puck) - light = ba.newnode('light', + light = bs.newnode('light', attrs={ - 'position': ba.getcollision().position, + 'position': bs.getcollision().position, 'height_attenuated': False, 'color': (1, 0, 0) }) - ba.animate(light, 'intensity', {0: 0, 0.5: 1, 1.0: 0}, loop=True) - ba.timer(1.0, light.delete) + bs.animate(light, 'intensity', {0: 0, 0.5: 1, 1.0: 0}, loop=True) + bs.timer(1.0, light.delete) - ba.cameraflash(duration=10.0) + bs.cameraflash(duration=10.0) self._update_scoreboard() def end_game(self) -> None: - results = ba.GameResults() + results = bs.GameResults() for team in self.teams: results.set_team_score(team, team.score) self.end(results=results) @@ -467,7 +468,7 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): def handlemessage(self, msg: Any) -> Any: # Respawn dead players if they're still in the game. - if isinstance(msg, ba.PlayerDiedMessage): + if isinstance(msg, bs.PlayerDiedMessage): # Augment standard behavior... super().handlemessage(msg) self.respawn_player(msg.getplayer(Player)) @@ -475,23 +476,23 @@ class AirSoccerGame(ba.TeamGameActivity[Player, Team]): # Respawn dead pucks. elif isinstance(msg, PuckDiedMessage): if not self.has_ended(): - ba.timer(3.0, self._spawn_puck) + bs.timer(3.0, self._spawn_puck) else: super().handlemessage(msg) def _flash_puck_spawn(self) -> None: - light = ba.newnode('light', + light = bs.newnode('light', attrs={ 'position': self._puck_spawn_pos, 'height_attenuated': False, 'color': (1, 0, 0) }) - ba.animate(light, 'intensity', {0.0: 0, 0.25: 1, 0.5: 0}, loop=True) - ba.timer(1.0, light.delete) + bs.animate(light, 'intensity', {0.0: 0, 0.25: 1, 0.5: 0}, loop=True) + bs.timer(1.0, light.delete) def _spawn_puck(self) -> None: - ba.playsound(self._swipsound) - ba.playsound(self._whistle_sound) + self._swipsound.play() + self._whistle_sound.play() self._flash_puck_spawn() assert self._puck_spawn_pos is not None self._puck = Puck(position=self._puck_spawn_pos) @@ -541,7 +542,7 @@ class mapdefs: 0.5245740665, 0.5245740665, 0.01941146064) -class CreativeThoughts(ba.Map): +class CreativeThoughts(bs.Map): """Freaking map by smoothy.""" defs = mapdefs @@ -562,26 +563,26 @@ class CreativeThoughts(ba.Map): @classmethod def on_preload(cls) -> Any: data: Dict[str, Any] = { - 'model': ba.getmodel('alwaysLandLevel'), - 'bottom_model': ba.getmodel('alwaysLandLevelBottom'), - 'bgmodel': ba.getmodel('alwaysLandBG'), - 'collide_model': ba.getcollidemodel('alwaysLandLevelCollide'), - 'tex': ba.gettexture('alwaysLandLevelColor'), - 'bgtex': ba.gettexture('alwaysLandBGColor'), - 'vr_fill_mound_model': ba.getmodel('alwaysLandVRFillMound'), - 'vr_fill_mound_tex': ba.gettexture('vrFillMound') + 'mesh': bs.getmesh('alwaysLandLevel'), + 'bottom_mesh': bs.getmesh('alwaysLandLevelBottom'), + 'bgmesh': bs.getmesh('alwaysLandBG'), + 'collision_mesh': bs.getcollisionmesh('alwaysLandLevelCollide'), + 'tex': bs.gettexture('alwaysLandLevelColor'), + 'bgtex': bs.gettexture('alwaysLandBGColor'), + 'vr_fill_mound_mesh': bs.getmesh('alwaysLandVRFillMound'), + 'vr_fill_mound_tex': bs.gettexture('vrFillMound') } return data @classmethod - def get_music_type(cls) -> ba.MusicType: - return ba.MusicType.FLYING + def get_music_type(cls) -> bs.MusicType: + return bs.MusicType.FLYING def __init__(self) -> None: super().__init__(vr_overlay_offset=(0, -3.7, 2.5)) shared = SharedObjects.get() - self._fake_wall_material = ba.Material() - self._real_wall_material = ba.Material() + self._fake_wall_material = bs.Material() + self._real_wall_material = bs.Material() self._fake_wall_material.add_actions( conditions=(('they_are_younger_than', 9000), 'and', ('they_have_material', shared.player_material)), @@ -597,29 +598,29 @@ class CreativeThoughts(ba.Map): ('modify_part_collision', 'physical', True) )) - self.background = ba.newnode( + self.background = bs.newnode( 'terrain', attrs={ - 'model': self.preloaddata['bgmodel'], + 'mesh': self.preloaddata['bgmesh'], 'lighting': False, 'background': True, - 'color_texture': ba.gettexture("rampageBGColor") + 'color_texture': bs.gettexture("rampageBGColor") }) - self.leftwall = ba.newnode('region', attrs={'position': (-17.75152479, 13, -5.52), 'scale': ( + self.leftwall = bs.newnode('region', attrs={'position': (-17.75152479, 13, -5.52), 'scale': ( 0.1, 15.5, 2), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - self.rightwall = ba.newnode('region', attrs={'position': (17.75, 13, -5.52), 'scale': ( + self.rightwall = bs.newnode('region', attrs={'position': (17.75, 13, -5.52), 'scale': ( 0.1, 15.5, 2), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - self.topwall = ba.newnode('region', attrs={'position': (0, 21.0, -5.52), 'scale': ( + self.topwall = bs.newnode('region', attrs={'position': (0, 21.0, -5.52), 'scale': ( 35.4, 0.2, 2), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (-17.75152479, 13, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (-17.75152479, 13, -5.52), 'color': ( 0, 0, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (0.1, 15.5, 2)}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (17.75, 13, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (17.75, 13, -5.52), 'color': ( 0, 0, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (0.1, 15.5, 2)}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (0, 21.0, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (0, 21.0, -5.52), 'color': ( 0, 0, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (35.4, 0.2, 2)}) - gnode = ba.getactivity().globalsnode + gnode = bs.getactivity().globalsnode gnode.happy_thoughts_mode = True gnode.shadow_offset = (0.0, 8.0, 5.0) gnode.tint = (1.3, 1.23, 1.0) @@ -630,9 +631,9 @@ class CreativeThoughts(ba.Map): self.is_flying = True # throw out some tips on flying - txt = ba.newnode('text', + txt = bs.newnode('text', attrs={ - 'text': ba.Lstr(resource='pressJumpToFlyText'), + 'text': babase.Lstr(resource='pressJumpToFlyText'), 'scale': 1.2, 'maxwidth': 800, 'position': (0, 200), @@ -641,7 +642,7 @@ class CreativeThoughts(ba.Map): 'h_align': 'center', 'v_attach': 'bottom' }) - cmb = ba.newnode('combine', + cmb = bs.newnode('combine', owner=txt, attrs={ 'size': 4, @@ -649,12 +650,12 @@ class CreativeThoughts(ba.Map): 'input1': 0.9, 'input2': 0.0 }) - ba.animate(cmb, 'input3', {3.0: 0, 4.0: 1, 9.0: 1, 10.0: 0}) + bs.animate(cmb, 'input3', {3.0: 0, 4.0: 1, 9.0: 1, 10.0: 0}) cmb.connectattr('output', txt, 'color') - ba.timer(10.0, txt.delete) + bs.timer(10.0, txt.delete) try: - ba._map.register_map(CreativeThoughts) + bs._map.register_map(CreativeThoughts) except: pass diff --git a/plugins/minigames/basket_bomb.py b/plugins/minigames/basket_bomb.py index 4da374d..8c33edb 100644 --- a/plugins/minigames/basket_bomb.py +++ b/plugins/minigames/basket_bomb.py @@ -1,19 +1,22 @@ +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) # Released under the MIT License. See LICENSE for details. -# ba_meta require api 7 +# ba_meta require api 8 # (see https://ballistica.net/wiki/meta-tag-system) from __future__ import annotations from typing import TYPE_CHECKING -import ba -import _ba -from bastd.actor.playerspaz import PlayerSpaz -from bastd.actor.scoreboard import Scoreboard -from bastd.actor.powerupbox import PowerupBoxFactory -from bastd.gameutils import SharedObjects -from bastd.actor import playerspaz as ps -from bastd import maps +import babase +import bauiv1 as bui +import bascenev1 as bs +import _babase +from bascenev1lib.actor.playerspaz import PlayerSpaz +from bascenev1lib.actor.scoreboard import Scoreboard +from bascenev1lib.actor.powerupbox import PowerupBoxFactory +from bascenev1lib.gameutils import SharedObjects +from bascenev1lib.actor import playerspaz as ps +from bascenev1lib import maps if TYPE_CHECKING: from typing import Any, Sequence, Dict, Type, List, Optional, Union @@ -22,7 +25,7 @@ bsuSpaz = None def getlanguage(text, sub: str = ''): - lang = _ba.app.lang.language + lang = bs.app.lang.language translate = { "Name": {"Spanish": "Baloncesto", @@ -60,7 +63,7 @@ class BallDiedMessage: self.ball = ball -class Ball(ba.Actor): +class Ball(bs.Actor): def __init__(self, position: Sequence[float] = (0.0, 1.0, 0.0)): super().__init__() shared = SharedObjects.get() @@ -76,10 +79,10 @@ class Ball(ba.Actor): assert isinstance(activity, BasketGame) pmats = [shared.object_material, activity.ball_material] - self.node = ba.newnode('prop', + self.node = bs.newnode('prop', delegate=self, attrs={ - 'model': activity.ball_model, + 'mesh': activity.ball_mesh, 'color_texture': activity.ball_tex, 'body': 'sphere', 'reflection': 'soft', @@ -92,22 +95,22 @@ class Ball(ba.Actor): 'velocity': velocty, 'materials': pmats}) self.scale = scale = 0.25 * _scale - ba.animate(self.node, 'model_scale', {0: 0, 0.2: scale*1.3, 0.26: scale}) + bs.animate(self.node, 'mesh_scale', {0: 0, 0.2: scale*1.3, 0.26: scale}) def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.DieMessage): + if isinstance(msg, bs.DieMessage): assert self.node self.node.delete() activity = self._activity() if activity and not msg.immediate: activity.handlemessage(BallDiedMessage(self)) - elif isinstance(msg, ba.OutOfBoundsMessage): + elif isinstance(msg, bs.OutOfBoundsMessage): assert self.node self.node.position = self._spawn_pos self.node.velocity = (0.0, 0.0, 0.0) - elif isinstance(msg, ba.HitMessage): + elif isinstance(msg, bs.HitMessage): assert self.node assert msg.force_direction is not None self.node.handlemessage( @@ -127,11 +130,11 @@ class Ball(ba.Actor): super().handlemessage(msg) -class Player(ba.Player['Team']): +class Player(bs.Player['Team']): """Our player type for this game.""" -class Team(ba.Team[Player]): +class Team(bs.Team[Player]): """Our team type for this game.""" def __init__(self) -> None: @@ -144,21 +147,21 @@ class Points: postes['pal_0'] = (10.64702320098877, 0.0000000000000000, 0.0000000000000000) postes['pal_1'] = (-10.64702320098877, 0.0000000000000000, 0.0000000000000000) -# ba_meta export game +# ba_meta export bascenev1.GameActivity -class BasketGame(ba.TeamGameActivity[Player, Team]): +class BasketGame(bs.TeamGameActivity[Player, Team]): name = getlanguage('Name') description = getlanguage('Info') available_settings = [ - ba.IntSetting( + bs.IntSetting( 'Score to Win', min_value=1, default=1, increment=1, ), - ba.IntChoiceSetting( + bs.IntChoiceSetting( 'Time Limit', choices=[ ('None', 0), @@ -170,7 +173,7 @@ class BasketGame(ba.TeamGameActivity[Player, Team]): ], default=0, ), - ba.FloatChoiceSetting( + bs.FloatChoiceSetting( 'Respawn Times', choices=[ ('Shorter', 0.25), @@ -181,38 +184,38 @@ class BasketGame(ba.TeamGameActivity[Player, Team]): ], default=1.0, ), - ba.BoolSetting(getlanguage('S: Powerups'), default=True), - ba.BoolSetting(getlanguage('S: Velocity'), default=False), - ba.BoolSetting('Epic Mode', default=False), + bs.BoolSetting(getlanguage('S: Powerups'), default=True), + bs.BoolSetting(getlanguage('S: Velocity'), default=False), + bs.BoolSetting('Epic Mode', default=False), ] - default_music = ba.MusicType.HOCKEY + default_music = bs.MusicType.HOCKEY @classmethod - def supports_session_type(cls, sessiontype: Type[ba.Session]) -> bool: - return issubclass(sessiontype, ba.DualTeamSession) + def supports_session_type(cls, sessiontype: Type[bs.Session]) -> bool: + return issubclass(sessiontype, bs.DualTeamSession) @classmethod - def get_supported_maps(cls, sessiontype: Type[ba.Session]) -> List[str]: + def get_supported_maps(cls, sessiontype: Type[bs.Session]) -> List[str]: return ['BasketBall Stadium', 'BasketBall Stadium V2'] def __init__(self, settings: dict): super().__init__(settings) shared = SharedObjects.get() self._scoreboard = Scoreboard() - self._cheer_sound = ba.getsound('cheer') - self._chant_sound = ba.getsound('crowdChant') - self._foghorn_sound = ba.getsound('foghorn') - self._swipsound = ba.getsound('swip') - self._whistle_sound = ba.getsound('refWhistle') - self.ball_model = ba.getmodel('shield') - self.ball_tex = ba.gettexture('fontExtras3') - self._ball_sound = ba.getsound('bunnyJump') + self._cheer_sound = bs.getsound('cheer') + self._chant_sound = bs.getsound('crowdChant') + self._foghorn_sound = bs.getsound('foghorn') + self._swipsound = bs.getsound('swip') + self._whistle_sound = bs.getsound('refWhistle') + self.ball_mesh = bs.getmesh('shield') + self.ball_tex = bs.gettexture('fontExtras3') + self._ball_sound = bs.getsound('bunnyJump') self._powerups = bool(settings[getlanguage('S: Powerups')]) self._speed = bool(settings[getlanguage('S: Velocity')]) self._epic_mode = bool(settings['Epic Mode']) self.slow_motion = self._epic_mode - self.ball_material = ba.Material() + self.ball_material = bs.Material() self.ball_material.add_actions(actions=(('modify_part_collision', 'friction', 0.5))) self.ball_material.add_actions(conditions=('they_have_material', @@ -238,14 +241,14 @@ class BasketGame(ba.TeamGameActivity[Player, Team]): actions=(('call', 'at_connect', self._handle_ball_player_collide), )) - self._score_region_material = ba.Material() + self._score_region_material = bs.Material() self._score_region_material.add_actions( conditions=('they_have_material', self.ball_material), actions=(('modify_part_collision', 'collide', True), ('modify_part_collision', 'physical', False), ('call', 'at_connect', self._handle_score))) self._ball_spawn_pos: Optional[Sequence[float]] = None - self._score_regions: Optional[List[ba.NodeActor]] = None + self._score_regions: Optional[List[bs.NodeActor]] = None self._ball: Optional[Ball] = None self._score_to_win = int(settings['Score to Win']) self._time_limit = float(settings['Time Limit']) @@ -270,8 +273,8 @@ class BasketGame(ba.TeamGameActivity[Player, Team]): defs = self.map.defs self._score_regions = [] self._score_regions.append( - ba.NodeActor( - ba.newnode('region', + bs.NodeActor( + bs.newnode('region', attrs={ 'position': defs.boxes['goal1'][0:3], 'scale': defs.boxes['goal1'][6:9], @@ -279,8 +282,8 @@ class BasketGame(ba.TeamGameActivity[Player, Team]): 'materials': [] }))) self._score_regions.append( - ba.NodeActor( - ba.newnode('region', + bs.NodeActor( + bs.newnode('region', attrs={ 'position': defs.boxes['goal2'][0:3], 'scale': defs.boxes['goal2'][6:9], @@ -288,7 +291,7 @@ class BasketGame(ba.TeamGameActivity[Player, Team]): 'materials': [] }))) self._update_scoreboard() - ba.playsound(self._chant_sound) + self._chant_sound.play() for id, team in enumerate(self.teams): self.postes(id) @@ -297,13 +300,13 @@ class BasketGame(ba.TeamGameActivity[Player, Team]): self._update_scoreboard() def _handle_ball_player_collide(self) -> None: - collision = ba.getcollision() + collision = bs.getcollision() try: ball = collision.sourcenode.getdelegate(Ball, True) player = collision.opposingnode.getdelegate(PlayerSpaz, True).getplayer( Player, True) - except ba.NotFoundError: + except bs.NotFoundError: return ball.last_players_to_touch[player.team.id] = player @@ -318,7 +321,7 @@ class BasketGame(ba.TeamGameActivity[Player, Team]): if self._ball.scored: return - region = ba.getcollision().sourcenode + region = bs.getcollision().sourcenode index = 0 for index in range(len(self._score_regions)): if region == self._score_regions[index].node: @@ -334,7 +337,7 @@ class BasketGame(ba.TeamGameActivity[Player, Team]): for player in team.players: if player.actor: - player.actor.handlemessage(ba.CelebrateMessage(2.0)) + player.actor.handlemessage(bs.CelebrateMessage(2.0)) if (scoring_team.id in self._ball.last_players_to_touch and self._ball.last_players_to_touch[scoring_team.id]): @@ -345,28 +348,28 @@ class BasketGame(ba.TeamGameActivity[Player, Team]): if team.score >= self._score_to_win: self.end_game() - # ba.playsound(self._foghorn_sound) - ba.playsound(self._cheer_sound) + # self._foghorn_sound.play() + self._cheer_sound.play() self._ball.scored = True # Kill the ball (it'll respawn itself shortly). - ba.timer(1.0, self._kill_ball) + bs.timer(1.0, self._kill_ball) - light = ba.newnode('light', + light = bs.newnode('light', attrs={ - 'position': ba.getcollision().position, + 'position': bs.getcollision().position, 'height_attenuated': False, 'color': (1, 0, 0) }) - ba.animate(light, 'intensity', {0: 0, 0.5: 1, 1.0: 0}, loop=True) - ba.timer(1.0, light.delete) + bs.animate(light, 'intensity', {0: 0, 0.5: 1, 1.0: 0}, loop=True) + bs.timer(1.0, light.delete) - ba.cameraflash(duration=10.0) + bs.cameraflash(duration=10.0) self._update_scoreboard() def end_game(self) -> None: - results = ba.GameResults() + results = bs.GameResults() for team in self.teams: results.set_team_score(team, team.score) self.end(results=results) @@ -377,7 +380,7 @@ class BasketGame(ba.TeamGameActivity[Player, Team]): self._scoreboard.set_team_value(team, team.score, winscore) # self.postes(id) - def spawn_player(self, player: Player) -> ba.Actor: + def spawn_player(self, player: Player) -> bs.Actor: if bsuSpaz is None: spaz = self.spawn_player_spaz(player) else: @@ -390,12 +393,12 @@ class BasketGame(ba.TeamGameActivity[Player, Team]): return spaz def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.PlayerDiedMessage): + if isinstance(msg, bs.PlayerDiedMessage): super().handlemessage(msg) self.respawn_player(msg.getplayer(Player)) elif isinstance(msg, BallDiedMessage): if not self.has_ended(): - ba.timer(3.0, self._spawn_ball) + bs.timer(3.0, self._spawn_ball) else: super().handlemessage(msg) @@ -407,24 +410,24 @@ class BasketGame(ba.TeamGameActivity[Player, Team]): str(team_id)]).autoretain()) def _flash_ball_spawn(self) -> None: - light = ba.newnode('light', + light = bs.newnode('light', attrs={ 'position': self._ball_spawn_pos, 'height_attenuated': False, 'color': (1, 0, 0) }) - ba.animate(light, 'intensity', {0.0: 0, 0.25: 1, 0.5: 0}, loop=True) - ba.timer(1.0, light.delete) + bs.animate(light, 'intensity', {0.0: 0, 0.25: 1, 0.5: 0}, loop=True) + bs.timer(1.0, light.delete) def _spawn_ball(self) -> None: - ba.playsound(self._swipsound) - ba.playsound(self._whistle_sound) + self._swipsound.play() + self._whistle_sound.play() self._flash_ball_spawn() assert self._ball_spawn_pos is not None self._ball = Ball(position=self._ball_spawn_pos) -class Aro(ba.Actor): +class Aro(bs.Actor): def __init__(self, team: int = 0, position: Sequence[float] = (0.0, 1.0, 0.0)): super().__init__() @@ -434,16 +437,16 @@ class Aro(ba.Actor): setattr(self, 'locs', []) # Material Para; Traspasar Objetos - self.no_collision = ba.Material() + self.no_collision = bs.Material() self.no_collision.add_actions( actions=(('modify_part_collision', 'collide', False))) - self.collision = ba.Material() + self.collision = bs.Material() self.collision.add_actions( actions=(('modify_part_collision', 'collide', True))) # Score - self._score_region_material = ba.Material() + self._score_region_material = bs.Material() self._score_region_material.add_actions( conditions=('they_have_material', act.ball_material), actions=(('modify_part_collision', 'collide', @@ -454,14 +457,14 @@ class Aro(ba.Actor): self._materials_region0 = [self.collision, shared.footing_material] - model = None - tex = ba.gettexture('null') + mesh = None + tex = bs.gettexture('null') pmats = [self.no_collision] - self.node = ba.newnode('prop', + self.node = bs.newnode('prop', delegate=self, attrs={ - 'model': model, + 'mesh': mesh, 'color_texture': tex, 'body': 'box', 'reflection': 'soft', @@ -471,17 +474,17 @@ class Aro(ba.Actor): 'materials': pmats}) self.scale = scale = 1.4 - ba.animate(self.node, 'model_scale', {0: 0}) + bs.animate(self.node, 'mesh_scale', {0: 0}) pos = (position[0], position[1]+0.6, position[2]) - self.regions: List[ba.Node] = [ - ba.newnode('region', + self.regions: List[bs.Node] = [ + bs.newnode('region', attrs={'position': position, 'scale': (0.6, 0.05, 0.6), 'type': 'box', 'materials': self._materials_region0}), - ba.newnode('region', + bs.newnode('region', attrs={'position': pos, 'scale': (0.5, 0.3, 0.9), 'type': 'box', @@ -502,7 +505,7 @@ class Aro(ba.Actor): while locs_count > 1: scale = (1.5 * 0.1 * locs_count) + 0.8 - self.locs.append(ba.newnode('locator', + self.locs.append(bs.newnode('locator', owner=self.node, attrs={'shape': 'circleOutline', 'position': pos, @@ -528,14 +531,14 @@ class Aro(ba.Actor): act._handle_score(self.team) def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.DieMessage): + if isinstance(msg, bs.DieMessage): if self.node.exists(): self.node.delete() else: super().handlemessage(msg) -class Cuadro(ba.Actor): +class Cuadro(bs.Actor): def __init__(self, team: int = 0, position: Sequence[float] = (0.0, 1.0, 0.0)): super().__init__() @@ -543,19 +546,19 @@ class Cuadro(ba.Actor): shared = SharedObjects.get() setattr(self, 'locs', []) - self.collision = ba.Material() + self.collision = bs.Material() self.collision.add_actions( actions=(('modify_part_collision', 'collide', True))) pos = (position[0], position[1]+0.9, position[2]+1.5) - self.region: ba.Node = ba.newnode('region', + self.region: bs.Node = bs.newnode('region', attrs={'position': pos, 'scale': (0.5, 2.7, 2.5), 'type': 'box', 'materials': [self.collision, shared.footing_material]}) - # self.shield = ba.newnode('shield', attrs={'radius': 1.0, 'color': (0,10,0)}) + # self.shield = bs.newnode('shield', attrs={'radius': 1.0, 'color': (0,10,0)}) # self.region.connectattr('position', self.shield, 'position') position = (position[0], position[1], position[2]+0.09) @@ -578,7 +581,7 @@ class Cuadro(ba.Actor): pos[2] += 0.19 self.locs.append( - ba.newnode('locator', + bs.newnode('locator', owner=self.region, attrs={'shape': 'circle', 'position': pos, @@ -595,14 +598,14 @@ class Cuadro(ba.Actor): count_y -= 1 def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.DieMessage): + if isinstance(msg, bs.DieMessage): if self.node.exists(): self.node.delete() else: super().handlemessage(msg) -class Palos(ba.Actor): +class Palos(bs.Actor): def __init__(self, team: int = 0, position: Sequence[float] = (0.0, 1.0, 0.0)): super().__init__() @@ -613,26 +616,26 @@ class Palos(ba.Actor): self.cua = None # Material Para; Traspasar Objetos - self.no_collision = ba.Material() + self.no_collision = bs.Material() self.no_collision.add_actions( actions=(('modify_part_collision', 'collide', False))) # - self.collision = ba.Material() + self.collision = bs.Material() self.collision.add_actions( actions=(('modify_part_collision', 'collide', True))) # Spawn just above the provided point. self._spawn_pos = (position[0], position[2]+2.5, position[2]) - model = ba.getmodel('flagPole') - tex = ba.gettexture('flagPoleColor') + mesh = bs.getmesh('flagPole') + tex = bs.gettexture('flagPoleColor') pmats = [self.no_collision] - self.node = ba.newnode('prop', + self.node = bs.newnode('prop', delegate=self, attrs={ - 'model': model, + 'mesh': mesh, 'color_texture': tex, 'body': 'puck', 'reflection': 'soft', @@ -643,9 +646,9 @@ class Palos(ba.Actor): 'materials': pmats }) self.scale = scale = 4.0 - ba.animate(self.node, 'model_scale', {0: scale}) + bs.animate(self.node, 'mesh_scale', {0: scale}) - self.loc = ba.newnode('locator', + self.loc = bs.newnode('locator', owner=self.node, attrs={'shape': 'circle', 'position': position, @@ -657,7 +660,7 @@ class Palos(ba.Actor): self._y = _y = 0.30 _x = -0.25 if team == 1 else 0.25 _pos = (position[0]+_x, position[1]-1.5 + _y, position[2]) - self.region = ba.newnode('region', + self.region = bs.newnode('region', attrs={ 'position': _pos, 'scale': (0.4, 8, 0.4), @@ -680,7 +683,7 @@ class Palos(ba.Actor): self.cua = Cuadro(team, pos).autoretain() def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.DieMessage): + if isinstance(msg, bs.DieMessage): if self.node.exists(): self.node.delete() else: @@ -698,7 +701,7 @@ class BasketMap(maps.FootballStadium): def __init__(self) -> None: super().__init__() - gnode = ba.getactivity().globalsnode + gnode = bs.getactivity().globalsnode gnode.tint = [(0.806, 0.8, 1.0476), (1.3, 1.2, 1.0)][0] gnode.ambient_color = (1.3, 1.2, 1.0) gnode.vignette_outer = (0.57, 0.57, 0.57) @@ -715,21 +718,21 @@ class BasketMapV2(maps.HockeyStadium): shared = SharedObjects.get() self.node.materials = [shared.footing_material] - self.node.collide_model = ba.getcollidemodel('footballStadiumCollide') - self.node.model = None - self.stands.model = None + self.node.collision_mesh = bs.getcollisionmesh('footballStadiumCollide') + self.node.mesh = None + self.stands.mesh = None self.floor.reflection = 'soft' self.floor.reflection_scale = [1.6] self.floor.color = (1.1, 0.05, 0.8) - self.background = ba.newnode('terrain', - attrs={'model': ba.getmodel('thePadBG'), + self.background = bs.newnode('terrain', + attrs={'mesh': bs.getmesh('thePadBG'), 'lighting': False, 'background': True, 'color': (1.0, 0.2, 1.0), - 'color_texture': ba.gettexture('menuBG')}) + 'color_texture': bs.gettexture('menuBG')}) - gnode = ba.getactivity().globalsnode + gnode = bs.getactivity().globalsnode gnode.floor_reflection = True gnode.debris_friction = 0.3 gnode.debris_kill_height = -0.3 @@ -742,24 +745,24 @@ class BasketMapV2(maps.HockeyStadium): self.is_hockey = False ################## - self.collision = ba.Material() + self.collision = bs.Material() self.collision.add_actions( actions=(('modify_part_collision', 'collide', True))) - self.regions: List[ba.Node] = [ - ba.newnode('region', + self.regions: List[bs.Node] = [ + bs.newnode('region', attrs={'position': (12.676897048950195, 0.2997918128967285, 5.583303928375244), 'scale': (1.01, 12, 28), 'type': 'box', 'materials': [self.collision]}), - ba.newnode('region', + bs.newnode('region', attrs={'position': (11.871315956115723, 0.29975247383117676, 5.711406707763672), 'scale': (50, 12, 0.9), 'type': 'box', 'materials': [self.collision]}), - ba.newnode('region', + bs.newnode('region', attrs={'position': (-12.776557922363281, 0.30036890506744385, 4.96237850189209), 'scale': (1.01, 12, 28), 'type': 'box', @@ -767,5 +770,5 @@ class BasketMapV2(maps.HockeyStadium): ] -ba._map.register_map(BasketMap) -ba._map.register_map(BasketMapV2) +bs._map.register_map(BasketMap) +bs._map.register_map(BasketMapV2) diff --git a/plugins/minigames/castel_queen.py b/plugins/minigames/castel_queen.py index df86368..e3d7bc5 100644 --- a/plugins/minigames/castel_queen.py +++ b/plugins/minigames/castel_queen.py @@ -1,3 +1,4 @@ +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) # Released under the MIT License. See LICENSE for details. # """ @@ -8,24 +9,24 @@ Youtube: https://www.youtube.com/c/HeySmoothy Website: https://bombsquad-community.web.app Github: https://github.com/bombsquad-community """ -# ba_meta require api 7 +# ba_meta require api 8 # (see https://ballistica.net/wiki/meta-tag-system) from __future__ import annotations from typing import TYPE_CHECKING -import ba -import _ba +import babase +import bascenev1 as bs -from bastd.gameutils import SharedObjects -from bastd.actor.playerspaz import PlayerSpaz -from bastd.game.keepaway import KeepAwayGame, FlagState, Player -from bastd.actor import spaz +from bascenev1lib.gameutils import SharedObjects +from bascenev1lib.actor.playerspaz import PlayerSpaz +from bascenev1lib.game.keepaway import KeepAwayGame, FlagState, Player +from bascenev1lib.actor import spaz if TYPE_CHECKING: from typing import Any, Sequence, Dict, Type, List, Optional, Union -# ba_meta export game +# ba_meta export bascenev1.GameActivity class ChooseQueen(KeepAwayGame): @@ -33,11 +34,11 @@ class ChooseQueen(KeepAwayGame): description = 'Carry the queen for a set length of time' @classmethod - def supports_session_type(cls, sessiontype: Type[ba.Session]) -> bool: - return issubclass(sessiontype, ba.DualTeamSession) + def supports_session_type(cls, sessiontype: Type[bs.Session]) -> bool: + return issubclass(sessiontype, bs.DualTeamSession) @classmethod - def get_supported_maps(cls, sessiontype: Type[ba.Session]) -> List[str]: + def get_supported_maps(cls, sessiontype: Type[bs.Session]) -> List[str]: return ['Creative Thoughts'] def get_instance_description(self) -> str | Sequence: @@ -50,13 +51,13 @@ class ChooseQueen(KeepAwayGame): super().__init__(settings) shared = SharedObjects.get() self.lifts = {} - self._room_wall_material = ba.Material() + self._room_wall_material = bs.Material() self._room_wall_material.add_actions( actions=( ('modify_part_collision', 'collide', False), ('modify_part_collision', 'physical', False) )) - self._queen_material = ba.Material() + self._queen_material = bs.Material() self._queen_material.add_actions( conditions=('they_have_material', self._room_wall_material), actions=( @@ -74,7 +75,7 @@ class ChooseQueen(KeepAwayGame): ('modify_part_collision', 'collide', True), ('modify_part_collision', 'physical', True) )) - self._real_wall_material = ba.Material() + self._real_wall_material = bs.Material() self._real_wall_material.add_actions( actions=( ('modify_part_collision', 'collide', True), @@ -90,17 +91,17 @@ class ChooseQueen(KeepAwayGame): )) def on_begin(self): - ba.getactivity().globalsnode.happy_thoughts_mode = True + bs.getactivity().globalsnode.happy_thoughts_mode = True super().on_begin() self.make_map() def _spawn_flag(self) -> None: - ba.playsound(self._swipsound) + self._swipsound.play() self._flash_flag_spawn() assert self._flag_spawn_pos is not None shared = SharedObjects.get() self._flag = spaz.Spaz((0, 0, 0), character="Pixel").autoretain() - self._flag.handlemessage(ba.StandMessage((0, 14.63, -5.52), 93)) + self._flag.handlemessage(bs.StandMessage((0, 14.63, -5.52), 93)) self._flag.node.hold_position_pressed = True self._flag.node.materials = (self._queen_material, shared.object_material) # self._flag.node.extras_material= tuple(list(self._flag.node.extras_material).append(self._queen_materia)) @@ -108,7 +109,7 @@ class ChooseQueen(KeepAwayGame): self._flag.hitpoints_max = 5000 self._flag_state = FlagState.NEW - self._flag_light = ba.newnode( + self._flag_light = bs.newnode( 'light', owner=self._flag.node, attrs={'intensity': 0.2, 'radius': 0.3, 'color': (0.2, 0.2, 0.2)}, @@ -136,7 +137,7 @@ class ChooseQueen(KeepAwayGame): player.actor.node.hold_node == self._flag.node ) except Exception: - ba.print_exception('Error checking hold flag.') + babase.print_exception('Error checking hold flag.') if holdingflag: self._holding_players.append(player) player.team.holdingflag = True @@ -158,43 +159,43 @@ class ChooseQueen(KeepAwayGame): self._scoring_team = None if self._flag_state != prevstate: - ba.playsound(self._swipsound) + self._swipsound.play() def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.PlayerDiedMessage): + if isinstance(msg, bs.PlayerDiedMessage): # Augment standard behavior. super().handlemessage(msg) self.respawn_player(msg.getplayer(Player)) - elif isinstance(msg, (ba.PickedUpMessage, ba.DroppedMessage)): + elif isinstance(msg, (bs.PickedUpMessage, bs.DroppedMessage)): self._update_flag_state() else: super().handlemessage(msg) def make_map(self): shared = SharedObjects.get() - _ba.get_foreground_host_activity()._map.leftwall.materials = [ + bs.get_foreground_host_activity()._map.leftwall.materials = [ shared.footing_material, self._real_wall_material] - _ba.get_foreground_host_activity()._map.rightwall.materials = [ + bs.get_foreground_host_activity()._map.rightwall.materials = [ shared.footing_material, self._real_wall_material] - _ba.get_foreground_host_activity()._map.topwall.materials = [ + bs.get_foreground_host_activity()._map.topwall.materials = [ shared.footing_material, self._real_wall_material] - self.floorwall1 = ba.newnode('region', attrs={'position': (-10, 5, -5.52), 'scale': + self.floorwall1 = bs.newnode('region', attrs={'position': (-10, 5, -5.52), 'scale': (15, 0.2, 2), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - self.floorwall2 = ba.newnode('region', attrs={'position': (10, 5, -5.52), 'scale': ( + self.floorwall2 = bs.newnode('region', attrs={'position': (10, 5, -5.52), 'scale': ( 15, 0.2, 2), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - self.wall1 = ba.newnode('region', attrs={'position': (0, 11, -6.90), 'scale': ( + self.wall1 = bs.newnode('region', attrs={'position': (0, 11, -6.90), 'scale': ( 35.4, 20, 1), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - self.wall2 = ba.newnode('region', attrs={'position': (0, 11, -4.14), 'scale': ( + self.wall2 = bs.newnode('region', attrs={'position': (0, 11, -4.14), 'scale': ( 35.4, 20, 1), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (-10, 5, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (-10, 5, -5.52), 'color': ( 0, 0, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (15, 0.2, 2)}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (10, 5, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (10, 5, -5.52), 'color': ( 0, 0, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (15, 0.2, 2)}) self.create_static_step(0, 14.29) @@ -219,25 +220,25 @@ class ChooseQueen(KeepAwayGame): self.create_static_step(-3, 10) # create queen personal room - self.room_wall_left = ba.newnode('region', attrs={'position': (-3.633, 16.63, -5.52), 'scale': + self.room_wall_left = bs.newnode('region', attrs={'position': (-3.633, 16.63, -5.52), 'scale': (2, 4, 5), 'type': 'box', 'materials': [shared.footing_material, self._room_wall_material]}) - self.room_wall_right = ba.newnode('region', attrs={'position': (3.533, 16.63, -5.52), 'scale': + self.room_wall_right = bs.newnode('region', attrs={'position': (3.533, 16.63, -5.52), 'scale': (2, 4, 5), 'type': 'box', 'materials': [shared.footing_material, self._room_wall_material]}) def create_static_step(self, x, y): shared = SharedObjects.get() - ba.newnode('region', attrs={'position': (x, y, -5.52), 'scale': (5.5, 0.1, 6), + bs.newnode('region', attrs={'position': (x, y, -5.52), 'scale': (5.5, 0.1, 6), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (x, y, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (x, y, -5.52), 'color': ( 1, 1, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (5.5, 0.1, 2)}) def create_slope(self, x, y, backslash): shared = SharedObjects.get() for _ in range(0, 21): - ba.newnode('region', attrs={'position': (x, y, -5.52), 'scale': (0.2, 0.1, 6), + bs.newnode('region', attrs={'position': (x, y, -5.52), 'scale': (0.2, 0.1, 6), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (x, y, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (x, y, -5.52), 'color': ( 1, 1, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (0.2, 0.1, 2)}) if backslash: x = x + 0.1 @@ -291,7 +292,7 @@ class mapdefs: 0.5245740665, 0.5245740665, 0.01941146064) -class CreativeThoughts(ba.Map): +class CreativeThoughts(bs.Map): """Freaking map by smoothy.""" defs = mapdefs @@ -312,26 +313,26 @@ class CreativeThoughts(ba.Map): @classmethod def on_preload(cls) -> Any: data: Dict[str, Any] = { - 'model': ba.getmodel('alwaysLandLevel'), - 'bottom_model': ba.getmodel('alwaysLandLevelBottom'), - 'bgmodel': ba.getmodel('alwaysLandBG'), - 'collide_model': ba.getcollidemodel('alwaysLandLevelCollide'), - 'tex': ba.gettexture('alwaysLandLevelColor'), - 'bgtex': ba.gettexture('alwaysLandBGColor'), - 'vr_fill_mound_model': ba.getmodel('alwaysLandVRFillMound'), - 'vr_fill_mound_tex': ba.gettexture('vrFillMound') + 'mesh': bs.getmesh('alwaysLandLevel'), + 'bottom_mesh': bs.getmesh('alwaysLandLevelBottom'), + 'bgmesh': bs.getmesh('alwaysLandBG'), + 'collision_mesh': bs.getcollisionmesh('alwaysLandLevelCollide'), + 'tex': bs.gettexture('alwaysLandLevelColor'), + 'bgtex': bs.gettexture('alwaysLandBGColor'), + 'vr_fill_mound_mesh': bs.getmesh('alwaysLandVRFillMound'), + 'vr_fill_mound_tex': bs.gettexture('vrFillMound') } return data @classmethod - def get_music_type(cls) -> ba.MusicType: - return ba.MusicType.FLYING + def get_music_type(cls) -> bs.MusicType: + return bs.MusicType.FLYING def __init__(self) -> None: super().__init__(vr_overlay_offset=(0, -3.7, 2.5)) shared = SharedObjects.get() - self._fake_wall_material = ba.Material() - self._real_wall_material = ba.Material() + self._fake_wall_material = bs.Material() + self._real_wall_material = bs.Material() self._fake_wall_material.add_actions( conditions=(('they_are_younger_than', 9000), 'and', ('they_have_material', shared.player_material)), @@ -347,29 +348,29 @@ class CreativeThoughts(ba.Map): ('modify_part_collision', 'physical', True) )) - self.background = ba.newnode( + self.background = bs.newnode( 'terrain', attrs={ - 'model': self.preloaddata['bgmodel'], + 'mesh': self.preloaddata['bgmesh'], 'lighting': False, 'background': True, - 'color_texture': ba.gettexture("rampageBGColor") + 'color_texture': bs.gettexture("rampageBGColor") }) - self.leftwall = ba.newnode('region', attrs={'position': (-17.75152479, 13, -5.52), 'scale': ( + self.leftwall = bs.newnode('region', attrs={'position': (-17.75152479, 13, -5.52), 'scale': ( 0.1, 15.5, 2), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - self.rightwall = ba.newnode('region', attrs={'position': (17.75, 13, -5.52), 'scale': ( + self.rightwall = bs.newnode('region', attrs={'position': (17.75, 13, -5.52), 'scale': ( 0.1, 15.5, 2), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - self.topwall = ba.newnode('region', attrs={'position': (0, 21.0, -5.52), 'scale': ( + self.topwall = bs.newnode('region', attrs={'position': (0, 21.0, -5.52), 'scale': ( 35.4, 0.2, 2), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (-17.75152479, 13, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (-17.75152479, 13, -5.52), 'color': ( 0, 0, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (0.1, 15.5, 2)}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (17.75, 13, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (17.75, 13, -5.52), 'color': ( 0, 0, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (0.1, 15.5, 2)}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (0, 21.0, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (0, 21.0, -5.52), 'color': ( 0, 0, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (35.4, 0.2, 2)}) - gnode = ba.getactivity().globalsnode + gnode = bs.getactivity().globalsnode gnode.happy_thoughts_mode = True gnode.shadow_offset = (0.0, 8.0, 5.0) gnode.tint = (1.3, 1.23, 1.0) @@ -380,9 +381,9 @@ class CreativeThoughts(ba.Map): self.is_flying = True # throw out some tips on flying - txt = ba.newnode('text', + txt = bs.newnode('text', attrs={ - 'text': ba.Lstr(resource='pressJumpToFlyText'), + 'text': babase.Lstr(resource='pressJumpToFlyText'), 'scale': 1.2, 'maxwidth': 800, 'position': (0, 200), @@ -391,7 +392,7 @@ class CreativeThoughts(ba.Map): 'h_align': 'center', 'v_attach': 'bottom' }) - cmb = ba.newnode('combine', + cmb = bs.newnode('combine', owner=txt, attrs={ 'size': 4, @@ -399,12 +400,12 @@ class CreativeThoughts(ba.Map): 'input1': 0.9, 'input2': 0.0 }) - ba.animate(cmb, 'input3', {3.0: 0, 4.0: 1, 9.0: 1, 10.0: 0}) + bs.animate(cmb, 'input3', {3.0: 0, 4.0: 1, 9.0: 1, 10.0: 0}) cmb.connectattr('output', txt, 'color') - ba.timer(10.0, txt.delete) + bs.timer(10.0, txt.delete) try: - ba._map.register_map(CreativeThoughts) + bs._map.register_map(CreativeThoughts) except: pass diff --git a/plugins/minigames/drone_war.py b/plugins/minigames/drone_war.py index 4877afa..21eafb1 100644 --- a/plugins/minigames/drone_war.py +++ b/plugins/minigames/drone_war.py @@ -1,3 +1,4 @@ +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) # Released under the MIT License. See LICENSE for details. # """ @@ -8,22 +9,22 @@ Youtube: https://www.youtube.com/c/HeySmoothy Website: https://bombsquad-community.web.app Github: https://github.com/bombsquad-community """ -# ba_meta require api 7 +# ba_meta require api 8 # (see https://ballistica.net/wiki/meta-tag-system) from __future__ import annotations from typing import TYPE_CHECKING -import ba -import _ba -from ba._generated.enums import InputType -from bastd.actor.bomb import Blast +import babase +import bascenev1 as bs +from babase._mgen.enums import InputType +from bascenev1lib.actor.bomb import Blast -from bastd.gameutils import SharedObjects -from bastd.actor.playerspaz import PlayerSpaz, PlayerType -from bastd.game.deathmatch import DeathMatchGame, Player -from bastd.actor import spaz +from bascenev1lib.gameutils import SharedObjects +from bascenev1lib.actor.playerspaz import PlayerSpaz, PlayerT +from bascenev1lib.game.deathmatch import DeathMatchGame, Player +from bascenev1lib.actor import spaz if TYPE_CHECKING: from typing import Any, Sequence, Dict, Type, List, Optional, Union @@ -33,11 +34,11 @@ STORAGE_ATTR_NAME = f'_shared_{__name__}_factory' # use drone as long as you want , unlike floater which dies after being idle. -class Drone(ba.Actor): +class Drone(bs.Actor): def __init__(self, spaz): super().__init__() shared = SharedObjects.get() - self._drone_material = ba.Material() + self._drone_material = bs.Material() self.loop_ascend = None self.loop_descend = None self.loop_lr = None @@ -59,45 +60,45 @@ class Drone(ba.Actor): ('they_have_material', self._drone_material)), actions=('modify_part_collision', 'physical', False)) - self.node = ba.newnode( + self.node = bs.newnode( 'prop', delegate=self, owner=None, attrs={ 'position': spaz.node.position, - 'model': ba.getmodel('landMine'), - 'light_model': ba.getmodel('landMine'), + 'mesh': bs.getmesh('landMine'), + 'light_mesh': bs.getmesh('landMine'), 'body': 'landMine', 'body_scale': 1, - 'model_scale': 1, + 'mesh_scale': 1, 'shadow_size': 0.25, 'density': 999999, 'gravity_scale': 0.0, - 'color_texture': ba.gettexture('achievementCrossHair'), + 'color_texture': bs.gettexture('achievementCrossHair'), 'reflection': 'soft', 'reflection_scale': [0.25], 'materials': [shared.footing_material, self._drone_material] }) - self.grab_node = ba.newnode( + self.grab_node = bs.newnode( 'prop', owner=self.node, attrs={ 'position': (0, 0, 0), 'body': 'sphere', - 'model': None, + 'mesh': None, 'color_texture': None, 'body_scale': 0.2, 'reflection': 'powerup', 'density': 999999, 'reflection_scale': [1.0], - 'model_scale': 0.2, + 'mesh_scale': 0.2, 'gravity_scale': 0, 'shadow_size': 0.1, 'is_area_of_interest': True, 'materials': [shared.object_material, self._drone_material] }) self.node.connectattr('position', self.grab_node, 'position') - self._rcombine = ba.newnode('combine', + self._rcombine = bs.newnode('combine', owner=self.node, attrs={ 'input0': self.spaz.node.position[0], @@ -119,12 +120,12 @@ class Drone(ba.Actor): def ascend(self): def loop(): if self.node.exists(): - ba.animate(self._rcombine, 'input1', { + bs.animate(self._rcombine, 'input1', { 0: self.node.position[1], 1: self.node.position[1] + 2 }) loop() - self.loop_ascend = ba.Timer(1, loop, repeat=True) + self.loop_ascend = bs.Timer(1, loop, repeat=True) def pause_movement(self): self.loop_ascend = None @@ -132,12 +133,12 @@ class Drone(ba.Actor): def decend(self): def loop(): if self.node.exists(): - ba.animate(self._rcombine, 'input1', { + bs.animate(self._rcombine, 'input1', { 0: self.node.position[1], 1: self.node.position[1] - 2 }) loop() - self.loop_ascend = ba.Timer(1, loop, repeat=True) + self.loop_ascend = bs.Timer(1, loop, repeat=True) def pause_lr(self): self.loop_lr = None @@ -148,7 +149,7 @@ class Drone(ba.Actor): def left_(self, value=-1): def loop(): if self.node.exists(): - ba.animate(self._rcombine, 'input0', { + bs.animate(self._rcombine, 'input0', { 0: self.node.position[0], 1: self.node.position[0] + 2 * value }) @@ -158,12 +159,12 @@ class Drone(ba.Actor): self.x_direction = value self.z_direction = 0 loop() - self.loop_lr = ba.Timer(1, loop, repeat=True) + self.loop_lr = bs.Timer(1, loop, repeat=True) def right_(self, value=1): def loop(): if self.node.exists(): - ba.animate(self._rcombine, 'input0', { + bs.animate(self._rcombine, 'input0', { 0: self.node.position[0], 1: self.node.position[0] + 2 * value }) @@ -173,12 +174,12 @@ class Drone(ba.Actor): self.x_direction = value self.z_direction = 0 loop() - self.loop_lr = ba.Timer(1, loop, repeat=True) + self.loop_lr = bs.Timer(1, loop, repeat=True) def up_(self, value=1): def loop(): if self.node.exists(): - ba.animate(self._rcombine, 'input2', { + bs.animate(self._rcombine, 'input2', { 0: self.node.position[2], 1: self.node.position[2] - 2 * value }) @@ -188,12 +189,12 @@ class Drone(ba.Actor): self.x_direction = 0 self.z_direction = - value loop() - self.loop_ud = ba.Timer(1, loop, repeat=True) + self.loop_ud = bs.Timer(1, loop, repeat=True) def down_(self, value=-1): def loop(): if self.node.exists(): - ba.animate(self._rcombine, 'input2', { + bs.animate(self._rcombine, 'input2', { 0: self.node.position[2], 1: self.node.position[2] - 2 * value }) @@ -203,17 +204,17 @@ class Drone(ba.Actor): self.x_direction = 0 self.z_direction = - value loop() - self.loop_ud = ba.Timer(1, loop, repeat=True) + self.loop_ud = bs.Timer(1, loop, repeat=True) def handlemessage(self, msg): - if isinstance(msg, ba.DieMessage): + if isinstance(msg, bs.DieMessage): self.node.delete() self.grab_node.delete() self.loop_ascend = None self.loop_ud = None self.loop_lr = None - elif isinstance(msg, ba.OutOfBoundsMessage): - self.handlemessage(ba.DieMessage()) + elif isinstance(msg, bs.OutOfBoundsMessage): + self.handlemessage(bs.DieMessage()) else: super().handlemessage(msg) @@ -224,7 +225,7 @@ class RocketFactory: """Quake Rocket factory""" def __init__(self) -> None: - self.ball_material = ba.Material() + self.ball_material = bs.Material() self.ball_material.add_actions( conditions=((('we_are_younger_than', 5), 'or', @@ -251,7 +252,7 @@ class RocketFactory: @classmethod def get(cls): """Get factory if exists else create new""" - activity = ba.getactivity() + activity = bs.getactivity() if hasattr(activity, STORAGE_ATTR_NAME): return getattr(activity, STORAGE_ATTR_NAME) factory = cls() @@ -263,30 +264,30 @@ class RocketLauncher: """Very dangerous weapon""" def __init__(self): - self.last_shot = ba.time() + self.last_shot = bs.time() def give(self, spaz: spaz.Spaz) -> None: """Give spaz a rocket launcher""" spaz.punch_callback = self.shot - self.last_shot = ba.time() + self.last_shot = bs.time() # FIXME # noinspection PyUnresolvedReferences def shot(self, spaz, x, z, position) -> None: """Release a rocket""" - time = ba.time() + time = bs.time() if time - self.last_shot > 0.6: self.last_shot = time direction = [x, 0, z] direction[1] = 0.0 - mag = 10.0 / 1 if ba.Vec3(*direction).length() == 0 else ba.Vec3(*direction).length() + mag = 10.0 / 1 if babase.Vec3(*direction).length() == 0 else babase.Vec3(*direction).length() vel = [v * mag for v in direction] Rocket(position=position, velocity=vel, - owner=spaz.getplayer(ba.Player), - source_player=spaz.getplayer(ba.Player), + owner=spaz.getplayer(bs.Player), + source_player=spaz.getplayer(bs.Player), color=spaz.node.color).autoretain() @@ -294,7 +295,7 @@ class ImpactMessage: """Rocket touched something""" -class Rocket(ba.Actor): +class Rocket(bs.Actor): """Epic rocket from rocket launcher""" def __init__(self, @@ -309,16 +310,16 @@ class Rocket(ba.Actor): self._color = color factory = RocketFactory.get() - self.node = ba.newnode('prop', + self.node = bs.newnode('prop', delegate=self, attrs={ 'position': position, 'velocity': velocity, - 'model': ba.getmodel('impactBomb'), + 'mesh': bs.getmesh('impactBomb'), 'body': 'sphere', - 'color_texture': ba.gettexture( + 'color_texture': bs.gettexture( 'bunnyColor'), - 'model_scale': 0.2, + 'mesh_scale': 0.2, 'is_area_of_interest': True, 'body_scale': 0.8, 'materials': [ @@ -328,17 +329,17 @@ class Rocket(ba.Actor): self.node.extra_acceleration = (self.node.velocity[0] * 200, 0, self.node.velocity[2] * 200) - self._life_timer = ba.Timer( - 5, ba.WeakCall(self.handlemessage, ba.DieMessage())) + self._life_timer = bs.Timer( + 5, bs.WeakCall(self.handlemessage, bs.DieMessage())) - self._emit_timer = ba.Timer(0.001, ba.WeakCall(self.emit), repeat=True) + self._emit_timer = bs.Timer(0.001, bs.WeakCall(self.emit), repeat=True) self.base_pos_y = self.node.position[1] - ba.camerashake(5.0) + bs.camerashake(5.0) def emit(self) -> None: """Emit a trace after rocket""" - ba.emitfx(position=self.node.position, + bs.emitfx(position=self.node.position, scale=0.4, spread=0.01, chunk_type='spark') @@ -346,7 +347,7 @@ class Rocket(ba.Actor): return self.node.position = (self.node.position[0], self.base_pos_y, self.node.position[2]) # ignore y - ba.newnode('explosion', + bs.newnode('explosion', owner=self.node, attrs={ 'position': self.node.position, @@ -358,9 +359,9 @@ class Rocket(ba.Actor): """Message handling for rocket""" super().handlemessage(msg) if isinstance(msg, ImpactMessage): - self.node.handlemessage(ba.DieMessage()) + self.node.handlemessage(bs.DieMessage()) - elif isinstance(msg, ba.DieMessage): + elif isinstance(msg, bs.DieMessage): if self.node: Blast(position=self.node.position, blast_radius=2, @@ -369,25 +370,25 @@ class Rocket(ba.Actor): self.node.delete() self._emit_timer = None - elif isinstance(msg, ba.OutOfBoundsMessage): - self.handlemessage(ba.DieMessage()) + elif isinstance(msg, bs.OutOfBoundsMessage): + self.handlemessage(bs.DieMessage()) -# ba_meta export game +# ba_meta export bascenev1.GameActivity class ChooseQueen(DeathMatchGame): name = 'Drone War' @classmethod - def supports_session_type(cls, sessiontype: Type[ba.Session]) -> bool: - return issubclass(sessiontype, ba.DualTeamSession) + def supports_session_type(cls, sessiontype: Type[bs.Session]) -> bool: + return issubclass(sessiontype, bs.DualTeamSession) @classmethod - def get_supported_maps(cls, sessiontype: Type[ba.Session]) -> List[str]: + def get_supported_maps(cls, sessiontype: Type[bs.Session]) -> List[str]: return ['Football Stadium'] def spawn_player_spaz( self, - player: PlayerType, + player: PlayerT, position: Sequence[float] | None = None, angle: float | None = None, ) -> PlayerSpaz: @@ -398,29 +399,29 @@ class ChooseQueen(DeathMatchGame): def on_begin(self): super().on_begin() shared = SharedObjects.get() - self.ground_material = ba.Material() + self.ground_material = bs.Material() self.ground_material.add_actions( conditions=('they_have_material', shared.player_material), actions=( ('modify_part_collision', 'collide', True), - ('call', 'at_connect', ba.Call(self._handle_player_collide)), + ('call', 'at_connect', babase.Call(self._handle_player_collide)), ), ) pos = (0, 0.1, -5) - self.main_region = ba.newnode('region', attrs={'position': pos, 'scale': ( + self.main_region = bs.newnode('region', attrs={'position': pos, 'scale': ( 30, 0.001, 23), 'type': 'box', 'materials': [shared.footing_material, self.ground_material]}) def _handle_player_collide(self): try: - player = ba.getcollision().opposingnode.getdelegate( + player = bs.getcollision().opposingnode.getdelegate( PlayerSpaz, True) - except ba.NotFoundError: + except bs.NotFoundError: return if player.is_alive(): player.shatter(True) def spawn_drone(self, spaz): - with ba.Context(_ba.get_foreground_host_activity()): + with bs.get_foreground_host_activity().context: drone = Drone(spaz) r_launcher = RocketLauncher() diff --git a/plugins/minigames/hot_potato.py b/plugins/minigames/hot_potato.py index 2eed1dc..9acc355 100644 --- a/plugins/minigames/hot_potato.py +++ b/plugins/minigames/hot_potato.py @@ -1,3 +1,4 @@ +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) """ Hot Potato by TheMikirog#1984 @@ -13,20 +14,23 @@ """ -# ba_meta require api 7 +# ba_meta require api 8 from __future__ import annotations from typing import TYPE_CHECKING # Define only what we need and nothing more -import ba -from bastd.actor.spaz import SpazFactory -from bastd.actor.spaz import PickupMessage -from bastd.actor.spaz import BombDiedMessage -from bastd.actor.playerspaz import PlayerSpaz -from bastd.actor.bomb import Bomb -from bastd.actor.bomb import Blast +from baenv import TARGET_BALLISTICA_BUILD as build_number +import babase +import bauiv1 as bui +import bascenev1 as bs +from bascenev1lib.actor.spaz import SpazFactory +from bascenev1lib.actor.spaz import PickupMessage +from bascenev1lib.actor.spaz import BombDiedMessage +from bascenev1lib.actor.playerspaz import PlayerSpaz +from bascenev1lib.actor.bomb import Bomb +from bascenev1lib.actor.bomb import Blast from enum import Enum import random @@ -72,7 +76,7 @@ class PlayerState(Enum): # Here's the behavior of each icon. -class Icon(ba.Actor): +class Icon(bs.Actor): """Creates in in-game icon on screen.""" def __init__(self, @@ -88,11 +92,11 @@ class Icon(ba.Actor): self._player = player self._name_scale = name_scale - self._outline_tex = ba.gettexture('characterIconMask') + self._outline_tex = bui.gettexture('characterIconMask') # Character portrait icon = player.get_icon() - self.node = ba.newnode('image', + self.node = bs.newnode('image', delegate=self, attrs={ 'texture': icon['texture'], @@ -106,12 +110,12 @@ class Icon(ba.Actor): 'attach': 'bottomCenter' }) # Player name - self._name_text = ba.newnode( + self._name_text = bs.newnode( 'text', owner=self.node, attrs={ - 'text': ba.Lstr(value=player.getname()), - 'color': ba.safecolor(player.team.color), + 'text': babase.Lstr(value=player.getname()), + 'color': babase.safecolor(player.team.color), 'h_align': 'center', 'v_align': 'center', 'vr_depth': 410, @@ -122,7 +126,7 @@ class Icon(ba.Actor): 'v_attach': 'bottom' }) # Status text (such as Marked!, Stunned! and You're Out!) - self._marked_text = ba.newnode( + self._marked_text = bs.newnode( 'text', owner=self.node, attrs={ @@ -137,11 +141,11 @@ class Icon(ba.Actor): 'v_attach': 'bottom' }) # Status icon overlaying the character portrait - self._marked_icon = ba.newnode( + self._marked_icon = bs.newnode( 'text', owner=self.node, attrs={ - 'text': ba.charstr(ba.SpecialChar.HAL), + 'text': babase.charstr(babase.SpecialChar.HAL), 'color': (1, 1, 1), 'h_align': 'center', 'v_align': 'center', @@ -169,7 +173,7 @@ class Icon(ba.Actor): self.node.color = (1.0, 1.0, 1.0) # Marked players get ALL of the attention - red portrait, red text and icon overlaying the portrait elif type is PlayerState.MARKED: - self._marked_icon.text = ba.charstr(ba.SpecialChar.HAL) + self._marked_icon.text = babase.charstr(babase.SpecialChar.HAL) self._marked_icon.position = (pos[0] - 1, pos[1] - 13) self._marked_icon.opacity = 1.0 self._marked_text.text = 'Marked!' @@ -179,7 +183,7 @@ class Icon(ba.Actor): self.node.color = (1.0, 0.2, 0.2) # Stunned players are just as important - yellow portrait, yellow text and moon icon. elif type is PlayerState.STUNNED: - self._marked_icon.text = ba.charstr(ba.SpecialChar.MOON) + self._marked_icon.text = babase.charstr(babase.SpecialChar.MOON) self._marked_icon.position = (pos[0] - 2, pos[1] - 12) self._marked_icon.opacity = 1.0 self._marked_text.text = 'Stunned!' @@ -189,17 +193,17 @@ class Icon(ba.Actor): # Eliminated players get special treatment. # We make the portrait semi-transparent, while adding some visual flair with an fading skull icon and text. elif type is PlayerState.ELIMINATED: - self._marked_icon.text = ba.charstr(ba.SpecialChar.SKULL) + self._marked_icon.text = babase.charstr(babase.SpecialChar.SKULL) self._marked_icon.position = (pos[0] - 2, pos[1] - 12) self._marked_text.text = 'You\'re Out!' self._marked_text.color = (0.5, 0.5, 0.5) # Animate text and icon animation_end_time = 1.5 if bool(self.activity.settings['Epic Mode']) else 3.0 - ba.animate(self._marked_icon, 'opacity', { + bs.animate(self._marked_icon, 'opacity', { 0: 1.0, animation_end_time: 0.0}) - ba.animate(self._marked_text, 'opacity', { + bs.animate(self._marked_text, 'opacity', { 0: 1.0, animation_end_time: 0.0}) @@ -235,7 +239,7 @@ class PotatoPlayerSpaz(PlayerSpaz): self.dropped_bombs = [] # we use this to track bombs thrown by the player # Define a marked light - self.marked_light = ba.newnode('light', + self.marked_light = bs.newnode('light', owner=self.node, attrs={'position': self.node.position, 'radius': 0.15, @@ -244,7 +248,7 @@ class PotatoPlayerSpaz(PlayerSpaz): 'color': (1.0, 0.0, 0.0)}) # Pulsing red light when the player is Marked - ba.animate(self.marked_light, 'radius', { + bs.animate(self.marked_light, 'radius', { 0: 0.1, 0.3: 0.15, 0.6: 0.1}, @@ -252,12 +256,12 @@ class PotatoPlayerSpaz(PlayerSpaz): self.node.connectattr('position_center', self.marked_light, 'position') # Marked timer. It should be above our head, so we attach the text to the offset that's attached to the player. - self.marked_timer_offset = ba.newnode('math', owner=self.node, attrs={ + self.marked_timer_offset = bs.newnode('math', owner=self.node, attrs={ 'input1': (0, 1.2, 0), 'operation': 'add'}) self.node.connectattr('torso_position', self.marked_timer_offset, 'input2') - self.marked_timer_text = ba.newnode('text', owner=self.node, attrs={ + self.marked_timer_text = bs.newnode('text', owner=self.node, attrs={ 'text': '', 'in_world': True, 'shadow': 0.4, @@ -278,7 +282,7 @@ class PotatoPlayerSpaz(PlayerSpaz): # Add our bomb to the list of our tracked bombs self.dropped_bombs.append(bomb) # Bring a light - bomb.bomb_marked_light = ba.newnode('light', + bomb.bomb_marked_light = bs.newnode('light', owner=bomb.node, attrs={'position': bomb.node.position, 'radius': 0.04, @@ -291,7 +295,7 @@ class PotatoPlayerSpaz(PlayerSpaz): self.set_bombs_marked() # When the bomb physics node dies, call a function. bomb.node.add_death_action( - ba.WeakCall(self.bomb_died, bomb)) + bs.WeakCall(self.bomb_died, bomb)) # Here's the function that gets called when one of the player's bombs dies. # We reference the player's dropped_bombs list and remove the bomb that died. @@ -309,7 +313,7 @@ class PotatoPlayerSpaz(PlayerSpaz): # Since our gamemode relies heavily on players passing the mark to other players # we need to have access to this message. This gets called when the player takes damage for any reason. def handlemessage(self, msg): - if isinstance(msg, ba.HitMessage): + if isinstance(msg, bs.HitMessage): # This is basically the same HitMessage code as in the original Spaz. # The only difference is that there is no health bar and you can't die with punches or bombs. # Also some useless or redundant code was removed. @@ -326,9 +330,7 @@ class PotatoPlayerSpaz(PlayerSpaz): # If the attacker is healthy and we're stunned, do a flash and play a sound, then ignore the rest of the code. if self.source_player.state == PlayerState.STUNNED and msg._source_player != PlayerState.MARKED: self.node.handlemessage('flash') - ba.playsound(SpazFactory.get().block_sound, - 1.0, - position=self.node.position) + SpazFactory.get().block_sound.play(1.0, position=self.node.position) return True # Here's all the damage and force calculations unchanged from the source. @@ -360,11 +362,11 @@ class PotatoPlayerSpaz(PlayerSpaz): sound = SpazFactory.get().punch_sound else: sound = SpazFactory.get().punch_sound_weak - ba.playsound(sound, 1.0, position=self.node.position) + sound.play(1.0, position=self.node.position) # Throw up some chunks. assert msg.force_direction is not None - ba.emitfx(position=msg.pos, + bs.emitfx(position=msg.pos, velocity=(msg.force_direction[0] * 0.5, msg.force_direction[1] * 0.5, msg.force_direction[2] * 0.5), @@ -372,7 +374,7 @@ class PotatoPlayerSpaz(PlayerSpaz): scale=0.3, spread=0.03) - ba.emitfx(position=msg.pos, + bs.emitfx(position=msg.pos, chunk_type='sweat', velocity=(msg.force_direction[0] * 1.3, msg.force_direction[1] * 1.3 + 5.0, @@ -387,7 +389,7 @@ class PotatoPlayerSpaz(PlayerSpaz): msg.pos[1] + msg.force_direction[1] * 0.02, msg.pos[2] + msg.force_direction[2] * 0.02) flash_color = (1.0, 0.8, 0.4) - light = ba.newnode( + light = bs.newnode( 'light', attrs={ 'position': punchpos, @@ -396,20 +398,20 @@ class PotatoPlayerSpaz(PlayerSpaz): 'height_attenuated': False, 'color': flash_color }) - ba.timer(0.06, light.delete) + bs.timer(0.06, light.delete) - flash = ba.newnode('flash', + flash = bs.newnode('flash', attrs={ 'position': punchpos, 'size': 0.17 + 0.17 * hurtiness, 'color': flash_color }) - ba.timer(0.06, flash.delete) + bs.timer(0.06, flash.delete) # Physics collision particles. if msg.hit_type == 'impact': assert msg.force_direction is not None - ba.emitfx(position=msg.pos, + bs.emitfx(position=msg.pos, velocity=(msg.force_direction[0] * 2.0, msg.force_direction[1] * 2.0, msg.force_direction[2] * 2.0), @@ -435,9 +437,9 @@ class PotatoPlayerSpaz(PlayerSpaz): # Let's get all collision data if we can. Otherwise cancel. try: - collision = ba.getcollision() + collision = bs.getcollision() opposingnode = collision.opposingnode - except ba.NotFoundError: + except bs.NotFoundError: return True # Our grabber needs to be a Spaz @@ -447,9 +449,7 @@ class PotatoPlayerSpaz(PlayerSpaz): # It's the same sound and flashing behavior as hitting a stunned player as a healthy player. if (opposingnode.source_player.state == PlayerState.STUNNED and self.source_player.state != PlayerState.MARKED): opposingnode.handlemessage('flash') - ba.playsound(SpazFactory.get().block_sound, - 1.0, - position=opposingnode.position) + SpazFactory.get().block_sound.play(1.0, position=opposingnode.position) return True # If they're marked and we're healthy or stunned, pass that mark along to us. elif opposingnode.source_player.state in [PlayerState.REGULAR, PlayerState.STUNNED] and self.source_player.state == PlayerState.MARKED: @@ -458,10 +458,10 @@ class PotatoPlayerSpaz(PlayerSpaz): # Our work is done. Continue with the rest of the grabbing behavior as usual. super().handlemessage(msg) # Dying is important in this gamemode and as such we need to address this behavior. - elif isinstance(msg, ba.DieMessage): + elif isinstance(msg, bs.DieMessage): # If a player left the game, inform our gamemode logic. - if msg.how == ba.DeathType.LEFT_GAME: + if msg.how == bs.DeathType.LEFT_GAME: self.activity.player_left(self.source_player) # If a MARKED or STUNNED player dies, hide the text from the previous spaz. @@ -470,7 +470,7 @@ class PotatoPlayerSpaz(PlayerSpaz): self.marked_timer_text.color[1], self.marked_timer_text.color[2], 0.0) - ba.animate(self.marked_light, 'intensity', { + bs.animate(self.marked_light, 'intensity', { 0: self.marked_light.intensity, 0.5: 0.0}) @@ -483,7 +483,7 @@ class PotatoPlayerSpaz(PlayerSpaz): # A concept of a player is very useful to reference if we don't have a player character present (maybe they died). -class Player(ba.Player['Team']): +class Player(bs.Player['Team']): """Our player type for this game.""" def __init__(self) -> None: @@ -535,8 +535,8 @@ class Player(ba.Player['Team']): self.stunned_time_remaining = stun_time # Set our stun time remaining # Remove our stun once the time is up - self.stunned_timer = ba.Timer(stun_time + 0.1, ba.Call(self.stun_remove)) - self.stunned_update_timer = ba.Timer(0.1, ba.Call( + self.stunned_timer = bs.Timer(stun_time + 0.1, babase.Call(self.stun_remove)) + self.stunned_update_timer = bs.Timer(0.1, babase.Call( self.stunned_timer_tick), repeat=True) # Call a function every 0.1 seconds self.fall_times += 1 # Increase the amount of times we fell by one # Change the text above the Spaz's head to total stun time @@ -579,8 +579,8 @@ class Player(ba.Player['Team']): self.icon.set_marked_icon(state) # Update our icon -# ba_meta export game -class HotPotato(ba.TeamGameActivity[Player, ba.Team]): +# ba_meta export bascenev1.GameActivity +class HotPotato(bs.TeamGameActivity[Player, bs.Team]): # Let's define the basics like the name of the game, description and some tips that should appear at the start of a match. name = 'Hot Potato' @@ -604,8 +604,8 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): # We're gonna distribute end of match session scores based on who dies first and who survives. # First place gets most points, then second, then third. - scoreconfig = ba.ScoreConfig(label='Place', - scoretype=ba.ScoreType.POINTS, + scoreconfig = bs.ScoreConfig(label='Place', + scoretype=bs.ScoreType.POINTS, lower_is_better=True) # These variables are self explanatory too. @@ -614,25 +614,25 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): # Let's define some settings the user can mess around with to fit their needs. available_settings = [ - ba.IntSetting('Elimination Timer', + bs.IntSetting('Elimination Timer', min_value=5, default=15, increment=1, ), - ba.BoolSetting('Marked Players use Impact Bombs', default=False), - ba.BoolSetting('Epic Mode', default=False), + bs.BoolSetting('Marked Players use Impact Bombs', default=False), + bs.BoolSetting('Epic Mode', default=False), ] # Hot Potato is strictly a Free-For-All gamemode, so only picking the gamemode in FFA playlists. @classmethod - def supports_session_type(cls, sessiontype: type[ba.Session]) -> bool: - return issubclass(sessiontype, ba.FreeForAllSession) + def supports_session_type(cls, sessiontype: type[bs.Session]) -> bool: + return issubclass(sessiontype, bs.FreeForAllSession) # Most maps should work in Hot Potato. Generally maps marked as 'melee' are the most versatile map types of them all. # As the name implies, fisticuffs are common forms of engagement. @classmethod - def get_supported_maps(cls, sessiontype: type[ba.Session]) -> list[str]: - return ba.getmaps('melee') + def get_supported_maps(cls, sessiontype: type[bs.Session]) -> list[str]: + return bs.app.classic.getmaps('melee') # Here we define everything the gamemode needs, like sounds and settings. def __init__(self, settings: dict): @@ -640,22 +640,22 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): self.settings = settings # Let's define all of the sounds we need. - self._tick_sound = ba.getsound('tick') - self._player_eliminated_sound = ba.getsound('playerDeath') + self._tick_sound = bui.getsound('tick') + self._player_eliminated_sound = bui.getsound('playerDeath') # These next sounds are arrays instead of single sounds. # We'll use that fact later. - self._danger_tick_sounds = [ba.getsound('orchestraHit'), - ba.getsound('orchestraHit2'), - ba.getsound('orchestraHit3')] - self._marked_sounds = [ba.getsound('powerdown01'), - ba.getsound('activateBeep'), - ba.getsound('hiss')] + self._danger_tick_sounds = [bui.getsound('orchestraHit'), + bui.getsound('orchestraHit2'), + bui.getsound('orchestraHit3')] + self._marked_sounds = [bui.getsound('powerdown01'), + bui.getsound('activateBeep'), + bui.getsound('hiss')] # Normally play KOTH music, but switch to Epic music if we're in slow motion. self._epic_mode = bool(settings['Epic Mode']) self.slow_motion = self._epic_mode - self.default_music = (ba.MusicType.EPIC if self._epic_mode else - ba.MusicType.SCARY) + self.default_music = (bs.MusicType.EPIC if self._epic_mode else + bs.MusicType.SCARY) # This description appears below the title card after it comes crashing when the game begins. def get_instance_description(self) -> str | Sequence: @@ -680,7 +680,7 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): # Returns every single marked player. # This piece of info is used excensively in this gamemode, so it's advantageous to have a function to cut on # work and make the gamemode easier to maintain - def get_marked_players(self) -> Sequence[ba.Player]: + def get_marked_players(self) -> Sequence[bs.Player]: marked_players = [] for p in self.players: if p.state == PlayerState.MARKED: @@ -691,7 +691,7 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): def mark(self, target: Player) -> None: target.set_state(PlayerState.MARKED) - ba.emitfx(position=target.actor.node.position, + bs.emitfx(position=target.actor.node.position, velocity=target.actor.node.velocity, chunk_type='spark', count=int(20.0+random.random()*20), @@ -738,7 +738,7 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): sound_volume = 1.0 / marked_player_amount for target in marked_players: - ba.playsound(self._tick_sound, sound_volume, target.actor.node.position) + self._tick_sound.play(sound_volume, target.actor.node.position) target.actor.marked_timer_text.text = str(self.elimination_timer_display) # When counting down 3, 2, 1 play some dramatic sounds @@ -746,7 +746,7 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): # We store our dramatic sounds in an array, so we target a specific element on the array # depending on time remaining. Arrays start at index 0, so we need to decrease # our variable by 1 to get the element index. - ba.playsound(self._danger_tick_sounds[self.elimination_timer_display - 1], 1.5) + self._danger_tick_sounds[self.elimination_timer_display - 1].play(1.5) else: # Elimination timer is up! Let's eliminate all marked players. self.elimination_timer_display -= 1 # Decrease our timer by one second. @@ -763,18 +763,18 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): velocity=target.actor.node.velocity, blast_radius=3.0, source_player=target).autoretain() - ba.emitfx(position=target.actor.node.position, + bs.emitfx(position=target.actor.node.position, velocity=target.actor.node.velocity, count=int(16.0+random.random()*60), scale=1.5, spread=2, chunk_type='spark') - target.actor.handlemessage(ba.DieMessage(how='marked_elimination')) + target.actor.handlemessage(bs.DieMessage(how='marked_elimination')) target.actor.shatter(extreme=True) self.match_placement.append(target.team) - ba.playsound(self._player_eliminated_sound, 1.0) + self._player_eliminated_sound.play(1.0) # Let the gamemode know a Marked self.marked_players_died() @@ -788,13 +788,13 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): # Let's add our lone survivor to the match placement list. self.match_placement.append(alive_players[0].team) # Wait a while to let this sink in before we announce our victor. - self._end_game_timer = ba.Timer(1.25, ba.Call(self.end_game)) + self._end_game_timer = bs.Timer(1.25, babase.Call(self.end_game)) else: # There's still players remaining, so let's wait a while before marking a new player. - self.new_mark_timer = ba.Timer(2.0 if self.slow_motion else 4.0, ba.Call(self.new_mark)) + self.new_mark_timer = bs.Timer(2.0 if self.slow_motion else 4.0, babase.Call(self.new_mark)) # Another extensively used function that returns all alive players. - def get_alive_players(self) -> Sequence[ba.Player]: + def get_alive_players(self) -> Sequence[bs.Player]: alive_players = [] for player in self.players: if player.state == PlayerState.ELIMINATED: @@ -829,14 +829,14 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): # Set time until marked players explode self.elimination_timer_display = self.settings['Elimination Timer'] # Set a timer that calls _eliminate_tick every second - self.marked_tick_timer = ba.Timer(1.0, ba.Call(self._eliminate_tick), repeat=True) + self.marked_tick_timer = bs.Timer(1.0, babase.Call(self._eliminate_tick), repeat=True) # Mark all chosen victims and play a sound for new_victim in all_victims: # _marked_sounds is an array. # To make a nice marked sound effect, I play multiple sounds at once # All of them are contained in the array. for sound in self._marked_sounds: - ba.playsound(sound, 1.0, new_victim.actor.node.position) + sound.play(1.0, new_victim.actor.node.position) self.mark(new_victim) # This function is called when the gamemode first loads. @@ -849,10 +849,10 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): # End the game if there's only one player if len(self.players) < 2: self.match_placement.append(self.players[0].team) - self._round_end_timer = ba.Timer(0.5, self.end_game) + self._round_end_timer = bs.Timer(0.5, self.end_game) else: # Pick random player(s) to get marked - self.new_mark_timer = ba.Timer(2.0 if self.slow_motion else 5.2, ba.Call(self.new_mark)) + self.new_mark_timer = bs.Timer(2.0 if self.slow_motion else 5.2, babase.Call(self.new_mark)) self._update_icons() # Create player state icons @@ -873,17 +873,17 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): # I'm gonna modify this function to move the tip text above the icons. def _show_tip(self) -> None: - from ba._gameutils import animate, GameTip - from ba._generated.enums import SpecialChar - from ba._language import Lstr + from bascenev1._gameutils import animate, GameTip + from babase._mgen.enums import SpecialChar + from babase._language import Lstr # If there's any tips left on the list, display one. if self.tips: tip = self.tips.pop(random.randrange(len(self.tips))) tip_title = Lstr(value='${A}:', subs=[('${A}', Lstr(resource='tipText'))]) - icon: ba.Texture | None = None - sound: ba.Sound | None = None + icon: babase.Texture | None = None + sound: babase.Sound | None = None if isinstance(tip, GameTip): icon = tip.icon sound = tip.sound @@ -893,15 +893,15 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): # Do a few replacements. tip_lstr = Lstr(translate=('tips', tip), subs=[('${PICKUP}', - ba.charstr(SpecialChar.TOP_BUTTON))]) + babase.charstr(SpecialChar.TOP_BUTTON))]) base_position = (75, 50) tip_scale = 0.8 tip_title_scale = 1.2 - vrmode = ba.app.vr_mode + vrmode = babase.app.vr_mode if build_number < 21282 else babase.app.env.vr t_offs = -350.0 height_offs = 100.0 - tnode = ba.newnode('text', + tnode = bs.newnode('text', attrs={ 'text': tip_lstr, 'scale': tip_scale, @@ -917,7 +917,7 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): }) t2pos = (base_position[0] + t_offs - (20 if icon is None else 82), base_position[1] + 2 + height_offs) - t2node = ba.newnode('text', + t2node = bs.newnode('text', owner=tnode, attrs={ 'text': tip_title, @@ -933,7 +933,7 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): }) if icon is not None: ipos = (base_position[0] + t_offs - 40, base_position[1] + 1 + height_offs) - img = ba.newnode('image', + img = bs.newnode('image', attrs={ 'texture': icon, 'position': ipos, @@ -945,11 +945,11 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): 'attach': 'bottomCenter' }) animate(img, 'opacity', {0: 0, 1.0: 1, 4.0: 1, 5.0: 0}) - ba.timer(5.0, img.delete) + bs.timer(5.0, img.delete) if sound is not None: - ba.playsound(sound) + sound.play() - combine = ba.newnode('combine', + combine = bs.newnode('combine', owner=tnode, attrs={ 'input0': 1.0, @@ -960,7 +960,7 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): combine.connectattr('output', tnode, 'color') combine.connectattr('output', t2node, 'color') animate(combine, 'input3', {0: 0, 1.0: 1, 4.0: 1, 5.0: 0}) - ba.timer(5.0, tnode.delete) + bs.timer(5.0, tnode.delete) # This function is called when a player leaves the game. # This is only called when the player already joined with a character. @@ -985,7 +985,7 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): player.set_state(PlayerState.ELIMINATED) # This function is called every time a player spawns - def spawn_player(self, player: Player) -> ba.Actor: + def spawn_player(self, player: Player) -> bs.Actor: position = self.map.get_ffa_start_position(self.players) position = (position[0], position[1] - 0.3, # Move the spawn a bit lower @@ -993,8 +993,8 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): name = player.getname() - light_color = ba.normalized_color(player.color) - display_color = ba.safecolor(player.color, target_intensity=0.75) + light_color = babase.normalized_color(player.color) + display_color = babase.safecolor(player.color, target_intensity=0.75) # Here we actually crate the player character spaz = PotatoPlayerSpaz(color=player.color, @@ -1009,20 +1009,20 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): spaz.connect_controls_to_player() # Move to the stand position and add a flash of light - spaz.handlemessage(ba.StandMessage(position, random.uniform(0, 360))) - t = ba.time(ba.TimeType.BASE) - ba.playsound(self._spawn_sound, 1.0, position=spaz.node.position) - light = ba.newnode('light', attrs={'color': light_color}) + spaz.handlemessage(bs.StandMessage(position, random.uniform(0, 360))) + t = bs.time() + self._spawn_sound.play(1.0, position=spaz.node.position) + light = bs.newnode('light', attrs={'color': light_color}) spaz.node.connectattr('position', light, 'position') - ba.animate(light, 'intensity', {0: 0, + bs.animate(light, 'intensity', {0: 0, 0.25: 1, 0.5: 0}) - ba.timer(0.5, light.delete) + bs.timer(0.5, light.delete) # Game reacts to various events def handlemessage(self, msg: Any) -> Any: # This is called if the player dies. - if isinstance(msg, ba.PlayerDiedMessage): + if isinstance(msg, bs.PlayerDiedMessage): super().handlemessage(msg) player = msg.getplayer(Player) @@ -1046,7 +1046,7 @@ class HotPotato(ba.TeamGameActivity[Player, ba.Team]): # Proceed only if the game hasn't ended yet. if self.has_ended(): return - results = ba.GameResults() + results = bs.GameResults() # By this point our match placement list should be filled with all players. # Players that died/left earliest should be the first entries. # We're gonna use array indexes to decide match placements. diff --git a/plugins/minigames/invisible_one.py b/plugins/minigames/invisible_one.py index 3b9bdd8..ad5676c 100644 --- a/plugins/minigames/invisible_one.py +++ b/plugins/minigames/invisible_one.py @@ -1,3 +1,4 @@ +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) # Released under the MIT License. See LICENSE for details. # # By itsre3 @@ -6,39 +7,41 @@ # Besides that, enjoy.......!! """Provides the chosen-one mini-game.""" -# ba_meta require api 7 +# ba_meta require api 8 # (see https://ballistica.net/wiki/meta-tag-system) from __future__ import annotations from typing import TYPE_CHECKING -import ba -from bastd.actor.flag import Flag -from bastd.actor.playerspaz import PlayerSpaz -from bastd.actor.scoreboard import Scoreboard -from bastd.gameutils import SharedObjects +import babase +import bauiv1 as bui +import bascenev1 as bs +from bascenev1lib.actor.flag import Flag +from bascenev1lib.actor.playerspaz import PlayerSpaz +from bascenev1lib.actor.scoreboard import Scoreboard +from bascenev1lib.gameutils import SharedObjects if TYPE_CHECKING: from typing import Any, Type, List, Dict, Optional, Sequence, Union -class Player(ba.Player['Team']): +class Player(bs.Player['Team']): """Our player type for this game.""" def __init__(self) -> None: - self.chosen_light: Optional[ba.NodeActor] = None + self.chosen_light: Optional[bs.NodeActor] = None -class Team(ba.Team[Player]): +class Team(bs.Team[Player]): """Our team type for this game.""" def __init__(self, time_remaining: int) -> None: self.time_remaining = time_remaining -# ba_meta export game -class InvicibleOneGame(ba.TeamGameActivity[Player, Team]): +# ba_meta export bascenev1.GameActivity +class InvicibleOneGame(bs.TeamGameActivity[Player, Team]): """ Game involving trying to remain the one 'invisible one' for a set length of time while everyone else tries to @@ -49,15 +52,15 @@ class InvicibleOneGame(ba.TeamGameActivity[Player, Team]): description = ('Be the invisible one for a length of time to win.\n' 'Kill the invisible one to become it.') available_settings = [ - ba.IntSetting( + bs.IntSetting( 'Invicible One Time', min_value=10, default=30, increment=10, ), - ba.BoolSetting('Invicible one is lazy', default=True), - ba.BoolSetting('Night mode', default=False), - ba.IntChoiceSetting( + bs.BoolSetting('Invicible one is lazy', default=True), + bs.BoolSetting('Night mode', default=False), + bs.IntChoiceSetting( 'Time Limit', choices=[ ('None', 0), @@ -69,7 +72,7 @@ class InvicibleOneGame(ba.TeamGameActivity[Player, Team]): ], default=0, ), - ba.FloatChoiceSetting( + bs.FloatChoiceSetting( 'Respawn Times', choices=[ ('Shorter', 0.25), @@ -80,35 +83,35 @@ class InvicibleOneGame(ba.TeamGameActivity[Player, Team]): ], default=1.0, ), - ba.BoolSetting('Epic Mode', default=False), + bs.BoolSetting('Epic Mode', default=False), ] - scoreconfig = ba.ScoreConfig(label='Time Held') + scoreconfig = bs.ScoreConfig(label='Time Held') @classmethod - def get_supported_maps(cls, sessiontype: Type[ba.Session]) -> List[str]: - return ba.getmaps('keep_away') + def get_supported_maps(cls, sessiontype: Type[bs.Session]) -> List[str]: + return bs.app.classic.getmaps('keep_away') def __init__(self, settings: dict): super().__init__(settings) self._scoreboard = Scoreboard() self._invicible_one_player: Optional[Player] = None - self._swipsound = ba.getsound('swip') - self._countdownsounds: Dict[int, ba.Sound] = { - 10: ba.getsound('announceTen'), - 9: ba.getsound('announceNine'), - 8: ba.getsound('announceEight'), - 7: ba.getsound('announceSeven'), - 6: ba.getsound('announceSix'), - 5: ba.getsound('announceFive'), - 4: ba.getsound('announceFour'), - 3: ba.getsound('announceThree'), - 2: ba.getsound('announceTwo'), - 1: ba.getsound('announceOne') + self._swipsound = bs.getsound('swip') + self._countdownsounds: Dict[int, babase.Sound] = { + 10: bs.getsound('announceTen'), + 9: bs.getsound('announceNine'), + 8: bs.getsound('announceEight'), + 7: bs.getsound('announceSeven'), + 6: bs.getsound('announceSix'), + 5: bs.getsound('announceFive'), + 4: bs.getsound('announceFour'), + 3: bs.getsound('announceThree'), + 2: bs.getsound('announceTwo'), + 1: bs.getsound('announceOne') } self._flag_spawn_pos: Optional[Sequence[float]] = None - self._reset_region_material: Optional[ba.Material] = None + self._reset_region_material: Optional[bs.Material] = None self._flag: Optional[Flag] = None - self._reset_region: Optional[ba.Node] = None + self._reset_region: Optional[bs.Node] = None self._epic_mode = bool(settings['Epic Mode']) self._invicible_one_time = int(settings['Invicible One Time']) self._time_limit = float(settings['Time Limit']) @@ -117,13 +120,13 @@ class InvicibleOneGame(ba.TeamGameActivity[Player, Team]): # Base class overrides self.slow_motion = self._epic_mode - self.default_music = (ba.MusicType.EPIC - if self._epic_mode else ba.MusicType.CHOSEN_ONE) + self.default_music = (bs.MusicType.EPIC + if self._epic_mode else bs.MusicType.CHOSEN_ONE) def get_instance_description(self) -> Union[str, Sequence]: return 'Show your invisibility powers.' - def create_team(self, sessionteam: ba.SessionTeam) -> Team: + def create_team(self, sessionteam: bs.SessionTeam) -> Team: return Team(time_remaining=self._invicible_one_time) def on_team_join(self, team: Team) -> None: @@ -143,13 +146,13 @@ class InvicibleOneGame(ba.TeamGameActivity[Player, Team]): Flag.project_stand(self._flag_spawn_pos) self._set_invicible_one_player(None) if self._night_mode: - gnode = ba.getactivity().globalsnode + gnode = bs.getactivity().globalsnode gnode.tint = (0.4, 0.4, 0.4) pos = self._flag_spawn_pos - ba.timer(1.0, call=self._tick, repeat=True) + bs.timer(1.0, call=self._tick, repeat=True) - mat = self._reset_region_material = ba.Material() + mat = self._reset_region_material = bs.Material() mat.add_actions( conditions=( 'they_have_material', @@ -159,11 +162,11 @@ class InvicibleOneGame(ba.TeamGameActivity[Player, Team]): ('modify_part_collision', 'collide', True), ('modify_part_collision', 'physical', False), ('call', 'at_connect', - ba.WeakCall(self._handle_reset_collide)), + bs.WeakCall(self._handle_reset_collide)), ), ) - self._reset_region = ba.newnode('region', + self._reset_region = bs.newnode('region', attrs={ 'position': (pos[0], pos[1] + 0.75, pos[2]), @@ -185,24 +188,24 @@ class InvicibleOneGame(ba.TeamGameActivity[Player, Team]): # Attempt to get a Player controlling a Spaz that we hit. try: - player = ba.getcollision().opposingnode.getdelegate( + player = bs.getcollision().opposingnode.getdelegate( PlayerSpaz, True).getplayer(Player, True) - except ba.NotFoundError: + except bs.NotFoundError: return if player.is_alive(): self._set_invicible_one_player(player) def _flash_flag_spawn(self) -> None: - light = ba.newnode('light', + light = bs.newnode('light', attrs={ 'position': self._flag_spawn_pos, 'color': (1, 1, 1), 'radius': 0.3, 'height_attenuated': False }) - ba.animate(light, 'intensity', {0: 0, 0.25: 0.5, 0.5: 0}, loop=True) - ba.timer(1.0, light.delete) + bs.animate(light, 'intensity', {0: 0, 0.25: 0.5, 0.5: 0}, loop=True) + bs.timer(1.0, light.delete) def _tick(self) -> None: @@ -212,7 +215,7 @@ class InvicibleOneGame(ba.TeamGameActivity[Player, Team]): # This shouldn't happen, but just in case. if not player.is_alive(): - ba.print_error('got dead player as chosen one in _tick') + babase.print_error('got dead player as chosen one in _tick') self._set_invicible_one_player(None) else: scoring_team = player.team @@ -229,9 +232,7 @@ class InvicibleOneGame(ba.TeamGameActivity[Player, Team]): # announce numbers we have sounds for if scoring_team.time_remaining in self._countdownsounds: - ba.playsound( - self._countdownsounds[scoring_team.time_remaining]) - + self._countdownsounds[scoring_team.time_remaining].play() # Winner! if scoring_team.time_remaining <= 0: self.end_game() @@ -242,11 +243,11 @@ class InvicibleOneGame(ba.TeamGameActivity[Player, Team]): # (Chosen-one player ceasing to exist should # trigger on_player_leave which resets chosen-one) if self._invicible_one_player is not None: - ba.print_error('got nonexistent player as chosen one in _tick') + babase.print_error('got nonexistent player as chosen one in _tick') self._set_invicible_one_player(None) def end_game(self) -> None: - results = ba.GameResults() + results = bs.GameResults() for team in self.teams: results.set_team_score(team, self._invicible_one_time - team.time_remaining) @@ -256,7 +257,7 @@ class InvicibleOneGame(ba.TeamGameActivity[Player, Team]): existing = self._get_invicible_one_player() if existing: existing.chosen_light = None - ba.playsound(self._swipsound) + self._swipsound.play() if not player: assert self._flag_spawn_pos is not None self._flag = Flag(color=(1, 0.9, 0.2), @@ -266,7 +267,7 @@ class InvicibleOneGame(ba.TeamGameActivity[Player, Team]): # Create a light to highlight the flag; # this will go away when the flag dies. - ba.newnode('light', + bs.newnode('light', owner=self._flag.node, attrs={ 'position': self._flag_spawn_pos, @@ -287,18 +288,18 @@ class InvicibleOneGame(ba.TeamGameActivity[Player, Team]): if self._invicible_one_is_lazy: player.actor.connect_controls_to_player( enable_punch=False, enable_pickup=False, enable_bomb=False) - if player.actor.node.torso_model != None: + if player.actor.node.torso_mesh != None: player.actor.node.color_mask_texture = None player.actor.node.color_texture = None - player.actor.node.head_model = None - player.actor.node.torso_model = None - player.actor.node.upper_arm_model = None - player.actor.node.forearm_model = None - player.actor.node.pelvis_model = None - player.actor.node.toes_model = None - player.actor.node.upper_leg_model = None - player.actor.node.lower_leg_model = None - player.actor.node.hand_model = None + player.actor.node.head_mesh = None + player.actor.node.torso_mesh = None + player.actor.node.upper_arm_mesh = None + player.actor.node.forearm_mesh = None + player.actor.node.pelvis_mesh = None + player.actor.node.toes_mesh = None + player.actor.node.upper_leg_mesh = None + player.actor.node.lower_leg_mesh = None + player.actor.node.hand_mesh = None player.actor.node.style = 'cyborg' invi_sound = [] player.actor.node.jump_sounds = invi_sound @@ -311,7 +312,7 @@ class InvicibleOneGame(ba.TeamGameActivity[Player, Team]): player.actor.node.name = '' def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.PlayerDiedMessage): + if isinstance(msg, bs.PlayerDiedMessage): # Augment standard behavior. super().handlemessage(msg) player = msg.getplayer(Player) diff --git a/plugins/minigames/last_punch_stand.py b/plugins/minigames/last_punch_stand.py index 41fe281..75d3a40 100644 --- a/plugins/minigames/last_punch_stand.py +++ b/plugins/minigames/last_punch_stand.py @@ -1,17 +1,20 @@ -# ba_meta require api 7 +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) +# ba_meta require api 8 from typing import Sequence -import ba -import _ba +import babase +import bauiv1 as bui +import bascenev1 as bs +import _babase import random -from bastd.actor.spaz import Spaz -from bastd.actor.scoreboard import Scoreboard +from bascenev1lib.actor.spaz import Spaz +from bascenev1lib.actor.scoreboard import Scoreboard -class Player(ba.Player['Team']): +class Player(bs.Player['Team']): """Our player type for this game.""" -class Team(ba.Team[Player]): +class Team(bs.Team[Player]): """Our team type for this game.""" def __init__(self) -> None: @@ -39,7 +42,7 @@ class ChooseingSpaz(Spaz): super().__init__(color, highlight, "Spaz", None, True, True, False, False) self.last_player_attacked_by = None self.stand(pos) - self.loc = ba.newnode( + self.loc = bs.newnode( 'locator', attrs={ 'shape': 'circleOutline', @@ -51,37 +54,37 @@ class ChooseingSpaz(Spaz): }, ) self.node.connectattr("position", self.loc, "position") - ba.animate_array(self.loc, "size", 1, keys={0: [0.5,], 1: [2,], 1.5: [0.5]}, loop=True) + bs.animate_array(self.loc, "size", 1, keys={0: [0.5,], 1: [2,], 1.5: [0.5]}, loop=True) def handlemessage(self, msg): - if isinstance(msg, ba.FreezeMessage): + if isinstance(msg, bs.FreezeMessage): return - if isinstance(msg, ba.PowerupMessage): + if isinstance(msg, bs.PowerupMessage): if not (msg.poweruptype == "health"): return super().handlemessage(msg) - if isinstance(msg, ba.HitMessage): - self.handlemessage(ba.PowerupMessage("health")) + if isinstance(msg, bs.HitMessage): + self.handlemessage(bs.PowerupMessage("health")) player = msg.get_source_player(Player) if self.is_alive(): self.activity.handlemessage(ChooseingSpazHitMessage(player)) self.last_player_attacked_by = player - elif isinstance(msg, ba.DieMessage): + elif isinstance(msg, bs.DieMessage): player = self.last_player_attacked_by - if msg.how.value != ba.DeathType.GENERIC.value: + if msg.how.value != bs.DeathType.GENERIC.value: self._dead = True self.activity.handlemessage(ChooseingSpazDieMessage(player)) self.loc.delete() def stand(self, pos=(0, 0, 0), angle=0): - self.handlemessage(ba.StandMessage(pos, angle)) + self.handlemessage(bs.StandMessage(pos, angle)) def recolor(self, color, highlight=(1, 1, 1)): self.node.color = color @@ -89,14 +92,14 @@ class ChooseingSpaz(Spaz): self.loc.color = color -class ChooseBilbord(ba.Actor): +class ChooseBilbord(bs.Actor): def __init__(self, player: Player, delay=0.1) -> None: super().__init__() icon = player.get_icon() self.scale = 100 - self.node = ba.newnode( + self.node = bs.newnode( 'image', delegate=self, attrs={ @@ -111,13 +114,13 @@ class ChooseBilbord(ba.Actor): }, ) - self.name_node = ba.newnode( + self.name_node = bs.newnode( 'text', owner=self.node, attrs={ 'position': (60, -185), - 'text': ba.Lstr(value=player.getname()), - 'color': ba.safecolor(player.team.color), + 'text': babase.Lstr(value=player.getname()), + 'color': babase.safecolor(player.team.color), 'h_align': 'center', 'v_align': 'center', 'vr_depth': 410, @@ -128,26 +131,26 @@ class ChooseBilbord(ba.Actor): }, ) - ba.animate_array(self.node, "scale", keys={ + bs.animate_array(self.node, "scale", keys={ 0 + delay: [0, 0], 0.05 + delay: [self.scale, self.scale]}, size=1) - ba.animate(self.name_node, "scale", {0 + delay: 0, 0.07 + delay: 1}) + bs.animate(self.name_node, "scale", {0 + delay: 0, 0.07 + delay: 1}) def handlemessage(self, msg): super().handlemessage(msg) - if isinstance(msg, ba.DieMessage): - ba.animate_array(self.node, "scale", keys={0: self.node.scale, 0.05: [0, 0]}, size=1) - ba.animate(self.name_node, "scale", {0: self.name_node.scale, 0.07: 0}) + if isinstance(msg, bs.DieMessage): + bs.animate_array(self.node, "scale", keys={0: self.node.scale, 0.05: [0, 0]}, size=1) + bs.animate(self.name_node, "scale", {0: self.name_node.scale, 0.07: 0}) def __delete(): self.node.delete() self.name_node.delete() - ba.timer(0.2, __delete) + bs.timer(0.2, __delete) -# ba_meta export game +# ba_meta export bascenev1.GameActivity -class LastPunchStand(ba.TeamGameActivity[Player, Team]): +class LastPunchStand(bs.TeamGameActivity[Player, Team]): name = "Last Punch Stand" description = "Last one punchs the choosing spaz wins" tips = [ @@ -156,11 +159,11 @@ class LastPunchStand(ba.TeamGameActivity[Player, Team]): "evry time you punch the choosing spaz, you will get one point", ] - default_music = ba.MusicType.TO_THE_DEATH + default_music = bs.MusicType.TO_THE_DEATH available_settings = [ - ba.FloatSetting("min time limit (in seconds)", 50.0, min_value=30.0), - ba.FloatSetting("max time limit (in seconds)", 160.0, 60), + bs.FloatSetting("min time limit (in seconds)", 50.0, min_value=30.0), + bs.FloatSetting("max time limit (in seconds)", 160.0, 60), ] @@ -203,12 +206,12 @@ class LastPunchStand(ba.TeamGameActivity[Player, Team]): super().on_begin() time_limit = random.randint(self._min_timelimit, self._max_timelimit) self.spaw_bot() - ba.timer(time_limit, self.times_up) + bs.timer(time_limit, self.times_up) self.setup_standard_powerup_drops(False) def end_game(self) -> None: - results = ba.GameResults() + results = bs.GameResults() for team in self.teams: if self.choosed_player and (team.id == self.choosed_player.team.id): team.score += 100 @@ -261,7 +264,7 @@ class LastPunchStand(ba.TeamGameActivity[Player, Team]): self.spaw_bot() self.change_choosed_player(None) - elif isinstance(msg, ba.PlayerDiedMessage): + elif isinstance(msg, bs.PlayerDiedMessage): player = msg.getplayer(Player) if not (self.has_ended() or self.times_uped): self.respawn_player(player, 0) diff --git a/plugins/minigames/meteor_shower.py b/plugins/minigames/meteor_shower.py index 0f87f39..5cb2f8c 100644 --- a/plugins/minigames/meteor_shower.py +++ b/plugins/minigames/meteor_shower.py @@ -1,4 +1,5 @@ -# ba_meta require api 7 +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) +# ba_meta require api 8 # (see https://ballistica.net/wiki/meta-tag-system) from __future__ import annotations @@ -6,15 +7,17 @@ from __future__ import annotations import random from typing import TYPE_CHECKING -import ba -from bastd.actor.bomb import Bomb -from bastd.actor.onscreentimer import OnScreenTimer +import babase +import bauiv1 as bui +import bascenev1 as bs +from bascenev1lib.actor.bomb import Bomb +from bascenev1lib.actor.onscreentimer import OnScreenTimer if TYPE_CHECKING: from typing import Any, Sequence -lang = ba.app.lang.language +lang = bs.app.lang.language if lang == 'Spanish': name = 'Lluvia de Meteoritos v2' @@ -48,7 +51,7 @@ else: random_rain = 'Random Rain' -class Player(ba.Player['Team']): +class Player(bs.Player['Team']): """Our player type for this game.""" def __init__(self) -> None: @@ -56,18 +59,18 @@ class Player(ba.Player['Team']): self.death_time: float | None = None -class Team(ba.Team[Player]): +class Team(bs.Team[Player]): """Our team type for this game.""" -# ba_meta export game -class MeteorShowerv2Game(ba.TeamGameActivity[Player, Team]): +# ba_meta export bascenev1.GameActivity +class MeteorShowerv2Game(bs.TeamGameActivity[Player, Team]): """Minigame involving dodging falling bombs.""" name = name description = 'Dodge the falling bombs.' - scoreconfig = ba.ScoreConfig( - label='Survived', scoretype=ba.ScoreType.MILLISECONDS, version='B' + scoreconfig = bs.ScoreConfig( + label='Survived', scoretype=bs.ScoreType.MILLISECONDS, version='B' ) # Print messages when players die (since its meaningful in this game). @@ -79,10 +82,10 @@ class MeteorShowerv2Game(ba.TeamGameActivity[Player, Team]): @classmethod def get_available_settings( - cls, sessiontype: type[ba.Session] - ) -> list[ba.Setting]: + cls, sessiontype: type[bs.Session] + ) -> list[babase.Setting]: settings = [ - ba.IntChoiceSetting( + bs.IntChoiceSetting( bomb_type, choices=[ ('normal', 0), @@ -95,22 +98,22 @@ class MeteorShowerv2Game(ba.TeamGameActivity[Player, Team]): ], default=0, ), - ba.BoolSetting('Epic Mode', default=False), + bs.BoolSetting('Epic Mode', default=False), ] return settings # We're currently hard-coded for one map. @classmethod - def get_supported_maps(cls, sessiontype: type[ba.Session]) -> list[str]: + def get_supported_maps(cls, sessiontype: type[bs.Session]) -> list[str]: return ['Rampage'] # We support teams, free-for-all, and co-op sessions. @classmethod - def supports_session_type(cls, sessiontype: type[ba.Session]) -> bool: + def supports_session_type(cls, sessiontype: type[bs.Session]) -> bool: return ( - issubclass(sessiontype, ba.DualTeamSession) - or issubclass(sessiontype, ba.FreeForAllSession) - or issubclass(sessiontype, ba.CoopSession) + issubclass(sessiontype, bs.DualTeamSession) + or issubclass(sessiontype, bs.FreeForAllSession) + or issubclass(sessiontype, bs.CoopSession) ) def __init__(self, settings: dict): @@ -138,7 +141,7 @@ class MeteorShowerv2Game(ba.TeamGameActivity[Player, Team]): # Some base class overrides: self.default_music = ( - ba.MusicType.EPIC if self._epic_mode else ba.MusicType.SURVIVAL + bs.MusicType.EPIC if self._epic_mode else bs.MusicType.SURVIVAL ) if self._epic_mode: self.slow_motion = True @@ -152,19 +155,19 @@ class MeteorShowerv2Game(ba.TeamGameActivity[Player, Team]): delay = 5.0 if len(self.players) > 2 else 2.5 if self._epic_mode: delay *= 0.25 - ba.timer(delay, self._decrement_meteor_time, repeat=True) + bs.timer(delay, self._decrement_meteor_time, repeat=True) # Kick off the first wave in a few seconds. delay = 3.0 if self._epic_mode: delay *= 0.25 - ba.timer(delay, self._set_meteor_timer) + bs.timer(delay, self._set_meteor_timer) self._timer = OnScreenTimer() self._timer.start() # Check for immediate end (if we've only got 1 player, etc). - ba.timer(5.0, self._check_end_game) + bs.timer(5.0, self._check_end_game) def on_player_leave(self, player: Player) -> None: # Augment default behavior. @@ -174,7 +177,7 @@ class MeteorShowerv2Game(ba.TeamGameActivity[Player, Team]): self._check_end_game() # overriding the default character spawning.. - def spawn_player(self, player: Player) -> ba.Actor: + def spawn_player(self, player: Player) -> bs.Actor: spaz = self.spawn_player_spaz(player) # Let's reconnect this player's controls to this @@ -189,12 +192,12 @@ class MeteorShowerv2Game(ba.TeamGameActivity[Player, Team]): # Various high-level game events come through this method. def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.PlayerDiedMessage): + if isinstance(msg, bs.PlayerDiedMessage): # Augment standard behavior. super().handlemessage(msg) - curtime = ba.time() + curtime = bs.time() # Record the player's moment of death. # assert isinstance(msg.spaz.player @@ -204,15 +207,15 @@ class MeteorShowerv2Game(ba.TeamGameActivity[Player, Team]): # (more accurate looking). # In teams/ffa, allow a one-second fudge-factor so we can # get more draws if players die basically at the same time. - if isinstance(self.session, ba.CoopSession): + if isinstance(self.session, bs.CoopSession): # Teams will still show up if we check now.. check in # the next cycle. - ba.pushcall(self._check_end_game) + babase.pushcall(self._check_end_game) # Also record this for a final setting of the clock. self._last_player_death_time = curtime else: - ba.timer(1.0, self._check_end_game) + bs.timer(1.0, self._check_end_game) else: # Default handler: @@ -229,7 +232,7 @@ class MeteorShowerv2Game(ba.TeamGameActivity[Player, Team]): # In co-op, we go till everyone is dead.. otherwise we go # until one team remains. - if isinstance(self.session, ba.CoopSession): + if isinstance(self.session, bs.CoopSession): if living_team_count <= 0: self.end_game() else: @@ -237,7 +240,7 @@ class MeteorShowerv2Game(ba.TeamGameActivity[Player, Team]): self.end_game() def _set_meteor_timer(self) -> None: - ba.timer( + bs.timer( (1.0 + 0.2 * random.random()) * self._meteor_time, self._drop_bomb_cluster, ) @@ -248,10 +251,10 @@ class MeteorShowerv2Game(ba.TeamGameActivity[Player, Team]): # and debug things. loc_test = False if loc_test: - ba.newnode('locator', attrs={'position': (8, 6, -5.5)}) - ba.newnode('locator', attrs={'position': (8, 6, -2.3)}) - ba.newnode('locator', attrs={'position': (-7.3, 6, -5.5)}) - ba.newnode('locator', attrs={'position': (-7.3, 6, -2.3)}) + bs.newnode('locator', attrs={'position': (8, 6, -5.5)}) + bs.newnode('locator', attrs={'position': (8, 6, -2.3)}) + bs.newnode('locator', attrs={'position': (-7.3, 6, -5.5)}) + bs.newnode('locator', attrs={'position': (-7.3, 6, -2.3)}) # Drop several bombs in series. delay = 0.0 @@ -269,7 +272,7 @@ class MeteorShowerv2Game(ba.TeamGameActivity[Player, Team]): random.uniform(-3.066, -4.12), 0, ) - ba.timer(delay, ba.Call(self._drop_bomb, pos, vel)) + bs.timer(delay, babase.Call(self._drop_bomb, pos, vel)) delay += 0.1 self._set_meteor_timer() @@ -294,7 +297,7 @@ class MeteorShowerv2Game(ba.TeamGameActivity[Player, Team]): self._meteor_time = max(0.01, self._meteor_time * 0.9) def end_game(self) -> None: - cur_time = ba.time() + cur_time = bs.time() assert self._timer is not None start_time = self._timer.getstarttime() @@ -325,7 +328,7 @@ class MeteorShowerv2Game(ba.TeamGameActivity[Player, Team]): # Ok now calc game results: set a score for each team and then tell # the game to end. - results = ba.GameResults() + results = bs.GameResults() # Remember that 'free-for-all' mode is simply a special form # of 'teams' mode where each player gets their own team, so we can @@ -346,58 +349,58 @@ class MeteorShowerv2Game(ba.TeamGameActivity[Player, Team]): # ba_meta export plugin -class MeteorShowerv2Coop(ba.Plugin): +class MeteorShowerv2Coop(babase.Plugin): def on_app_running(self) -> None: - ba.app.add_coop_practice_level( - ba.Level( + babase.app.classic.add_coop_practice_level( + bs._level.Level( normal_rain, gametype=MeteorShowerv2Game, settings={bomb_type: 0}, preview_texture_name='rampagePreview', ) ) - ba.app.add_coop_practice_level( - ba.Level( + babase.app.classic.add_coop_practice_level( + bs._level.Level( frozen_rain, gametype=MeteorShowerv2Game, settings={bomb_type: 1}, preview_texture_name='rampagePreview', ) ) - ba.app.add_coop_practice_level( - ba.Level( + babase.app.classic.add_coop_practice_level( + bs._level.Level( sticky_rain, gametype=MeteorShowerv2Game, settings={bomb_type: 2}, preview_texture_name='rampagePreview', ) ) - ba.app.add_coop_practice_level( - ba.Level( + babase.app.classic.add_coop_practice_level( + bs._level.Level( impact_rain, gametype=MeteorShowerv2Game, settings={bomb_type: 3}, preview_texture_name='rampagePreview', ) ) - ba.app.add_coop_practice_level( - ba.Level( + babase.app.classic.add_coop_practice_level( + bs._level.Level( mine_rain, gametype=MeteorShowerv2Game, settings={bomb_type: 4}, preview_texture_name='rampagePreview', ) ) - ba.app.add_coop_practice_level( - ba.Level( + babase.app.classic.add_coop_practice_level( + bs._level.Level( tnt_rain, gametype=MeteorShowerv2Game, settings={bomb_type: 5}, preview_texture_name='rampagePreview', ) ) - ba.app.add_coop_practice_level( - ba.Level( + babase.app.classic.add_coop_practice_level( + bs._level.Level( random_rain, gametype=MeteorShowerv2Game, settings={bomb_type: 6}, diff --git a/plugins/minigames/port_7_to_8.py b/plugins/minigames/port_7_to_8.py new file mode 100644 index 0000000..1a8c94e --- /dev/null +++ b/plugins/minigames/port_7_to_8.py @@ -0,0 +1,441 @@ +# Usage: port_7_to_8.py + +# You'll have to manually update the following: +# with ba.Context(_ba.foreground_host_activity()): +# To: +# with _ba.foreground_host_activity().context: +# +# ba.time(timeformat=ba.TimeFormat.MILLISECONDS) +# To: +# ba.time() * 1000 +# +# ba.Timer((POWERUP_WEAR_OFF_TIME - 2000),ba.WeakCall(self._multi_bomb_wear_off_flash),timeformat=ba.TimeFormat.MILLISECONDS) +# To: +# ba.Timer((POWERUP_WEAR_OFF_TIME - 2000 / 1000),ba.WeakCall(self._multi_bomb_wear_off_flash)) + +import re +import sys +import codecs + +def detect_encoding(filename): + encodings = ['utf-8', 'latin-1', 'ascii', 'cp1252'] + for encoding in encodings: + try: + with open(filename, 'rb') as f: + f.read().decode(encoding) + return encoding + except UnicodeDecodeError: + pass + return None + +filename = sys.argv[2] +encoding = detect_encoding(filename) +if encoding: + with open(filename, 'r', encoding=encoding) as f: + print("Porting "+ sys.argv[2]) + content = f.read() +else: + print('Could not detect encoding') + +content = content.replace("# ba_meta require api 7", "# ba_meta require api 8") +content = content.replace("# ba_meta export game", "# ba_meta export bascenev1.GameActivity") + + +content = content.replace("user_agent_string", "legacy_user_agent_string") +content = re.sub(r'^(import\s+[\w]+(\s*,\s*[\w]+)+)', lambda match: re.sub(r'\s*,\s*', '\nimport ', match.group()), content, flags=re.MULTILINE) +content = content.replace("_ba.", "_babase.") +content = content.replace("_ba.", "_babase.") +content = content.replace("ba.", "babase.") +content = content.replace("import _ba", "import _babase") +content = content.replace("from ba import", "from babase import") +content = content.replace("from _ba import", "from _babase import") +content = re.sub(r'\bimport _ba\b', "import _babase", content) +content = re.sub(r'\bimport ba(\b|\.(\w+))', "import babase\nimport bauiv1\nimport bascenev1", content) +match = re.search(r'^(import\s+[\w]+(\s*,\s*[\w]+)*)', content, flags=re.MULTILINE) +affected_methods = ["build_number", "device_name", "config_file_path", "version", "debug_build", "test_build", "data_directory", "python_directory_user", "python_directory_app", "python_directory_app_site", "api_version", "on_tv", "vr_mode","toolbar_test", "arcade_test", "headless_mode", "demo_mode", "protocol_version", "get_connection_to_host_info"] +for word in affected_methods: + if f".{word}" in content: + first_import_index = match.start() + content = content[:first_import_index] + 'from baenv import TARGET_BALLISTICA_BUILD as build_number\n' + content[first_import_index:] +content = content.replace("babase.app.ui", "bauiv1.app.ui_v1") +content = content.replace("babase.app.accounts_v1", "bauiv1.app.classic.accounts") + +################################################################################### +# Comment out one of these as per your requirements, depending whether to +# stay local or if it'll also be needed to transmitted to the clients. + +## For local: +if sys.argv[1] == "client": + content = content.replace("_babase.screenmessage", "bauiv1.screenmessage") + content = content.replace("babase.screenmessage", "bauiv1.screenmessage") + content = content.replace("babase.getsound", "bauiv1.getsound") + content = content.replace("_babase.gettexture", "bauiv1.gettexture") + content = content.replace("babase.gettexture", "bauiv1.gettexture") + content = content.replace("babase.getmesh", "bauiv1.getmesh") + content = content.replace("babase.getcollisionmesh", "bauiv1.getcollisionmesh") +else: +## For transmission: + content = content.replace("_babase.screenmessage", "bascenev1.broadcastmessage") + content = content.replace("babase.screenmessage", "bascenev1.broadcastmessage") + content = content.replace("babase.getsound", "bascenev1.getsound") + content = content.replace("_babase.gettexture", "bascenev1.gettexture") + content = content.replace("babase.gettexture", "bascenev1.gettexture") + content = content.replace("babase.getmesh", "bascenev1.getmesh") + content = content.replace("babase.getcollisionmesh", "bascenev1.getcollisionmesh") +################################################################################### +content = content.replace("babase.getcollidemesh", "bascenev1.getcollisionmesh") +content = content.replace("collide_mesh", "collision_mesh") +content = content.replace("babase.open_url", "bauiv1.open_url") +content = content.replace("babase.IntSetting", "bascenev1.IntSetting") +content = content.replace("babase.IntChoiceSetting", "bascenev1.IntChoiceSetting") +content = content.replace("babase.FloatChoiceSetting", "bascenev1.FloatChoiceSetting") +content = content.replace("babase.BoolSetting", "bascenev1.BoolSetting") +content = content.replace("babase.Actor", "bascenev1.Actor") +content = content.replace("babase.Player", "bascenev1.Player") +content = content.replace("babase.PlayerDiedMessage", "bascenev1.PlayerDiedMessage") +content = content.replace("babase.time", "bascenev1.time") +content = content.replace("babase.Timer", "bascenev1.Timer") +content = content.replace("babase.newnode", "bascenev1.newnode") +content = content.replace("babase.Node", "bascenev1.Node") +content = content.replace("babase.emitfx", "bascenev1.emitfx") +content = content.replace("babase.animate", "bascenev1.animate") +content = content.replace("babase.FreeForAllSession", "bascenev1.FreeForAllSession") +content = content.replace("babase.DualTeamSession", "bascenev1.DualTeamSession") +content = content.replace("babase.MultiTeamSession", "bascenev1.MultiTeamSession") +content = content.replace("babase.EndSession", "bascenev1.EndSession") +content = content.replace("babase.CoopSession", "bascenev1.CoopSession") +content = content.replace("babase.TeamGameActivity", "bascenev1.TeamGameActivity") +content = content.replace("babase.Team", "bascenev1.Team") +content = content.replace("babase.Session", "bascenev1.Session") +content = content.replace("babase.getsession", "bascenev1.getsession") +content = content.replace("babase.Material", "bascenev1.Material") +content = content.replace("babase.WeakCall", "bascenev1.WeakCall") +content = content.replace("babase.DieMessage", "bascenev1.DieMessage") +content = content.replace("babase.OutOfBoundsMessage", "bascenev1.OutOfBoundsMessage") +content = content.replace("babase.DroppedMessage", "bascenev1.DroppedMessage") +content = content.replace("babase.HitMessage", "bascenev1.HitMessage") +content = content.replace("babase.ThawMessage", "bascenev1.ThawMessage") +content = content.replace("babase.NotFoundError", "bascenev1.NotFoundError") +content = content.replace("babase.getcollision", "bascenev1.getcollision") +content = content.replace("babase.app.lang", "bascenev1.app.lang") +content = content.replace("babase.MusicType", "bascenev1.MusicType") +content = content.replace("babase.getactivity", "bascenev1.getactivity") +content = content.replace("babase.getactivity", "bascenev1.getactivity") +content = content.replace("babase.CelebrateMessage", "bascenev1.CelebrateMessage") +content = content.replace("babase.ScoreConfig", "bascenev1.ScoreConfig") +content = content.replace("babase.ScoreType", "bascenev1.ScoreType") +content = content.replace("babase.GameResults", "bascenev1.GameResults") +content = content.replace("babase.getmaps", "bascenev1.app.classic.getmaps") +content = content.replace("babase.cameraflash", "bascenev1.cameraflash") +content = content.replace("babase.getmodel", "bascenev1.getmesh") +content = content.replace("babase.Map", "bascenev1.Map") +content = content.replace("babase.DeathType", "bascenev1.DeathType") +content = content.replace("babase.GameActivity", "bascenev1.GameActivity") +content = content.replace("_babase.app.stress_test_reset_timer", "_babase.app.classic.stress_test_reset_timer") +content = content.replace("babase.app.stress_test_reset_timer", "_babase.app.classic.stress_test_reset_timer") +content = content.replace("babase._map", "bascenev1._map") +content = content.replace("babase._session.", "bascenev1._session.") +content = content.replace("babase._activity", "bascenev1._activity") +content = content.replace("_babase.get_client_public_device_uuid", "_bascenev1.get_client_public_device_uuid") +content = content.replace("babase.PickedUpMessage", "bascenev1.PickedUpMessage") +content = content.replace("babase.PowerupMessage", "bascenev1.PowerupMessage") +content = content.replace("babase.FreezeMessage", "bascenev1.FreezeMessage") +content = content.replace("with babase.ContextRef(activity):", "with activity.context:") +content = content.replace("babase.Context", "babase.ContextRef") +content = content.replace("babase._dualteamsession", "bascenev1._dualteamsession") +content = content.replace("babase._freeforallsession", "bascenev1._freeforallsession") +content = content.replace("babase._multiteamsession", "bascenev1._multiteamsession") +content = content.replace("babase._gameactivity", "bascenev1._gameactivity") +content = content.replace("babase._powerup", "bascenev1._powerup") +content = content.replace("babase.Chooser", "bascenev1.Chooser") +content = content.replace("babase._lobby", "bascenev1._lobby") +content = content.replace("babase._stats", "bascenev1._stats") +content = content.replace("babase._team", "bascenev1._team") +content = content.replace("PlayerType", "PlayerT") +content = content.replace("babase.app.spaz_appearances", "babase.app.classic.spaz_appearances") +content = content.replace("babase._coopsession", "bascenev1._coopsession") +content = content.replace("babase._servermode", "baclassic._servermode") +content = content.replace("_babase.app.server", "babase.app.classic.server") +content = content.replace("_babase.chatmessage", "bascenev1.chatmessage") +content = content.replace("_babase.disconnect_client", "_bascenev1.disconnect_client") +content = content.replace("_babase.get_game_roster", "bascenev1.get_game_roster") +content = content.replace("_babase.get_public_party_max_size", "bascenev1.get_public_party_max_size") +content = content.replace("_babase.new_host_session", "bascenev1.new_host_session") +content = content.replace("babase._playlist", "bascenev1._playlist") +content = content.replace("model", "mesh") +content = content.replace("TimeType.REAL", "use `bascenev1.apptimer` in `activity.context` instead") +content = content.replace("_babase.app.coop_session_args", "babase.app.classic.coop_session_args") +content = content.replace("_babase.app.campaigns", "babase.app.classic.campaigns") + +content = content.replace("_babase.newactivity", "bascenev1.newactivity") +content = content.replace("babase.Window", "bauiv1.Window") +content = content.replace("babase.Widget", "bauiv1.Widget") +content = content.replace("babase.widget", "bauiv1.widget") +content = content.replace("babase.containerwidget", "bauiv1.containerwidget") +content = content.replace("babase.scrollwidget", "bauiv1.scrollwidget") +content = content.replace("babase.buttonwidget", "bauiv1.buttonwidget") +content = content.replace("babase.textwidget", "bauiv1.textwidget") +content = content.replace("babase.checkboxwidget", "bauiv1.checkboxwidget") +content = content.replace("babase.imagewidget", "bauiv1.imagewidget") +content = content.replace("babase.uicleanupcheck", "bauiv1.uicleanupcheck") +content = content.replace("_babase.set_public_party_max_size", "bascenev1.set_public_party_max_size") +content = content.replace("_bauiv1", "bauiv1") +content = content.replace("babase.show_damage_count", "bascenev1.show_damage_count") +content = content.replace("babase._gameutils", "bascenev1._gameutils") +content = content.replace("babase.StandMessage", "bascenev1.StandMessage") +content = content.replace("babase.PowerupAcceptMessage", "bascenev1.PowerupAcceptMessage") +content = content.replace("babase._gameutils", "bascenev1._gameutils") +content = content.replace("babase.camerashake", "bascenev1.camerashake") +content = content.replace("babase.app.add_coop_practice_level", "babase.app.classic.add_coop_practice_level") +content = content.replace("babase._campaign", "bascenev1._campaign") +content = content.replace("babase.Level", "bascenev1._level.Level") +content = content.replace("babase.app.cloud.send_message_cb", "bauiv1.app.plus.cloud.send_message_cb") +content = content.replace("_babase.get_special_widget", "bauiv1.get_special_widget") + +content = content.replace(".app.platform", ".app.classic.platform") +content = content.replace(".app.subplatform", ".app.classic.subplatform") +content = content.replace(".getlog", ".get_v1_cloud_log") +# Converting `ba.playsound(abc)` to `abc.play()` is tricky. +# Do it manually in case regex substitution fails.# Do it manually in case regex substitution fails. Are you sure!! +#! FIXME May cause syntax warning on 3.12 +content = re.sub( + r'babase\.playsound\(\s*([^,\n]+),\s*([^,\n]+)\)', + r'\1.play(\2)', + content, + flags=re.MULTILINE +) +content = re.sub( + r'babase\.playsound\(\s*([^,\n]+),\s*([^,\n]+),\s*position=([^,\n]+)\)', + r'\1.play(\2, position=\3)', + content, + flags=re.MULTILINE +) +content = re.sub("babase\.playsound\((.+?), (.+?), (.+?)\)", "\\1.play(\\2, \\3)", content) +content = re.sub( + r'babase\.playsound\(([^,\n]+),\s*position=([^,\n]+)\)', + r'\1.play(position=\2)', + content +) +content = re.sub("babase\.playsound\((.*)\)", "\\1.play()", content) + +content = content.replace("babase.internal.add_transaction", "bauiv1.app.plus.add_v1_account_transaction") +content = content.replace("babase.internal.run_transaction", "bauiv1.app.plus.run_v1_account_transaction") +content = content.replace("_babase.add_transaction", "bauiv1.app.plus.add_v1_account_transaction") +content = content.replace("_babase.run_transactions", "bauiv1.app.plus.run_v1_account_transactions") +content = content.replace("babase._store.get_store_layout", "bauiv1.app.classic.store.get_store_layout") +content = content.replace("babase.internal.get_store_layout", "bauiv1.app.classic.store.get_store_layout") +content = content.replace("babase.internal.connect_to_party", "bascenev1.connect_to_party") +content = content.replace("babase.internal.get_default_powerup_distribution", "bascenev1._powerup.get_default_powerup_distribution") +content = content.replace("babase.internal.DEFAULT_REQUEST_TIMEOUT_SECONDS", "babase.DEFAULT_REQUEST_TIMEOUT_SECONDS") +content = content.replace("babase.internal.DEFAULT_TEAM_COLORS", "bascenev1.DEFAULT_TEAM_COLORS") +content = content.replace("babase.internal.DEFAULT_TEAM_NAMES", "bascenev1.DEFAULT_TEAM_NAMES") +content = content.replace("babase.internal.JoinActivity", "bascenev1.JoinActivity") +content = content.replace("babase.internal.LoginAdapter", "babase._login.LoginAdapter") +content = content.replace("babase.internal.PlayerProfilesChangedMessage", "bascenev1._messages.PlayerProfilesChangedMessage") +content = content.replace("babase.internal.ScoreScreenActivity", "bascenev1.ScoreScreenActivity") +content = content.replace("babase.internal.add_clean_frame_callback", "babase.add_clean_frame_callback") +content = content.replace("babase.internal.android_get_external_files_dir", "babase.android_get_external_files_dir") +content = content.replace("babase.internal.appname", "babase.appname") +content = content.replace("babase.internal.appnameupper", "babase.appnameupper") +content = content.replace("babase.internal.capture_gamepad_input", "bascenev1.capture_gamepad_input") +content = content.replace("babase.internal.capture_keyboard_input", "bascenev1.capture_keyboard_input") +content = content.replace("babase.internal.charstr", "babase.charstr") +content = content.replace("babase.internal.chatmessage", "bascenev1.chatmessage") +content = content.replace("babase.internal.commit_app_config", "bauiv1.commit_app_config") +content = content.replace("babase.internal.disconnect_client", "bascenev1.disconnect_client") +content = content.replace("babase.internal.disconnect_from_host", "bascenev1.disconnect_from_host") +content = content.replace("babase.internal.do_play_music", "babase.app.classic.music.do_play_music") +content = content.replace("babase.internal.end_host_scanning", "bascenev1.end_host_scanning") +content = content.replace("babase.internal.fade_screen", "bauiv1.fade_screen") +content = content.replace("babase.internal.filter_playlist", "bascenev1.filter_playlist") +content = content.replace("babase.internal.game_service_has_leaderboard", "_baplus.game_service_has_leaderboard") +content = content.replace("babase.internal.get_available_purchase_count", "bauiv1.app.classic.store.get_available_purchase_count") +content = content.replace("babase.internal.get_available_sale_time", "bauiv1.app.classic.store.get_available_sale_time") +content = content.replace("babase.internal.get_chat_messages", "bascenev1.get_chat_messages") +content = content.replace("babase.internal.get_clean_price", "bauiv1.app.classic.store.get_clean_price") +content = content.replace("babase.internal.get_connection_to_host_info", "bascenev1.get_connection_to_host_info_2") +content = content.replace("babase.internal.get_default_free_for_all_playlist", "bascenev1._playlist.get_default_free_for_all_playlist") +content = content.replace("babase.internal.get_default_teams_playlist", "bascenev1._playlist.get_default_teams_playlist") +content = content.replace("babase.internal.get_display_resolution", "babase.get_display_resolution") +content = content.replace("babase.internal.get_filtered_map_name", "bascenev1._map.get_filtered_map_name") +content = content.replace("babase.internal.get_foreground_host_session", "bascenev1.get_foreground_host_session") +content = content.replace("babase.internal.get_game_port", "bascenev1.get_game_port") +content = content.replace("babase.internal.get_game_roster", "bascenev1.get_game_roster") +content = content.replace("babase.internal.get_input_device_config", "bauiv1.app.classic.get_input_device_config") +content = content.replace("babase.internal.get_ip_address_type", "babase.get_ip_address_type") +content = content.replace("babase.internal.get_local_active_input_devices_count", "bascenev1.get_local_active_input_devices_count") +content = content.replace("babase.internal.get_low_level_config_value", "bauiv1.get_low_level_config_value") +content = content.replace("babase.internal.get_map_class", "bascenev1.get_map_class") +content = content.replace("babase.internal.get_map_display_string", "bascenev1.get_map_display_string") +content = content.replace("babase.internal.get_master_server_address", "bauiv1.app.plus.get_master_server_address") +content = content.replace("babase.internal.get_max_graphics_quality", "babase.get_max_graphics_quality") +content = content.replace("babase.internal.get_news_show", "_babase.app.plus.get_news_show") +content = content.replace("babase.internal.get_next_tip", "bascenev1.app.classic.get_next_tip") +content = content.replace("babase.internal.get_player_colors", "bascenev1.get_player_colors") +content = content.replace("babase.internal.get_player_profile_colors", "bascenev1.get_player_profile_colors") +content = content.replace("babase.internal.get_player_profile_icon", "bascenev1.get_player_profile_icon") +content = content.replace("babase.internal.get_price", "bauiv1.app.plus.get_price") +content = content.replace("babase.internal.get_public_party_enabled", "bascenev1.get_public_party_enabled") +content = content.replace("babase.internal.get_public_party_max_size", "bascenev1.get_public_party_max_size") +content = content.replace("babase.internal.get_purchased", "bauiv1.app.plus.get_purchased") +content = content.replace("babase.internal.get_purchases_state", "_baplus.get_purchases_state") +content = content.replace("babase.internal.get_qrcode_texture", "bauiv1.get_qrcode_texture") +content = content.replace("babase.internal.get_random_names", "bascenev1.get_random_names") +content = content.replace("babase.internal.get_remote_app_name", "bascenev1.get_remote_app_name") +content = content.replace("babase.internal.get_replay_speed_exponent", "bascenev1.get_replay_speed_exponent") +content = content.replace("babase.internal.get_replays_dir", "babase.get_replays_dir") +content = content.replace("babase.internal.get_special_widget", "bauiv1.get_special_widget") +content = content.replace("babase.internal.get_store_item", "babase.app.classic.store.get_store_item") +content = content.replace("babase.internal.get_store_item_display_size", "babase.app.classic.store.get_store_item_display_size") +content = content.replace("babase.internal.get_store_item_name_translated", "babase.app.classic.store.get_store_item_name_translated") +content = content.replace("babase.internal.get_string_height", "babase.get_string_height") +content = content.replace("babase.internal.get_string_width", "babase.get_string_width") +content = content.replace("babase.internal.get_tournament_prize_strings", "bascenev1.app.classic.get_tournament_prize_strings") +content = content.replace("babase.internal.get_trophy_string", "bascenev1.get_trophy_string") +content = content.replace("babase.internal.get_type_name", "babase.get_type_name") +content = content.replace("babase.internal.get_ui_input_device", "bascenev1.get_ui_input_device") +content = content.replace("babase.internal.get_unowned_game_types", "babase.app.classic.store.get_unowned_game_types") +content = content.replace("babase.internal.get_unowned_maps", "babase.app.classic.store.get_unowned_maps") +content = content.replace("babase.internal.get_v1_account_display_string", "bauiv1.app.plus.get_v1_account_display_string") +content = content.replace("babase.internal.get_v1_account_misc_read_val", "bauiv1.app.plus.get_v1_account_misc_read_val") +content = content.replace("babase.internal.get_v1_account_misc_read_val_2", "bauiv1.app.plus.get_v1_account_misc_read_val_2") +content = content.replace("babase.internal.get_v1_account_misc_val", "bauiv1.app.plus.get_v1_account_misc_val") +content = content.replace("babase.internal.get_v1_account_name", "bauiv1.app.plus.get_v1_account_name") +content = content.replace("babase.internal.get_v1_account_state", "bauiv1.app.plus.get_v1_account_state") +content = content.replace("babase.internal.get_v1_account_state_num", "bauiv1.app.plus.get_v1_account_state_num") +content = content.replace("babase.internal.get_v1_account_ticket_count", "bauiv1.app.plus.get_v1_account_ticket_count") +content = content.replace("babase.internal.get_v1_account_type", "bauiv1.app.plus.get_v1_account_type") +content = content.replace("babase.internal.get_v2_fleet", "_baplus.get_v2_fleet") +content = content.replace("babase.internal.getcampaign", "bauiv1.app.classic.getcampaign") +content = content.replace("babase.internal.getclass", "babase.getclass") +content = content.replace("babase.internal.getinputdevice", "bascenev1.getinputdevice") +content = content.replace("babase.internal.has_gamma_control", "babase.has_gamma_control") +content = content.replace("babase.internal.has_video_ads", "bauiv1.has_video_ads") +content = content.replace("babase.internal.have_incentivized_ad", "bauiv1.have_incentivized_ad") +content = content.replace("babase.internal.have_permission", "babase.have_permission") +content = content.replace("babase.internal.have_touchscreen_input", "bascenev1.have_touchscreen_input") +content = content.replace("babase.internal.host_scan_cycle", "bascenev1.host_scan_cycle") +content = content.replace("babase.internal.in_game_purchase", "bui.app.plus.in_game_purchase") +content = content.replace("babase.internal.increment_analytics_count", "babase.increment_analytics_count") +content = content.replace("babase.internal.is_blessed", "bui.app.plus.is_blessed") +content = content.replace("babase.internal.is_browser_likely_available", "bauiv1.is_browser_likely_available") +content = content.replace("babase.internal.is_in_replay", "bascenev1.is_in_replay") +content = content.replace("babase.internal.is_party_icon_visible", "bauiv1.is_party_icon_visible") +content = content.replace("babase.internal.is_running_on_fire_tv", "babase.is_running_on_fire_tv") +content = content.replace("babase.internal.is_xcode_build", "babase.is_xcode_build") +content = content.replace("babase.internal.json_prep", "babase.json_prep") +content = content.replace("babase.internal.lock_all_input", "babase.lock_all_input") +content = content.replace("babase.internal.mark_config_dirty", "_babase.app.plus.mark_config_dirty") +content = content.replace("babase.internal.new_host_session", "bascenev1.new_host_session") +content = content.replace("babase.internal.new_replay_session", "bascenev1.new_replay_session") +content = content.replace("babase.internal.open_file_externally", "bauiv1.open_file_externally") +content = content.replace("babase.internal.power_ranking_query", "_baplus.power_ranking_query") +content = content.replace("babase.internal.preload_map_preview_media", "bauiv1.app.classic.preload_map_preview_media") +content = content.replace("babase.internal.purchase", "_baplus.purchase") +content = content.replace("babase.internal.register_map", "bascenev1.register_map") +content = content.replace("babase.internal.release_gamepad_input", "bascenev1.release_gamepad_input") +content = content.replace("babase.internal.release_keyboard_input", "bascenev1.release_keyboard_input") +content = content.replace("babase.internal.report_achievement", "babase.app.plus.report_achievement") +content = content.replace("babase.internal.request_permission", "babase.request_permission") +content = content.replace("babase.internal.reset_achievements", "_baplus.reset_achievements") +content = content.replace("babase.internal.reset_random_player_names", "bascenev1.reset_random_player_names") +content = content.replace("babase.internal.restore_purchases", "_baplus.restore_purchases") +content = content.replace("babase.internal.run_cpu_benchmark", "baclassic._benchmark.run_cpu_benchmark") +content = content.replace("babase.internal.run_gpu_benchmark", "baclassic._benchmark.run_gpu_benchmark") +content = content.replace("babase.internal.run_media_reload_benchmark", "baclassic._benchmark.run_media_reload_benchmark") +content = content.replace("babase.internal.run_stress_test", "babase.app.classic.run_stress_test") +content = content.replace("babase.internal.set_authenticate_clients", "bascenev1.set_authenticate_clients") +content = content.replace("babase.internal.set_debug_speed_exponent", "bascenev1.set_debug_speed_exponent") +content = content.replace("babase.internal.set_low_level_config_value", "babase.set_low_level_config_value") +content = content.replace("babase.internal.set_party_icon_always_visible", "bauiv1.set_party_icon_always_visible") +content = content.replace("babase.internal.set_party_window_open", "bauiv1.set_party_window_open") +content = content.replace("babase.internal.set_public_party_enabled", "bascenev1.set_public_party_enabled") +content = content.replace("babase.internal.set_public_party_max_size", "bascenev1.set_public_party_max_size") +content = content.replace("babase.internal.set_public_party_name", "bascenev1.set_public_party_name") +content = content.replace("babase.internal.set_public_party_queue_enabled", "bascenev1.set_public_party_queue_enabled") +content = content.replace("babase.internal.set_replay_speed_exponent", "bascenev1.set_replay_speed_exponent") +content = content.replace("babase.internal.set_touchscreen_editing", "bascenev1.set_touchscreen_editing") +content = content.replace("babase.internal.set_ui_input_device", "babase.set_ui_input_device") +content = content.replace("babase.internal.should_submit_debug_info", "babase._apputils.should_submit_debug_info") +content = content.replace("babase.internal.show_online_score_ui", "bauiv1.show_online_score_ui") +content = content.replace("babase.internal.sign_in_v1", "babase.app.plus.sign_in_v1") +content = content.replace("babase.internal.sign_out_v1", "babase.app.plus.sign_out_v1") +content = content.replace("babase.internal.submit_score", "bascenev1.app.plus.submit_score") +content = content.replace("babase.internal.tournament_query", "_baplus.tournament_query") +content = content.replace("babase.internal.unlock_all_input", "babase.unlock_all_input") +content = content.replace("babase.internal.value_test", "bauiv1.app.classic.value_test") +content = content.replace("babase.internal.workspaces_in_use", "babase.workspaces_in_use") +content = content.replace("babase.internal.dump_tracebacks", "babase._apputils.dump_app_state") +content = content.replace("babase.internal.show_app_invite", "_bauiv1.show_app_invite") +content = content.replace("babase._generated", "babase._mgen") +content = content.replace("_babase.disconnect_from_host", "bascenev1.disconnect_from_host") +content = content.replace("babase.disconnect_from_host", "bascenev1.disconnect_from_host") +content = content.replace("_babase.connect_to_party", "bascenev1.connect_to_party") +content = content.replace("babase.connect_to_party", "bascenev1.connect_to_party") +content = content.replace("babase.set_party_window_open", "bauiv1.set_party_window_open") +content = content.replace("babase.set_party_window_open", "bauiv1.set_party_window_open") +content = content.replace("babase.getcollidemesh", "bascenev1.getcollisionmesh") +content = content.replace("collide_mesh", "collision_mesh") +content = content.replace("babase.FloatSetting", "bascenev1.FloatSetting") +# Removed in API 8: +# content = content.replace("babase.internal.set_telnet_access_enabled", "") + +content = content.replace("babase.internal.master_server_get", "babase.app.classic.master_server_v1_get") +content = content.replace("babase.internal.master_server_post", "babase.app.classic.master_server_v1_post") +content = content.replace("babase.internal.log_dumped_tracebacks", "babase._apputils.log_dumped_app_state") +content = content.replace("babase.internal.have_outstanding_transactions", "bauiv1.app.plus.have_outstanding_v1_account_transactions") +content = content.replace("babase.internal.get_public_login_id", "bauiv1.app.plus.get_v1_account_public_login_id") +content = content.replace("babase.internal.get_input_map_hash", "bauiv1.app.classic.get_input_device_map_hash") +content = content.replace("babase.internal.get_device_value", "bauiv1.app.classic.get_input_device_mapped_value") + +# Depracations +content = content.replace("babase.app.build_number", "babase.app.build_number if build_number < 21282 else babase.app.env.build_number") +content = content.replace("babase.app.device_name", "babase.app.device_name if build_number < 21282 else babase.app.env.device_name") +content = content.replace("babase.app.config_file_path", "babase.app.config_file_path if build_number < 21282 else babase.app.env.config_file_path") +content = content.replace("babase.app.version", "babase.app.version if build_number < 21282 else babase.app.env") +content = content.replace("babase.app.debug_build", "babase.app.debug_build if build_number < 21282 else babase.app.env.debug_build") +content = content.replace("babase.app.test_build", "babase.app.test_build if build_number < 21282 else babase.app.env.test_build") +content = content.replace("babase.app.data_directory", "babase.app.data_directory if build_number < 21282 else babase.app.env.data_directory") +content = content.replace("babase.app.python_directory_user", "babase.app.python_directory_user if build_number < 21282 else babase.app.env.python_directory_user") +content = content.replace("babase.app.python_directory_app", "babase.app.env") +content = content.replace("babase.app.python_directory_app_site", "babase.app.python_directory_app_site if build_number < 21282 else babase.app.env.python_directory_app_site") +content = content.replace("babase.app.api_version", "babase.app.api_version if build_number < 21282 else babase.app.env.api_version") +content = content.replace("babase.app.on_tv", "babase.app.on_tv if build_number < 21282 else babase.app.env.on_tv") +content = content.replace("babase.app.vr_mode", "babase.app.vr_mode if build_number < 21282 else babase.app.env.vr") +content = content.replace("babase.app.toolbar_test", "babase.app.toolbar_test if build_number < 21282 else babase.app.env.toolbar_test") +content = content.replace("babase.app.arcade_mode", "babase.app.arcade_mode if build_number < 21282 else babase.app.env.arcade_mode") +content = content.replace("babase.app.headless_mode", "babase.app.headless_mode if build_number < 21282 else babase.app.env.headless_mode") +content = content.replace("babase.app.demo_mode", "babase.app.demo_mode if build_number < 21282 else babase.app.env.demo_mode") +content = content.replace("babase.app.protocol_version", "babase.app.protocol_version if build_number < 21282 else babase.app.env.protocol_version") +content = content.replace("bascenev1.get_connection_to_host_info", "bascenev1.get_connection_to_host_info if build_number < 21697 else bascenev1.get_connection_to_host_info_2") + +content = content.replace("babase._store", "bauiv1.app.classic.store") +# content = content.replace("babase.internal", "") +content = content.replace("bastd.ui", "bauiv1lib") +content = content.replace("bastd", "bascenev1lib") +content = content.replace("timetype=","") +content = content.replace("babase.columnwidget", "bauiv1.columnwidget") +content = content.replace("_babase.get_game_port", "bascenev1.get_game_port") +content = content.replace("_babase.get_chat_messages", "bascenev1.get_chat_messages") +content = content.replace("_babase.get_foreground_host_session", "bascenev1.get_foreground_host_session") +content = content.replace("_babase.get_foreground_host_activity", "bascenev1.get_foreground_host_activity") +content = content.replace("bascenev1.SessionPlayerNotFoundError", "babase.SessionPlayerNotFoundError") +content = content.replace("bascenev1", "bs") +content = content.replace("bauiv1", "bui") +content = content.replace("import bs", "import bascenev1 as bs") +content = content.replace("import bui", "import bauiv1 as bui") +content = content.replace("bslib", "bascenev1lib") +content = content.replace("builib", "bauiv1lib") +content = content.replace("from bs.", "from bascenev1.") +content = content.replace("from bui.", "from bauiv1.") +content = content.replace("import bascenev1 as bascenev1lib", "import bascenev1lib") +content = content.replace("import bauiv1 as bauiv1lib", "import bauiv1lib") +content = content.replace("# ba_meta export bs.GameActivity", "# ba_meta export bascenev1.GameActivity") +content = content.replace("_bs", "bs") + +content = re.sub(r'bs\.Timer\(([^)]*)\bTimeType\.REAL\b([^)]*)\)', r'babase.AppTimer(\1\2)', content) +trademark = "# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport)\n" +with open(sys.argv[2], "w", encoding=encoding) as f: + f.write(trademark + content) + + diff --git a/plugins/minigames/quake.py b/plugins/minigames/quake.py index e0bb33b..65fcfcb 100644 --- a/plugins/minigames/quake.py +++ b/plugins/minigames/quake.py @@ -1,24 +1,27 @@ +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) """Quake Game Activity""" -# ba_meta require api 7 +# ba_meta require api 8 from __future__ import annotations from typing import TYPE_CHECKING import random import enum -import ba -import _ba +import babase +import bauiv1 as bui +import bascenev1 as bs +import _babase -from bastd.actor.scoreboard import Scoreboard -from bastd.actor.powerupbox import PowerupBox -from bastd.gameutils import SharedObjects +from bascenev1lib.actor.scoreboard import Scoreboard +from bascenev1lib.actor.powerupbox import PowerupBox +from bascenev1lib.gameutils import SharedObjects # from rocket -from bastd.actor.bomb import Blast +from bascenev1lib.actor.bomb import Blast # from railgun -from bastd.actor.playerspaz import PlayerSpaz -from bastd.actor.spaz import Spaz +from bascenev1lib.actor.playerspaz import PlayerSpaz +from bascenev1lib.actor.spaz import Spaz if TYPE_CHECKING: @@ -33,7 +36,7 @@ class RocketFactory: """Quake Rocket factory""" def __init__(self) -> None: - self.ball_material = ba.Material() + self.ball_material = bs.Material() self.ball_material.add_actions( conditions=((('we_are_younger_than', 5), 'or', @@ -60,7 +63,7 @@ class RocketFactory: @classmethod def get(cls): """Get factory if exists else create new""" - activity = ba.getactivity() + activity = bs.getactivity() if hasattr(activity, STORAGE_ATTR_NAME): return getattr(activity, STORAGE_ATTR_NAME) factory = cls() @@ -77,13 +80,13 @@ class RocketLauncher: def give(self, spaz: Spaz) -> None: """Give spaz a rocket launcher""" spaz.punch_callback = self.shot - self.last_shot = ba.time() + self.last_shot = bs.time() # FIXME # noinspection PyUnresolvedReferences def shot(self, spaz: Spaz) -> None: """Release a rocket""" - time = ba.time() + time = bs.time() if time - self.last_shot > 0.6: self.last_shot = time center = spaz.node.position_center @@ -92,12 +95,12 @@ class RocketLauncher: center[2] - forward[2]] direction[1] = 0.0 - mag = 10.0 / ba.Vec3(*direction).length() + mag = 10.0 / babase.Vec3(*direction).length() vel = [v * mag for v in direction] Rocket(position=spaz.node.position, velocity=vel, - owner=spaz.getplayer(ba.Player), - source_player=spaz.getplayer(ba.Player), + owner=spaz.getplayer(bs.Player), + source_player=spaz.getplayer(bs.Player), color=spaz.node.color).autoretain() @@ -105,7 +108,7 @@ class ImpactMessage: """Rocket touched something""" -class Rocket(ba.Actor): +class Rocket(bs.Actor): """Epic rocket from rocket launcher""" def __init__(self, @@ -120,16 +123,16 @@ class Rocket(ba.Actor): self._color = color factory = RocketFactory.get() - self.node = ba.newnode('prop', + self.node = bs.newnode('prop', delegate=self, attrs={ 'position': position, 'velocity': velocity, - 'model': ba.getmodel('impactBomb'), + 'mesh': bs.getmesh('impactBomb'), 'body': 'sphere', - 'color_texture': ba.gettexture( + 'color_texture': bs.gettexture( 'bunnyColor'), - 'model_scale': 0.2, + 'mesh_scale': 0.2, 'is_area_of_interest': True, 'body_scale': 0.8, 'materials': [ @@ -139,17 +142,17 @@ class Rocket(ba.Actor): self.node.extra_acceleration = (self.node.velocity[0] * 200, 0, self.node.velocity[2] * 200) - self._life_timer = ba.Timer( - 5, ba.WeakCall(self.handlemessage, ba.DieMessage())) + self._life_timer = bs.Timer( + 5, bs.WeakCall(self.handlemessage, bs.DieMessage())) - self._emit_timer = ba.Timer(0.001, ba.WeakCall(self.emit), repeat=True) + self._emit_timer = bs.Timer(0.001, bs.WeakCall(self.emit), repeat=True) self.base_pos_y = self.node.position[1] - ba.camerashake(5.0) + bs.camerashake(5.0) def emit(self) -> None: """Emit a trace after rocket""" - ba.emitfx(position=self.node.position, + bs.emitfx(position=self.node.position, scale=0.4, spread=0.01, chunk_type='spark') @@ -157,7 +160,7 @@ class Rocket(ba.Actor): return self.node.position = (self.node.position[0], self.base_pos_y, self.node.position[2]) # ignore y - ba.newnode('explosion', + bs.newnode('explosion', owner=self.node, attrs={ 'position': self.node.position, @@ -169,9 +172,9 @@ class Rocket(ba.Actor): """Message handling for rocket""" super().handlemessage(msg) if isinstance(msg, ImpactMessage): - self.node.handlemessage(ba.DieMessage()) + self.node.handlemessage(bs.DieMessage()) - elif isinstance(msg, ba.DieMessage): + elif isinstance(msg, bs.DieMessage): if self.node: Blast(position=self.node.position, blast_radius=2, @@ -180,8 +183,8 @@ class Rocket(ba.Actor): self.node.delete() self._emit_timer = None - elif isinstance(msg, ba.OutOfBoundsMessage): - self.handlemessage(ba.DieMessage()) + elif isinstance(msg, bs.OutOfBoundsMessage): + self.handlemessage(bs.DieMessage()) # -------------------Rocket-------------------------- @@ -196,13 +199,13 @@ class Railgun: def give(self, spaz: Spaz) -> None: """Give spaz a railgun""" spaz.punch_callback = self.shot - self.last_shot = ba.time() + self.last_shot = bs.time() # FIXME # noinspection PyUnresolvedReferences def shot(self, spaz: Spaz) -> None: """Release a rocket""" - time = ba.time() + time = bs.time() if time - self.last_shot > 0.6: self.last_shot = time center = spaz.node.position_center @@ -215,8 +218,8 @@ class Railgun: RailBullet(position=spaz.node.position, direction=direction, - owner=spaz.getplayer(ba.Player), - source_player=spaz.getplayer(ba.Player), + owner=spaz.getplayer(bs.Player), + source_player=spaz.getplayer(bs.Player), color=spaz.node.color).autoretain() @@ -227,7 +230,7 @@ class TouchedToSpazMessage: self.spaz = spaz -class RailBullet(ba.Actor): +class RailBullet(bs.Actor): """Railgun bullet""" def __init__(self, @@ -239,23 +242,23 @@ class RailBullet(ba.Actor): super().__init__() self._color = color - self.node = ba.newnode('light', + self.node = bs.newnode('light', delegate=self, attrs={ 'position': position, 'color': self._color }) - ba.animate(self.node, 'radius', {0: 0, 0.1: 0.5, 0.5: 0}) + bs.animate(self.node, 'radius', {0: 0, 0.1: 0.5, 0.5: 0}) self.source_player = source_player self.owner = owner - self._life_timer = ba.Timer( - 0.5, ba.WeakCall(self.handlemessage, ba.DieMessage())) + self._life_timer = bs.Timer( + 0.5, bs.WeakCall(self.handlemessage, bs.DieMessage())) pos = position - vel = tuple(i / 5 for i in ba.Vec3(direction).normalized()) + vel = tuple(i / 5 for i in babase.Vec3(direction).normalized()) for _ in range(500): # Optimization :( - ba.newnode('explosion', + bs.newnode('explosion', owner=self.node, attrs={ 'position': pos, @@ -264,25 +267,25 @@ class RailBullet(ba.Actor): }) pos = (pos[0] + vel[0], pos[1] + vel[1], pos[2] + vel[2]) - for node in _ba.getnodes(): + for node in _babase.getnodes(): if node and node.getnodetype() == 'spaz': # pylint: disable=invalid-name - m3 = ba.Vec3(position) - a = ba.Vec3(direction[2], direction[1], direction[0]) - m1 = ba.Vec3(node.position) + m3 = babase.Vec3(position) + a = babase.Vec3(direction[2], direction[1], direction[0]) + m1 = babase.Vec3(node.position) # pylint: enable=invalid-name # distance between node and line dist = (a * (m1 - m3)).length() / a.length() if dist < 0.3: if node and node != self.owner and node.getdelegate( PlayerSpaz, True).getplayer( - ba.Player, True).team != self.owner.team: - node.handlemessage(ba.FreezeMessage()) + bs.Player, True).team != self.owner.team: + node.handlemessage(bs.FreezeMessage()) pos = self.node.position hit_dir = (0, 10, 0) node.handlemessage( - ba.HitMessage(pos=pos, + bs.HitMessage(pos=pos, magnitude=50, velocity_magnitude=50, radius=0, @@ -292,21 +295,21 @@ class RailBullet(ba.Actor): def handlemessage(self, msg: Any) -> Any: super().handlemessage(msg) - if isinstance(msg, ba.DieMessage): + if isinstance(msg, bs.DieMessage): if self.node: self.node.delete() - elif isinstance(msg, ba.OutOfBoundsMessage): - self.handlemessage(ba.DieMessage()) + elif isinstance(msg, bs.OutOfBoundsMessage): + self.handlemessage(bs.DieMessage()) # ------------------Railgun------------------------- -class Player(ba.Player['Team']): +class Player(bs.Player['Team']): """Our player""" -class Team(ba.Team[Player]): +class Team(bs.Team[Player]): """Our team""" def __init__(self) -> None: @@ -326,91 +329,91 @@ class ObstaclesForm(enum.Enum): RANDOM = 2 -# ba_meta export game -class QuakeGame(ba.TeamGameActivity[Player, Team]): +# ba_meta export bascenev1.GameActivity +class QuakeGame(bs.TeamGameActivity[Player, Team]): """Quake Team Game Activity""" name = 'Quake' description = 'Kill a set number of enemies to win.' available_settings = [ - ba.IntSetting( + bs.IntSetting( 'Kills to Win Per Player', default=15, min_value=1, increment=1, ), - ba.IntChoiceSetting( + bs.IntChoiceSetting( 'Time Limit', choices=[('None', 0), ('1 Minute', 60), ('2 Minutes', 120), ('5 Minutes', 300), ('10 Minutes', 600), ('20 Minutes', 1200)], default=0, ), - ba.FloatChoiceSetting( + bs.FloatChoiceSetting( 'Respawn Times', choices=[('At once', 0.0), ('Shorter', 0.25), ('Short', 0.5), ('Normal', 1.0), ('Long', 2.0), ('Longer', 4.0)], default=1.0, ), - ba.BoolSetting( + bs.BoolSetting( 'Speed', default=True, ), - ba.BoolSetting( + bs.BoolSetting( 'Enable Jump', default=True, ), - ba.BoolSetting( + bs.BoolSetting( 'Enable Pickup', default=True, ), - ba.BoolSetting( + bs.BoolSetting( 'Enable Bomb', default=False, ), - ba.BoolSetting( + bs.BoolSetting( 'Obstacles', default=True, ), - ba.IntChoiceSetting( + bs.IntChoiceSetting( 'Obstacles Form', choices=[('Cube', ObstaclesForm.CUBE.value), ('Sphere', ObstaclesForm.SPHERE.value), ('Random', ObstaclesForm.RANDOM.value)], default=0, ), - ba.IntChoiceSetting( + bs.IntChoiceSetting( 'Weapon Type', choices=[('Rocket', WeaponType.ROCKET.value), ('Railgun', WeaponType.RAILGUN.value)], default=WeaponType.ROCKET.value, ), - ba.BoolSetting( + bs.BoolSetting( 'Obstacles Mirror Shots', default=False, ), - ba.IntSetting( + bs.IntSetting( 'Obstacles Count', default=16, min_value=0, increment=2, ), - ba.BoolSetting( + bs.BoolSetting( 'Random Obstacles Color', default=True, ), - ba.BoolSetting( + bs.BoolSetting( 'Epic Mode', default=False, ), ] @classmethod - def supports_session_type(cls, sessiontype: Type[ba.Session]) -> bool: - return issubclass(sessiontype, ba.MultiTeamSession) or issubclass( - sessiontype, ba.FreeForAllSession) + def supports_session_type(cls, sessiontype: Type[bs.Session]) -> bool: + return issubclass(sessiontype, bs.MultiTeamSession) or issubclass( + sessiontype, bs.FreeForAllSession) @classmethod - def get_supported_maps(cls, sessiontype: Type[ba.Session]) -> List[str]: + def get_supported_maps(cls, sessiontype: Type[bs.Session]) -> List[str]: # TODO add more maps return ['Football Stadium', 'Monkey Face', 'Doom Shroom'] @@ -426,15 +429,15 @@ class QuakeGame(ba.TeamGameActivity[Player, Team]): self._pickup_enabled = self.settings_raw['Enable Pickup'] self._jump_enabled = self.settings_raw['Enable Jump'] self._weapon_type = WeaponType(self.settings_raw['Weapon Type']) - self.default_music = (ba.MusicType.EPIC - if self._epic_mode else ba.MusicType.GRAND_ROMP) + self.default_music = (bs.MusicType.EPIC + if self._epic_mode else bs.MusicType.GRAND_ROMP) self.slow_motion = self._epic_mode self.announce_player_deaths = True self._scoreboard = Scoreboard() - self._ding_sound = ba.getsound('dingSmall') + self._ding_sound = bs.getsound('dingSmall') - self._shield_dropper: Optional[ba.Timer] = None + self._shield_dropper: Optional[bs.Timer] = None def get_instance_description(self) -> Union[str, Sequence]: return 'Kill ${ARG1} enemies.', self._score_to_win @@ -445,11 +448,11 @@ class QuakeGame(ba.TeamGameActivity[Player, Team]): self._update_scoreboard() def on_begin(self) -> None: - ba.TeamGameActivity.on_begin(self) - ba.getactivity().globalsnode.tint = (0.5, 0.7, 1) + bs.TeamGameActivity.on_begin(self) + bs.getactivity().globalsnode.tint = (0.5, 0.7, 1) self.drop_shield() - self._shield_dropper = ba.Timer(8, - ba.WeakCall(self.drop_shield), + self._shield_dropper = bs.Timer(8, + bs.WeakCall(self.drop_shield), repeat=True) self.setup_standard_time_limit(self._time_limit) if self._obstacles_enabled: @@ -483,9 +486,9 @@ class QuakeGame(ba.TeamGameActivity[Player, Team]): position=(random.uniform(-10, 10), 6, random.uniform(-5, 5))).autoretain() - ba.playsound(self._ding_sound) + self._ding_sound.play() - p_light = ba.newnode('light', + p_light = bs.newnode('light', owner=shield.node, attrs={ 'position': (0, 0, 0), @@ -497,7 +500,7 @@ class QuakeGame(ba.TeamGameActivity[Player, Team]): shield.node.connectattr('position', p_light, 'position') - ba.animate(p_light, 'intensity', {0: 2, 8: 0}) + bs.animate(p_light, 'intensity', {0: 2, 8: 0}) def spawn_player(self, player: Player) -> None: spaz = self.spawn_player_spaz(player) @@ -511,7 +514,7 @@ class QuakeGame(ba.TeamGameActivity[Player, Team]): enable_fly=False) spaz.node.hockey = self._speed_enabled - spaz.spaz_light = ba.newnode('light', + spaz.spaz_light = bs.newnode('light', owner=spaz.node, attrs={ 'position': (0, 0, 0), @@ -524,8 +527,8 @@ class QuakeGame(ba.TeamGameActivity[Player, Team]): spaz.node.connectattr('position', spaz.spaz_light, 'position') def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.PlayerDiedMessage): - ba.TeamGameActivity.handlemessage(self, msg) + if isinstance(msg, bs.PlayerDiedMessage): + bs.TeamGameActivity.handlemessage(self, msg) player = msg.getplayer(Player) self.respawn_player(player) killer = msg.getkillerplayer(Player) @@ -535,20 +538,20 @@ class QuakeGame(ba.TeamGameActivity[Player, Team]): # handle team-kills if killer.team is player.team: # in free-for-all, killing yourself loses you a point - if isinstance(self.session, ba.FreeForAllSession): + if isinstance(self.session, bs.FreeForAllSession): new_score = player.team.score - 1 new_score = max(0, new_score) player.team.score = new_score # in teams-mode it gives a point to the other team else: - ba.playsound(self._ding_sound) + self._ding_sound.play() for team in self.teams: if team is not killer.team: team.score += 1 # killing someone on another team nets a kill else: killer.team.score += 1 - ba.playsound(self._ding_sound) + self._ding_sound.play() # in FFA show our score since its hard to find on # the scoreboard assert killer.actor is not None @@ -564,10 +567,10 @@ class QuakeGame(ba.TeamGameActivity[Player, Team]): # (allows the dust to clear and draws to occur if # deaths are close enough) if any(team.score >= self._score_to_win for team in self.teams): - ba.timer(0.5, self.end_game) + bs.timer(0.5, self.end_game) else: - ba.TeamGameActivity.handlemessage(self, msg) + bs.TeamGameActivity.handlemessage(self, msg) def _update_scoreboard(self) -> None: for team in self.teams: @@ -575,51 +578,51 @@ class QuakeGame(ba.TeamGameActivity[Player, Team]): self._score_to_win) def end_game(self) -> None: - results = ba.GameResults() + results = bs.GameResults() for team in self.teams: results.set_team_score(team, team.score) self.end(results=results) -class Obstacle(ba.Actor): +class Obstacle(bs.Actor): """Scene object""" def __init__(self, position, form=ObstaclesForm.CUBE, mirror=False) -> None: - ba.Actor.__init__(self) + bs.Actor.__init__(self) if form == ObstaclesForm.CUBE: - model = 'tnt' + mesh = 'tnt' body = 'crate' elif form == ObstaclesForm.SPHERE: - model = 'bomb' + mesh = 'bomb' body = 'sphere' else: # ObstaclesForm.RANDOM: - model = random.choice(['tnt', 'bomb']) - body = 'sphere' if model == 'bomb' else 'crate' + mesh = random.choice(['tnt', 'bomb']) + body = 'sphere' if mesh == 'bomb' else 'crate' - self.node = ba.newnode( + self.node = bs.newnode( 'prop', delegate=self, attrs={ 'position': position, - 'model': - ba.getmodel(model), + 'mesh': + bs.getmesh(mesh), 'body': body, 'body_scale': 1.3, - 'model_scale': + 'mesh_scale': 1.3, 'reflection': 'powerup', 'reflection_scale': [0.7], 'color_texture': - ba.gettexture('bunnyColor'), + bs.gettexture('bunnyColor'), 'materials': [SharedObjects.get().footing_material] if mirror else [ SharedObjects.get().object_material, @@ -628,15 +631,15 @@ class Obstacle(ba.Actor): }) def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.DieMessage): + if isinstance(msg, bs.DieMessage): if self.node: self.node.delete() - elif isinstance(msg, ba.OutOfBoundsMessage): + elif isinstance(msg, bs.OutOfBoundsMessage): if self.node: - self.handlemessage(ba.DieMessage()) + self.handlemessage(bs.DieMessage()) - elif isinstance(msg, ba.HitMessage): + elif isinstance(msg, bs.HitMessage): self.node.handlemessage('impulse', msg.pos[0], msg.pos[1], msg.pos[2], msg.velocity[0], msg.velocity[1], msg.velocity[2], diff --git a/plugins/minigames/shimla.py b/plugins/minigames/shimla.py index da96392..2316194 100644 --- a/plugins/minigames/shimla.py +++ b/plugins/minigames/shimla.py @@ -1,43 +1,43 @@ +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) # Released under the MIT License. See LICENSE for details. # """DeathMatch game and support classes.""" -# ba_meta require api 7 +# ba_meta require api 8 # (see https://ballistica.net/wiki/meta-tag-system) from __future__ import annotations from typing import TYPE_CHECKING -import ba -import _ba -from bastd.actor.playerspaz import PlayerSpaz -from bastd.actor.scoreboard import Scoreboard -from bastd.gameutils import SharedObjects -from bastd.game.deathmatch import DeathMatchGame, Player, Team -from bastd.gameutils import SharedObjects +import babase +import bascenev1 as bs +from bascenev1lib.actor.playerspaz import PlayerSpaz +from bascenev1lib.gameutils import SharedObjects +from bascenev1lib.game.deathmatch import DeathMatchGame, Player +from bascenev1lib.gameutils import SharedObjects if TYPE_CHECKING: from typing import Any, Sequence, Dict, Type, List, Optional, Union -# ba_meta export game +# ba_meta export bascenev1.GameActivity class ShimlaGame(DeathMatchGame): name = 'Shimla' @classmethod - def supports_session_type(cls, sessiontype: Type[ba.Session]) -> bool: - return issubclass(sessiontype, ba.DualTeamSession) + def supports_session_type(cls, sessiontype: Type[bs.Session]) -> bool: + return issubclass(sessiontype, bs.DualTeamSession) @classmethod - def get_supported_maps(cls, sessiontype: Type[ba.Session]) -> List[str]: + def get_supported_maps(cls, sessiontype: Type[bs.Session]) -> List[str]: return ['Creative Thoughts'] def __init__(self, settings: dict): super().__init__(settings) shared = SharedObjects.get() self.lifts = {} - self._real_wall_material = ba.Material() + self._real_wall_material = bs.Material() self._real_wall_material.add_actions( actions=( @@ -53,7 +53,7 @@ class ShimlaGame(DeathMatchGame): ('modify_part_collision', 'physical', True) )) - self._lift_material = ba.Material() + self._lift_material = bs.Material() self._lift_material.add_actions( actions=( @@ -71,14 +71,14 @@ class ShimlaGame(DeathMatchGame): ) def on_begin(self): - ba.getactivity().globalsnode.happy_thoughts_mode = False + bs.getactivity().globalsnode.happy_thoughts_mode = False super().on_begin() self.make_map() - ba.timer(2, self.disable_fly) + bs.timer(2, self.disable_fly) def disable_fly(self): - activity = _ba.get_foreground_host_activity() + activity = bs.get_foreground_host_activity() for players in activity.players: players.actor.node.fly = False @@ -102,29 +102,29 @@ class ShimlaGame(DeathMatchGame): def make_map(self): shared = SharedObjects.get() - _ba.get_foreground_host_activity()._map.leftwall.materials = [ + bs.get_foreground_host_activity()._map.leftwall.materials = [ shared.footing_material, self._real_wall_material] - _ba.get_foreground_host_activity()._map.rightwall.materials = [ + bs.get_foreground_host_activity()._map.rightwall.materials = [ shared.footing_material, self._real_wall_material] - _ba.get_foreground_host_activity()._map.topwall.materials = [ + bs.get_foreground_host_activity()._map.topwall.materials = [ shared.footing_material, self._real_wall_material] - self.floorwall1 = ba.newnode('region', attrs={'position': (-10, 5, -5.52), 'scale': + self.floorwall1 = bs.newnode('region', attrs={'position': (-10, 5, -5.52), 'scale': (15, 0.2, 2), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - self.floorwall2 = ba.newnode('region', attrs={'position': (10, 5, -5.52), 'scale': ( + self.floorwall2 = bs.newnode('region', attrs={'position': (10, 5, -5.52), 'scale': ( 15, 0.2, 2), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - self.wall1 = ba.newnode('region', attrs={'position': (0, 11, -6.90), 'scale': ( + self.wall1 = bs.newnode('region', attrs={'position': (0, 11, -6.90), 'scale': ( 35.4, 20, 1), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - self.wall2 = ba.newnode('region', attrs={'position': (0, 11, -4.14), 'scale': ( + self.wall2 = bs.newnode('region', attrs={'position': (0, 11, -4.14), 'scale': ( 35.4, 20, 1), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (-10, 5, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (-10, 5, -5.52), 'color': ( 0, 0, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (15, 0.2, 2)}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (10, 5, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (10, 5, -5.52), 'color': ( 0, 0, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (15, 0.2, 2)}) self.create_lift(-16.65, 8) @@ -151,32 +151,32 @@ class ShimlaGame(DeathMatchGame): shared = SharedObjects.get() - ba.newnode('region', attrs={'position': (x, y, -5.52), 'scale': (5.5, 0.1, 6), + bs.newnode('region', attrs={'position': (x, y, -5.52), 'scale': (5.5, 0.1, 6), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (x, y, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (x, y, -5.52), 'color': ( 1, 1, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (5.5, 0.1, 2)}) def create_lift(self, x, y): shared = SharedObjects.get() color = (0.7, 0.6, 0.5) - floor = ba.newnode('region', attrs={'position': (x, y, -5.52), 'scale': ( + floor = bs.newnode('region', attrs={'position': (x, y, -5.52), 'scale': ( 1.8, 0.1, 2), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material, self._lift_material]}) - cleaner = ba.newnode('region', attrs={'position': (x, y, -5.52), 'scale': ( + cleaner = bs.newnode('region', attrs={'position': (x, y, -5.52), 'scale': ( 2, 0.3, 2), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - lift = ba.newnode('locator', attrs={'shape': 'box', 'position': ( + lift = bs.newnode('locator', attrs={'shape': 'box', 'position': ( x, y, -5.52), 'color': color, 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (1.8, 3.7, 2)}) - _tcombine = ba.newnode('combine', + _tcombine = bs.newnode('combine', owner=floor, attrs={ 'input0': x, 'input2': -5.5, 'size': 3 }) - mnode = ba.newnode('math', + mnode = bs.newnode('math', owner=lift, attrs={ 'input1': (0, 2, 0), @@ -184,7 +184,7 @@ class ShimlaGame(DeathMatchGame): }) _tcombine.connectattr('output', mnode, 'input2') - _cleaner_combine = ba.newnode('combine', + _cleaner_combine = bs.newnode('combine', owner=cleaner, attrs={ 'input1': 5.6, @@ -192,10 +192,10 @@ class ShimlaGame(DeathMatchGame): 'size': 3 }) _cleaner_combine.connectattr('output', cleaner, 'position') - ba.animate(_tcombine, 'input1', { + bs.animate(_tcombine, 'input1', { 0: 5.1, }) - ba.animate(_cleaner_combine, 'input0', { + bs.animate(_cleaner_combine, 'input0', { 0: -19 if x < 0 else 19, }) @@ -205,29 +205,29 @@ class ShimlaGame(DeathMatchGame): "cleaner": _cleaner_combine, 'leftLift': x < 0} def _handle_lift(self): - region = ba.getcollision().sourcenode + region = bs.getcollision().sourcenode lift = self.lifts[region] def clean(lift): - ba.animate(lift["cleaner"], 'input0', { + bs.animate(lift["cleaner"], 'input0', { 0: -19 if lift["leftLift"] else 19, 2: -16 if lift["leftLift"] else 16, 4.3: -19 if lift["leftLift"] else 19 }) if lift["state"] == "origin": lift["state"] = "transition" - ba.animate(lift["lift"], 'input1', { + bs.animate(lift["lift"], 'input1', { 0: 5.1, 1.3: 5.1, 6: 5+12, 9: 5+12, 15: 5.1 }) - ba.timer(16, ba.Call(lambda lift: lift.update({'state': 'end'}), lift)) - ba.timer(12, ba.Call(clean, lift)) + bs.timer(16, babase.Call(lambda lift: lift.update({'state': 'end'}), lift)) + bs.timer(12, babase.Call(clean, lift)) def _handle_lift_disconnect(self): - region = ba.getcollision().sourcenode + region = bs.getcollision().sourcenode lift = self.lifts[region] if lift["state"] == 'end': lift["state"] = "origin" @@ -236,9 +236,9 @@ class ShimlaGame(DeathMatchGame): shared = SharedObjects.get() for i in range(0, 21): - ba.newnode('region', attrs={'position': (x, y, -5.52), 'scale': (0.2, 0.1, 6), + bs.newnode('region', attrs={'position': (x, y, -5.52), 'scale': (0.2, 0.1, 6), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (x, y, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (x, y, -5.52), 'color': ( 1, 1, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (0.2, 0.1, 2)}) if backslash: x = x+0.1 @@ -292,7 +292,7 @@ class mapdefs: 0.5245740665, 0.5245740665, 0.01941146064) -class CreativeThoughts(ba.Map): +class CreativeThoughts(bs.Map): """Freaking map by smoothy.""" defs = mapdefs @@ -313,26 +313,26 @@ class CreativeThoughts(ba.Map): @classmethod def on_preload(cls) -> Any: data: Dict[str, Any] = { - 'model': ba.getmodel('alwaysLandLevel'), - 'bottom_model': ba.getmodel('alwaysLandLevelBottom'), - 'bgmodel': ba.getmodel('alwaysLandBG'), - 'collide_model': ba.getcollidemodel('alwaysLandLevelCollide'), - 'tex': ba.gettexture('alwaysLandLevelColor'), - 'bgtex': ba.gettexture('alwaysLandBGColor'), - 'vr_fill_mound_model': ba.getmodel('alwaysLandVRFillMound'), - 'vr_fill_mound_tex': ba.gettexture('vrFillMound') + 'mesh': bs.getmesh('alwaysLandLevel'), + 'bottom_mesh': bs.getmesh('alwaysLandLevelBottom'), + 'bgmesh': bs.getmesh('alwaysLandBG'), + 'collision_mesh': bs.getcollisionmesh('alwaysLandLevelCollide'), + 'tex': bs.gettexture('alwaysLandLevelColor'), + 'bgtex': bs.gettexture('alwaysLandBGColor'), + 'vr_fill_mound_mesh': bs.getmesh('alwaysLandVRFillMound'), + 'vr_fill_mound_tex': bs.gettexture('vrFillMound') } return data @classmethod - def get_music_type(cls) -> ba.MusicType: - return ba.MusicType.FLYING + def get_music_type(cls) -> bs.MusicType: + return bs.MusicType.FLYING def __init__(self) -> None: super().__init__(vr_overlay_offset=(0, -3.7, 2.5)) shared = SharedObjects.get() - self._fake_wall_material = ba.Material() - self._real_wall_material = ba.Material() + self._fake_wall_material = bs.Material() + self._real_wall_material = bs.Material() self._fake_wall_material.add_actions( conditions=(('they_are_younger_than', 9000), 'and', ('they_have_material', shared.player_material)), @@ -348,29 +348,29 @@ class CreativeThoughts(ba.Map): ('modify_part_collision', 'physical', True) )) - self.background = ba.newnode( + self.background = bs.newnode( 'terrain', attrs={ - 'model': self.preloaddata['bgmodel'], + 'mesh': self.preloaddata['bgmesh'], 'lighting': False, 'background': True, - 'color_texture': ba.gettexture("rampageBGColor") + 'color_texture': bs.gettexture("rampageBGColor") }) - self.leftwall = ba.newnode('region', attrs={'position': (-17.75152479, 13, -5.52), 'scale': ( + self.leftwall = bs.newnode('region', attrs={'position': (-17.75152479, 13, -5.52), 'scale': ( 0.1, 15.5, 2), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - self.rightwall = ba.newnode('region', attrs={'position': (17.75, 13, -5.52), 'scale': ( + self.rightwall = bs.newnode('region', attrs={'position': (17.75, 13, -5.52), 'scale': ( 0.1, 15.5, 2), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - self.topwall = ba.newnode('region', attrs={'position': (0, 21.0, -5.52), 'scale': ( + self.topwall = bs.newnode('region', attrs={'position': (0, 21.0, -5.52), 'scale': ( 35.4, 0.2, 2), 'type': 'box', 'materials': [shared.footing_material, self._real_wall_material]}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (-17.75152479, 13, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (-17.75152479, 13, -5.52), 'color': ( 0, 0, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (0.1, 15.5, 2)}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (17.75, 13, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (17.75, 13, -5.52), 'color': ( 0, 0, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (0.1, 15.5, 2)}) - ba.newnode('locator', attrs={'shape': 'box', 'position': (0, 21.0, -5.52), 'color': ( + bs.newnode('locator', attrs={'shape': 'box', 'position': (0, 21.0, -5.52), 'color': ( 0, 0, 0), 'opacity': 1, 'draw_beauty': True, 'additive': False, 'size': (35.4, 0.2, 2)}) - gnode = ba.getactivity().globalsnode + gnode = bs.getactivity().globalsnode gnode.happy_thoughts_mode = True gnode.shadow_offset = (0.0, 8.0, 5.0) gnode.tint = (1.3, 1.23, 1.0) @@ -381,9 +381,9 @@ class CreativeThoughts(ba.Map): self.is_flying = True # throw out some tips on flying - txt = ba.newnode('text', + txt = bs.newnode('text', attrs={ - 'text': ba.Lstr(resource='pressJumpToFlyText'), + 'text': babase.Lstr(resource='pressJumpToFlyText'), 'scale': 1.2, 'maxwidth': 800, 'position': (0, 200), @@ -392,7 +392,7 @@ class CreativeThoughts(ba.Map): 'h_align': 'center', 'v_attach': 'bottom' }) - cmb = ba.newnode('combine', + cmb = bs.newnode('combine', owner=txt, attrs={ 'size': 4, @@ -400,12 +400,12 @@ class CreativeThoughts(ba.Map): 'input1': 0.9, 'input2': 0.0 }) - ba.animate(cmb, 'input3', {3.0: 0, 4.0: 1, 9.0: 1, 10.0: 0}) + bs.animate(cmb, 'input3', {3.0: 0, 4.0: 1, 9.0: 1, 10.0: 0}) cmb.connectattr('output', txt, 'color') - ba.timer(10.0, txt.delete) + bs.timer(10.0, txt.delete) try: - ba._map.register_map(CreativeThoughts) + bs._map.register_map(CreativeThoughts) except: pass diff --git a/plugins/minigames/simon_says.py b/plugins/minigames/simon_says.py index ad3ac27..5640951 100644 --- a/plugins/minigames/simon_says.py +++ b/plugins/minigames/simon_says.py @@ -1,6 +1,7 @@ +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) # SimonSays # you had really better do what Simon says... -# ba_meta require api 7 +# ba_meta require api 8 from __future__ import annotations from typing import TYPE_CHECKING @@ -8,19 +9,21 @@ from typing import TYPE_CHECKING if TYPE_CHECKING: from typing import Any, Union, Sequence -from ba import _gameutils -import ba +from bascenev1 import _gameutils +import babase +import bauiv1 as bui +import bascenev1 as bs import random -class CustomText(ba.Actor): +class CustomText(bs.Actor): """Text that pops up above a position to denote something special. category: Gameplay Classes """ def __init__(self, - text: Union[str, ba.Lstr], + text: Union[str, babase.Lstr], position: Sequence[float] = (0.0, 0.0, 0.0), color: Sequence[float] = (1.0, 1.0, 1.0, 1.0), random_offset: float = 0.5, @@ -34,7 +37,7 @@ class CustomText(ba.Actor): (0.5 - random.random()), position[1] + offset[0] + random_offset * (0.5 - random.random()), position[2] + offset[0] + random_offset * (0.5 - random.random())) - self.node = ba.newnode('text', + self.node = bs.newnode('text', attrs={ 'text': text, 'in_world': True, @@ -42,27 +45,27 @@ class CustomText(ba.Actor): 'flatness': 1.0, 'h_align': 'center'}, delegate=self) lifespan = duration - ba.animate( + bs.animate( self.node, 'scale', { 0: 0.0, lifespan * 0.11: 0.020 * 0.7 * scale, lifespan * 0.16: 0.013 * 0.7 * scale, lifespan * 0.25: 0.014 * 0.7 * scale }) - self._tcombine = ba.newnode('combine', + self._tcombine = bs.newnode('combine', owner=self.node, attrs={ 'input0': pos[0], 'input2': pos[2], 'size': 3 }) - ba.animate(self._tcombine, 'input1', { + bs.animate(self._tcombine, 'input1', { 0: pos[1] + 1.5, lifespan: pos[1] + 2.0 }) self._tcombine.connectattr('output', self.node, 'position') # fade our opacity in/out - self._combine = ba.newnode('combine', + self._combine = bs.newnode('combine', owner=self.node, attrs={ 'input0': color[0], @@ -71,64 +74,64 @@ class CustomText(ba.Actor): 'size': 4 }) for i in range(4): - ba.animate( + bs.animate( self._combine, 'input' + str(i), { 0.13 * lifespan: color[i], 0.18 * lifespan: 4.0 * color[i], 0.22 * lifespan: color[i]}) - ba.animate(self._combine, 'input3', { + bs.animate(self._combine, 'input3', { 0: 0, 0.1 * lifespan: color[3], 0.7 * lifespan: color[3], lifespan: 0}) self._combine.connectattr('output', self.node, 'color') - self._die_timer = ba.Timer( - lifespan, ba.WeakCall(self.handlemessage, ba.DieMessage())) + self._die_timer = bs.Timer( + lifespan, bs.WeakCall(self.handlemessage, bs.DieMessage())) def handlemessage(self, msg: Any) -> Any: assert not self.expired - if isinstance(msg, ba.DieMessage): + if isinstance(msg, bs.DieMessage): if self.node: self.node.delete() else: super().handlemessage(msg) -class Player(ba.Player['Team']): +class Player(bs.Player['Team']): """Our player type for this game.""" def __init__(self) -> None: self.score = 0 -class Team(ba.Team[Player]): +class Team(bs.Team[Player]): """Our team type for this game.""" def __init__(self) -> None: self.score = 0 -# ba_meta export game +# ba_meta export bascenev1.GameActivity -class SimonSays(ba.TeamGameActivity[Player, Team]): +class SimonSays(bs.TeamGameActivity[Player, Team]): name = "Simon Says" description = "You have to better do what Simon says!" @classmethod - def get_available_settings(cls, sessiontype: Type[ba.Session]) -> List[ba.Setting]: + def get_available_settings(cls, sessiontype: Type[bs.Session]) -> List[babase.Setting]: settings = [ - ba.BoolSetting("Epic Mode", default=False), - ba.BoolSetting("Enable Jumping", default=False), - ba.BoolSetting("Enable Punching", default=False), - ba.BoolSetting("Enable Picking Up", default=False), - ba.IntChoiceSetting("Timer Speed", + bs.BoolSetting("Epic Mode", default=False), + bs.BoolSetting("Enable Jumping", default=False), + bs.BoolSetting("Enable Punching", default=False), + bs.BoolSetting("Enable Picking Up", default=False), + bs.IntChoiceSetting("Timer Speed", choices=[("Snaily", 1200), ("Slow", 900), ("Normal", 655), ("Fast", 544), ("Turbo", 460)], default=655), - ba.FloatChoiceSetting("Text Duration", + bs.FloatChoiceSetting("Text Duration", choices=[("Slow", 2.5), ("Normal", 1.5), ("Mediocre", 1.0), @@ -136,12 +139,12 @@ class SimonSays(ba.TeamGameActivity[Player, Team]): return settings @classmethod - def get_supported_maps(cls, sessiontype: Type[ba.Session]) -> List[str]: + def get_supported_maps(cls, sessiontype: Type[bs.Session]) -> List[str]: return ["Courtyard"] @classmethod - def supports_session_type(cls, sessiontype: Type[ba.Session]) -> bool: - return issubclass(sessiontype, ba.FreeForAllSession) + def supports_session_type(cls, sessiontype: Type[bs.Session]) -> bool: + return issubclass(sessiontype, bs.FreeForAllSession) def __init__(self, settings: dict): super().__init__(settings) @@ -157,7 +160,7 @@ class SimonSays(ba.TeamGameActivity[Player, Team]): self.counter_loop = None self.time = 5000 self._r1 = 2 - self.ct_text = ba.newnode('text', attrs={ + self.ct_text = bs.newnode('text', attrs={ 'in_world': True, 'text': '......', 'shadow': 1.0, @@ -165,44 +168,44 @@ class SimonSays(ba.TeamGameActivity[Player, Team]): 'flatness': 0.5, 'position': (-5.627144702, 3.3275475, -9.572879116), 'scale': 0.05}) - self.n1 = ba.newnode('locator', attrs={'shape': 'circle', 'position': (-4, 0, -6), + self.n1 = bs.newnode('locator', attrs={'shape': 'circle', 'position': (-4, 0, -6), 'color': (1, 0, 0), 'opacity': 0.5, 'draw_beauty': True, 'additive': True}) - self.n2 = ba.newnode('locator', attrs={'shape': 'circle', 'position': (0, 0, -6), + self.n2 = bs.newnode('locator', attrs={'shape': 'circle', 'position': (0, 0, -6), 'color': (0, 1, 0), 'opacity': 0.5, 'draw_beauty': True, 'additive': True}) - self.n3 = ba.newnode('locator', attrs={'shape': 'circle', 'position': (4, 0, -6), + self.n3 = bs.newnode('locator', attrs={'shape': 'circle', 'position': (4, 0, -6), 'color': (0, 0, 1), 'opacity': 0.5, 'draw_beauty': True, 'additive': True}) - self.n4 = ba.newnode('locator', attrs={'shape': 'circle', 'position': (-4, 0, -2), + self.n4 = bs.newnode('locator', attrs={'shape': 'circle', 'position': (-4, 0, -2), 'color': (1, 1, 0), 'opacity': 0.5, 'draw_beauty': True, 'additive': True}) - self.n5 = ba.newnode('locator', attrs={'shape': 'circle', 'position': (0, 0, -2), + self.n5 = bs.newnode('locator', attrs={'shape': 'circle', 'position': (0, 0, -2), 'color': (0, 1, 1), 'opacity': 0.5, 'draw_beauty': True, 'additive': True}) - self.n6 = ba.newnode('locator', attrs={'shape': 'circle', 'position': (4, 0, -2), + self.n6 = bs.newnode('locator', attrs={'shape': 'circle', 'position': (4, 0, -2), 'color': (1, 0, 1), 'opacity': 0.5, 'draw_beauty': True, 'additive': True}) - self.n7 = ba.newnode('locator', attrs={'shape': 'circle', 'position': (-4, 0, 2), + self.n7 = bs.newnode('locator', attrs={'shape': 'circle', 'position': (-4, 0, 2), 'color': (.5, .5, .5), 'opacity': 0.5, 'draw_beauty': True, 'additive': True}) - self.n8 = ba.newnode('locator', attrs={'shape': 'circle', 'position': (0, 0, 2), + self.n8 = bs.newnode('locator', attrs={'shape': 'circle', 'position': (0, 0, 2), 'color': (.5, .325, 0), 'opacity': 0.5, 'draw_beauty': True, 'additive': True}) - self.n9 = ba.newnode('locator', attrs={'shape': 'circle', 'position': (4, 0, 2), + self.n9 = bs.newnode('locator', attrs={'shape': 'circle', 'position': (4, 0, 2), 'color': (1, 1, 1), 'opacity': 0.5, 'draw_beauty': True, 'additive': True}) self.options = ["red", "green", "blue", "yellow", "teal", "purple", "gray", "orange", "white", "top", "bottom", "middle row", "left", "right", "center column", "outside"] - self.default_music = ba.MusicType.FLAG_CATCHER + self.default_music = bs.MusicType.FLAG_CATCHER def get_instance_description(self) -> str: return 'Follow the commands... but only when \"Simon says!"' def on_player_join(self, player: Player) -> None: if self.has_begun(): - ba.screenmessage( - ba.Lstr(resource='playerDelayedJoinText', + bs.broadcastmessage( + babase.Lstr(resource='playerDelayedJoinText', subs=[('${PLAYER}', player.getname(full=True))]), color=(0, 1, 0),) return @@ -227,11 +230,11 @@ class SimonSays(ba.TeamGameActivity[Player, Team]): player.score = 0 # check for immediate end if theres only 1 player if len(self.players) == 1: - ba.timer(4000, lambda: self.check_end(), timeformat=ba.TimeFormat.MILLISECONDS) + bs.timer(4000/1000, lambda: self.check_end()) else: - ba.timer(6000, self.call_round, timeformat=ba.TimeFormat.MILLISECONDS) + bs.timer(6000/1000, self.call_round) - def spawn_player(self, player: PlayerType) -> ba.Actor: + def spawn_player(self, player: PlayerT) -> bs.Actor: assert player spaz = self.spawn_player_spaz(player, position=( 0 + random.uniform(-3.6, 3.6), 2.9, -2 + random.uniform(-3.6, 3.6))) @@ -291,12 +294,11 @@ class SimonSays(ba.TeamGameActivity[Player, Team]): self.string = "0" self.ct_text.text = self.string self.counter_loop = None - ba.timer(1, dummy_check, timeformat=ba.TimeFormat.MILLISECONDS) + bs.timer(1/1000, dummy_check) else: self.ct_text.text = str(self.now) - ba.playsound(ba.getsound('tick')) - self.counter_loop = ba.Timer(self.speed, set_counter, - timeformat=ba.TimeFormat.MILLISECONDS, repeat=True) + bs.getsound('tick').play() + self.counter_loop = bs.Timer(self.speed/1000, set_counter, repeat=True) def check_round(self) -> None: if self.ended: @@ -307,8 +309,8 @@ class SimonSays(ba.TeamGameActivity[Player, Team]): player.actor.node.position_center) else False if ((self.simon and safe == False) or ((not self.simon) and safe == True)): player.team.score = self.round_num - player.actor.handlemessage(ba.DieMessage()) - ba.timer(1633, self.call_round, timeformat=ba.TimeFormat.MILLISECONDS) + player.actor.handlemessage(bs.DieMessage()) + bs.timer(1633/1000, self.call_round) def in_circle(self, pos) -> None: circles = [] @@ -349,14 +351,14 @@ class SimonSays(ba.TeamGameActivity[Player, Team]): return circles def handlemessage(self, msg) -> None: - if isinstance(msg, ba.PlayerDiedMessage): + if isinstance(msg, bs.PlayerDiedMessage): self.check_end() else: super().handlemessage(msg) def end_game(self) -> None: self.ended = True - results = ba.GameResults() + results = bs.GameResults() for team in self.teams: results.set_team_score(team, team.score) self.end(results=results) @@ -367,4 +369,4 @@ class SimonSays(ba.TeamGameActivity[Player, Team]): if player.is_alive(): i += 1 if i <= 2: - ba.timer(0.6, lambda: self.end_game()) + bs.timer(0.6, lambda: self.end_game()) diff --git a/plugins/minigames/sleep_race.py b/plugins/minigames/sleep_race.py index 104c98c..3f00312 100644 --- a/plugins/minigames/sleep_race.py +++ b/plugins/minigames/sleep_race.py @@ -1,3 +1,4 @@ +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) # Released under the MIT License. See LICENSE for details. # y me (: itsre3 # =>2<= @@ -5,7 +6,7 @@ # """Defines Race mini-game.""" -# ba_meta require api 7 +# ba_meta require api 8 # (see https://ballistica.net/wiki/meta-tag-system) from __future__ import annotations @@ -14,17 +15,17 @@ import random from typing import TYPE_CHECKING from dataclasses import dataclass -import ba -import _ba -from bastd.actor.bomb import Bomb -from bastd.actor.playerspaz import PlayerSpaz -from bastd.actor.scoreboard import Scoreboard -from bastd.gameutils import SharedObjects +import babase +import bascenev1 as bs +from bascenev1lib.actor.bomb import Bomb +from bascenev1lib.actor.playerspaz import PlayerSpaz +from bascenev1lib.actor.scoreboard import Scoreboard +from bascenev1lib.gameutils import SharedObjects if TYPE_CHECKING: from typing import (Any, Type, Tuple, List, Sequence, Optional, Dict, Union) - from bastd.actor.onscreentimer import OnScreenTimer + from bascenev1lib.actor.onscreentimer import OnScreenTimer @dataclass @@ -34,7 +35,7 @@ class RaceMine: mine: Optional[Bomb] -class RaceRegion(ba.Actor): +class RaceRegion(bs.Actor): """Region used to track progress during a race.""" def __init__(self, pt: Sequence[float], index: int): @@ -43,7 +44,7 @@ class RaceRegion(ba.Actor): assert isinstance(activity, RaceGame) self.pos = pt self.index = index - self.node = ba.newnode( + self.node = bs.newnode( 'region', delegate=self, attrs={ @@ -54,11 +55,11 @@ class RaceRegion(ba.Actor): }) -class Player(ba.Player['Team']): +class Player(bs.Player['Team']): """Our player type for this game.""" def __init__(self) -> None: - self.distance_txt: Optional[ba.Node] = None + self.distance_txt: Optional[bs.Node] = None self.last_region = 0 self.lap = 0 self.distance = 0.0 @@ -66,7 +67,7 @@ class Player(ba.Player['Team']): self.rank: Optional[int] = None -class Team(ba.Team[Player]): +class Team(bs.Team[Player]): """Our team type for this game.""" def __init__(self) -> None: @@ -75,22 +76,22 @@ class Team(ba.Team[Player]): self.finished = False -# ba_meta export game -class SleepRaceGame(ba.TeamGameActivity[Player, Team]): +# ba_meta export bascenev1.GameActivity +class SleepRaceGame(bs.TeamGameActivity[Player, Team]): """Game of racing around a track.""" name = 'Sleep Race' description = 'Can you run while sleeping?' - scoreconfig = ba.ScoreConfig(label='Time', + scoreconfig = bs.ScoreConfig(label='Time', lower_is_better=True, - scoretype=ba.ScoreType.MILLISECONDS) + scoretype=bs.ScoreType.MILLISECONDS) @classmethod def get_available_settings( - cls, sessiontype: Type[ba.Session]) -> List[ba.Setting]: + cls, sessiontype: Type[bs.Session]) -> List[babase.Setting]: settings = [ - ba.IntSetting('Laps', min_value=1, default=2, increment=1), - ba.IntChoiceSetting( + bs.IntSetting('Laps', min_value=1, default=2, increment=1), + bs.IntChoiceSetting( 'Time Limit', default=0, choices=[ @@ -102,7 +103,7 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): ('20 Minutes', 1200), ], ), - ba.IntChoiceSetting( + bs.IntChoiceSetting( 'Mine Spawning', default=4000, choices=[ @@ -112,7 +113,7 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): ('2 Seconds', 2000), ], ), - ba.IntChoiceSetting( + bs.IntChoiceSetting( 'Bomb Spawning', choices=[ ('None', 0), @@ -123,7 +124,7 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): ], default=2000, ), - ba.IntChoiceSetting( + bs.IntChoiceSetting( 'Knockout Time', choices=[ ('8 Seconds', 8000), @@ -131,48 +132,48 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): ], default=5000, ), - ba.BoolSetting('Epic Mode', default=False), - ba.BoolSetting('Credits', default=True), + bs.BoolSetting('Epic Mode', default=False), + bs.BoolSetting('Credits', default=True), ] # We have some specific settings in teams mode. - if issubclass(sessiontype, ba.DualTeamSession): + if issubclass(sessiontype, bs.DualTeamSession): settings.append( - ba.BoolSetting('Entire Team Must Finish', default=False)) + bs.BoolSetting('Entire Team Must Finish', default=False)) return settings @classmethod - def supports_session_type(cls, sessiontype: Type[ba.Session]) -> bool: - return issubclass(sessiontype, ba.MultiTeamSession) + def supports_session_type(cls, sessiontype: Type[bs.Session]) -> bool: + return issubclass(sessiontype, bs.MultiTeamSession) @classmethod - def get_supported_maps(cls, sessiontype: Type[ba.Session]) -> List[str]: - return ba.getmaps('race') + def get_supported_maps(cls, sessiontype: Type[bs.Session]) -> List[str]: + return bs.app.classic.getmaps('race') def __init__(self, settings: dict): self._race_started = False super().__init__(settings) self._scoreboard = Scoreboard() - self._score_sound = ba.getsound('score') - self._swipsound = ba.getsound('swip') + self._score_sound = bs.getsound('score') + self._swipsound = bs.getsound('swip') self._last_team_time: Optional[float] = None self._front_race_region: Optional[int] = None - self._nub_tex = ba.gettexture('nub') - self._beep_1_sound = ba.getsound('raceBeep1') - self._beep_2_sound = ba.getsound('raceBeep2') - self.race_region_material: Optional[ba.Material] = None + self._nub_tex = bs.gettexture('nub') + self._beep_1_sound = bs.getsound('raceBeep1') + self._beep_2_sound = bs.getsound('raceBeep2') + self.race_region_material: Optional[bs.Material] = None self._regions: List[RaceRegion] = [] self._team_finish_pts: Optional[int] = None - self._time_text: Optional[ba.Actor] = None - self._cd_text: Optional[ba.Actor] = None + self._time_text: Optional[bs.Actor] = None + self._cd_text: Optional[bs.Actor] = None self._timer: Optional[OnScreenTimer] = None self._race_mines: Optional[List[RaceMine]] = None - self._race_mine_timer: Optional[ba.Timer] = None - self._scoreboard_timer: Optional[ba.Timer] = None - self._player_order_update_timer: Optional[ba.Timer] = None - self._start_lights: Optional[List[ba.Node]] = None - self._bomb_spawn_timer: Optional[ba.Timer] = None - self._knockout_timer: Optional[ba.Timer] = None + self._race_mine_timer: Optional[bs.Timer] = None + self._scoreboard_timer: Optional[bs.Timer] = None + self._player_order_update_timer: Optional[bs.Timer] = None + self._start_lights: Optional[List[bs.Node]] = None + self._bomb_spawn_timer: Optional[bs.Timer] = None + self._knockout_timer: Optional[bs.Timer] = None self._laps = int(settings['Laps']) self._entire_team_must_finish = bool( settings.get('Entire Team Must Finish', False)) @@ -185,11 +186,11 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): # Base class overrides. self.slow_motion = self._epic_mode - self.default_music = (ba.MusicType.EPIC_RACE - if self._epic_mode else ba.MusicType.RACE) + self.default_music = (bs.MusicType.EPIC_RACE + if self._epic_mode else bs.MusicType.RACE) def get_instance_description(self) -> Union[str, Sequence]: - if (isinstance(self.session, ba.DualTeamSession) + if (isinstance(self.session, bs.DualTeamSession) and self._entire_team_must_finish): t_str = ' Your entire team has to finish.' else: @@ -208,7 +209,7 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): super().on_transition_in() shared = SharedObjects.get() pts = self.map.get_def_points('race_point') - mat = self.race_region_material = ba.Material() + mat = self.race_region_material = bs.Material() mat.add_actions(conditions=('they_have_material', shared.player_material), actions=( @@ -224,28 +225,28 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): assert isinstance(player.actor, PlayerSpaz) assert player.actor.node pos = player.actor.node.position - light = ba.newnode('light', + light = bs.newnode('light', attrs={ 'position': pos, 'color': (1, 1, 0), 'height_attenuated': False, 'radius': 0.4 }) - ba.timer(0.5, light.delete) - ba.animate(light, 'intensity', {0: 0, 0.1: 1.0 * scale, 0.5: 0}) + bs.timer(0.5, light.delete) + bs.animate(light, 'intensity', {0: 0, 0.1: 1.0 * scale, 0.5: 0}) def _handle_race_point_collide(self) -> None: # FIXME: Tidy this up. # pylint: disable=too-many-statements # pylint: disable=too-many-branches # pylint: disable=too-many-nested-blocks - collision = ba.getcollision() + collision = bs.getcollision() try: region = collision.sourcenode.getdelegate(RaceRegion, True) player = collision.opposingnode.getdelegate(PlayerSpaz, True).getplayer( Player, True) - except ba.NotFoundError: + except bs.NotFoundError: return last_region = player.last_region @@ -259,8 +260,8 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): if this_region > last_region + 2: if player.is_alive(): assert player.actor - player.actor.handlemessage(ba.DieMessage()) - ba.screenmessage(ba.Lstr( + player.actor.handlemessage(bs.DieMessage()) + bs.broadcastmessage(babase.Lstr( translate=('statements', 'Killing ${NAME} for' ' skipping part of the track!'), subs=[('${NAME}', player.getname(full=True))]), @@ -279,7 +280,7 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): # In teams mode with all-must-finish on, the team lap # value is the min of all team players. # Otherwise its the max. - if isinstance(self.session, ba.DualTeamSession + if isinstance(self.session, bs.DualTeamSession ) and self._entire_team_must_finish: team.lap = min([p.lap for p in team.players]) else: @@ -290,7 +291,7 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): # In teams mode, hand out points based on the order # players come in. - if isinstance(self.session, ba.DualTeamSession): + if isinstance(self.session, bs.DualTeamSession): assert self._team_finish_pts is not None if self._team_finish_pts > 0: self.stats.player_scored(player, @@ -303,7 +304,7 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): player.finished = True assert player.actor player.actor.handlemessage( - ba.DieMessage(immediate=True)) + bs.DieMessage(immediate=True)) # Makes sure noone behind them passes them in rank # while finishing. @@ -311,26 +312,26 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): # If the whole team has finished the race. if team.lap == self._laps: - ba.playsound(self._score_sound) + self._score_sound.play() player.team.finished = True assert self._timer is not None - elapsed = ba.time() - self._timer.getstarttime() + elapsed = bs.time() - self._timer.getstarttime() self._last_team_time = player.team.time = elapsed self._check_end_game() # Team has yet to finish. else: - ba.playsound(self._swipsound) + self._swipsound.play() # They've just finished a lap but not the race. else: - ba.playsound(self._swipsound) + self._swipsound.play() self._flash_player(player, 0.3) # Print their lap number over their head. try: assert isinstance(player.actor, PlayerSpaz) - mathnode = ba.newnode('math', + mathnode = bs.newnode('math', owner=player.actor.node, attrs={ 'input1': (0, 1.9, 0), @@ -338,12 +339,12 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): }) player.actor.node.connectattr( 'torso_position', mathnode, 'input2') - tstr = ba.Lstr(resource='lapNumberText', + tstr = babase.Lstr(resource='lapNumberText', subs=[('${CURRENT}', str(player.lap + 1)), ('${TOTAL}', str(self._laps)) ]) - txtnode = ba.newnode('text', + txtnode = bs.newnode('text', owner=mathnode, attrs={ 'text': tstr, @@ -353,15 +354,15 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): 'h_align': 'center' }) mathnode.connectattr('output', txtnode, 'position') - ba.animate(txtnode, 'scale', { + bs.animate(txtnode, 'scale', { 0.0: 0, 0.2: 0.019, 2.0: 0.019, 2.2: 0 }) - ba.timer(2.3, mathnode.delete) + bs.timer(2.3, mathnode.delete) except Exception: - ba.print_exception('Error printing lap.') + babase.print_exception('Error printing lap.') def on_team_join(self, team: Team) -> None: self._update_scoreboard() @@ -372,9 +373,9 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): # A player leaving disqualifies the team if 'Entire Team Must Finish' # is on (otherwise in teams mode everyone could just leave except the # leading player to win). - if (isinstance(self.session, ba.DualTeamSession) + if (isinstance(self.session, bs.DualTeamSession) and self._entire_team_must_finish): - ba.screenmessage(ba.Lstr( + bs.broadcastmessage(babase.Lstr( translate=('statements', '${TEAM} is disqualified because ${PLAYER} left'), subs=[('${TEAM}', player.team.name), @@ -383,18 +384,18 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): player.team.finished = True player.team.time = None player.team.lap = 0 - ba.playsound(ba.getsound('boo')) + bs.getsound('boo').play() for otherplayer in player.team.players: otherplayer.lap = 0 otherplayer.finished = True try: if otherplayer.actor is not None: - otherplayer.actor.handlemessage(ba.DieMessage()) + otherplayer.actor.handlemessage(bs.DieMessage()) except Exception: - ba.print_exception('Error sending DieMessage.') + babase.print_exception('Error sending DieMessage.') # Defer so team/player lists will be updated. - ba.pushcall(self._check_end_game) + babase.pushcall(self._check_end_game) def _update_scoreboard(self) -> None: for team in self.teams: @@ -402,7 +403,7 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): if not distances: teams_dist = 0.0 else: - if (isinstance(self.session, ba.DualTeamSession) + if (isinstance(self.session, bs.DualTeamSession) and self._entire_team_must_finish): teams_dist = min(distances) else: @@ -415,14 +416,14 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): show_value=False) def on_begin(self) -> None: - from bastd.actor.onscreentimer import OnScreenTimer + from bascenev1lib.actor.onscreentimer import OnScreenTimer super().on_begin() self.setup_standard_time_limit(self._time_limit) self.setup_standard_powerup_drops() self._team_finish_pts = 100 if self._credits: - self._cd_text = ba.NodeActor( - ba.newnode('text', + self._cd_text = bs.NodeActor( + bs.newnode('text', attrs={ 'position': (0, 0), 'h_attach': 'center', @@ -437,8 +438,8 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): })) # Throw a timer up on-screen. - self._time_text = ba.NodeActor( - ba.newnode('text', + self._time_text = bs.NodeActor( + bs.newnode('text', attrs={ 'v_attach': 'top', 'h_attach': 'center', @@ -458,14 +459,14 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): for p in self.map.get_def_points('race_mine') ] if self._race_mines: - self._race_mine_timer = ba.Timer(0.001 * self._mine_spawning, + self._race_mine_timer = bs.Timer(0.001 * self._mine_spawning, self._update_race_mine, repeat=True) - self._scoreboard_timer = ba.Timer(0.25, + self._scoreboard_timer = bs.Timer(0.25, self._update_scoreboard, repeat=True) - self._player_order_update_timer = ba.Timer(0.25, + self._player_order_update_timer = bs.Timer(0.25, self._update_player_order, repeat=True) @@ -478,30 +479,30 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): lstart = 7.1 * t_scale inc = 1.25 * t_scale - ba.timer(lstart, self._do_light_1) - ba.timer(lstart + inc, self._do_light_2) - ba.timer(lstart + 2 * inc, self._do_light_3) - ba.timer(lstart + 3 * inc, self._start_race) + bs.timer(lstart, self._do_light_1) + bs.timer(lstart + inc, self._do_light_2) + bs.timer(lstart + 2 * inc, self._do_light_3) + bs.timer(lstart + 3 * inc, self._start_race) self._start_lights = [] for i in range(4): - lnub = ba.newnode('image', + lnub = bs.newnode('image', attrs={ - 'texture': ba.gettexture('nub'), + 'texture': bs.gettexture('nub'), 'opacity': 1.0, 'absolute_scale': True, 'position': (-75 + i * 50, light_y), 'scale': (50, 50), 'attach': 'center' }) - ba.animate( + bs.animate( lnub, 'opacity', { 4.0 * t_scale: 0, 5.0 * t_scale: 1.0, 12.0 * t_scale: 1.0, 12.5 * t_scale: 0.0 }) - ba.timer(13.0 * t_scale, lnub.delete) + bs.timer(13.0 * t_scale, lnub.delete) self._start_lights.append(lnub) self._start_lights[0].color = (0.2, 0, 0) @@ -512,45 +513,45 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): def _do_light_1(self) -> None: assert self._start_lights is not None self._start_lights[0].color = (1.0, 0, 0) - ba.playsound(self._beep_1_sound) + self._beep_1_sound.play() def _do_light_2(self) -> None: assert self._start_lights is not None self._start_lights[1].color = (1.0, 0, 0) - ba.playsound(self._beep_1_sound) + self._beep_1_sound.play() def _do_light_3(self) -> None: assert self._start_lights is not None self._start_lights[2].color = (1.0, 0.3, 0) - ba.playsound(self._beep_1_sound) + self._beep_1_sound.play() def _start_race(self) -> None: assert self._start_lights is not None self._start_lights[3].color = (0.0, 1.0, 0) - ba.playsound(self._beep_2_sound) + self._beep_2_sound.play() for player in self.players: if player.actor is not None: try: assert isinstance(player.actor, PlayerSpaz) player.actor.connect_controls_to_player() except Exception: - ba.print_exception('Error in race player connects.') + babase.print_exception('Error in race player connects.') assert self._timer is not None self._timer.start() if self._bomb_spawning != 0: - self._bomb_spawn_timer = ba.Timer(0.001 * self._bomb_spawning, + self._bomb_spawn_timer = bs.Timer(0.001 * self._bomb_spawning, self._spawn_bomb, repeat=True) def knock_players(): - activity = _ba.get_foreground_host_activity() - gnode = ba.getactivity().globalsnode + activity = bs.get_foreground_host_activity() + gnode = bs.getactivity().globalsnode for players in activity.players: gnode.tint = (0.5, 0.5, 0.5) node = players.actor.node node.handlemessage('knockout', 600.0) - self.text_offset = ba.newnode('math', + self.text_offset = bs.newnode('math', owner=node, attrs={'input1': (-0.5, 0.5, 0.25), 'operation': 'add'}) @@ -558,7 +559,7 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): 'torso_position', self.text_offset, 'input2') - self.text = ba.newnode('text', + self.text = bs.newnode('text', owner=node, attrs={ 'h_align': 'right', @@ -571,12 +572,12 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): 'output', self.text, 'position') - ba.animate(self.text, 'scale', {0: 0.0, 1.0: 0.01}) - ba.timer(2, self.text.delete) + bs.animate(self.text, 'scale', {0: 0.0, 1.0: 0.01}) + bs.timer(2, self.text.delete) if self._knockout_time != 0: knock_time = 0.001 * self._knockout_time - self._knockout_timer = ba.Timer(knock_time, + self._knockout_timer = bs.Timer(knock_time, knock_players, repeat=True) @@ -586,18 +587,18 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): # Calc all player distances. for player in self.players: - pos: Optional[ba.Vec3] + pos: Optional[babase.Vec3] try: pos = player.position - except ba.NotFoundError: + except bs.NotFoundError: pos = None if pos is not None: r_index = player.last_region rg1 = self._regions[r_index] - r1pt = ba.Vec3(rg1.pos[:3]) + r1pt = babase.Vec3(rg1.pos[:3]) rg2 = self._regions[0] if r_index == len( self._regions) - 1 else self._regions[r_index + 1] - r2pt = ba.Vec3(rg2.pos[:3]) + r2pt = babase.Vec3(rg2.pos[:3]) r2dist = (pos - r2pt).length() amt = 1.0 - (r2dist / (r2pt - r1pt).length()) amt = player.lap + (r_index + amt) * (1.0 / len(self._regions)) @@ -628,8 +629,8 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): (-region_scale * pos[5], region_scale * pos[5])) pos = (pos[0] + random.uniform(*x_range), pos[1] + 1.0, pos[2] + random.uniform(*z_range)) - ba.timer(random.uniform(0.0, 2.0), - ba.WeakCall(self._spawn_bomb_at_pos, pos)) + bs.timer(random.uniform(0.0, 2.0), + bs.WeakCall(self._spawn_bomb_at_pos, pos)) def _spawn_bomb_at_pos(self, pos: Sequence[float]) -> None: if self.has_ended(): @@ -645,15 +646,15 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): def _flash_mine(self, i: int) -> None: assert self._race_mines is not None rmine = self._race_mines[i] - light = ba.newnode('light', + light = bs.newnode('light', attrs={ 'position': rmine.point[:3], 'color': (1, 0.2, 0.2), 'radius': 0.1, 'height_attenuated': False }) - ba.animate(light, 'intensity', {0.0: 0, 0.1: 1.0, 0.2: 0}, loop=True) - ba.timer(1.0, light.delete) + bs.animate(light, 'intensity', {0.0: 0, 0.1: 1.0, 0.2: 0}, loop=True) + bs.timer(1.0, light.delete) def _update_race_mine(self) -> None: assert self._race_mines is not None @@ -667,9 +668,9 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): assert rmine is not None if not rmine.mine: self._flash_mine(m_index) - ba.timer(0.95, ba.Call(self._make_mine, m_index)) + bs.timer(0.95, babase.Call(self._make_mine, m_index)) - def spawn_player(self, player: Player) -> ba.Actor: + def spawn_player(self, player: Player) -> bs.Actor: if player.team.finished: # FIXME: This is not type-safe! # This call is expected to always return an Actor! @@ -692,7 +693,7 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): # Prevent controlling of characters before the start of the race. if not self._race_started: spaz.disconnect_controls_from_player() - mathnode = ba.newnode('math', + mathnode = bs.newnode('math', owner=spaz.node, attrs={ 'input1': (0, 1.4, 0), @@ -700,7 +701,7 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): }) spaz.node.connectattr('torso_position', mathnode, 'input2') - distance_txt = ba.newnode('text', + distance_txt = bs.newnode('text', owner=spaz.node, attrs={ 'text': '', @@ -730,14 +731,14 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): # In teams mode its over as soon as any team finishes the race # FIXME: The get_ffa_point_awards code looks dangerous. - if isinstance(session, ba.DualTeamSession): + if isinstance(session, bs.DualTeamSession): self.end_game() else: # In ffa we keep the race going while there's still any points # to be handed out. Find out how many points we have to award # and how many teams have finished, and once that matches # we're done. - assert isinstance(session, ba.FreeForAllSession) + assert isinstance(session, bs.FreeForAllSession) points_to_award = len(session.get_ffa_point_awards()) if teams_completed >= points_to_award - teams_completed: self.end_game() @@ -754,7 +755,7 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): endtime=None if self._last_team_time is None else ( self._timer.getstarttime() + self._last_team_time)) - results = ba.GameResults() + results = bs.GameResults() for team in self.teams: if team.time is not None: @@ -768,10 +769,10 @@ class SleepRaceGame(ba.TeamGameActivity[Player, Team]): # odd to be announcing that now. self.end(results=results, announce_winning_team=isinstance(self.session, - ba.DualTeamSession)) + bs.DualTeamSession)) def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.PlayerDiedMessage): + if isinstance(msg, bs.PlayerDiedMessage): # Augment default behavior. super().handlemessage(msg) player = msg.getplayer(Player) diff --git a/plugins/minigames/snake.py b/plugins/minigames/snake.py index 84e912b..454a070 100644 --- a/plugins/minigames/snake.py +++ b/plugins/minigames/snake.py @@ -1,19 +1,22 @@ +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) # snake # Released under the MIT License. See LICENSE for details. # """Snake game by SEBASTIAN2059""" -# ba_meta require api 7 +# ba_meta require api 8 # (see https://ballistica.net/wiki/meta-tag-system) from __future__ import annotations from typing import TYPE_CHECKING -import ba -from bastd.actor.playerspaz import PlayerSpaz -from bastd.actor.scoreboard import Scoreboard -from bastd.actor import bomb as stdbomb +import babase +import bauiv1 as bui +import bascenev1 as bs +from bascenev1lib.actor.playerspaz import PlayerSpaz +from bascenev1lib.actor.scoreboard import Scoreboard +from bascenev1lib.actor import bomb as stdbomb if TYPE_CHECKING: from typing import Any, Type, List, Dict, Tuple, Union, Sequence, Optional @@ -29,7 +32,7 @@ class ScoreMessage: return self.player -class Player(ba.Player['Team']): +class Player(bs.Player['Team']): """Our player type for this game.""" def __init__(self) -> None: @@ -38,14 +41,14 @@ class Player(ba.Player['Team']): self.actived = None -class Team(ba.Team[Player]): +class Team(bs.Team[Player]): """Our team type for this game.""" def __init__(self) -> None: self.score = 0 -lang = ba.app.lang.language +lang = bs.app.lang.language if lang == 'Spanish': description = 'Sobrevive a un número determinado de minas para ganar.' join_description = 'Corre y no te dejes matar.' @@ -65,15 +68,15 @@ class Custom_Mine(stdbomb.Bomb): source_player=source_player) def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.HitMessage): + if isinstance(msg, bs.HitMessage): return else: super().handlemessage(msg) -# ba_meta export game +# ba_meta export bascenev1.GameActivity -class SnakeGame(ba.TeamGameActivity[Player, Team]): +class SnakeGame(bs.TeamGameActivity[Player, Team]): """A game type based on acquiring kills.""" name = 'Snake' @@ -84,15 +87,15 @@ class SnakeGame(ba.TeamGameActivity[Player, Team]): @classmethod def get_available_settings( - cls, sessiontype: Type[ba.Session]) -> List[ba.Setting]: + cls, sessiontype: Type[bs.Session]) -> List[babase.Setting]: settings = [ - ba.IntSetting( + bs.IntSetting( 'Score to Win', min_value=40, default=80, increment=5, ), - ba.IntChoiceSetting( + bs.IntChoiceSetting( 'Time Limit', choices=[ ('None', 0), @@ -104,7 +107,7 @@ class SnakeGame(ba.TeamGameActivity[Player, Team]): ], default=0, ), - ba.FloatChoiceSetting( + bs.FloatChoiceSetting( 'Respawn Times', choices=[ ('Shorter', 0.25), @@ -115,27 +118,27 @@ class SnakeGame(ba.TeamGameActivity[Player, Team]): ], default=1.0, ), - ba.BoolSetting('Epic Mode', default=False), + bs.BoolSetting('Epic Mode', default=False), ] return settings @classmethod - def supports_session_type(cls, sessiontype: Type[ba.Session]) -> bool: - return (issubclass(sessiontype, ba.DualTeamSession) - or issubclass(sessiontype, ba.FreeForAllSession)) + def supports_session_type(cls, sessiontype: Type[bs.Session]) -> bool: + return (issubclass(sessiontype, bs.DualTeamSession) + or issubclass(sessiontype, bs.FreeForAllSession)) @classmethod - def get_supported_maps(cls, sessiontype: Type[ba.Session]) -> List[str]: - return ba.getmaps('melee') + def get_supported_maps(cls, sessiontype: Type[bs.Session]) -> List[str]: + return bs.app.classic.getmaps('melee') def __init__(self, settings: dict): super().__init__(settings) self._scoreboard = Scoreboard() self._score_to_win: Optional[int] = None - self._dingsound = ba.getsound('dingSmall') + self._dingsound = bs.getsound('dingSmall') - self._beep_1_sound = ba.getsound('raceBeep1') - self._beep_2_sound = ba.getsound('raceBeep2') + self._beep_1_sound = bs.getsound('raceBeep1') + self._beep_2_sound = bs.getsound('raceBeep2') self._epic_mode = bool(settings['Epic Mode']) self._kills_to_win_per_player = int( @@ -146,8 +149,8 @@ class SnakeGame(ba.TeamGameActivity[Player, Team]): # Base class overrides. self.slow_motion = self._epic_mode - self.default_music = (ba.MusicType.EPIC if self._epic_mode else - ba.MusicType.TO_THE_DEATH) + self.default_music = (bs.MusicType.EPIC if self._epic_mode else + bs.MusicType.TO_THE_DEATH) def get_instance_description(self) -> Union[str, Sequence]: return join_description @@ -178,30 +181,30 @@ class SnakeGame(ba.TeamGameActivity[Player, Team]): lstart = 7.1 * t_scale inc = 1.25 * t_scale - ba.timer(lstart, self._do_light_1) - ba.timer(lstart + inc, self._do_light_2) - ba.timer(lstart + 2 * inc, self._do_light_3) - ba.timer(lstart + 3 * inc, self._start_race) + bs.timer(lstart, self._do_light_1) + bs.timer(lstart + inc, self._do_light_2) + bs.timer(lstart + 2 * inc, self._do_light_3) + bs.timer(lstart + 3 * inc, self._start_race) self._start_lights = [] for i in range(4): - lnub = ba.newnode('image', + lnub = bs.newnode('image', attrs={ - 'texture': ba.gettexture('nub'), + 'texture': bs.gettexture('nub'), 'opacity': 1.0, 'absolute_scale': True, 'position': (-75 + i * 50, light_y), 'scale': (50, 50), 'attach': 'center' }) - ba.animate( + bs.animate( lnub, 'opacity', { 4.0 * t_scale: 0, 5.0 * t_scale: 1.0, 12.0 * t_scale: 1.0, 12.5 * t_scale: 0.0 }) - ba.timer(13.0 * t_scale, lnub.delete) + bs.timer(13.0 * t_scale, lnub.delete) self._start_lights.append(lnub) self._start_lights[0].color = (0.2, 0, 0) @@ -212,22 +215,22 @@ class SnakeGame(ba.TeamGameActivity[Player, Team]): def _do_light_1(self) -> None: assert self._start_lights is not None self._start_lights[0].color = (1.0, 0, 0) - ba.playsound(self._beep_1_sound) + self._beep_1_sound.play() def _do_light_2(self) -> None: assert self._start_lights is not None self._start_lights[1].color = (1.0, 0, 0) - ba.playsound(self._beep_1_sound) + self._beep_1_sound.play() def _do_light_3(self) -> None: assert self._start_lights is not None self._start_lights[2].color = (1.0, 0.3, 0) - ba.playsound(self._beep_1_sound) + self._beep_1_sound.play() def _start_race(self) -> None: assert self._start_lights is not None self._start_lights[3].color = (0.0, 1.0, 0) - ba.playsound(self._beep_2_sound) + self._beep_2_sound.play() self._started = True @@ -235,7 +238,7 @@ class SnakeGame(ba.TeamGameActivity[Player, Team]): self.generate_mines(player) # overriding the default character spawning.. - def spawn_player(self, player: Player) -> ba.Actor: + def spawn_player(self, player: Player) -> bs.Actor: spaz = self.spawn_player_spaz(player) # Let's reconnect this player's controls to this @@ -252,7 +255,7 @@ class SnakeGame(ba.TeamGameActivity[Player, Team]): def generate_mines(self, player: Player): try: - player.actived = ba.Timer(0.5, ba.Call(self.spawn_mine, player), repeat=True) + player.actived = bs.Timer(0.5, babase.Call(self.spawn_mine, player), repeat=True) except Exception as e: print('Exception -> ' + str(e)) @@ -271,7 +274,7 @@ class SnakeGame(ba.TeamGameActivity[Player, Team]): def arm(): mine.arm() - ba.timer(0.5, arm) + bs.timer(0.5, arm) player.mines.append(mine) if len(player.mines) > 15: @@ -286,7 +289,7 @@ class SnakeGame(ba.TeamGameActivity[Player, Team]): self.handlemessage(ScoreMessage(player)) def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.PlayerDiedMessage): + if isinstance(msg, bs.PlayerDiedMessage): # Augment standard behavior. super().handlemessage(msg) @@ -304,7 +307,7 @@ class SnakeGame(ba.TeamGameActivity[Player, Team]): assert self._score_to_win is not None if any(team.score >= self._score_to_win for team in self.teams): - self.end_game() # ba.timer(0.5, self.end_game) + self.end_game() # bs.timer(0.5, self.end_game) else: return super().handlemessage(msg) return None @@ -315,7 +318,7 @@ class SnakeGame(ba.TeamGameActivity[Player, Team]): self._score_to_win) def end_game(self) -> None: - results = ba.GameResults() + results = bs.GameResults() for team in self.teams: results.set_team_score(team, team.score) self.end(results=results) diff --git a/plugins/minigames/squid_race.py b/plugins/minigames/squid_race.py index d8cd54b..0dea319 100644 --- a/plugins/minigames/squid_race.py +++ b/plugins/minigames/squid_race.py @@ -1,8 +1,9 @@ +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) # Released under the MIT License. See LICENSE for details. # """Defines Race mini-game.""" -# ba_meta require api 7 +# ba_meta require api 8 # (see https://ballistica.net/wiki/meta-tag-system) from __future__ import annotations @@ -11,16 +12,18 @@ import random from typing import TYPE_CHECKING from dataclasses import dataclass -import ba -from bastd.actor.bomb import Bomb, Blast, ExplodeHitMessage -from bastd.actor.playerspaz import PlayerSpaz -from bastd.actor.scoreboard import Scoreboard -from bastd.gameutils import SharedObjects +import babase +import bauiv1 as bui +import bascenev1 as bs +from bascenev1lib.actor.bomb import Bomb, Blast, ExplodeHitMessage +from bascenev1lib.actor.playerspaz import PlayerSpaz +from bascenev1lib.actor.scoreboard import Scoreboard +from bascenev1lib.gameutils import SharedObjects if TYPE_CHECKING: from typing import (Any, Type, Tuple, List, Sequence, Optional, Dict, Union) - from bastd.actor.onscreentimer import OnScreenTimer + from bascenev1lib.actor.onscreentimer import OnScreenTimer class NewBlast(Blast): @@ -38,7 +41,7 @@ class RaceMine: mine: Optional[Bomb] -class RaceRegion(ba.Actor): +class RaceRegion(bs.Actor): """Region used to track progress during a race.""" def __init__(self, pt: Sequence[float], index: int): @@ -47,7 +50,7 @@ class RaceRegion(ba.Actor): assert isinstance(activity, RaceGame) self.pos = pt self.index = index - self.node = ba.newnode( + self.node = bs.newnode( 'region', delegate=self, attrs={ @@ -58,11 +61,11 @@ class RaceRegion(ba.Actor): }) -class Player(ba.Player['Team']): +class Player(bs.Player['Team']): """Our player type for this game.""" def __init__(self) -> None: - self.distance_txt: Optional[ba.Node] = None + self.distance_txt: Optional[bs.Node] = None self.last_region = 0 self.lap = 0 self.distance = 0.0 @@ -70,7 +73,7 @@ class Player(ba.Player['Team']): self.rank: Optional[int] = None -class Team(ba.Team[Player]): +class Team(bs.Team[Player]): """Our team type for this game.""" def __init__(self) -> None: @@ -79,22 +82,22 @@ class Team(ba.Team[Player]): self.finished = False -# ba_meta export game -class SquidRaceGame(ba.TeamGameActivity[Player, Team]): +# ba_meta export bascenev1.GameActivity +class SquidRaceGame(bs.TeamGameActivity[Player, Team]): """Game of racing around a track.""" name = 'Squid Race' description = 'Run real fast!' - scoreconfig = ba.ScoreConfig(label='Time', + scoreconfig = bs.ScoreConfig(label='Time', lower_is_better=True, - scoretype=ba.ScoreType.MILLISECONDS) + scoretype=bs.ScoreType.MILLISECONDS) @classmethod def get_available_settings( - cls, sessiontype: Type[ba.Session]) -> List[ba.Setting]: + cls, sessiontype: Type[bs.Session]) -> List[babase.Setting]: settings = [ - ba.IntSetting('Laps', min_value=1, default=3, increment=1), - ba.IntChoiceSetting( + bs.IntSetting('Laps', min_value=1, default=3, increment=1), + bs.IntChoiceSetting( 'Time Limit', default=0, choices=[ @@ -106,7 +109,7 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): ('20 Minutes', 1200), ], ), - ba.IntChoiceSetting( + bs.IntChoiceSetting( 'Mine Spawning', default=4000, choices=[ @@ -116,7 +119,7 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): ('2 Seconds', 2000), ], ), - ba.IntChoiceSetting( + bs.IntChoiceSetting( 'Bomb Spawning', choices=[ ('None', 0), @@ -127,49 +130,49 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): ], default=2000, ), - ba.BoolSetting('Epic Mode', default=False), + bs.BoolSetting('Epic Mode', default=False), ] # We have some specific settings in teams mode. - if issubclass(sessiontype, ba.DualTeamSession): + if issubclass(sessiontype, bs.DualTeamSession): settings.append( - ba.BoolSetting('Entire Team Must Finish', default=False)) + bs.BoolSetting('Entire Team Must Finish', default=False)) return settings @classmethod - def supports_session_type(cls, sessiontype: Type[ba.Session]) -> bool: - return issubclass(sessiontype, ba.MultiTeamSession) + def supports_session_type(cls, sessiontype: Type[bs.Session]) -> bool: + return issubclass(sessiontype, bs.MultiTeamSession) @classmethod - def get_supported_maps(cls, sessiontype: Type[ba.Session]) -> List[str]: - return ba.getmaps('race') + def get_supported_maps(cls, sessiontype: Type[bs.Session]) -> List[str]: + return bs.app.classic.getmaps('race') def __init__(self, settings: dict): self._race_started = False super().__init__(settings) self._scoreboard = Scoreboard() - self._score_sound = ba.getsound('score') - self._swipsound = ba.getsound('swip') + self._score_sound = bs.getsound('score') + self._swipsound = bs.getsound('swip') self._last_team_time: Optional[float] = None self._front_race_region: Optional[int] = None - self._nub_tex = ba.gettexture('nub') - self._beep_1_sound = ba.getsound('raceBeep1') - self._beep_2_sound = ba.getsound('raceBeep2') - self.race_region_material: Optional[ba.Material] = None + self._nub_tex = bs.gettexture('nub') + self._beep_1_sound = bs.getsound('raceBeep1') + self._beep_2_sound = bs.getsound('raceBeep2') + self.race_region_material: Optional[bs.Material] = None self._regions: List[RaceRegion] = [] self._team_finish_pts: Optional[int] = None - self._time_text: Optional[ba.Actor] = None + self._time_text: Optional[bs.Actor] = None self._timer: Optional[OnScreenTimer] = None self._race_mines: Optional[List[RaceMine]] = None - self._race_mine_timer: Optional[ba.Timer] = None - self._scoreboard_timer: Optional[ba.Timer] = None - self._player_order_update_timer: Optional[ba.Timer] = None - self._start_lights: Optional[List[ba.Node]] = None - self._squid_lights: Optional[List[ba.Node]] = None + self._race_mine_timer: Optional[bs.Timer] = None + self._scoreboard_timer: Optional[bs.Timer] = None + self._player_order_update_timer: Optional[bs.Timer] = None + self._start_lights: Optional[List[bs.Node]] = None + self._squid_lights: Optional[List[bs.Node]] = None self._countdown_timer: int = 0 self._sq_mode: str = 'Easy' - self._tick_timer: Optional[ba.Timer] = None - self._bomb_spawn_timer: Optional[ba.Timer] = None + self._tick_timer: Optional[bs.Timer] = None + self._bomb_spawn_timer: Optional[bs.Timer] = None self._laps = int(settings['Laps']) self._entire_team_must_finish = bool( settings.get('Entire Team Must Finish', False)) @@ -179,25 +182,25 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): self._epic_mode = bool(settings['Epic Mode']) self._countdownsounds = { - 10: ba.getsound('announceTen'), - 9: ba.getsound('announceNine'), - 8: ba.getsound('announceEight'), - 7: ba.getsound('announceSeven'), - 6: ba.getsound('announceSix'), - 5: ba.getsound('announceFive'), - 4: ba.getsound('announceFour'), - 3: ba.getsound('announceThree'), - 2: ba.getsound('announceTwo'), - 1: ba.getsound('announceOne') + 10: bs.getsound('announceTen'), + 9: bs.getsound('announceNine'), + 8: bs.getsound('announceEight'), + 7: bs.getsound('announceSeven'), + 6: bs.getsound('announceSix'), + 5: bs.getsound('announceFive'), + 4: bs.getsound('announceFour'), + 3: bs.getsound('announceThree'), + 2: bs.getsound('announceTwo'), + 1: bs.getsound('announceOne') } # Base class overrides. self.slow_motion = self._epic_mode - self.default_music = (ba.MusicType.EPIC_RACE - if self._epic_mode else ba.MusicType.RACE) + self.default_music = (bs.MusicType.EPIC_RACE + if self._epic_mode else bs.MusicType.RACE) def get_instance_description(self) -> Union[str, Sequence]: - if (isinstance(self.session, ba.DualTeamSession) + if (isinstance(self.session, bs.DualTeamSession) and self._entire_team_must_finish): t_str = ' Your entire team has to finish.' else: @@ -216,7 +219,7 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): super().on_transition_in() shared = SharedObjects.get() pts = self.map.get_def_points('race_point') - mat = self.race_region_material = ba.Material() + mat = self.race_region_material = bs.Material() mat.add_actions(conditions=('they_have_material', shared.player_material), actions=( @@ -232,28 +235,28 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): assert isinstance(player.actor, PlayerSpaz) assert player.actor.node pos = player.actor.node.position - light = ba.newnode('light', + light = bs.newnode('light', attrs={ 'position': pos, 'color': (1, 1, 0), 'height_attenuated': False, 'radius': 0.4 }) - ba.timer(0.5, light.delete) - ba.animate(light, 'intensity', {0: 0, 0.1: 1.0 * scale, 0.5: 0}) + bs.timer(0.5, light.delete) + bs.animate(light, 'intensity', {0: 0, 0.1: 1.0 * scale, 0.5: 0}) def _handle_race_point_collide(self) -> None: # FIXME: Tidy this up. # pylint: disable=too-many-statements # pylint: disable=too-many-branches # pylint: disable=too-many-nested-blocks - collision = ba.getcollision() + collision = bs.getcollision() try: region = collision.sourcenode.getdelegate(RaceRegion, True) player = collision.opposingnode.getdelegate(PlayerSpaz, True).getplayer( Player, True) - except ba.NotFoundError: + except bs.NotFoundError: return last_region = player.last_region @@ -267,8 +270,8 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): if this_region > last_region + 2: if player.is_alive(): assert player.actor - player.actor.handlemessage(ba.DieMessage()) - ba.screenmessage(ba.Lstr( + player.actor.handlemessage(bs.DieMessage()) + bs.broadcastmessage(babase.Lstr( translate=('statements', 'Killing ${NAME} for' ' skipping part of the track!'), subs=[('${NAME}', player.getname(full=True))]), @@ -287,7 +290,7 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): # In teams mode with all-must-finish on, the team lap # value is the min of all team players. # Otherwise its the max. - if isinstance(self.session, ba.DualTeamSession + if isinstance(self.session, bs.DualTeamSession ) and self._entire_team_must_finish: team.lap = min([p.lap for p in team.players]) else: @@ -298,7 +301,7 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): # In teams mode, hand out points based on the order # players come in. - if isinstance(self.session, ba.DualTeamSession): + if isinstance(self.session, bs.DualTeamSession): assert self._team_finish_pts is not None if self._team_finish_pts > 0: self.stats.player_scored(player, @@ -311,7 +314,7 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): player.finished = True assert player.actor player.actor.handlemessage( - ba.DieMessage(immediate=True)) + bs.DieMessage(immediate=True)) # Makes sure noone behind them passes them in rank # while finishing. @@ -319,25 +322,25 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): # If the whole team has finished the race. if team.lap == self._laps: - ba.playsound(self._score_sound) + self._score_sound.play() player.team.finished = True assert self._timer is not None - elapsed = ba.time() - self._timer.getstarttime() + elapsed = bs.time() - self._timer.getstarttime() self._last_team_time = player.team.time = elapsed # Team has yet to finish. else: - ba.playsound(self._swipsound) + self._swipsound.play() # They've just finished a lap but not the race. else: - ba.playsound(self._swipsound) + self._swipsound.play() self._flash_player(player, 0.3) # Print their lap number over their head. try: assert isinstance(player.actor, PlayerSpaz) - mathnode = ba.newnode('math', + mathnode = bs.newnode('math', owner=player.actor.node, attrs={ 'input1': (0, 1.9, 0), @@ -345,12 +348,12 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): }) player.actor.node.connectattr( 'torso_position', mathnode, 'input2') - tstr = ba.Lstr(resource='lapNumberText', + tstr = babase.Lstr(resource='lapNumberText', subs=[('${CURRENT}', str(player.lap + 1)), ('${TOTAL}', str(self._laps)) ]) - txtnode = ba.newnode('text', + txtnode = bs.newnode('text', owner=mathnode, attrs={ 'text': tstr, @@ -360,15 +363,15 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): 'h_align': 'center' }) mathnode.connectattr('output', txtnode, 'position') - ba.animate(txtnode, 'scale', { + bs.animate(txtnode, 'scale', { 0.0: 0, 0.2: 0.019, 2.0: 0.019, 2.2: 0 }) - ba.timer(2.3, mathnode.delete) + bs.timer(2.3, mathnode.delete) except Exception: - ba.print_exception('Error printing lap.') + babase.print_exception('Error printing lap.') def on_team_join(self, team: Team) -> None: self._update_scoreboard() @@ -377,8 +380,8 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): # Don't allow joining after we start # (would enable leave/rejoin tomfoolery). if self.has_begun(): - ba.screenmessage( - ba.Lstr(resource='playerDelayedJoinText', + bs.broadcastmessage( + babase.Lstr(resource='playerDelayedJoinText', subs=[('${PLAYER}', player.getname(full=True))]), color=(0, 1, 0), ) @@ -391,9 +394,9 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): # A player leaving disqualifies the team if 'Entire Team Must Finish' # is on (otherwise in teams mode everyone could just leave except the # leading player to win). - if (isinstance(self.session, ba.DualTeamSession) + if (isinstance(self.session, bs.DualTeamSession) and self._entire_team_must_finish): - ba.screenmessage(ba.Lstr( + bs.broadcastmessage(babase.Lstr( translate=('statements', '${TEAM} is disqualified because ${PLAYER} left'), subs=[('${TEAM}', player.team.name), @@ -402,18 +405,18 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): player.team.finished = True player.team.time = None player.team.lap = 0 - ba.playsound(ba.getsound('boo')) + bs.getsound('boo').play() for otherplayer in player.team.players: otherplayer.lap = 0 otherplayer.finished = True try: if otherplayer.actor is not None: - otherplayer.actor.handlemessage(ba.DieMessage()) + otherplayer.actor.handlemessage(bs.DieMessage()) except Exception: - ba.print_exception('Error sending DieMessage.') + babase.print_exception('Error sending DieMessage.') # Defer so team/player lists will be updated. - ba.pushcall(self._check_end_game) + babase.pushcall(self._check_end_game) def _update_scoreboard(self) -> None: for team in self.teams: @@ -421,7 +424,7 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): if not distances: teams_dist = 0.0 else: - if (isinstance(self.session, ba.DualTeamSession) + if (isinstance(self.session, bs.DualTeamSession) and self._entire_team_must_finish): teams_dist = min(distances) else: @@ -434,15 +437,15 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): show_value=False) def on_begin(self) -> None: - from bastd.actor.onscreentimer import OnScreenTimer + from bascenev1lib.actor.onscreentimer import OnScreenTimer super().on_begin() self.setup_standard_time_limit(self._time_limit) self.setup_standard_powerup_drops() self._team_finish_pts = 100 # Throw a timer up on-screen. - self._time_text = ba.NodeActor( - ba.newnode('text', + self._time_text = bs.NodeActor( + bs.newnode('text', attrs={ 'v_attach': 'top', 'h_attach': 'center', @@ -462,14 +465,14 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): for p in self.map.get_def_points('race_mine') ] if self._race_mines: - self._race_mine_timer = ba.Timer(0.001 * self._mine_spawning, + self._race_mine_timer = bs.Timer(0.001 * self._mine_spawning, self._update_race_mine, repeat=True) - self._scoreboard_timer = ba.Timer(0.25, + self._scoreboard_timer = bs.Timer(0.25, self._update_scoreboard, repeat=True) - self._player_order_update_timer = ba.Timer(0.25, + self._player_order_update_timer = bs.Timer(0.25, self._update_player_order, repeat=True) @@ -482,30 +485,30 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): lstart = 7.1 * t_scale inc = 1.25 * t_scale - ba.timer(lstart, self._do_light_1) - ba.timer(lstart + inc, self._do_light_2) - ba.timer(lstart + 2 * inc, self._do_light_3) - ba.timer(lstart + 3 * inc, self._start_race) + bs.timer(lstart, self._do_light_1) + bs.timer(lstart + inc, self._do_light_2) + bs.timer(lstart + 2 * inc, self._do_light_3) + bs.timer(lstart + 3 * inc, self._start_race) self._start_lights = [] for i in range(4): - lnub = ba.newnode('image', + lnub = bs.newnode('image', attrs={ - 'texture': ba.gettexture('nub'), + 'texture': bs.gettexture('nub'), 'opacity': 1.0, 'absolute_scale': True, 'position': (-75 + i * 50, light_y), 'scale': (50, 50), 'attach': 'center' }) - ba.animate( + bs.animate( lnub, 'opacity', { 4.0 * t_scale: 0, 5.0 * t_scale: 1.0, 12.0 * t_scale: 1.0, 12.5 * t_scale: 0.0 }) - ba.timer(13.0 * t_scale, lnub.delete) + bs.timer(13.0 * t_scale, lnub.delete) self._start_lights.append(lnub) self._start_lights[0].color = (0.2, 0, 0) @@ -515,16 +518,16 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): self._squid_lights = [] for i in range(2): - lnub = ba.newnode('image', + lnub = bs.newnode('image', attrs={ - 'texture': ba.gettexture('nub'), + 'texture': bs.gettexture('nub'), 'opacity': 1.0, 'absolute_scale': True, 'position': (-33 + i * 65, 220), 'scale': (60, 60), 'attach': 'center' }) - ba.animate( + bs.animate( lnub, 'opacity', { 4.0 * t_scale: 0, 5.0 * t_scale: 1.0}) @@ -532,12 +535,12 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): self._squid_lights[0].color = (0.2, 0, 0) self._squid_lights[1].color = (0.0, 0.3, 0) - ba.timer(1.0, self._check_squid_end, repeat=True) + bs.timer(1.0, self._check_squid_end, repeat=True) self._squidgame_countdown() def _squidgame_countdown(self) -> None: self._countdown_timer = 80 * self._laps # 80 - ba.newnode( + bs.newnode( 'image', attrs={ 'opacity': 0.7, @@ -545,8 +548,8 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): 'attach': 'topCenter', 'position': (-220, -40), 'scale': (135, 45), - 'texture': ba.gettexture('bar')}) - ba.newnode( + 'texture': bs.gettexture('bar')}) + bs.newnode( 'image', attrs={ 'opacity': 1.0, @@ -554,9 +557,9 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): 'attach': 'topCenter', 'position': (-220, -38), 'scale': (155, 65), - 'texture': ba.gettexture('uiAtlas'), - 'model_transparent': ba.getmodel('meterTransparent')}) - self._sgcountdown_text = ba.newnode( + 'texture': bs.gettexture('uiAtlas'), + 'mesh_transparent': bs.getmesh('meterTransparent')}) + self._sgcountdown_text = bs.newnode( 'text', attrs={ 'v_attach': 'top', @@ -576,14 +579,14 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): self._squid_game_all_die() if self._countdown_timer == 20: self._sq_mode = 'Hard' - ba.playsound(ba.getsound('alarm')) + bs.getsound('alarm').play() if self._countdown_timer == 40: self._sq_mode = 'Normal' if self._countdown_timer <= 20: self._sgcountdown_text.color = (1.2, 0.0, 0.0) self._sgcountdown_text.scale = 1.2 if self._countdown_timer in self._countdownsounds: - ba.playsound(self._countdownsounds[self._countdown_timer]) + self._countdownsounds[self._countdown_timer].play() else: self._sgcountdown_text.color = (1.0, 1.0, 1.0) self._sgcountdown_text.text = str(self._countdown_timer)+"s" @@ -592,14 +595,14 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): for player in self.players: if player.is_alive(): player.actor._cursed = True - player.actor.handlemessage(ba.DieMessage()) + player.actor.handlemessage(bs.DieMessage()) NewBlast( position=player.actor.node.position, velocity=player.actor.node.velocity, blast_radius=3.0, blast_type='normal').autoretain() player.actor.handlemessage( - ba.HitMessage( + bs.HitMessage( pos=player.actor.node.position, velocity=player.actor.node.velocity, magnitude=2000, @@ -612,8 +615,8 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): def _do_ticks(self) -> None: def do_ticks(): if self._ticks: - ba.playsound(ba.getsound('tick')) - self._tick_timer = ba.timer(1.0, do_ticks, repeat=True) + bs.getsound('tick').play() + self._tick_timer = bs.timer(1.0, do_ticks, repeat=True) def _start_squid_game(self) -> None: easy = [4.5, 5, 5.5, 6] @@ -623,30 +626,30 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): hard if self._sq_mode == 'Hard' else normal if self._sq_mode == 'Normal' else easy) # if random_number == 6: - # ba.playsound(ba.getsound('lrlg_06s')) + # bs.getsound('lrlg_06s').play() # elif random_number == 5.5: - # ba.playsound(ba.getsound('lrlg_055s')) + # bs.getsound('lrlg_055s').play() # elif random_number == 5: - # ba.playsound(ba.getsound('lrlg_05s')) + # bs.getsound('lrlg_05s').play() # elif random_number == 4.5: - # ba.playsound(ba.getsound('lrlg_045s')) + # bs.getsound('lrlg_045s').play() # elif random_number == 4: - # ba.playsound(ba.getsound('lrlg_04s')) + # bs.getsound('lrlg_04s').play() # elif random_number == 3.5: - # ba.playsound(ba.getsound('lrlg_035s')) + # bs.getsound('lrlg_035s').play() # elif random_number == 3: - # ba.playsound(ba.getsound('lrlg_03s')) + # bs.getsound('lrlg_03s').play() self._squid_lights[0].color = (0.2, 0, 0) self._squid_lights[1].color = (0.0, 1.0, 0) self._do_delete = False self._ticks = True - ba.timer(random_number, self._stop_squid_game) + bs.timer(random_number, self._stop_squid_game) def _stop_squid_game(self) -> None: self._ticks = False self._squid_lights[0].color = (1.0, 0, 0) self._squid_lights[1].color = (0.0, 0.3, 0) - ba.timer(0.2, self._check_delete) + bs.timer(0.2, self._check_delete) def _check_delete(self) -> None: for player in self.players: @@ -654,7 +657,7 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): player.customdata['position'] = None player.customdata['position'] = player.actor.node.position self._do_delete = True - ba.timer(3.0 if self._sq_mode == 'Hard' else 4.0, + bs.timer(3.0 if self._sq_mode == 'Hard' else 4.0, self._start_squid_game) def _start_delete(self) -> None: @@ -684,14 +687,14 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): current_posz in posz_list) or not ( current_posy in posy_list): player.actor._cursed = True - player.actor.handlemessage(ba.DieMessage()) + player.actor.handlemessage(bs.DieMessage()) NewBlast( position=player.actor.node.position, velocity=player.actor.node.velocity, blast_radius=3.0, blast_type='normal').autoretain() player.actor.handlemessage( - ba.HitMessage( + bs.HitMessage( pos=player.actor.node.position, velocity=player.actor.node.velocity, magnitude=2000, @@ -713,34 +716,34 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): def _do_light_1(self) -> None: assert self._start_lights is not None self._start_lights[0].color = (1.0, 0, 0) - ba.playsound(self._beep_1_sound) + self._beep_1_sound.play() def _do_light_2(self) -> None: assert self._start_lights is not None self._start_lights[1].color = (1.0, 0, 0) - ba.playsound(self._beep_1_sound) + self._beep_1_sound.play() def _do_light_3(self) -> None: assert self._start_lights is not None self._start_lights[2].color = (1.0, 0.3, 0) - ba.playsound(self._beep_1_sound) + self._beep_1_sound.play() def _start_race(self) -> None: assert self._start_lights is not None self._start_lights[3].color = (0.0, 1.0, 0) - ba.playsound(self._beep_2_sound) + self._beep_2_sound.play() for player in self.players: if player.actor is not None: try: assert isinstance(player.actor, PlayerSpaz) player.actor.connect_controls_to_player() except Exception: - ba.print_exception('Error in race player connects.') + babase.print_exception('Error in race player connects.') assert self._timer is not None self._timer.start() if self._bomb_spawning != 0: - self._bomb_spawn_timer = ba.Timer(0.001 * self._bomb_spawning, + self._bomb_spawn_timer = bs.Timer(0.001 * self._bomb_spawning, self._spawn_bomb, repeat=True) @@ -748,25 +751,25 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): self._squid_lights[1].color = (0.0, 1.0, 0) self._start_squid_game() self._do_ticks() - ba.timer(0.2, self._start_delete, repeat=True) - ba.timer(1.0, self._update_sgcountdown, repeat=True) + bs.timer(0.2, self._start_delete, repeat=True) + bs.timer(1.0, self._update_sgcountdown, repeat=True) def _update_player_order(self) -> None: # Calc all player distances. for player in self.players: - pos: Optional[ba.Vec3] + pos: Optional[babase.Vec3] try: pos = player.position - except ba.NotFoundError: + except bs.NotFoundError: pos = None if pos is not None: r_index = player.last_region rg1 = self._regions[r_index] - r1pt = ba.Vec3(rg1.pos[:3]) + r1pt = babase.Vec3(rg1.pos[:3]) rg2 = self._regions[0] if r_index == len( self._regions) - 1 else self._regions[r_index + 1] - r2pt = ba.Vec3(rg2.pos[:3]) + r2pt = babase.Vec3(rg2.pos[:3]) r2dist = (pos - r2pt).length() amt = 1.0 - (r2dist / (r2pt - r1pt).length()) amt = player.lap + (r_index + amt) * (1.0 / len(self._regions)) @@ -797,8 +800,8 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): (-region_scale * pos[5], region_scale * pos[5])) pos = (pos[0] + random.uniform(*x_range), pos[1] + 1.0, pos[2] + random.uniform(*z_range)) - ba.timer(random.uniform(0.0, 2.0), - ba.WeakCall(self._spawn_bomb_at_pos, pos)) + bs.timer(random.uniform(0.0, 2.0), + bs.WeakCall(self._spawn_bomb_at_pos, pos)) def _spawn_bomb_at_pos(self, pos: Sequence[float]) -> None: if self.has_ended(): @@ -814,15 +817,15 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): def _flash_mine(self, i: int) -> None: assert self._race_mines is not None rmine = self._race_mines[i] - light = ba.newnode('light', + light = bs.newnode('light', attrs={ 'position': rmine.point[:3], 'color': (1, 0.2, 0.2), 'radius': 0.1, 'height_attenuated': False }) - ba.animate(light, 'intensity', {0.0: 0, 0.1: 1.0, 0.2: 0}, loop=True) - ba.timer(1.0, light.delete) + bs.animate(light, 'intensity', {0.0: 0, 0.1: 1.0, 0.2: 0}, loop=True) + bs.timer(1.0, light.delete) def _update_race_mine(self) -> None: assert self._race_mines is not None @@ -836,9 +839,9 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): assert rmine is not None if not rmine.mine: self._flash_mine(m_index) - ba.timer(0.95, ba.Call(self._make_mine, m_index)) + bs.timer(0.95, babase.Call(self._make_mine, m_index)) - def spawn_player(self, player: Player) -> ba.Actor: + def spawn_player(self, player: Player) -> bs.Actor: if player.team.finished: # FIXME: This is not type-safe! # This call is expected to always return an Actor! @@ -863,7 +866,7 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): if not self._race_started: spaz.disconnect_controls_from_player() - mathnode = ba.newnode('math', + mathnode = bs.newnode('math', owner=spaz.node, attrs={ 'input1': (0, 1.4, 0), @@ -871,7 +874,7 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): }) spaz.node.connectattr('torso_position', mathnode, 'input2') - distance_txt = ba.newnode('text', + distance_txt = bs.newnode('text', owner=spaz.node, attrs={ 'text': '', @@ -902,14 +905,14 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): # In teams mode its over as soon as any team finishes the race # FIXME: The get_ffa_point_awards code looks dangerous. - if isinstance(session, ba.DualTeamSession): + if isinstance(session, bs.DualTeamSession): self.end_game() else: # In ffa we keep the race going while there's still any points # to be handed out. Find out how many points we have to award # and how many teams have finished, and once that matches # we're done. - assert isinstance(session, ba.FreeForAllSession) + assert isinstance(session, bs.FreeForAllSession) points_to_award = len(session.get_ffa_point_awards()) if teams_completed >= points_to_award - teams_completed: self.end_game() @@ -926,7 +929,7 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): endtime=None if self._last_team_time is None else ( self._timer.getstarttime() + self._last_team_time)) - results = ba.GameResults() + results = bs.GameResults() for team in self.teams: if team.time is not None: @@ -940,10 +943,10 @@ class SquidRaceGame(ba.TeamGameActivity[Player, Team]): # odd to be announcing that now. self.end(results=results, announce_winning_team=isinstance(self.session, - ba.DualTeamSession)) + bs.DualTeamSession)) def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.PlayerDiedMessage): + if isinstance(msg, bs.PlayerDiedMessage): # Augment default behavior. super().handlemessage(msg) else: diff --git a/plugins/minigames/the_spaz_game.py b/plugins/minigames/the_spaz_game.py index 278b521..74857c1 100644 --- a/plugins/minigames/the_spaz_game.py +++ b/plugins/minigames/the_spaz_game.py @@ -1,5 +1,6 @@ +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) -# ba_meta require api 7 +# ba_meta require api 8 """ TheSpazGame - Mini game where all characters looks identical , identify enemies and kill them. Author: Mr.Smoothy @@ -12,9 +13,11 @@ from __future__ import annotations from typing import TYPE_CHECKING -import ba -from bastd.game.elimination import EliminationGame, Player -from bastd.actor.spazfactory import SpazFactory +import babase +import bauiv1 as bui +import bascenev1 as bs +from bascenev1lib.game.elimination import EliminationGame, Player +from bascenev1lib.actor.spazfactory import SpazFactory import random if TYPE_CHECKING: @@ -23,14 +26,14 @@ if TYPE_CHECKING: CHARACTER = 'Spaz' -# ba_meta export game +# ba_meta export bascenev1.GameActivity class TheSpazGame(EliminationGame): name = 'TheSpazGame' description = 'Enemy Spaz AmongUs. Kill them all' - scoreconfig = ba.ScoreConfig( - label='Survived', scoretype=ba.ScoreType.SECONDS, none_is_winner=True + scoreconfig = bs.ScoreConfig( + label='Survived', scoretype=bs.ScoreType.SECONDS, none_is_winner=True ) announce_player_deaths = False @@ -39,17 +42,17 @@ class TheSpazGame(EliminationGame): @classmethod def get_available_settings( - cls, sessiontype: type[ba.Session] - ) -> list[ba.Setting]: + cls, sessiontype: type[bs.Session] + ) -> list[babase.Setting]: settings = [ - ba.IntSetting( + bs.IntSetting( 'Lives Per Player', default=1, min_value=1, max_value=10, increment=1, ), - ba.IntChoiceSetting( + bs.IntChoiceSetting( 'Time Limit', choices=[ ('None', 0), @@ -61,31 +64,31 @@ class TheSpazGame(EliminationGame): ], default=0, ), - ba.FloatChoiceSetting( + bs.FloatChoiceSetting( 'Respawn Times', choices=[ ('Shorter', 0.15) ], default=1.0, ), - ba.BoolSetting('Epic Mode', default=False), + bs.BoolSetting('Epic Mode', default=False), ] - if issubclass(sessiontype, ba.DualTeamSession): - settings.append(ba.BoolSetting('Solo Mode', default=False)) + if issubclass(sessiontype, bs.DualTeamSession): + settings.append(bs.BoolSetting('Solo Mode', default=False)) settings.append( - ba.BoolSetting('Balance Total Lives', default=False) + bs.BoolSetting('Balance Total Lives', default=False) ) return settings @classmethod - def supports_session_type(cls, sessiontype: type[ba.Session]) -> bool: - return issubclass(sessiontype, ba.DualTeamSession) or issubclass( - sessiontype, ba.FreeForAllSession + def supports_session_type(cls, sessiontype: type[bs.Session]) -> bool: + return issubclass(sessiontype, bs.DualTeamSession) or issubclass( + sessiontype, bs.FreeForAllSession ) @classmethod - def get_supported_maps(cls, sessiontype: type[ba.Session]) -> list[str]: - return ba.getmaps('melee') + def get_supported_maps(cls, sessiontype: type[bs.Session]) -> list[str]: + return bs.app.classic.getmaps('melee') def get_instance_description(self) -> str | Sequence: return ( @@ -101,7 +104,7 @@ class TheSpazGame(EliminationGame): super().__init__(settings) self._solo_mode = False - def spawn_player(self, player: Player) -> ba.Actor: + def spawn_player(self, player: Player) -> bs.Actor: p = [-6, -4.3, -2.6, -0.9, 0.8, 2.5, 4.2, 5.9] q = [-4, -2.3, -0.6, 1.1, 2.8, 4.5] diff --git a/plugins/minigames/ufo_fight.py b/plugins/minigames/ufo_fight.py index 4823904..d8849f8 100644 --- a/plugins/minigames/ufo_fight.py +++ b/plugins/minigames/ufo_fight.py @@ -1,4 +1,4 @@ -"""UFO Boss Fight v1.0: +"""UFO Boss Fight v2.0: Made by Cross Joy""" # Anyone who wanna help me in giving suggestion/ fix bugs/ by creating PR, @@ -8,21 +8,28 @@ Made by Cross Joy""" # My Discord Id: Cross Joy#0721 # My BS Discord Server: https://discford.gg/JyBY6haARJ -# ba_meta require api 7 +# ba_meta require api 8 # (see https://ballistica.net/wiki/meta-tag-system) +# --------------------------------------- +# Update v2.0 + +# updated to api 8 +# --------------------------------------- + from __future__ import annotations import random from typing import TYPE_CHECKING -import ba -import _ba -from bastd.actor.playerspaz import PlayerSpaz -from bastd.actor.spaz import Spaz -from bastd.actor.bomb import Blast, Bomb -from bastd.actor.onscreentimer import OnScreenTimer -from bastd.actor.spazbot import SpazBotSet, StickyBot -from bastd.gameutils import SharedObjects + +import babase +import bascenev1 as bs +from bascenev1lib.actor.playerspaz import PlayerSpaz +from bascenev1lib.actor.spaz import Spaz +from bascenev1lib.actor.bomb import Blast, Bomb +from bascenev1lib.actor.onscreentimer import OnScreenTimer +from bascenev1lib.actor.spazbot import SpazBotSet, StickyBot +from bascenev1lib.gameutils import SharedObjects if TYPE_CHECKING: from typing import Any, Sequence, Union, Callable @@ -32,17 +39,17 @@ class UFODiedMessage: ufo: UFO """The UFO that was killed.""" - killerplayer: ba.Player | None - """The ba.Player that killed it (or None).""" + killerplayer: bs.Player | None + """The bs.Player that killed it (or None).""" - how: ba.DeathType + how: bs.DeathType """The particular type of death.""" def __init__( self, ufo: UFO, - killerplayer: ba.Player | None, - how: ba.DeathType, + killerplayer: bs.Player | None, + how: bs.DeathType, ): """Instantiate with given values.""" self.spazbot = ufo @@ -57,7 +64,7 @@ class RoboBot(StickyBot): highlight = (3, 3, 3) -class UFO(ba.Actor): +class UFO(bs.Actor): """ New AI for Boss """ @@ -65,7 +72,7 @@ class UFO(ba.Actor): # pylint: disable=too-many-public-methods # pylint: disable=too-many-locals - node: ba.Node + node: bs.Node def __init__(self, hitpoints: int = 5000): @@ -74,32 +81,29 @@ class UFO(ba.Actor): self.update_callback: Callable[[UFO], Any] | None = None activity = self.activity - assert isinstance(activity, ba.GameActivity) + assert isinstance(activity, bs.GameActivity) - self.platform_material = ba.Material() + self.platform_material = bs.Material() self.platform_material.add_actions( conditions=('they_have_material', shared.footing_material), actions=( 'modify_part_collision', 'collide', True)) - self.ice_material = ba.Material() + self.ice_material = bs.Material() self.ice_material.add_actions( actions=('modify_part_collision', 'friction', 0.0)) - self._player_pts: list[tuple[ba.Vec3, ba.Vec3]] | None = None - self._ufo_update_timer: ba.Timer | None = None - self.last_player_attacked_by: ba.Player | None = None + self._player_pts: list[tuple[bs.Vec3, bs.Vec3]] | None = None + self._ufo_update_timer: bs.Timer | None = None + self.last_player_attacked_by: bs.Player | None = None self.last_attacked_time = 0.0 self.last_attacked_type: tuple[str, str] | None = None - self.to_target: ba.Vec3 = ba.Vec3(0, 0, 0) + self.to_target: bs.Vec3 = bs.Vec3(0, 0, 0) self.dist = (0, 0, 0) self._bots = SpazBotSet() self.frozen = False - self.y_pos = 3 - self.xz_pos = 1 self.bot_count = 3 - self.bot_dur_froze = False self.hitpoints = hitpoints self.hitpoints_max = hitpoints @@ -108,18 +112,18 @@ class UFO(ba.Actor): self._height = 35 self._bar_width = 240 self._bar_height = 35 - self._bar_tex = self._backing_tex = ba.gettexture('bar') - self._cover_tex = ba.gettexture('uiAtlas') - self._model = ba.getmodel('meterTransparent') + self._bar_tex = self._backing_tex = bs.gettexture('bar') + self._cover_tex = bs.gettexture('uiAtlas') + self._mesh = bs.getmesh('meterTransparent') self.bar_posx = -120 self._last_hit_time: int | None = None self.impact_scale = 1.0 self._num_times_hit = 0 - self._sucker_mat = ba.Material() + self._sucker_mat = bs.Material() - self.ufo_material = ba.Material() + self.ufo_material = bs.Material() self.ufo_material.add_actions( conditions=('they_have_material', shared.player_material), @@ -135,31 +139,30 @@ class UFO(ba.Actor): self.ufo_material)), actions=('modify_part_collision', 'physical', False)) - activity = _ba.get_foreground_host_activity() - with ba.Context(activity): - point = activity.map.get_flag_position(None) - boss_spawn_pos = (point[0], point[1] + 1, point[2]) + activity = bs.get_foreground_host_activity() + point = activity.map.get_flag_position(None) + boss_spawn_pos = (point[0], point[1] + 1, point[2]) - self.node = ba.newnode('prop', delegate=self, attrs={ + self.node = bs.newnode('prop', delegate=self, attrs={ 'position': boss_spawn_pos, 'velocity': (2, 0, 0), - 'color_texture': ba.gettexture('achievementFootballShutout'), - 'model': ba.getmodel('landMine'), - # 'light_model': ba.getmodel('powerupSimple'), - 'model_scale': 3.3, + 'color_texture': bs.gettexture('achievementFootballShutout'), + 'mesh': bs.getmesh('landMine'), + # 'light_mesh': bs.getmesh('powerupSimple'), + 'mesh_scale': 3.3, 'body': 'landMine', 'body_scale': 3.3, - 'gravity_scale': 0.05, + 'gravity_scale': 0.2, 'density': 1, 'reflection': 'soft', 'reflection_scale': [0.25], 'shadow_size': 0.1, 'max_speed': 1.5, 'is_area_of_interest': - True, + True, 'materials': [shared.footing_material, shared.object_material]}) - self.holder = ba.newnode('region', attrs={ + self.holder = bs.newnode('region', attrs={ 'position': ( boss_spawn_pos[0], boss_spawn_pos[1] - 0.25, boss_spawn_pos[2]), @@ -168,7 +171,7 @@ class UFO(ba.Actor): 'materials': (self.platform_material, self.ice_material, shared.object_material)}) - self.suck_anim = ba.newnode('locator', + self.suck_anim = bs.newnode('locator', owner=self.node, attrs={'shape': 'circleOutline', 'position': ( @@ -181,7 +184,7 @@ class UFO(ba.Actor): 'additive': True}) def suck_anim(): - ba.animate_array(self.suck_anim, 'position', 3, + bs.animate_array(self.suck_anim, 'position', 3, {0: ( self.node.position[0], self.node.position[1] - 5, @@ -194,7 +197,7 @@ class UFO(ba.Actor): self.node.position[ 2] + self.to_target.z / 2)}) - self.suck_timer = ba.Timer(0.5, suck_anim, repeat=True) + self.suck_timer = bs.Timer(0.5, suck_anim, repeat=True) self.blocks = [] @@ -209,14 +212,14 @@ class UFO(ba.Actor): )) - # self.sucker = ba.newnode('region', attrs={ + # self.sucker = bs.newnode('region', attrs={ # 'position': ( # boss_spawn_pos[0], boss_spawn_pos[1] - 2, boss_spawn_pos[2]), # 'scale': [2, 10, 2], # 'type': 'box', # 'materials': self._sucker_mat, }) - self.suck = ba.newnode('region', + self.suck = bs.newnode('region', attrs={'position': ( boss_spawn_pos[0], boss_spawn_pos[1] - 2, boss_spawn_pos[2]), @@ -227,69 +230,65 @@ class UFO(ba.Actor): self.node.connectattr('position', self.holder, 'position') self.node.connectattr('position', self.suck, 'position') - ba.animate(self.node, 'model_scale', { + bs.animate(self.node, 'mesh_scale', { 0: 0, - 0.2: self.node.model_scale * 1.1, - 0.26: self.node.model_scale}) + 0.2: self.node.mesh_scale * 1.1, + 0.26: self.node.mesh_scale}) - self.shield_deco = ba.newnode('shield', owner=self.node, + self.shield_deco = bs.newnode('shield', owner=self.node, attrs={'color': (4, 4, 4), 'radius': 1.2}) self.node.connectattr('position', self.shield_deco, 'position') self._scoreboard() self._update() - self.drop_bomb_timer = ba.Timer(1.5, ba.Call(self._drop_bomb), + self.drop_bomb_timer = bs.Timer(1.5, bs.Call(self._drop_bomb), repeat=True) - self.drop_bots_timer = ba.Timer(15.0, ba.Call(self._drop_bots), repeat=True) + self.drop_bots_timer = bs.Timer(15.0, bs.Call(self._drop_bots), repeat=True) def _drop_bots(self) -> None: p = self.node.position - if not self.frozen: - for i in range(self.bot_count): - ba.timer( - 1.0 + i, - lambda: self._bots.spawn_bot( - RoboBot, pos=(self.node.position[0], - self.node.position[1] - 1, - self.node.position[2]), spawn_time=0.0 - ), - ) - else: - self.bot_dur_froze = True + for i in range(self.bot_count): + bs.timer( + 1.0 + i, + lambda: self._bots.spawn_bot( + RoboBot, pos=(self.node.position[0], + self.node.position[1] - 1, + self.node.position[2]), spawn_time=0.0 + ), + ) def _drop_bomb(self) -> None: t = self.to_target p = self.node.position - if not self.frozen: - if abs(self.dist[0]) < 2 and abs(self.dist[2]) < 2: - Bomb(position=(p[0], p[1] - 0.5, p[2]), - velocity=(t[0] * 5, 0, t[2] * 5), - bomb_type='land_mine').autoretain().arm() - elif self.hitpoints > self.hitpoints_max * 3 / 4: - Bomb(position=(p[0], p[1] - 1.5, p[2]), - velocity=(t[0] * 8, 2, t[2] * 8), - bomb_type='normal').autoretain() - elif self.hitpoints > self.hitpoints_max * 1 / 2: - Bomb(position=(p[0], p[1] - 1.5, p[2]), - velocity=(t[0] * 8, 2, t[2] * 8), - bomb_type='ice').autoretain() + if abs(self.dist[0]) < 2 and abs(self.dist[2]) < 2: + Bomb(position=(p[0], p[1] - 0.5, p[2]), + velocity=(t[0] * 5, 0, t[2] * 5), + bomb_type='land_mine').autoretain().arm() + elif self.hitpoints > self.hitpoints_max * 3 / 4: + Bomb(position=(p[0], p[1] - 1.5, p[2]), + velocity=(t[0] * 8, 2, t[2] * 8), + bomb_type='normal').autoretain() + elif self.hitpoints > self.hitpoints_max * 1 / 2: + Bomb(position=(p[0], p[1] - 1.5, p[2]), + velocity=(t[0] * 8, 2, t[2] * 8), + bomb_type='ice').autoretain() - elif self.hitpoints > self.hitpoints_max * 1 / 4: - Bomb(position=(p[0], p[1] - 1.5, p[2]), - velocity=(t[0] * 15, 2, t[2] * 15), - bomb_type='sticky').autoretain() - else: - Bomb(position=(p[0], p[1] - 1.5, p[2]), - velocity=(t[0] * 15, 2, t[2] * 15), - bomb_type='impact').autoretain() + elif self.hitpoints > self.hitpoints_max * 1 / 4: + Bomb(position=(p[0], p[1] - 1.5, p[2]), + velocity=(t[0] * 15, 2, t[2] * 15), + bomb_type='sticky').autoretain() + else: + Bomb(position=(p[0], p[1] - 1.5, p[2]), + velocity=(t[0] * 15, 2, t[2] * 15), + bomb_type='impact').autoretain() def _levitate(self): - node = ba.getcollision().opposingnode + node = bs.getcollision().opposingnode if node.exists(): p = node.getdelegate(Spaz, True) - def raise_player(player: ba.Player): + def raise_player(player: bs.Player): if player.is_alive(): node = player.node try: @@ -298,12 +297,13 @@ class UFO(ba.Actor): node.position[2], 0, 5, 0, 3, 10, 0, 0, 0, 5, 0) + except: pass if not self.frozen: for i in range(7): - ba.timer(0.05 + i / 20, ba.Call(raise_player, p)) + bs.timer(0.05 + i / 20, bs.Call(raise_player, p)) def on_punched(self, damage: int) -> None: """Called when this spaz gets punched.""" @@ -315,24 +315,22 @@ class UFO(ba.Actor): damage = abs(msg.magnitude) if msg.hit_type == 'explosion': damage /= 20 - else: - damage /= 5 self.hitpoints -= int(damage) if self.hitpoints <= 0: - self.handlemessage(ba.DieMessage()) + self.handlemessage(bs.DieMessage()) def _get_target_player_pt(self) -> tuple[ - ba.Vec3 | None, ba.Vec3 | None]: + bs.Vec3 | None, bs.Vec3 | None]: """Returns the position and velocity of our target. Both values will be None in the case of no target. """ assert self.node - botpt = ba.Vec3(self.node.position) + botpt = bs.Vec3(self.node.position) closest_dist: float | None = None - closest_vel: ba.Vec3 | None = None - closest: ba.Vec3 | None = None + closest_vel: bs.Vec3 | None = None + closest: bs.Vec3 | None = None assert self._player_pts is not None for plpt, plvel in self._player_pts: dist = (plpt - botpt).length() @@ -349,12 +347,12 @@ class UFO(ba.Actor): assert closest_vel is not None assert closest is not None return ( - ba.Vec3(closest[0], closest[1], closest[2]), - ba.Vec3(closest_vel[0], closest_vel[1], closest_vel[2]), + bs.Vec3(closest[0], closest[1], closest[2]), + bs.Vec3(closest_vel[0], closest_vel[1], closest_vel[2]), ) return None, None - def set_player_points(self, pts: list[tuple[ba.Vec3, ba.Vec3]]) -> None: + def set_player_points(self, pts: list[tuple[bs.Vec3, bs.Vec3]]) -> None: """Provide the spaz-bot with the locations of its enemies.""" self._player_pts = pts @@ -368,13 +366,13 @@ class UFO(ba.Actor): Category: Gameplay Functions """ lifespan = 1.0 - app = ba.app + app = bs.app # FIXME: Should never vary game elements based on local config. # (connected clients may have differing configs so they won't # get the intended results). - do_big = app.ui.uiscale is ba.UIScale.SMALL or app.vr_mode - txtnode = ba.newnode('text', + do_big = app.ui.uiscale is bs.UIScale.SMALL or app.vr_mode + txtnode = bs.newnode('text', attrs={ 'text': damage, 'in_world': True, @@ -385,7 +383,7 @@ class UFO(ba.Actor): 'scale': 0.035 if do_big else 0.03 }) # Translate upward. - tcombine = ba.newnode('combine', owner=txtnode, attrs={'size': 3}) + tcombine = bs.newnode('combine', owner=txtnode, attrs={'size': 3}) tcombine.connectattr('output', txtnode, 'position') v_vals = [] pval = 0.0 @@ -397,25 +395,25 @@ class UFO(ba.Actor): vval *= 0.5 p_start = position[0] p_dir = direction[0] - ba.animate(tcombine, 'input0', + bs.animate(tcombine, 'input0', {i[0] * lifespan: p_start + p_dir * i[1] for i in v_vals}) p_start = position[1] p_dir = direction[1] - ba.animate(tcombine, 'input1', + bs.animate(tcombine, 'input1', {i[0] * lifespan: p_start + p_dir * i[1] for i in v_vals}) p_start = position[2] p_dir = direction[2] - ba.animate(tcombine, 'input2', + bs.animate(tcombine, 'input2', {i[0] * lifespan: p_start + p_dir * i[1] for i in v_vals}) - ba.animate(txtnode, 'opacity', {0.7 * lifespan: 1.0, lifespan: 0.0}) - ba.timer(lifespan, txtnode.delete) + bs.animate(txtnode, 'opacity', {0.7 * lifespan: 1.0, lifespan: 0.0}) + bs.timer(lifespan, txtnode.delete) def _scoreboard(self) -> None: - self._backing = ba.NodeActor( - ba.newnode('image', + self._backing = bs.NodeActor( + bs.newnode('image', attrs={ 'position': (self.bar_posx + self._width / 2, -100), 'scale': (self._width, self._height), @@ -427,15 +425,15 @@ class UFO(ba.Actor): 'attach': 'topCenter', 'texture': self._backing_tex })) - self._bar = ba.NodeActor( - ba.newnode('image', + self._bar = bs.NodeActor( + bs.newnode('image', attrs={ 'opacity': 1.0, 'color': (0.5, 0.5, 0.5), 'attach': 'topCenter', 'texture': self._bar_tex })) - self._bar_scale = ba.newnode('combine', + self._bar_scale = bs.newnode('combine', owner=self._bar.node, attrs={ 'size': 2, @@ -443,7 +441,7 @@ class UFO(ba.Actor): 'input1': self._bar_height }) self._bar_scale.connectattr('output', self._bar.node, 'scale') - self._bar_position = ba.newnode( + self._bar_position = bs.newnode( 'combine', owner=self._bar.node, attrs={ @@ -452,8 +450,8 @@ class UFO(ba.Actor): 'input1': -100 }) self._bar_position.connectattr('output', self._bar.node, 'position') - self._cover = ba.NodeActor( - ba.newnode('image', + self._cover = bs.NodeActor( + bs.newnode('image', attrs={ 'position': (self.bar_posx + 120, -100), 'scale': @@ -465,10 +463,10 @@ class UFO(ba.Actor): 'vr_depth': 2, 'attach': 'topCenter', 'texture': self._cover_tex, - 'model_transparent': self._model + 'mesh_transparent': self._mesh })) - self._score_text = ba.NodeActor( - ba.newnode('text', + self._score_text = bs.NodeActor( + bs.newnode('text', attrs={ 'position': (self.bar_posx + 120, -100), 'h_attach': 'center', @@ -487,35 +485,36 @@ class UFO(ba.Actor): self._score_text.node.text = str(self.hitpoints) self._bar_width = self.hitpoints * self._width_max / self.hitpoints_max cur_width = self._bar_scale.input0 - ba.animate(self._bar_scale, 'input0', { + bs.animate(self._bar_scale, 'input0', { 0.0: cur_width, 0.1: self._bar_width }) cur_x = self._bar_position.input0 - ba.animate(self._bar_position, 'input0', { + bs.animate(self._bar_position, 'input0', { 0.0: cur_x, 0.1: self.bar_posx + self._bar_width / 2 }) if self.hitpoints > self.hitpoints_max * 3 / 4: - ba.animate_array(self.shield_deco, 'color', 3, + bs.animate_array(self.shield_deco, 'color', 3, {0: self.shield_deco.color, 0.2: (4, 4, 4)}) elif self.hitpoints > self.hitpoints_max * 1 / 2: - ba.animate_array(self.shield_deco, 'color', 3, + bs.animate_array(self.shield_deco, 'color', 3, {0: self.shield_deco.color, 0.2: (3, 3, 5)}) self.bot_count = 4 elif self.hitpoints > self.hitpoints_max * 1 / 4: - ba.animate_array(self.shield_deco, 'color', 3, + bs.animate_array(self.shield_deco, 'color', 3, {0: self.shield_deco.color, 0.2: (1, 5, 1)}) self.bot_count = 5 else: - ba.animate_array(self.shield_deco, 'color', 3, + bs.animate_array(self.shield_deco, 'color', 3, {0: self.shield_deco.color, 0.2: (5, 0.2, 0.2)}) self.bot_count = 6 + def update_ai(self) -> None: """Should be called periodically to update the spaz' AI.""" # pylint: disable=too-many-branches @@ -530,10 +529,10 @@ class UFO(ba.Actor): return pos = self.node.position - our_pos = ba.Vec3(pos[0], pos[1] - self.y_pos, pos[2]) + our_pos = bs.Vec3(pos[0], pos[1] - 3, pos[2]) - target_pt_raw: ba.Vec3 | None - target_vel: ba.Vec3 | None + target_pt_raw: bs.Vec3 | None + target_vel: bs.Vec3 | None target_pt_raw, target_vel = self._get_target_player_pt() @@ -562,15 +561,12 @@ class UFO(ba.Actor): setattr(self.node, 'extra_acceleration', (0, self.to_target.y * 80 + 70, 0)) - else: + elif not self.frozen: setattr(self.node, 'velocity', - (self.to_target.x * self.xz_pos, - self.to_target.y, - self.to_target.z * self.xz_pos)) + (self.to_target.x, self.to_target.y, self.to_target.z)) setattr(self.node, 'extra_acceleration', - (self.to_target.x * self.xz_pos, - self.to_target.y * 80 + 70, - self.to_target.z * self.xz_pos)) + (self.to_target.x, self.to_target.y * 80 + 70, + self.to_target.z)) def on_expire(self) -> None: super().on_expire() @@ -579,14 +575,14 @@ class UFO(ba.Actor): # no chance of them keeping activities or other things alive. self.update_callback = None - def animate_model(self) -> None: + def animate_mesh(self) -> None: if not self.node: return None - # ba.animate(self.node, 'model_scale', { - # 0: self.node.model_scale, - # 0.08: self.node.model_scale * 0.9, - # 0.15: self.node.model_scale}) - ba.emitfx(position=self.node.position, + # bs.animate(self.node, 'mesh_scale', { + # 0: self.node.mesh_scale, + # 0.08: self.node.mesh_scale * 0.9, + # 0.15: self.node.mesh_scale}) + bs.emitfx(position=self.node.position, velocity=self.node.velocity, count=int(6 + random.random() * 10), scale=0.5, @@ -597,15 +593,15 @@ class UFO(ba.Actor): # pylint: disable=too-many-branches assert not self.expired - if isinstance(msg, ba.HitMessage): + if isinstance(msg, bs.HitMessage): # Don't die on punches (that's annoying). - self.animate_model() + self.animate_mesh() if self.hitpoints != 0: self.do_damage(msg) # self.show_damage_msg(msg) self._update() - elif isinstance(msg, ba.DieMessage): + elif isinstance(msg, bs.DieMessage): if self.node: self.hitpoints = 0 self.frozen = True @@ -629,46 +625,52 @@ class UFO(ba.Actor): position=(p_x, p[1], p_z), blast_radius=2.0).autoretain() - ba.timer(0 + i, ba.Call(ded_explode, i)) + bs.timer(0 + i, bs.Call(ded_explode, i)) - ba.timer(5, self.node.delete) - ba.timer(0.1, self.suck.delete) - ba.timer(0.1, self.suck_anim.delete) + bs.timer(5, self.node.delete) + bs.timer(0.1, self.suck.delete) + bs.timer(0.1, self.suck_anim.delete) - elif isinstance(msg, ba.OutOfBoundsMessage): - activity = _ba.get_foreground_host_activity() + elif isinstance(msg, bs.OutOfBoundsMessage): + activity = bs.get_foreground_host_activity() try: point = activity.map.get_flag_position(None) boss_spawn_pos = (point[0], point[1] + 1.5, point[2]) assert self.node self.node.position = boss_spawn_pos except: - self.handlemessage(ba.DieMessage()) + self.handlemessage(bs.DieMessage()) - elif isinstance(msg, ba.FreezeMessage): + elif isinstance(msg, bs.FreezeMessage): if not self.frozen: self.frozen = True - self.y_pos = -1.5 - self.xz_pos = 0.01 + self.drop_bomb_timer = False + self.drop_bots_timer = False + setattr(self.node, 'velocity', + (0, self.to_target.y, 0)) + setattr(self.node, 'extra_acceleration', + (0, 0, 0)) self.node.reflection_scale = [2] def unfrozen(): self.frozen = False - if self.bot_dur_froze: - ba.timer(0.1, ba.Call(self._drop_bots)) - self.bot_dur_froze = False - self.y_pos = 3 - self.xz_pos = 1 + self.drop_bomb_timer = bs.Timer(1.5, + bs.Call(self._drop_bomb), + repeat=True) + + self.drop_bots_timer = bs.Timer(15.0, + bs.Call(self._drop_bots), + repeat=True) self.node.reflection_scale = [0.25] - ba.timer(5.0, unfrozen) + bs.timer(3.0, unfrozen) else: super().handlemessage(msg) class UFOSet: - """A container/controller for one or more ba.SpazBots. + """A container/controller for one or more bs.SpazBots. category: Bot Classes """ @@ -684,9 +686,9 @@ class UFOSet: self._ufo_bot_lists: list[list[UFO]] = [ [] for _ in range(self._ufo_bot_list_count) ] - self._ufo_spawn_sound = ba.getsound('spawn') + self._ufo_spawn_sound = bs.getsound('spawn') self._ufo_spawning_count = 0 - self._ufo_bot_update_timer: ba.Timer | None = None + self._ufo_bot_update_timer: bs.Timer | None = None self.start_moving() def _update(self) -> None: @@ -699,18 +701,18 @@ class UFOSet: ] except Exception: bot_list = [] - ba.print_exception( + bs.print_exception( 'Error updating bot list: ' + str(self._ufo_bot_lists[self._ufo_bot_update_list]) ) self._bot_update_list = ( - self._ufo_bot_update_list + 1 - ) % self._ufo_bot_list_count + self._ufo_bot_update_list + 1 + ) % self._ufo_bot_list_count # Update our list of player points for the bots to use. player_pts = [] - for player in ba.getactivity().players: - assert isinstance(player, ba.Player) + for player in bs.getactivity().players: + assert isinstance(player, bs.Player) try: # TODO: could use abstracted player.position here so we # don't have to assume their actor type, but we have no @@ -720,12 +722,12 @@ class UFOSet: assert player.actor.node player_pts.append( ( - ba.Vec3(player.actor.node.position), - ba.Vec3(player.actor.node.velocity), + bs.Vec3(player.actor.node.position), + bs.Vec3(player.actor.node.velocity), ) ) except Exception: - ba.print_exception('Error on bot-set _update.') + bs.print_exception('Error on bot-set _update.') for bot in bot_list: bot.set_player_points(player_pts) @@ -733,8 +735,8 @@ class UFOSet: def start_moving(self) -> None: """Start processing bot AI updates so they start doing their thing.""" - self._ufo_bot_update_timer = ba.Timer( - 0.05, ba.WeakCall(self._update), repeat=True + self._ufo_bot_update_timer = bs.Timer( + 0.05, bs.WeakCall(self._update), repeat=True ) def spawn_bot( @@ -745,13 +747,13 @@ class UFOSet: on_spawn_call: Callable[[UFO], Any] | None = None, ) -> None: """Spawn a bot from this set.""" - from bastd.actor import spawner + from bascenev1lib.actor import spawner spawner.Spawner( pt=pos, spawn_time=spawn_time, send_spawn_message=False, - spawn_callback=ba.Call( + spawn_callback=bs.Call( self._spawn_bot, bot_type, pos, on_spawn_call ), ) @@ -764,21 +766,21 @@ class UFOSet: on_spawn_call: Callable[[UFO], Any] | None, ) -> None: spaz = bot_type() - ba.playsound(self._ufo_spawn_sound, position=pos) + self._ufo_spawn_sound.play(position=pos) assert spaz.node spaz.node.handlemessage('flash') spaz.node.is_area_of_interest = False - spaz.handlemessage(ba.StandMessage(pos, random.uniform(0, 360))) + spaz.handlemessage(bs.StandMessage(pos, random.uniform(0, 360))) self.add_bot(spaz) self._ufo_spawning_count -= 1 if on_spawn_call is not None: on_spawn_call(spaz) def add_bot(self, bot: UFO) -> None: - """Add a ba.SpazBot instance to the set.""" + """Add a bs.SpazBot instance to the set.""" self._ufo_bot_lists[self._ufo_bot_add_list].append(bot) self._ufo_bot_add_list = ( - self._ufo_bot_add_list + 1) % self._ufo_bot_list_count + self._ufo_bot_add_list + 1) % self._ufo_bot_list_count def have_living_bots(self) -> bool: """Return whether any bots in the set are alive or spawning.""" @@ -799,26 +801,26 @@ class UFOSet: """Immediately clear out any bots in the set.""" # Don't do this if the activity is shutting down or dead. - activity = ba.getactivity(doraise=False) + activity = bs.getactivity(doraise=False) if activity is None or activity.expired: return for i, bot_list in enumerate(self._ufo_bot_lists): for bot in bot_list: - bot.handlemessage(ba.DieMessage(immediate=True)) + bot.handlemessage(bs.DieMessage(immediate=True)) self._ufo_bot_lists[i] = [] -class Player(ba.Player['Team']): +class Player(bs.Player['Team']): """Our player type for this game.""" -class Team(ba.Team[Player]): +class Team(bs.Team[Player]): """Our team type for this game.""" -# ba_meta export game -class UFOightGame(ba.TeamGameActivity[Player, Team]): +# ba_meta export bascenev1.GameActivity +class UFOightGame(bs.TeamGameActivity[Player, Team]): """ A co-op game where you try to defeat UFO Boss as fast as possible @@ -826,47 +828,49 @@ class UFOightGame(ba.TeamGameActivity[Player, Team]): name = 'UFO Fight' description = 'REal Boss Fight?' - scoreconfig = ba.ScoreConfig( - label='Time', scoretype=ba.ScoreType.MILLISECONDS, lower_is_better=True + scoreconfig = bs.ScoreConfig( + label='Time', scoretype=bs.ScoreType.MILLISECONDS, lower_is_better=True ) - default_music = ba.MusicType.TO_THE_DEATH + default_music = bs.MusicType.TO_THE_DEATH @classmethod - def get_supported_maps(cls, sessiontype: type[ba.Session]) -> list[str]: + def get_supported_maps(cls, sessiontype: type[bs.Session]) -> list[str]: # For now we're hard-coding spawn positions and whatnot # so we need to be sure to specify that we only support # a specific map. return ['Football Stadium'] @classmethod - def supports_session_type(cls, sessiontype: type[ba.Session]) -> bool: + def supports_session_type(cls, sessiontype: type[bs.Session]) -> bool: # We currently support Co-Op only. - return issubclass(sessiontype, ba.CoopSession) + return issubclass(sessiontype, bs.CoopSession) # In the constructor we should load any media we need/etc. # ...but not actually create anything yet. def __init__(self, settings: dict): super().__init__(settings) - self._winsound = ba.getsound('score') + self._winsound = bs.getsound('score') self._won = False self._timer: OnScreenTimer | None = None self._bots = UFOSet() self._preset = str(settings['preset']) - self._credit = ba.newnode('text', - attrs={ - 'v_attach': 'bottom', - 'h_align': 'center', - 'color': (0.4, 0.4, 0.4), - 'flatness': 0.5, - 'shadow': 0.5, - 'position': (0, 20), - 'scale': 0.7, - 'text': 'By Cross Joy' - }) + self._credit = bs.newnode('text', + attrs={ + 'v_attach': 'bottom', + 'h_align': 'center', + 'color': (0.4, 0.4, 0.4), + 'flatness': 0.5, + 'shadow': 0.5, + 'position': (0, 20), + 'scale': 0.7, + 'text': 'By Cross Joy' + }) + + def on_transition_in(self) -> None: super().on_transition_in() - gnode = ba.getactivity().globalsnode + gnode = bs.getactivity().globalsnode gnode.tint = (0.42, 0.55, 0.66) # Called when our game actually begins. @@ -874,24 +878,26 @@ class UFOightGame(ba.TeamGameActivity[Player, Team]): super().on_begin() self.setup_standard_powerup_drops() + + # In pro mode there's no powerups. # Make our on-screen timer and start it roughly when our bots appear. self._timer = OnScreenTimer() - ba.timer(4.0, self._timer.start) + bs.timer(4.0, self._timer.start) def checker(): if not self._won: - self.timer = ba.Timer(0.1, self._check_if_won, repeat=True) + self.timer = bs.Timer(0.1, self._check_if_won, repeat=True) - ba.timer(10, checker) - activity = _ba.get_foreground_host_activity() + bs.timer(10, checker) + activity = bs.get_foreground_host_activity() point = activity.map.get_flag_position(None) boss_spawn_pos = (point[0], point[1] + 1.5, point[2]) # Spawn some baddies. - ba.timer( + bs.timer( 1.0, lambda: self._bots.spawn_bot( UFO, pos=boss_spawn_pos, spawn_time=3.0 @@ -915,10 +921,10 @@ class UFOightGame(ba.TeamGameActivity[Player, Team]): def handlemessage(self, msg: Any) -> Any: # A player has died. - if isinstance(msg, ba.PlayerDiedMessage): + if isinstance(msg, bs.PlayerDiedMessage): player = msg.getplayer(Player) self.stats.player_was_killed(player) - ba.timer(0.1, self._checkroundover) + bs.timer(0.1, self._checkroundover) # A spaz-bot has died. elif isinstance(msg, UFODiedMessage): @@ -926,7 +932,7 @@ class UFOightGame(ba.TeamGameActivity[Player, Team]): # bots if we ask here (the currently-dying bot isn't officially # marked dead yet) ..so lets push a call into the event loop to # check once this guy has finished dying. - ba.pushcall(self._check_if_won) + bs.pushcall(self._check_if_won) # Let the base class handle anything we don't. else: @@ -948,20 +954,20 @@ class UFOightGame(ba.TeamGameActivity[Player, Team]): assert self._timer is not None self._timer.stop() - results = ba.GameResults() + results = bs.GameResults() # If we won, set our score to the elapsed time in milliseconds. # (there should just be 1 team here since this is co-op). # ..if we didn't win, leave scores as default (None) which means # we lost. if self._won: - elapsed_time_ms = int((ba.time() - self._timer.starttime) * 1000.0) - ba.cameraflash() - ba.playsound(self._winsound) + elapsed_time_ms = int((bs.time() - self._timer.starttime) * 1000.0) + bs.cameraflash() + self._winsound.play() for team in self.teams: for player in team.players: if player.actor: - player.actor.handlemessage(ba.CelebrateMessage()) + player.actor.handlemessage(bs.CelebrateMessage()) results.set_team_score(team, elapsed_time_ms) # Ends the activity. @@ -969,11 +975,11 @@ class UFOightGame(ba.TeamGameActivity[Player, Team]): # ba_meta export plugin -class MyUFOFightLevel(ba.Plugin): +class MyUFOFightLevel(babase.Plugin): def on_app_running(self) -> None: - ba.app.add_coop_practice_level( - ba.Level( + babase.app.classic.add_coop_practice_level( + bs.Level( name='The UFO Fight', displayname='${GAME}', gametype=UFOightGame, @@ -981,3 +987,4 @@ class MyUFOFightLevel(ba.Plugin): preview_texture_name='footballStadiumPreview', ) ) + diff --git a/plugins/minigames/ultimate_last_stand.py b/plugins/minigames/ultimate_last_stand.py index b74d002..842521d 100644 --- a/plugins/minigames/ultimate_last_stand.py +++ b/plugins/minigames/ultimate_last_stand.py @@ -1,3 +1,4 @@ +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) """Ultimate Last Stand V2: Made by Cross Joy""" @@ -25,7 +26,7 @@ Made by Cross Joy""" # ---------------------------------------------------------------------------- -# ba_meta require api 7 +# ba_meta require api 8 from __future__ import annotations @@ -33,13 +34,15 @@ import random from dataclasses import dataclass from typing import TYPE_CHECKING -import ba -from bastd.actor.playerspaz import PlayerSpaz -from bastd.actor.bomb import TNTSpawner -from bastd.actor.onscreentimer import OnScreenTimer -from bastd.actor.scoreboard import Scoreboard -from bastd.actor.spazfactory import SpazFactory -from bastd.actor.spazbot import (SpazBot, SpazBotSet, BomberBot, +import babase +import bauiv1 as bui +import bascenev1 as bs +from bascenev1lib.actor.playerspaz import PlayerSpaz +from bascenev1lib.actor.bomb import TNTSpawner +from bascenev1lib.actor.onscreentimer import OnScreenTimer +from bascenev1lib.actor.scoreboard import Scoreboard +from bascenev1lib.actor.spazfactory import SpazFactory +from bascenev1lib.actor.spazbot import (SpazBot, SpazBotSet, BomberBot, BomberBotPro, BomberBotProShielded, BrawlerBot, BrawlerBotPro, BrawlerBotProShielded, TriggerBot, @@ -48,7 +51,7 @@ from bastd.actor.spazbot import (SpazBot, SpazBotSet, BomberBot, if TYPE_CHECKING: from typing import Any, Sequence - from bastd.actor.spazbot import SpazBot + from bascenev1lib.actor.spazbot import SpazBot class IceBot(SpazBot): @@ -71,7 +74,7 @@ class IceBot(SpazBot): points_mult = 3 -class Icon(ba.Actor): +class Icon(bs.Actor): """Creates in in-game icon on screen.""" def __init__(self, @@ -90,10 +93,10 @@ class Icon(ba.Actor): self._show_lives = show_lives self._show_death = show_death self._name_scale = name_scale - self._outline_tex = ba.gettexture('characterIconMask') + self._outline_tex = bs.gettexture('characterIconMask') icon = player.get_icon() - self.node = ba.newnode('image', + self.node = bs.newnode('image', delegate=self, attrs={ 'texture': icon['texture'], @@ -106,12 +109,12 @@ class Icon(ba.Actor): 'absolute_scale': True, 'attach': 'bottomCenter' }) - self._name_text = ba.newnode( + self._name_text = bs.newnode( 'text', owner=self.node, attrs={ - 'text': ba.Lstr(value=player.getname()), - 'color': ba.safecolor(player.team.color), + 'text': babase.Lstr(value=player.getname()), + 'color': babase.safecolor(player.team.color), 'h_align': 'center', 'v_align': 'center', 'vr_depth': 410, @@ -122,7 +125,7 @@ class Icon(ba.Actor): 'v_attach': 'bottom' }) if self._show_lives: - self._lives_text = ba.newnode('text', + self._lives_text = bs.newnode('text', owner=self.node, attrs={ 'text': 'x0', @@ -178,7 +181,7 @@ class Icon(ba.Actor): if not self.node: return if self._show_death: - ba.animate( + bs.animate( self.node, 'opacity', { 0.00: 1.0, 0.05: 0.0, @@ -195,10 +198,10 @@ class Icon(ba.Actor): }) lives = self._player.lives if lives == 0: - ba.timer(0.6, self.update_for_lives) + bs.timer(0.6, self.update_for_lives) def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.DieMessage): + if isinstance(msg, bs.DieMessage): self.node.delete() return None return super().handlemessage(msg) @@ -212,7 +215,7 @@ class SpawnInfo: dincrease: float -class Player(ba.Player['Team']): +class Player(bs.Player['Team']): """Our player type for this game.""" def __init__(self) -> None: @@ -222,7 +225,7 @@ class Player(ba.Player['Team']): self.icons: list[Icon] = [] -class Team(ba.Team[Player]): +class Team(bs.Team[Player]): """Our team type for this game.""" def __init__(self) -> None: @@ -230,14 +233,14 @@ class Team(ba.Team[Player]): self.spawn_order: list[Player] = [] -# ba_meta export game -class UltimateLastStand(ba.TeamGameActivity[Player, Team]): +# ba_meta export bascenev1.GameActivity +class UltimateLastStand(bs.TeamGameActivity[Player, Team]): """Minigame involving dodging falling bombs.""" name = 'Ultimate Last Stand' description = 'Only the strongest will stand at the end.' - scoreconfig = ba.ScoreConfig(label='Survived', - scoretype=ba.ScoreType.SECONDS, + scoreconfig = bs.ScoreConfig(label='Survived', + scoretype=bs.ScoreType.SECONDS, none_is_winner=True) # Print messages when players die (since its meaningful in this game). @@ -250,16 +253,16 @@ class UltimateLastStand(ba.TeamGameActivity[Player, Team]): @classmethod def get_available_settings( cls, - sessiontype: type[ba.Session]) -> list[ba.Setting]: + sessiontype: type[bs.Session]) -> list[babase.Setting]: settings = [ - ba.IntSetting( + bs.IntSetting( 'Lives Per Player', default=1, min_value=1, max_value=10, increment=1, ), - ba.FloatChoiceSetting( + bs.FloatChoiceSetting( 'Respawn Times', choices=[ ('Shorter', 0.25), @@ -270,31 +273,31 @@ class UltimateLastStand(ba.TeamGameActivity[Player, Team]): ], default=1.0, ), - ba.BoolSetting('Epic Mode', default=False), + bs.BoolSetting('Epic Mode', default=False), ] - if issubclass(sessiontype, ba.DualTeamSession): + if issubclass(sessiontype, bs.DualTeamSession): settings.append( - ba.BoolSetting('Balance Total Lives', default=False)) + bs.BoolSetting('Balance Total Lives', default=False)) return settings # We're currently hard-coded for one map. @classmethod - def get_supported_maps(cls, sessiontype: type[ba.Session]) -> list[str]: + def get_supported_maps(cls, sessiontype: type[bs.Session]) -> list[str]: return ['Rampage'] # We support teams, free-for-all, and co-op sessions. @classmethod - def supports_session_type(cls, sessiontype: type[ba.Session]) -> bool: - return (issubclass(sessiontype, ba.DualTeamSession) - or issubclass(sessiontype, ba.FreeForAllSession)) + def supports_session_type(cls, sessiontype: type[bs.Session]) -> bool: + return (issubclass(sessiontype, bs.DualTeamSession) + or issubclass(sessiontype, bs.FreeForAllSession)) def __init__(self, settings: dict): super().__init__(settings) self._scoreboard = Scoreboard() self._start_time: float | None = None - self._vs_text: ba.Actor | None = None - self._round_end_timer: ba.Timer | None = None + self._vs_text: bs.Actor | None = None + self._round_end_timer: bs.Timer | None = None self._lives_per_player = int(settings['Lives Per Player']) self._balance_total_lives = bool( settings.get('Balance Total Lives', False)) @@ -302,17 +305,17 @@ class UltimateLastStand(ba.TeamGameActivity[Player, Team]): self._last_player_death_time: float | None = None self._timer: OnScreenTimer | None = None self._tntspawner: TNTSpawner | None = None - self._new_wave_sound = ba.getsound('scoreHit01') + self._new_wave_sound = bs.getsound('scoreHit01') self._bots = SpazBotSet() self._tntspawnpos = (0, 5.5, -6) self.spazList = [] # Base class overrides: self.slow_motion = self._epic_mode - self.default_music = (ba.MusicType.EPIC - if self._epic_mode else ba.MusicType.SURVIVAL) + self.default_music = (bs.MusicType.EPIC + if self._epic_mode else bs.MusicType.SURVIVAL) - self.node = ba.newnode('text', + self.node = bs.newnode('text', attrs={ 'v_attach': 'bottom', 'h_align': 'center', @@ -342,24 +345,24 @@ class UltimateLastStand(ba.TeamGameActivity[Player, Team]): } # yapf: disable # Some base class overrides: - self.default_music = (ba.MusicType.EPIC - if self._epic_mode else ba.MusicType.SURVIVAL) + self.default_music = (bs.MusicType.EPIC + if self._epic_mode else bs.MusicType.SURVIVAL) if self._epic_mode: self.slow_motion = True def get_instance_description(self) -> str | Sequence: return 'Only the strongest team will stand at the end.' if isinstance( self.session, - ba.DualTeamSession) else 'Only the strongest will stand at the end.' + bs.DualTeamSession) else 'Only the strongest will stand at the end.' def get_instance_description_short(self) -> str | Sequence: return 'Only the strongest team will stand at the end.' if isinstance( self.session, - ba.DualTeamSession) else 'Only the strongest will stand at the end.' + bs.DualTeamSession) else 'Only the strongest will stand at the end.' def on_transition_in(self) -> None: super().on_transition_in() - ba.timer(1.3, ba.Call(ba.playsound, self._new_wave_sound)) + bs.timer(1.3, babase.Call(babase.playsound, self._new_wave_sound)) def on_player_join(self, player: Player) -> None: player.lives = self._lives_per_player @@ -374,13 +377,13 @@ class UltimateLastStand(ba.TeamGameActivity[Player, Team]): def on_begin(self) -> None: super().on_begin() - ba.animate_array(node=self.node, attr='color', size=3, keys={ + bs.animate_array(node=self.node, attr='color', size=3, keys={ 0.0: (0.5, 0.5, 0.5), 0.8: (0.83, 0.69, 0.21), 1.6: (0.5, 0.5, 0.5) }, loop=True) - ba.timer(0.001, ba.WeakCall(self._start_bot_updates)) + bs.timer(0.001, bs.WeakCall(self._start_bot_updates)) self._tntspawner = TNTSpawner(position=self._tntspawnpos, respawn_time=10.0) @@ -389,11 +392,11 @@ class UltimateLastStand(ba.TeamGameActivity[Player, Team]): self.setup_standard_powerup_drops() # Check for immediate end (if we've only got 1 player, etc). - self._start_time = ba.time() + self._start_time = bs.time() # If balance-team-lives is on, add lives to the smaller team until # total lives match. - if (isinstance(self.session, ba.DualTeamSession) + if (isinstance(self.session, bs.DualTeamSession) and self._balance_total_lives and self.teams[0].players and self.teams[1].players): if self._get_total_team_lives( @@ -409,7 +412,7 @@ class UltimateLastStand(ba.TeamGameActivity[Player, Team]): lesser_team.players[add_index].lives += 1 add_index = (add_index + 1) % len(lesser_team.players) - ba.timer(1.0, self._update, repeat=True) + bs.timer(1.0, self._update, repeat=True) self._update_icons() # We could check game-over conditions at explicit trigger points, @@ -419,7 +422,7 @@ class UltimateLastStand(ba.TeamGameActivity[Player, Team]): # pylint: disable=too-many-branches # In free-for-all mode, everyone is just lined up along the bottom. - if isinstance(self.session, ba.FreeForAllSession): + if isinstance(self.session, bs.FreeForAllSession): count = len(self.teams) x_offs = 85 xval = x_offs * (count - 1) * -0.5 @@ -453,21 +456,21 @@ class UltimateLastStand(ba.TeamGameActivity[Player, Team]): # Update icons in a moment since our team will be gone from the # list then. - ba.timer(0, self._update_icons) + bs.timer(0, self._update_icons) # If the player to leave was the last in spawn order and had # their final turn currently in-progress, mark the survival time # for their team. if self._get_total_team_lives(player.team) == 0: assert self._start_time is not None - player.team.survival_seconds = int(ba.time() - self._start_time) + player.team.survival_seconds = int(bs.time() - self._start_time) # A departing player may trigger game-over. # overriding the default character spawning.. - def spawn_player(self, player: Player) -> ba.Actor: + def spawn_player(self, player: Player) -> bs.Actor: actor = self.spawn_player_spaz(player) - ba.timer(0.3, ba.Call(self._print_lives, player)) + bs.timer(0.3, babase.Call(self._print_lives, player)) # If we have any icons, update their state. for icon in player.icons: @@ -475,7 +478,7 @@ class UltimateLastStand(ba.TeamGameActivity[Player, Team]): return actor def _print_lives(self, player: Player) -> None: - from bastd.actor import popuptext + from bascenev1lib.actor import popuptext # We get called in a timer so it's possible our player has left/etc. if not player or not player.is_alive() or not player.node: @@ -499,14 +502,14 @@ class UltimateLastStand(ba.TeamGameActivity[Player, Team]): self._update_bots() if len(self.players) > 3: self._update_bots() - self._bot_update_timer = ba.Timer(self._bot_update_interval, - ba.WeakCall(self._update_bots)) + self._bot_update_timer = bs.Timer(self._bot_update_interval, + bs.WeakCall(self._update_bots)) def _update_bots(self) -> None: assert self._bot_update_interval is not None self._bot_update_interval = max(0.5, self._bot_update_interval * 0.98) - self._bot_update_timer = ba.Timer(self._bot_update_interval, - ba.WeakCall(self._update_bots)) + self._bot_update_timer = bs.Timer(self._bot_update_interval, + bs.WeakCall(self._update_bots)) botspawnpts: list[Sequence[float]] = [[-5.0, 5.5, -4.14], [0.0, 5.5, -4.14], [5.0, 5.5, -4.14]] @@ -516,7 +519,7 @@ class UltimateLastStand(ba.TeamGameActivity[Player, Team]): assert isinstance(player.actor, PlayerSpaz) assert player.actor.node except Exception: - ba.print_exception('Error updating bots.') + babase.print_exception('Error updating bots.') spawnpt = random.choice( [botspawnpts[0], botspawnpts[1], botspawnpts[2]]) @@ -550,12 +553,12 @@ class UltimateLastStand(ba.TeamGameActivity[Player, Team]): # Various high-level game events come through this method. def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.PlayerDiedMessage): + if isinstance(msg, bs.PlayerDiedMessage): # Augment standard behavior. super().handlemessage(msg) - curtime = ba.time() + curtime = bs.time() # Record the player's moment of death. # assert isinstance(msg.spaz.player @@ -574,14 +577,14 @@ class UltimateLastStand(ba.TeamGameActivity[Player, Team]): # Play big death sound on our last death # or for every one in solo mode. if player.lives == 0: - ba.playsound(SpazFactory.get().single_player_death_sound) + SpazFactory.get().single_player_death_sound.play() # If we hit zero lives, we're dead (and our team might be too). if player.lives == 0: # If the whole team is now dead, mark their survival time. if self._get_total_team_lives(player.team) == 0: assert self._start_time is not None - player.team.survival_seconds = int(ba.time() - + player.team.survival_seconds = int(bs.time() - self._start_time) else: # Otherwise, in regular mode, respawn. @@ -599,7 +602,7 @@ class UltimateLastStand(ba.TeamGameActivity[Player, Team]): # the game (allows the dust to settle and draws to occur if deaths # are close enough). if len(self._get_living_teams()) < 2: - self._round_end_timer = ba.Timer(0.5, self.end_game) + self._round_end_timer = bs.Timer(0.5, self.end_game) def end_game(self) -> None: # Stop updating our time text, and set the final time to match @@ -608,7 +611,7 @@ class UltimateLastStand(ba.TeamGameActivity[Player, Team]): # Ok now calc game results: set a score for each team and then tell # the game to end. - results = ba.GameResults() + results = bs.GameResults() # Remember that 'free-for-all' mode is simply a special form # of 'teams' mode where each player gets their own team, so we can diff --git a/plugins/minigames/zombie_horde.py b/plugins/minigames/zombie_horde.py index afb48f3..0728409 100644 --- a/plugins/minigames/zombie_horde.py +++ b/plugins/minigames/zombie_horde.py @@ -1,23 +1,26 @@ -# ba_meta require api 7 +# Porting to api 8 made easier by baport.(https://github.com/bombsquad-community/baport) +# ba_meta require api 8 # (see https://ballistica.net/wiki/meta-tag-system) from __future__ import annotations from typing import TYPE_CHECKING -import ba -import _ba +import babase +import bauiv1 as bui +import bascenev1 as bs +import _babase import copy import random -from ba import _math -from ba._coopsession import CoopSession -from ba._messages import PlayerDiedMessage, StandMessage -from bastd.actor.playerspaz import PlayerSpaz -from bastd.actor.scoreboard import Scoreboard -from bastd.game.elimination import Icon, Player -from bastd.actor.spaz import PickupMessage -from bastd.actor.spazbot import SpazBotSet, BrawlerBot, SpazBotDiedMessage -from bastd.actor.spazfactory import SpazFactory +from babase import _math +from bascenev1._coopsession import CoopSession +from bascenev1._messages import PlayerDiedMessage, StandMessage +from bascenev1lib.actor.playerspaz import PlayerSpaz +from bascenev1lib.actor.scoreboard import Scoreboard +from bascenev1lib.game.elimination import Icon, Player +from bascenev1lib.actor.spaz import PickupMessage +from bascenev1lib.actor.spazbot import SpazBotSet, BrawlerBot, SpazBotDiedMessage +from bascenev1lib.actor.spazfactory import SpazFactory if TYPE_CHECKING: @@ -26,7 +29,7 @@ if TYPE_CHECKING: class PlayerSpaz_Zom(PlayerSpaz): def handlemessage(self, m: Any) -> Any: - if isinstance(m, ba.HitMessage): + if isinstance(m, bs.HitMessage): if not self.node: return if not m._source_player is None: @@ -40,7 +43,7 @@ class PlayerSpaz_Zom(PlayerSpaz): else: super().handlemessage(m) - elif isinstance(m, ba.FreezeMessage): + elif isinstance(m, bs.FreezeMessage): pass elif isinstance(m, PickupMessage): @@ -48,10 +51,10 @@ class PlayerSpaz_Zom(PlayerSpaz): return None try: - collision = ba.getcollision() + collision = bs.getcollision() opposingnode = collision.opposingnode opposingbody = collision.opposingbody - except ba.NotFoundError: + except bs.NotFoundError: return True try: @@ -85,7 +88,7 @@ class PlayerSpaz_Zom(PlayerSpaz): class PlayerZombie(PlayerSpaz): def handlemessage(self, m: Any) -> Any: - if isinstance(m, ba.HitMessage): + if isinstance(m, bs.HitMessage): if not self.node: return None if not m._source_player is None: @@ -106,8 +109,8 @@ class PlayerZombie(PlayerSpaz): class zBotSet(SpazBotSet): def start_moving(self) -> None: """Start processing bot AI updates so they start doing their thing.""" - self._bot_update_timer = ba.Timer(0.05, - ba.WeakCall(self.zUpdate), + self._bot_update_timer = bs.Timer(0.05, + bs.WeakCall(self.zUpdate), repeat=True) def zUpdate(self) -> None: @@ -118,31 +121,31 @@ class zBotSet(SpazBotSet): ]) except Exception: bot_list = [] - ba.print_exception('Error updating bot list: ' + + babase.print_exception('Error updating bot list: ' + str(self._bot_lists[self._bot_update_list])) self._bot_update_list = (self._bot_update_list + 1) % self._bot_list_count player_pts = [] - for player in ba.getactivity().players: - assert isinstance(player, ba.Player) + for player in bs.getactivity().players: + assert isinstance(player, bs.Player) try: if player.is_alive(): assert isinstance(player.actor, Spaz) assert player.actor.node if player.lives > 0: player_pts.append( - (ba.Vec3(player.actor.node.position), - ba.Vec3(player.actor.node.velocity))) + (babase.Vec3(player.actor.node.position), + babase.Vec3(player.actor.node.velocity))) except Exception: - ba.print_exception('Error on bot-set _update.') + babase.print_exception('Error on bot-set _update.') for bot in bot_list: bot.set_player_points(player_pts) bot.update_ai() -class Team(ba.Team[Player]): +class Team(bs.Team[Player]): """Our team type for this game.""" def __init__(self) -> None: @@ -150,13 +153,13 @@ class Team(ba.Team[Player]): self.spawn_order: list[Player] = [] -# ba_meta export game -class ZombieHorde(ba.TeamGameActivity[Player, Team]): +# ba_meta export bascenev1.GameActivity +class ZombieHorde(bs.TeamGameActivity[Player, Team]): name = 'Zombie Horde' description = 'Kill walkers for points!' - scoreconfig = ba.ScoreConfig(label='Score', - scoretype=ba.ScoreType.POINTS, + scoreconfig = bs.ScoreConfig(label='Score', + scoretype=bs.ScoreType.POINTS, none_is_winner=False, lower_is_better=False) # Show messages when players die since it's meaningful here. @@ -164,23 +167,23 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): @classmethod def get_available_settings( - cls, sessiontype: type[ba.Session]) -> list[ba.Setting]: + cls, sessiontype: type[bs.Session]) -> list[babase.Setting]: settings = [ - ba.IntSetting( + bs.IntSetting( 'Lives Per Player', default=1, min_value=1, max_value=10, increment=1, ), - ba.IntSetting( + bs.IntSetting( 'Max Zombies', default=10, min_value=5, max_value=50, increment=5, ), - ba.IntChoiceSetting( + bs.IntChoiceSetting( 'Time Limit', choices=[ ('None', 0), @@ -192,7 +195,7 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): ], default=0, ), - ba.FloatChoiceSetting( + bs.FloatChoiceSetting( 'Respawn Times', choices=[ ('Shorter', 0.25), @@ -203,29 +206,29 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): ], default=1.0, ), - ba.BoolSetting('Epic Mode', default=False), + bs.BoolSetting('Epic Mode', default=False), ] - if issubclass(sessiontype, ba.DualTeamSession): - settings.append(ba.BoolSetting('Solo Mode', default=False)) + if issubclass(sessiontype, bs.DualTeamSession): + settings.append(bs.BoolSetting('Solo Mode', default=False)) settings.append( - ba.BoolSetting('Balance Total Lives', default=False)) + bs.BoolSetting('Balance Total Lives', default=False)) return settings @classmethod - def supports_session_type(cls, sessiontype: type[ba.Session]) -> bool: - return (issubclass(sessiontype, ba.DualTeamSession) - or issubclass(sessiontype, ba.FreeForAllSession)) + def supports_session_type(cls, sessiontype: type[bs.Session]) -> bool: + return (issubclass(sessiontype, bs.DualTeamSession) + or issubclass(sessiontype, bs.FreeForAllSession)) @classmethod - def get_supported_maps(cls, sessiontype: type[ba.Session]) -> list[str]: - return ba.getmaps('melee') + def get_supported_maps(cls, sessiontype: type[bs.Session]) -> list[str]: + return bs.app.classic.getmaps('melee') def __init__(self, settings: dict): super().__init__(settings) self._scoreboard = Scoreboard() self._start_time: float | None = None - self._vs_text: ba.Actor | None = None - self._round_end_timer: ba.Timer | None = None + self._vs_text: bs.Actor | None = None + self._round_end_timer: bs.Timer | None = None self._epic_mode = bool(settings['Epic Mode']) self._lives_per_player = int(settings['Lives Per Player']) self._max_zombies = int(settings['Max Zombies']) @@ -236,53 +239,53 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): # Base class overrides: self.slow_motion = self._epic_mode - self.default_music = (ba.MusicType.EPIC - if self._epic_mode else ba.MusicType.SURVIVAL) + self.default_music = (bs.MusicType.EPIC + if self._epic_mode else bs.MusicType.SURVIVAL) self.spazList = [] self.zombieQ = 0 - activity = ba.getactivity() + activity = bs.getactivity() my_factory = SpazFactory.get() appears = ['Kronk', 'Zoe', 'Pixel', 'Agent Johnson', 'Bones', 'Frosty', 'Kronk2'] - myAppear = copy.copy(ba.app.spaz_appearances['Kronk']) + myAppear = copy.copy(babase.app.classic.spaz_appearances['Kronk']) myAppear.name = 'Kronk2' - ba.app.spaz_appearances['Kronk2'] = myAppear + babase.app.classic.spaz_appearances['Kronk2'] = myAppear for appear in appears: my_factory.get_media(appear) med = my_factory.spaz_media - med['Kronk2']['head_model'] = med['Zoe']['head_model'] + med['Kronk2']['head_mesh'] = med['Zoe']['head_mesh'] med['Kronk2']['color_texture'] = med['Agent Johnson']['color_texture'] med['Kronk2']['color_mask_texture'] = med['Pixel']['color_mask_texture'] - med['Kronk2']['torso_model'] = med['Bones']['torso_model'] - med['Kronk2']['pelvis_model'] = med['Pixel']['pelvis_model'] - med['Kronk2']['upper_arm_model'] = med['Frosty']['upper_arm_model'] - med['Kronk2']['forearm_model'] = med['Frosty']['forearm_model'] - med['Kronk2']['hand_model'] = med['Bones']['hand_model'] - med['Kronk2']['upper_leg_model'] = med['Bones']['upper_leg_model'] - med['Kronk2']['lower_leg_model'] = med['Pixel']['lower_leg_model'] - med['Kronk2']['toes_model'] = med['Bones']['toes_model'] + med['Kronk2']['torso_mesh'] = med['Bones']['torso_mesh'] + med['Kronk2']['pelvis_mesh'] = med['Pixel']['pelvis_mesh'] + med['Kronk2']['upper_arm_mesh'] = med['Frosty']['upper_arm_mesh'] + med['Kronk2']['forearm_mesh'] = med['Frosty']['forearm_mesh'] + med['Kronk2']['hand_mesh'] = med['Bones']['hand_mesh'] + med['Kronk2']['upper_leg_mesh'] = med['Bones']['upper_leg_mesh'] + med['Kronk2']['lower_leg_mesh'] = med['Pixel']['lower_leg_mesh'] + med['Kronk2']['toes_mesh'] = med['Bones']['toes_mesh'] def get_instance_description(self) -> str | Sequence: return ('Kill walkers for points! ', 'Dead player walker: 2 points!') if isinstance( - self.session, ba.DualTeamSession) else ( + self.session, bs.DualTeamSession) else ( 'Kill walkers for points! Dead player walker: 2 points!') def get_instance_description_short(self) -> str | Sequence: return ('Kill walkers for points! ', 'Dead player walker: 2 points!') if isinstance( - self.session, ba.DualTeamSession) else ( + self.session, bs.DualTeamSession) else ( 'Kill walkers for points! Dead player walker: 2 points!') def on_player_join(self, player: Player) -> None: if self.has_begun(): player.lives = 0 player.icons = [] - ba.screenmessage( - ba.Lstr(resource='playerDelayedJoinText', + bs.broadcastmessage( + babase.Lstr(resource='playerDelayedJoinText', subs=[('${PLAYER}', player.getname(full=True))]), color=(0, 1, 0), ) @@ -314,13 +317,13 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): def on_begin(self) -> None: super().on_begin() - self._start_time = ba.time() + self._start_time = bs.time() self.setup_standard_time_limit(self._time_limit) self.setup_standard_powerup_drops() self.zombieQ = 1 if self._solo_mode: - self._vs_text = ba.NodeActor( - ba.newnode('text', + self._vs_text = bs.NodeActor( + bs.newnode('text', attrs={ 'position': (0, 105), 'h_attach': 'center', @@ -331,12 +334,12 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): 'scale': 0.6, 'v_attach': 'bottom', 'color': (0.8, 0.8, 0.3, 1.0), - 'text': ba.Lstr(resource='vsText') + 'text': babase.Lstr(resource='vsText') })) # If balance-team-lives is on, add lives to the smaller team until # total lives match. - if (isinstance(self.session, ba.DualTeamSession) + if (isinstance(self.session, bs.DualTeamSession) and self._balance_total_lives and self.teams[0].players and self.teams[1].players): if self._get_total_team_lives( @@ -365,13 +368,13 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): # We could check game-over conditions at explicit trigger points, # but lets just do the simple thing and poll it. - ba.timer(1.0, self._update, repeat=True) + bs.timer(1.0, self._update, repeat=True) def _update_icons(self) -> None: # pylint: disable=too-many-branches # In free-for-all mode, everyone is just lined up along the bottom. - if isinstance(self.session, ba.FreeForAllSession): + if isinstance(self.session, bs.FreeForAllSession): count = len(self.teams) x_offs = 85 xval = x_offs * (count - 1) * -0.5 @@ -437,7 +440,7 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): icon.update_for_lives() xval += x_offs - def _get_spawn_point(self, player: Player) -> ba.Vec3 | None: + def _get_spawn_point(self, player: Player) -> babase.Vec3 | None: del player # Unused. # In solo-mode, if there's an existing live player on the map, spawn at @@ -455,10 +458,10 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): break if living_player: assert living_player_pos is not None - player_pos = ba.Vec3(living_player_pos) - points: list[tuple[float, ba.Vec3]] = [] + player_pos = babase.Vec3(living_player_pos) + points: list[tuple[float, babase.Vec3]] = [] for team in self.teams: - start_pos = ba.Vec3(self.map.get_start_position(team.id)) + start_pos = babase.Vec3(self.map.get_start_position(team.id)) points.append( ((start_pos - player_pos).length(), start_pos)) # Hmm.. we need to sorting vectors too? @@ -466,13 +469,13 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): return points[-1][1] return None - def spawn_player(self, player: Player) -> ba.Actor: + def spawn_player(self, player: Player) -> bs.Actor: position = self.map.get_ffa_start_position(self.players) angle = 20 name = player.getname() light_color = _math.normalized_color(player.color) - display_color = _ba.safecolor(player.color, target_intensity=0.75) + display_color = _babase.safecolor(player.color, target_intensity=0.75) spaz = PlayerSpaz_Zom(color=player.color, highlight=player.highlight, character=player.character, @@ -500,14 +503,14 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): StandMessage( position, angle if angle is not None else random.uniform(0, 360))) - _ba.playsound(self._spawn_sound, 1, position=spaz.node.position) - light = _ba.newnode('light', attrs={'color': light_color}) + bs.Sound.play(self._spawn_sound, 1, position=spaz.node.position) + light = bs.newnode('light', attrs={'color': light_color}) spaz.node.connectattr('position', light, 'position') - ba.animate(light, 'intensity', {0: 0, 0.25: 1, 0.5: 0}) - _ba.timer(0.5, light.delete) + bs.animate(light, 'intensity', {0: 0, 0.25: 1, 0.5: 0}) + bs.timer(0.5, light.delete) if not self._solo_mode: - ba.timer(0.3, ba.Call(self._print_lives, player)) + bs.timer(0.3, babase.Call(self._print_lives, player)) for icon in player.icons: icon.handle_player_spawned() @@ -539,30 +542,30 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): respawn_time = round(max(1.0, respawn_time), 0) if player.actor and not self.has_ended(): - from bastd.actor.respawnicon import RespawnIcon - player.customdata['respawn_timer'] = _ba.Timer( - respawn_time, ba.WeakCall( + from bascenev1lib.actor.respawnicon import RespawnIcon + player.customdata['respawn_timer'] = bs.Timer( + respawn_time, bs.WeakCall( self.spawn_player_if_exists_as_zombie, player)) player.customdata['respawn_icon'] = RespawnIcon( player, respawn_time) - def spawn_player_if_exists_as_zombie(self, player: PlayerType) -> None: + def spawn_player_if_exists_as_zombie(self, player: PlayerT) -> None: """ A utility method which calls self.spawn_player() *only* if the - ba.Player provided still exists; handy for use in timers and whatnot. + bs.Player provided still exists; handy for use in timers and whatnot. There is no need to override this; just override spawn_player(). """ if player: self.spawn_player_zombie(player) - def spawn_player_zombie(self, player: PlayerType) -> ba.Actor: + def spawn_player_zombie(self, player: PlayerT) -> bs.Actor: position = self.map.get_ffa_start_position(self.players) angle = 20 name = player.getname() light_color = _math.normalized_color(player.color) - display_color = _ba.safecolor(player.color, target_intensity=0.75) + display_color = _babase.safecolor(player.color, target_intensity=0.75) spaz = PlayerSpaz_Zom(color=player.color, highlight=player.highlight, character='Kronk2', @@ -591,21 +594,21 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): StandMessage( position, angle if angle is not None else random.uniform(0, 360))) - _ba.playsound(self._spawn_sound, 1, position=spaz.node.position) - light = _ba.newnode('light', attrs={'color': light_color}) + bs.Sound.play(self._spawn_sound, 1, position=spaz.node.position) + light = bs.newnode('light', attrs={'color': light_color}) spaz.node.connectattr('position', light, 'position') - ba.animate(light, 'intensity', {0: 0, 0.25: 1, 0.5: 0}) - _ba.timer(0.5, light.delete) + bs.animate(light, 'intensity', {0: 0, 0.25: 1, 0.5: 0}) + bs.timer(0.5, light.delete) if not self._solo_mode: - ba.timer(0.3, ba.Call(self._print_lives, player)) + bs.timer(0.3, babase.Call(self._print_lives, player)) for icon in player.icons: icon.handle_player_spawned() return spaz def _print_lives(self, player: Player) -> None: - from bastd.actor import popuptext + from bascenev1lib.actor import popuptext # We get called in a timer so it's possible our player has left/etc. if not player or not player.is_alive() or not player.node: @@ -642,13 +645,13 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): # Update icons in a moment since our team will be gone from the # list then. - ba.timer(0, self._update_icons) + bs.timer(0, self._update_icons) def _get_total_team_lives(self, team: Team) -> int: return sum(player.lives for player in team.players) def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.PlayerDiedMessage): + if isinstance(msg, bs.PlayerDiedMessage): # Augment standard behavior. super().handlemessage(msg) @@ -665,7 +668,7 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): if msg._player in self.spazList: self.spazList.remove(msg._player) if player.lives < 0: - ba.print_error( + babase.print_error( "Got lives < 0 in Elim; this shouldn't happen. solo:" + str(self._solo_mode)) player.lives = 0 @@ -677,7 +680,7 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): # Play big death sound on our last death # or for every one in solo mode. if self._solo_mode or player.lives == 0: - ba.playsound(SpazFactory.get().single_player_death_sound) + SpazFactory.get().single_player_death_sound.play() # If we hit zero lives, we're dead (and our team might be too). if player.lives == 0: @@ -732,16 +735,16 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): theScores) and theScores.count(max(theScores)) > 1: pass else: - self._round_end_timer = ba.Timer(0.5, self.end_game) + self._round_end_timer = bs.Timer(0.5, self.end_game) else: - self._round_end_timer = ba.Timer(0.5, self.end_game) + self._round_end_timer = bs.Timer(0.5, self.end_game) def spawn_zombie(self) -> None: # We need a Z height... thePt = list(self.get_random_point_in_play()) thePt2 = self.map.get_ffa_start_position(self.players) thePt[1] = thePt2[1] - ba.timer(0.1, ba.Call( + bs.timer(0.1, babase.Call( self._bots.spawn_bot, BrawlerBot, pos=thePt, spawn_time=1.0)) def _onSpazBotDied(self, DeathMsg) -> None: @@ -816,25 +819,25 @@ class ZombieHorde(ba.TeamGameActivity[Player, Team]): setattr(BrawlerBot, 'color', (0.6, 0.6, 0.6)) setattr(BrawlerBot, 'highlight', (0.6, 0.6, 0.6)) setattr(BrawlerBot, 'character', 'Kronk') - results = ba.GameResults() + results = bs.GameResults() self._vs_text = None # Kill our 'vs' if its there. for team in self.teams: results.set_team_score(team, team.score) self.end(results=results) -# ba_meta export game +# ba_meta export bascenev1.GameActivity class ZombieHordeCoop(ZombieHorde): name = 'Zombie Horde' @classmethod - def get_supported_maps(cls, sessiontype: type[ba.Session]) -> list[str]: + def get_supported_maps(cls, sessiontype: type[bs.Session]) -> list[str]: return ['Football Stadium'] @classmethod - def supports_session_type(cls, sessiontype: type[ba.Session]) -> bool: - return (issubclass(sessiontype, ba.CoopSession)) + def supports_session_type(cls, sessiontype: type[bs.Session]) -> bool: + return (issubclass(sessiontype, bs.CoopSession)) def _update(self) -> None: if self.zombieQ > 0: @@ -855,12 +858,12 @@ class ZombieHordeCoop(ZombieHorde): break if not any(player.is_alive() for player in self.teams[0].players): - self._round_end_timer = ba.Timer(0.5, self.end_game) + self._round_end_timer = bs.Timer(0.5, self.end_game) def handlemessage(self, msg: Any) -> Any: - if isinstance(msg, ba.PlayerDiedMessage): + if isinstance(msg, bs.PlayerDiedMessage): # Augment standard behavior. - ba.TeamGameActivity.handlemessage(self, msg) + bs.TeamGameActivity.handlemessage(self, msg) player: Player = msg.getplayer(Player) # If we have any icons, update their state. for icon in player.icons: @@ -870,10 +873,10 @@ class ZombieHordeCoop(ZombieHorde): # ba_meta export plugin -class ZombieHordeLevel(ba.Plugin): +class ZombieHordeLevel(babase.Plugin): def on_app_running(self) -> None: - ba.app.add_coop_practice_level( - ba.Level( + babase.app.classic.add_coop_practice_level( + bs._level.Level( 'Zombie Horde', gametype=ZombieHordeCoop, settings={}, diff --git a/plugins/utilities/discord_richpresence.py b/plugins/utilities/discord_richpresence.py index 3028e64..2a74870 100644 --- a/plugins/utilities/discord_richpresence.py +++ b/plugins/utilities/discord_richpresence.py @@ -27,7 +27,7 @@ import _babase import bascenev1 as bs import bascenev1lib import bauiv1 as bui -from baenv import TARGET_BALLISTICA_BUILD +from baenv import TARGET_BALLISTICA_BUILD as build_number from typing import TYPE_CHECKING @@ -37,8 +37,8 @@ if TYPE_CHECKING: ANDROID = babase.app.classic.platform == "android" DIRPATH = Path( - f"{_babase.app.python_directory_user if TARGET_BALLISTICA_BUILD < 21282 else _babase.app.env.python_directory_user}/image_id.json") -APP_VERSION = _babase.app.version if TARGET_BALLISTICA_BUILD < 21282 else _babase.app.env.version + f"{_babase.app.python_directory_user if build_number < 21282 else _babase.app.env.python_directory_user}/image_id.json") +APP_VERSION = _babase.app.version if build_number < 21282 else _babase.app.env.version if ANDROID: # !can add ios in future diff --git a/plugins/utilities/ragdoll_b_gone.py b/plugins/utilities/ragdoll_b_gone.py index 6f229fc..3bd5e8b 100644 --- a/plugins/utilities/ragdoll_b_gone.py +++ b/plugins/utilities/ragdoll_b_gone.py @@ -98,7 +98,7 @@ class RagdollBGone(babase.Plugin): # Pick a random death noise sound = death_sounds[random.randrange(len(death_sounds))] # Play the sound where our Spaz is - sound.play(position=args[0].node.position) + bs.Sound.play(sound, position=args[0].node.position) # Delete our Spaz node immediately. # Removing stuff is weird and prone to errors, so we're gonna delay it. bs.timer(0.001, args[0].node.delete)