Add unit tests for UnitFactory functionality and initialize units package

This commit is contained in:
2025-08-13 20:36:51 +02:00
parent 088ae02080
commit 689b21bf65
10 changed files with 181 additions and 203 deletions
+5 -5
View File
@@ -7,9 +7,9 @@ class KeyBindings:
def key_pressed(self, key, coords=None):
keybindings = self.configs[f"keybinding_{self.game_status}"]
if key in keybindings.get("quit", []):
self.engine.close()
self.render_engine.close()
elif key in keybindings.get("new_rat", []):
self.new_rat()
self.spawn_rat()
elif key in keybindings.get("kill_rat", []):
if self.units:
self.units[random.choice(list(self.units.keys()))].die(score=5)
@@ -17,7 +17,7 @@ class KeyBindings:
self.audio = not self.audio
elif key in keybindings.get("toggle_full_screen", []):
self.full_screen = not self.full_screen
self.engine.full_screen(self.full_screen)
self.render_engine.full_screen(self.full_screen)
elif key in keybindings.get("scroll_up", []):
self.start_scrolling("Up")
elif key in keybindings.get("scroll_down", []):
@@ -27,7 +27,7 @@ class KeyBindings:
elif key in keybindings.get("scroll_right", []):
self.start_scrolling("Right")
elif key in keybindings.get("spawn_bomb", []):
self.play_sound("PUTDOWN.WAV")
self.render_engine.play_sound("PUTDOWN.WAV")
self.spawn_bomb(self.pointer)
elif key in keybindings.get("pause", []):
self.game_status = "paused" if self.game_status == "game" else "game"
@@ -44,7 +44,7 @@ class KeyBindings:
self.start_game()
def quit_game(self):
self.engine.close()
self.render_engine.close()
def key_released(self, key):
if key in ["Up", "Down", "Left", "Right", 8, 9, 10, 11]:
self.stop_scrolling()
+43
View File
@@ -0,0 +1,43 @@
import os
class Graphics():
def load_assets(self):
self.tunnel = self.render_engine.load_image("Rat/BMP_TUNNEL.png", surface=True)
self.grasses = [self.render_engine.load_image(f"Rat/BMP_1_GRASS_{i+1}.png", surface=True) for i in range(4)]
self.rat_assets = {}
self.bomb_assets = {}
for sex in ["MALE", "FEMALE", "BABY"]:
self.rat_assets[sex] = {}
for direction in ["UP", "DOWN", "LEFT", "RIGHT"]:
self.rat_assets[sex][direction] = self.render_engine.load_image(f"Rat/BMP_{sex}_{direction}.png", transparent_color=(128, 128, 128))
for n in range(5):
self.bomb_assets[n] = self.render_engine.load_image(f"Rat/BMP_BOMB{n}.png", transparent_color=(128, 128, 128))
self.assets = {}
for file in os.listdir("assets/Rat"):
if file.endswith(".png"):
self.assets[file[:-4]] = self.render_engine.load_image(f"Rat/{file}")
# ==================== RENDERING ====================
def draw_maze(self):
if self.background_texture is None:
texture_tiles = []
for y, row in enumerate(self.map.matrix):
for x, cell in enumerate(row):
variant = x*y % 4
tile = self.grasses[variant] if cell else self.tunnel
texture_tiles.append((tile, x*self.cell_size, y*self.cell_size))
self.background_texture = self.render_engine.create_texture(texture_tiles)
self.render_engine.draw_background(self.background_texture)
def scroll_cursor(self, x=0, y=0):
if self.pointer[0] + x > self.map.width or self.pointer[1] + y > self.map.height:
return
self.pointer = (
max(1, min(self.map.width-2, self.pointer[0] + x)),
max(1, min(self.map.height-2, self.pointer[1] + y))
)
self.render_engine.scroll_view(self.pointer)
+22
View File
@@ -0,0 +1,22 @@
import datetime
class Scoring:
# ==================== SCORING ====================
def save_score(self):
with open("scores.txt", "a") as f:
f.write(f"{datetime.datetime.now()} - {self.points}\n")
def read_score(self):
table = []
with open("scores.txt") as f:
rows = f.read().splitlines()
for row in rows:
table.append(row.split(" - "))
table.sort(key=lambda x: int(x[1]), reverse=True)
return table
def add_point(self, value):
self.points += value
-56
View File
@@ -1,56 +0,0 @@
import tkinter as tk
import os
class GameWindow:
"""Classe che gestisce la finestra di gioco e il rendering grafico."""
def __init__(self, width, height, cell_size, title, key_callback=None):
self.cell_size = cell_size
self.window = tk.Tk()
self.window.title(title)
self.canvas = tk.Canvas(self.window, width=width*cell_size, height=height*cell_size)
self.canvas.pack()
self.menu = tk.Menu(self.window)
self.menu.add_command(label="Quit", command=self.window.destroy)
self.status_bar = tk.Label(self.window, text=title, bd=1, relief=tk.SUNKEN, anchor=tk.W)
self.status_bar.pack(side=tk.BOTTOM, fill=tk.X)
self.window.config(menu=self.menu)
if key_callback:
self.window.bind("<Key>", key_callback)
def load_image(self, path, transparent_color=None):
image = tk.PhotoImage(file=os.path.join(os.path.dirname(__file__), "..", "assets", path))
if transparent_color:
gray_pixels = []
for y in range(image.height()):
for x in range(image.width()):
r, g, b = image.get(x, y)
if r == transparent_color[0] and g == transparent_color[1] and b == transparent_color[2]:
gray_pixels.append((x, y))
for x, y in gray_pixels:
image.transparency_set(x, y, 1)
return image.zoom(self.cell_size // 20)
def bind(self, event, callback):
self.window.bind(event, callback)
def draw_image(self, x, y, image, tag, anchor="nw"):
self.canvas.create_image(x, y, image=image, anchor=anchor, tag=tag)
def draw_rectangle(self, x, y, width, height, tag, outline="red"):
self.canvas.create_rectangle(x, y, x+width, y+height, outline=outline, tag=tag)
def delete_tag(self, tag):
self.canvas.delete(tag)
def update_status(self, text):
self.status_bar.config(text=text)
def new_cycle(self, delay, callback):
self.window.after(delay, callback)
def mainloop(self, **kwargs):
kwargs["update"]()
self.window.mainloop()
def get_image_size(self, image):
return image.width(), image.height()
+33
View File
@@ -0,0 +1,33 @@
import random
import uuid
from units import rat, bomb
class UnitManager:
def count_rats(self):
count = 0
for unit in self.units.values():
if isinstance(unit, rat.Rat):
count += 1
return count
def spawn_rat(self, position=None):
if position is None:
position = self.choose_start()
rat_class = rat.Male if random.random() < 0.5 else rat.Female
self.spawn_unit(rat_class, position)
def spawn_bomb(self, position):
self.spawn_unit(bomb.Timer, position)
def spawn_unit(self, unit, position, **kwargs):
id = uuid.uuid4()
self.units[id] = unit(self, position, id, **kwargs)
def choose_start(self):
if not hasattr(self, '_valid_positions'):
self._valid_positions = [
(x, y) for y in range(1, self.map.height-1)
for x in range(1, self.map.width-1)
if self.map.matrix[y][x]
]
return random.choice(self._valid_positions)