batframework 1.0.8a12__py3-none-any.whl → 1.0.8a14__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- batFramework/__init__.py +4 -3
- batFramework/animatedSprite.py +4 -52
- batFramework/animation.py +52 -0
- batFramework/character.py +3 -3
- batFramework/constants.py +4 -0
- batFramework/cutscene.py +7 -5
- batFramework/drawable.py +75 -0
- batFramework/entity.py +105 -55
- batFramework/gui/container.py +1 -1
- batFramework/gui/debugger.py +1 -1
- batFramework/gui/label.py +18 -41
- batFramework/gui/layout.py +2 -2
- batFramework/gui/root.py +0 -6
- batFramework/gui/widget.py +1 -1
- batFramework/manager.py +35 -34
- batFramework/particle.py +1 -1
- batFramework/scene.py +1 -34
- batFramework/sceneManager.py +5 -23
- batFramework/sprite.py +2 -2
- batFramework/templates/character.py +5 -6
- batFramework/{time.py → timeManager.py} +0 -2
- batFramework/utils.py +118 -19
- {batframework-1.0.8a12.dist-info → batframework-1.0.8a14.dist-info}/METADATA +1 -1
- {batframework-1.0.8a12.dist-info → batframework-1.0.8a14.dist-info}/RECORD +27 -26
- batFramework/object.py +0 -123
- {batframework-1.0.8a12.dist-info → batframework-1.0.8a14.dist-info}/LICENCE +0 -0
- {batframework-1.0.8a12.dist-info → batframework-1.0.8a14.dist-info}/WHEEL +0 -0
- {batframework-1.0.8a12.dist-info → batframework-1.0.8a14.dist-info}/top_level.txt +0 -0
batFramework/manager.py
CHANGED
@@ -1,23 +1,24 @@
|
|
1
1
|
import batFramework as bf
|
2
2
|
import pygame
|
3
3
|
import asyncio
|
4
|
-
import random
|
5
4
|
|
6
5
|
class Manager(bf.SceneManager):
|
7
6
|
def __init__(self, *initial_scene_list) -> None:
|
8
|
-
# random.seed("random")
|
9
7
|
super().__init__()
|
10
|
-
self.
|
11
|
-
self.
|
12
|
-
self.
|
13
|
-
self.
|
14
|
-
self.
|
15
|
-
self.
|
16
|
-
self.
|
8
|
+
self.debug_mode: bf.enums.debugMode = bf.debugMode.HIDDEN
|
9
|
+
self.screen: pygame.Surface | None = bf.const.SCREEN
|
10
|
+
self.timeManager = bf.TimeManager()
|
11
|
+
self.cutsceneManager = bf.CutsceneManager()
|
12
|
+
self.cutsceneManager.set_manager(self)
|
13
|
+
self.clock: pygame.Clock = pygame.Clock()
|
14
|
+
self.is_async_running : bool = False
|
15
|
+
self.running = False
|
17
16
|
pygame.mouse.set_cursor(bf.const.DEFAULT_CURSOR)
|
18
17
|
self.do_pre_init()
|
19
18
|
self.init_scenes(*initial_scene_list)
|
20
|
-
|
19
|
+
bf.ResourceManager().set_sharedVar("clock", self.clock)
|
20
|
+
bf.ResourceManager().set_sharedVar("debug_mode", self.debug_mode)
|
21
|
+
|
21
22
|
self.do_init()
|
22
23
|
|
23
24
|
@staticmethod
|
@@ -39,14 +40,14 @@ class Manager(bf.SceneManager):
|
|
39
40
|
print("=" * 50)
|
40
41
|
|
41
42
|
# Print the timers information
|
42
|
-
print(self.
|
43
|
+
print(self.timeManager)
|
43
44
|
|
44
45
|
# End with a visual separator
|
45
46
|
print("=" * 50 + "\n")
|
46
47
|
|
47
48
|
|
48
49
|
def get_fps(self) -> float:
|
49
|
-
return self.
|
50
|
+
return self.clock.get_fps()
|
50
51
|
|
51
52
|
def do_init(self) -> None:
|
52
53
|
pass
|
@@ -55,67 +56,67 @@ class Manager(bf.SceneManager):
|
|
55
56
|
pass
|
56
57
|
|
57
58
|
def stop(self) -> None:
|
58
|
-
self.
|
59
|
+
self.running = False
|
59
60
|
|
60
61
|
async def run_async(self):
|
61
|
-
if self.
|
62
|
+
if self.running:
|
62
63
|
print("Error : Already running")
|
63
64
|
return
|
64
|
-
self.
|
65
|
-
self.
|
65
|
+
self.is_async_running = True
|
66
|
+
self.running = True
|
66
67
|
dt: float = 0
|
67
|
-
while self.
|
68
|
+
while self.running:
|
68
69
|
for event in pygame.event.get():
|
69
70
|
event.consumed = False
|
70
71
|
self.process_event(event)
|
71
72
|
if not event.consumed:
|
72
73
|
if event.type == pygame.QUIT:
|
73
|
-
self.
|
74
|
+
self.running = False
|
74
75
|
break
|
75
76
|
if event.type == pygame.VIDEORESIZE and not (
|
76
77
|
bf.const.FLAGS & pygame.SCALED
|
77
78
|
):
|
78
79
|
bf.const.set_resolution((event.w, event.h))
|
79
80
|
# update
|
80
|
-
|
81
|
-
|
82
|
-
self._timeManager.update(dt)
|
83
|
-
self._cutsceneManager.update(dt)
|
81
|
+
self.timeManager.update(dt)
|
82
|
+
self.cutsceneManager.update(dt)
|
84
83
|
self.update(dt)
|
85
84
|
# render
|
86
|
-
self.
|
87
|
-
self.draw(self.
|
85
|
+
self.screen.fill((0, 0, 0))
|
86
|
+
self.draw(self.screen)
|
88
87
|
pygame.display.flip()
|
88
|
+
dt = self.clock.tick(bf.const.FPS) / 1000
|
89
|
+
# dt = min(dt, 0.02) dirty fix for dt being too high when window not focused for a long time
|
89
90
|
await asyncio.sleep(0)
|
90
91
|
pygame.quit()
|
91
92
|
|
92
93
|
|
93
94
|
def run(self) -> None:
|
94
|
-
if self.
|
95
|
+
if self.running:
|
95
96
|
print("Error : Already running")
|
96
97
|
return
|
97
|
-
self.
|
98
|
+
self.running = True
|
98
99
|
dt: float = 0
|
99
|
-
while self.
|
100
|
+
while self.running:
|
100
101
|
for event in pygame.event.get():
|
101
102
|
event.consumed = False
|
102
103
|
self.process_event(event)
|
103
104
|
if not event.consumed:
|
104
105
|
if event.type == pygame.QUIT:
|
105
|
-
self.
|
106
|
+
self.running = False
|
106
107
|
break
|
107
108
|
if event.type == pygame.VIDEORESIZE and not (
|
108
109
|
bf.const.FLAGS & pygame.SCALED
|
109
110
|
):
|
110
111
|
bf.const.set_resolution((event.w, event.h))
|
111
112
|
# update
|
112
|
-
|
113
|
-
|
114
|
-
self._timeManager.update(dt)
|
115
|
-
self._cutsceneManager.update(dt)
|
113
|
+
self.timeManager.update(dt)
|
114
|
+
self.cutsceneManager.update(dt)
|
116
115
|
self.update(dt)
|
117
116
|
# render
|
118
|
-
self.
|
119
|
-
self.draw(self.
|
117
|
+
self.screen.fill((0, 0, 0))
|
118
|
+
self.draw(self.screen)
|
120
119
|
pygame.display.flip()
|
120
|
+
dt = self.clock.tick(bf.const.FPS) / 1000
|
121
|
+
# dt = min(dt, 0.02) dirty fix for dt being too high when window not focused for a long time
|
121
122
|
pygame.quit()
|
batFramework/particle.py
CHANGED
batFramework/scene.py
CHANGED
@@ -70,35 +70,6 @@ class Scene:
|
|
70
70
|
"""Get the scene index."""
|
71
71
|
return self.scene_index
|
72
72
|
|
73
|
-
def set_sharedVar(self, name: str, value: Any) -> bool:
|
74
|
-
"""
|
75
|
-
Set a shared variable in the manager.
|
76
|
-
|
77
|
-
Args:
|
78
|
-
name: Name of the shared variable.
|
79
|
-
value: Value to set.
|
80
|
-
|
81
|
-
Returns:
|
82
|
-
bool: True if setting was successful, False otherwise.
|
83
|
-
"""
|
84
|
-
if not self.manager:
|
85
|
-
return False
|
86
|
-
return self.manager.set_sharedVar(name, value)
|
87
|
-
|
88
|
-
def get_sharedVar(self, name: str, error_value=None) -> Any:
|
89
|
-
"""
|
90
|
-
Get a shared variable from the manager.
|
91
|
-
|
92
|
-
Args:
|
93
|
-
name: Name of the shared variable.
|
94
|
-
|
95
|
-
Returns:
|
96
|
-
Any: Value of the shared variable.
|
97
|
-
"""
|
98
|
-
if not self.manager:
|
99
|
-
return error_value
|
100
|
-
return self.manager.get_sharedVar(name, error_value)
|
101
|
-
|
102
73
|
def do_when_added(self):
|
103
74
|
pass
|
104
75
|
|
@@ -277,7 +248,6 @@ class Scene:
|
|
277
248
|
self.actions.reset()
|
278
249
|
self.early_actions.reset()
|
279
250
|
|
280
|
-
|
281
251
|
if self.entities_to_add:
|
282
252
|
for e in self.entities_to_add:
|
283
253
|
self.world_entities[e] = None
|
@@ -337,7 +307,7 @@ class Scene:
|
|
337
307
|
|
338
308
|
def _draw_camera(self, camera: bf.Camera, entity_list):
|
339
309
|
_ = [entity.draw(camera) for entity in entity_list]
|
340
|
-
debugMode =
|
310
|
+
debugMode = bf.ResourceManager().get_sharedVar("debug_mode")
|
341
311
|
# Draw outlines for world entities if required
|
342
312
|
if debugMode == bf.debugMode.OUTLINES:
|
343
313
|
[self.debug_entity(e, camera) for e in entity_list]
|
@@ -355,15 +325,12 @@ class Scene:
|
|
355
325
|
self.set_active(True)
|
356
326
|
self.set_visible(True)
|
357
327
|
self.root.clear_hovered()
|
358
|
-
# self.root.clear_focused()
|
359
328
|
self.root.build()
|
360
329
|
bf.TimeManager().activate_register(self.name)
|
361
330
|
self.do_on_enter()
|
362
|
-
# self.root.visit(lambda e : e.resolve_constraints())
|
363
331
|
|
364
332
|
def on_exit(self):
|
365
333
|
self.root.clear_hovered()
|
366
|
-
# self.root.clear_focused()
|
367
334
|
self.set_active(False)
|
368
335
|
self.set_visible(False)
|
369
336
|
self.actions.hard_reset()
|
batFramework/sceneManager.py
CHANGED
@@ -2,7 +2,6 @@ import batFramework as bf
|
|
2
2
|
import pygame
|
3
3
|
from typing import Self
|
4
4
|
|
5
|
-
|
6
5
|
def swap(lst, index1, index2):
|
7
6
|
lst[index1], lst[index2] = lst[index2], lst[index1]
|
8
7
|
|
@@ -11,11 +10,6 @@ class SceneManager:
|
|
11
10
|
def __init__(self) -> None:
|
12
11
|
self.scenes: list[bf.Scene] = []
|
13
12
|
self.shared_events = {pygame.WINDOWRESIZED}
|
14
|
-
|
15
|
-
self.set_sharedVar("in_cutscene", False)
|
16
|
-
self.set_sharedVar("player_has_control", True)
|
17
|
-
self.old_player_control = True
|
18
|
-
self.debug_mode: bf.enums.debugMode = bf.debugMode.HIDDEN
|
19
13
|
self.current_transitions: dict[str, bf.transition.Transition] = {}
|
20
14
|
|
21
15
|
def init_scenes(self, *initial_scenes:bf.Scene):
|
@@ -23,7 +17,6 @@ class SceneManager:
|
|
23
17
|
s.set_scene_index(index)
|
24
18
|
for s in reversed(initial_scenes):
|
25
19
|
self.add_scene(s)
|
26
|
-
# self.scenes = list(initial_scenes)
|
27
20
|
self.set_scene(initial_scenes[0].get_name())
|
28
21
|
self.update_scene_states()
|
29
22
|
|
@@ -38,7 +31,7 @@ class SceneManager:
|
|
38
31
|
Print detailed information about the current state of the scenes and shared variables.
|
39
32
|
"""
|
40
33
|
|
41
|
-
def format_scene_info(scene):
|
34
|
+
def format_scene_info(scene:bf.Scene):
|
42
35
|
status = 'Active' if scene.active else 'Inactive'
|
43
36
|
visibility = 'Visible' if scene.visible else 'Invisible'
|
44
37
|
return f"{scene.name:<30} | {status:<8} | {visibility:<10} | Index={scene.scene_index}"
|
@@ -78,13 +71,6 @@ class SceneManager:
|
|
78
71
|
|
79
72
|
print("=" * 50 + "\n")
|
80
73
|
|
81
|
-
|
82
|
-
def set_sharedVar(self, name, value) -> None:
|
83
|
-
bf.ResourceManager().set_sharedVar(name,value)
|
84
|
-
|
85
|
-
def get_sharedVar(self, name, error_value=None):
|
86
|
-
return bf.ResourceManager().get_sharedVar(name, error_value)
|
87
|
-
|
88
74
|
def get_current_scene_name(self) -> str:
|
89
75
|
"""get the name of the current scene"""
|
90
76
|
return self.scenes[0].get_name()
|
@@ -106,10 +92,10 @@ class SceneManager:
|
|
106
92
|
def remove_scene(self, name: str):
|
107
93
|
self.scenes = [s for s in self.scenes if s.name != name]
|
108
94
|
|
109
|
-
def has_scene(self, name):
|
95
|
+
def has_scene(self, name:str):
|
110
96
|
return any(name == scene.name for scene in self.scenes)
|
111
97
|
|
112
|
-
def get_scene(self, name):
|
98
|
+
def get_scene(self, name:str):
|
113
99
|
if not self.has_scene(name):
|
114
100
|
return None
|
115
101
|
for scene in self.scenes:
|
@@ -150,8 +136,6 @@ class SceneManager:
|
|
150
136
|
def _start_transition(self, target_scene: bf.Scene):
|
151
137
|
target_scene.set_active(True)
|
152
138
|
target_scene.set_visible(True)
|
153
|
-
self.old_player_control = bool(self.get_sharedVar("player_has_control"))
|
154
|
-
self.set_sharedVar("player_has_control", False)
|
155
139
|
|
156
140
|
def _end_transition(self, scene_name, index):
|
157
141
|
self.set_scene(scene_name, index, True)
|
@@ -177,11 +161,10 @@ class SceneManager:
|
|
177
161
|
self.scenes[index].do_on_enter_early()
|
178
162
|
target_scene.on_enter()
|
179
163
|
|
180
|
-
self.set_sharedVar("player_has_control", self.old_player_control)
|
181
164
|
|
182
165
|
|
183
166
|
def cycle_debug_mode(self):
|
184
|
-
current_index =
|
167
|
+
current_index = bf.ResourceManager().get_sharedVar("debug_mode").value
|
185
168
|
next_index = (current_index + 1) % len(bf.debugMode)
|
186
169
|
return bf.debugMode(next_index)
|
187
170
|
|
@@ -193,8 +176,7 @@ class SceneManager:
|
|
193
176
|
and event.type == pygame.KEYDOWN
|
194
177
|
):
|
195
178
|
if event.key == pygame.K_d:
|
196
|
-
|
197
|
-
self.set_sharedVar("debug_mode", self.debug_mode)
|
179
|
+
bf.ResourceManager().set_sharedVar("debug_mode", self.cycle_debug_mode())
|
198
180
|
return
|
199
181
|
if event.key == pygame.K_p:
|
200
182
|
self.print_status()
|
batFramework/sprite.py
CHANGED
@@ -3,11 +3,11 @@ import pygame
|
|
3
3
|
from typing import Self
|
4
4
|
|
5
5
|
|
6
|
-
class Sprite(bf.
|
6
|
+
class Sprite(bf.Drawable):
|
7
7
|
def __init__(
|
8
8
|
self,
|
9
|
-
path=None,
|
10
9
|
size: None | tuple[int, int] = None,
|
10
|
+
path=None,
|
11
11
|
convert_alpha: bool = True,
|
12
12
|
):
|
13
13
|
self.original_surface: pygame.Surface = None
|
@@ -3,8 +3,8 @@ import pygame
|
|
3
3
|
from .states import *
|
4
4
|
|
5
5
|
class Platform2DCharacter(bf.Character):
|
6
|
-
def __init__(self):
|
7
|
-
super().__init__()
|
6
|
+
def __init__(self,*args,**kwargs):
|
7
|
+
super().__init__(*args,**kwargs)
|
8
8
|
self.actions = bf.ActionContainer(
|
9
9
|
*bf.DirectionalKeyControls(),
|
10
10
|
bf.Action("jump").add_key_control(pygame.K_SPACE).set_holding()
|
@@ -18,8 +18,6 @@ class Platform2DCharacter(bf.Character):
|
|
18
18
|
self.friction = 0.7
|
19
19
|
self.gravity = 300
|
20
20
|
self.terminal_velocity = 1000
|
21
|
-
self.state_machine.set_state("idle")
|
22
|
-
|
23
21
|
|
24
22
|
def do_setup_animations(self):
|
25
23
|
self.add_animation(bf.Animation("idle"))
|
@@ -33,7 +31,8 @@ class Platform2DCharacter(bf.Character):
|
|
33
31
|
self.state_machine.add_state(Platform2DRun())
|
34
32
|
self.state_machine.add_state(Platform2DJump())
|
35
33
|
self.state_machine.add_state(Platform2DFall())
|
36
|
-
|
34
|
+
self.state_machine.set_state("idle")
|
35
|
+
|
37
36
|
|
38
37
|
|
39
38
|
def do_reset_actions(self) -> None:
|
@@ -41,4 +40,4 @@ class Platform2DCharacter(bf.Character):
|
|
41
40
|
|
42
41
|
def do_process_actions(self, event: pygame.Event) -> None:
|
43
42
|
self.actions.process_event(event)
|
44
|
-
|
43
|
+
|
batFramework/utils.py
CHANGED
@@ -1,17 +1,16 @@
|
|
1
1
|
import pygame
|
2
|
-
from enum import Enum
|
3
|
-
import os
|
4
2
|
import batFramework as bf
|
5
|
-
import
|
3
|
+
import random
|
6
4
|
from .enums import *
|
7
5
|
import re
|
8
|
-
from typing import Callable, TYPE_CHECKING
|
6
|
+
from typing import Callable, TYPE_CHECKING
|
9
7
|
from functools import cache
|
10
8
|
if TYPE_CHECKING:
|
11
|
-
from .
|
9
|
+
from .drawable import Drawable
|
12
10
|
from .entity import Entity
|
13
11
|
|
14
12
|
|
13
|
+
|
15
14
|
class Singleton(type):
|
16
15
|
_instances = {}
|
17
16
|
|
@@ -28,9 +27,15 @@ class Utils:
|
|
28
27
|
surface: pygame.Surface, split_size: tuple[int, int], func=None
|
29
28
|
) -> dict[tuple[int, int], pygame.Surface]:
|
30
29
|
"""
|
31
|
-
Splits a surface into subsurfaces and returns a
|
32
|
-
|
33
|
-
|
30
|
+
Splits a surface into subsurfaces based on a given size and returns a dictionary of them with their coordinates as keys.
|
31
|
+
|
32
|
+
Args:
|
33
|
+
surface (pygame.Surface): The surface to be split.
|
34
|
+
split_size (tuple[int, int]): The size of each subsurface (width, height).
|
35
|
+
func (callable, optional): A function to apply to each subsurface. Defaults to None.
|
36
|
+
|
37
|
+
Returns:
|
38
|
+
dict[tuple[int, int], pygame.Surface]: A dictionary with (x, y) coordinates as keys and the corresponding subsurfaces as values.
|
34
39
|
"""
|
35
40
|
width, height = surface.get_size()
|
36
41
|
res = {}
|
@@ -47,6 +52,19 @@ class Utils:
|
|
47
52
|
|
48
53
|
@staticmethod
|
49
54
|
def filter_text(text_mode: textMode):
|
55
|
+
"""
|
56
|
+
Filters a string based on the specified text mode.
|
57
|
+
|
58
|
+
Args:
|
59
|
+
text_mode (textMode): Mode specifying the type of filtering (ALPHABETICAL, NUMERICAL, ALPHANUMERICAL).
|
60
|
+
|
61
|
+
Returns:
|
62
|
+
callable: A function that takes a string and removes all characters not allowed by the text mode.
|
63
|
+
|
64
|
+
Raises:
|
65
|
+
ValueError: If an unsupported text mode is provided.
|
66
|
+
"""
|
67
|
+
|
50
68
|
if text_mode == textMode.ALPHABETICAL:
|
51
69
|
pattern = re.compile(r"[^a-zA-Z]")
|
52
70
|
elif text_mode == textMode.NUMERICAL:
|
@@ -66,15 +84,20 @@ class Utils:
|
|
66
84
|
@cache
|
67
85
|
def create_spotlight(inside_color, outside_color, radius, radius_stop=None, dest_surf=None,size=None):
|
68
86
|
"""
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
87
|
+
Creates a spotlight effect on a surface with a gradient from inside_color to outside_color.
|
88
|
+
|
89
|
+
Args:
|
90
|
+
inside_color (tuple[int, int, int]): RGB color at the center of the spotlight.
|
91
|
+
outside_color (tuple[int, int, int]): RGB color at the outer edge of the spotlight.
|
92
|
+
radius (int): Radius of the inner circle.
|
93
|
+
radius_stop (int, optional): Radius where the spotlight ends. Defaults to the value of radius.
|
94
|
+
dest_surf (pygame.Surface, optional): Surface to draw the spotlight on. Defaults to None.
|
95
|
+
size (tuple[int, int], optional): Size of the surface if dest_surf is None. Defaults to a square based on radius_stop.
|
96
|
+
|
97
|
+
Returns:
|
98
|
+
pygame.Surface: The surface with the spotlight effect drawn on it.
|
77
99
|
"""
|
100
|
+
|
78
101
|
if radius_stop is None:
|
79
102
|
radius_stop = radius
|
80
103
|
diameter = radius_stop * 2
|
@@ -103,6 +126,18 @@ class Utils:
|
|
103
126
|
|
104
127
|
@staticmethod
|
105
128
|
def draw_spotlight(dest_surf:pygame.Surface,inside_color,outside_color,radius,radius_stop=None,center=None):
|
129
|
+
"""
|
130
|
+
Draws a spotlight effect directly onto an existing surface.
|
131
|
+
|
132
|
+
Args:
|
133
|
+
dest_surf (pygame.Surface): The surface to draw the spotlight on.
|
134
|
+
inside_color (tuple[int, int, int]): RGB color at the center of the spotlight.
|
135
|
+
outside_color (tuple[int, int, int]): RGB color at the outer edge of the spotlight.
|
136
|
+
radius (int): Radius of the inner circle.
|
137
|
+
radius_stop (int, optional): Radius where the spotlight ends. Defaults to the value of radius.
|
138
|
+
center (tuple[int, int], optional): Center point of the spotlight. Defaults to the center of dest_surf.
|
139
|
+
"""
|
140
|
+
|
106
141
|
if radius_stop is None:
|
107
142
|
radius_stop = radius
|
108
143
|
center = dest_surf.get_rect().center if center is None else center
|
@@ -117,12 +152,34 @@ class Utils:
|
|
117
152
|
pygame.draw.circle(dest_surf, inside_color, center, radius)
|
118
153
|
|
119
154
|
@staticmethod
|
120
|
-
def animate_move(entity:"
|
155
|
+
def animate_move(entity:"Entity", start_pos : tuple[float,float], end_pos:tuple[float,float])->Callable[[float],None]:
|
156
|
+
"""
|
157
|
+
Creates a function to animate the movement of an entity from start_pos to end_pos.
|
158
|
+
|
159
|
+
Args:
|
160
|
+
entity (Entity): The entity to move.
|
161
|
+
start_pos (tuple[float, float]): The starting position of the entity.
|
162
|
+
end_pos (tuple[float, float]): The ending position of the entity.
|
163
|
+
|
164
|
+
Returns:
|
165
|
+
Callable[[float], None]: A function that updates the entity's position based on a progression value (0 to 1).
|
166
|
+
"""
|
121
167
|
def func(x):
|
122
168
|
entity.set_center(start_pos[0]+(end_pos[0]-start_pos[0])*x,start_pos[1]+(end_pos[1]-start_pos[1])*x)
|
123
169
|
return func
|
124
170
|
|
125
|
-
def animate_move_to(entity: "
|
171
|
+
def animate_move_to(entity: "Entity", end_pos: tuple[float, float]) -> Callable[[float], None]:
|
172
|
+
"""
|
173
|
+
Creates a function to animate the movement of an entity to a specified end position, capturing the start position at the start of the animation.
|
174
|
+
|
175
|
+
Args:
|
176
|
+
entity (Entity): The entity to move.
|
177
|
+
end_pos (tuple[float, float]): The target position of the entity.
|
178
|
+
|
179
|
+
Returns:
|
180
|
+
Callable[[float], None]: A function that updates the entity's position based on a progression value (0 to 1).
|
181
|
+
"""
|
182
|
+
|
126
183
|
# Start position will be captured once when the animation starts
|
127
184
|
start_pos = [None]
|
128
185
|
|
@@ -140,10 +197,52 @@ class Utils:
|
|
140
197
|
return update_position
|
141
198
|
|
142
199
|
@staticmethod
|
143
|
-
def animate_alpha(entity:"
|
200
|
+
def animate_alpha(entity:"Drawable", start : int, end:int)->Callable[[float],None]:
|
201
|
+
"""
|
202
|
+
Creates a function to animate the alpha (transparency) of a drawable entity between a start and end value.
|
203
|
+
|
204
|
+
Args:
|
205
|
+
entity (Drawable): The entity to animate.
|
206
|
+
start (int): The starting alpha value (0 to 255).
|
207
|
+
end (int): The ending alpha value (0 to 255).
|
208
|
+
|
209
|
+
Returns:
|
210
|
+
Callable[[float], None]: A function that updates the entity's alpha based on a progression value (0 to 1).
|
211
|
+
"""
|
144
212
|
def func(x):
|
145
213
|
entity.set_alpha(int(pygame.math.clamp(start+(end-start)*x,0,255)))
|
146
214
|
return func
|
147
215
|
|
148
216
|
|
149
217
|
|
218
|
+
@staticmethod
|
219
|
+
def random_color(min_value: int = 0, max_value: int = 255) -> tuple[int, int, int]:
|
220
|
+
"""
|
221
|
+
Generates a random color as an RGB tuple.
|
222
|
+
|
223
|
+
Args:
|
224
|
+
min_value (int): Minimum value for each RGB component (inclusive). Defaults to 0.
|
225
|
+
max_value (int): Maximum value for each RGB component (inclusive). Defaults to 255.
|
226
|
+
|
227
|
+
Returns:
|
228
|
+
tuple[int, int, int]: A tuple representing a random color in RGB format, with each component
|
229
|
+
between min_value and max_value.
|
230
|
+
"""
|
231
|
+
return random.randint(min_value, max_value), random.randint(min_value, max_value), random.randint(min_value, max_value)
|
232
|
+
|
233
|
+
@staticmethod
|
234
|
+
def random_point_on_screen(margin: int = 0) -> tuple[int, int]:
|
235
|
+
"""
|
236
|
+
Generates a random point on the screen, considering a margin from the edges.
|
237
|
+
|
238
|
+
Args:
|
239
|
+
margin (int): Margin from the screen edges, where the point won't be generated.
|
240
|
+
If margin is less than 0 or greater than the screen resolution, returns (0, 0).
|
241
|
+
|
242
|
+
Returns:
|
243
|
+
tuple[int, int]: A tuple representing a random point (x, y) on the screen within the screen
|
244
|
+
resolution minus the margin.
|
245
|
+
"""
|
246
|
+
if margin < 0 or margin > bf.const.RESOLUTION[0] or margin > bf.const.RESOLUTION[1]:
|
247
|
+
return 0, 0
|
248
|
+
return random.randint(margin, bf.const.RESOLUTION[0] - margin), random.randint(margin, bf.const.RESOLUTION[1] - margin)
|