From 03ece1218b5fa8ed47292fcc4599c4a96ef1995f Mon Sep 17 00:00:00 2001 From: Eikthyrnir Date: Wed, 29 Mar 2023 11:27:59 +0200 Subject: [PATCH] refactoring --- domain/commands/command.py | 4 + domain/commands/random_cat_move_command.py | 63 +++++++++++++++ domain/commands/vacuum_move_command.py | 28 +++++++ domain/entities/cat.py | 16 +--- domain/entities/vacuum.py | 16 +--- domain/world.py | 34 +++----- main.py | 76 +++++++----------- .../sprites}/cat/standing_back.png | Bin .../sprites}/cat/standing_front.png | Bin .../sprites}/cat/standing_left.png | Bin .../sprites}/cat/standing_right.png | Bin .../sprites}/plants/plant1.png | Bin .../sprites}/plants/plant2.png | Bin .../sprites}/plants/plant3.png | Bin view/renderer.py | 17 ++-- 15 files changed, 146 insertions(+), 108 deletions(-) create mode 100644 domain/commands/command.py create mode 100644 domain/commands/random_cat_move_command.py create mode 100644 domain/commands/vacuum_move_command.py rename {Interface/images => media/sprites}/cat/standing_back.png (100%) rename {Interface/images => media/sprites}/cat/standing_front.png (100%) rename {Interface/images => media/sprites}/cat/standing_left.png (100%) rename {Interface/images => media/sprites}/cat/standing_right.png (100%) rename {Interface/images => media/sprites}/plants/plant1.png (100%) rename {Interface/images => media/sprites}/plants/plant2.png (100%) rename {Interface/images => media/sprites}/plants/plant3.png (100%) diff --git a/domain/commands/command.py b/domain/commands/command.py new file mode 100644 index 0000000..d90aed5 --- /dev/null +++ b/domain/commands/command.py @@ -0,0 +1,4 @@ +class Command: + def run(self): + raise NotImplementedError() + \ No newline at end of file diff --git a/domain/commands/random_cat_move_command.py b/domain/commands/random_cat_move_command.py new file mode 100644 index 0000000..378175e --- /dev/null +++ b/domain/commands/random_cat_move_command.py @@ -0,0 +1,63 @@ +from random import randint +from typing import Tuple + +import pygame + +from domain.commands.command import Command +from domain.entities.cat import Cat +from domain.world import World + + +class RandomCatMoveCommand(Command): + + def __init__(self, world: World, cat: Cat) -> None: + super().__init__() + self.world = world + self.cat = cat + + def run(self): + move_vector = (0, 0) + now = pygame.time.get_ticks() + # region cat random movement + cat = self.world.cat + if now - cat.last_tick >= cat.cooldown: + if not cat.busy: + while True: + cat.direction = randint(0, 3) + if not ((cat.direction == 0 and cat.y == 0) + or (cat.direction == 1 and cat.x == self.world.width - 1) + or (cat.direction == 2 and cat.y == self.world.height - 1) + or (cat.direction == 3 and cat.x == 0)): + break + + if cat.direction == 0: # up + if cat.busy: + move_vector = (0, - 1) + cat.busy = not cat.busy + if cat.direction == 1: # right + if cat.busy: + move_vector = (1, 0) + cat.busy = not cat.busy + if cat.direction == 2: # down + if cat.busy: + move_vector = (0, 1) + cat.busy = not cat.busy + if cat.direction == 3: # left + if cat.busy: + move_vector = (-1, 0) + cat.busy = not cat.busy + cat.last_tick = pygame.time.get_ticks() + + if move_vector == (0, 0): + return + + end_x = cat.x + move_vector[0] + end_y = cat.y + move_vector[1] + + if end_x > self.world.width - 1 or end_y > self.world.height - 1 or end_x < 0 or end_y < 0: + return + + self.world.obstacles[cat.x][cat.y].remove(cat) + cat.x = end_x + cat.y = end_y + self.world.obstacles[end_x][end_y].append(cat) diff --git a/domain/commands/vacuum_move_command.py b/domain/commands/vacuum_move_command.py new file mode 100644 index 0000000..9f1b558 --- /dev/null +++ b/domain/commands/vacuum_move_command.py @@ -0,0 +1,28 @@ +from typing import Tuple + +from domain.commands.command import Command +from domain.entities.vacuum import Vacuum +from domain.world import World + + +class VacuumMoveCommand(Command): + + def __init__(self, world: World, vacuum: Vacuum, move_vector: Tuple[int, int]) -> None: + super().__init__() + self.world = world + self.vacuum = vacuum + self.dx = move_vector[0] + self.dy = move_vector[1] + + def run(self): + end_x = self.vacuum.x + self.dx + end_y = self.vacuum.y + self.dy + + if end_x > self.world.width - 1 or end_y > self.world.height - 1 or end_x < 0 or end_y < 0: + return + + if self.world.is_obstacle_at(end_x, end_y): + return + + self.vacuum.x = end_x + self.vacuum.y = end_y diff --git a/domain/entities/cat.py b/domain/entities/cat.py index f2f082c..807e490 100644 --- a/domain/entities/cat.py +++ b/domain/entities/cat.py @@ -5,24 +5,10 @@ from domain.world import World class Cat(Entity): - def __init__(self, x: int, y: int, world: World): + def __init__(self, x: int, y: int): super().__init__(x, y, "CAT") - self.world = world self.last_tick = pygame.time.get_ticks() self.cooldown = 1000 self.velocity = 1 self.busy = False self.direction = 0 - - def move(self, dx: int, dy: int): - end_x = self.x + dx - end_y = self.y + dy - - if end_x > self.world.width - 1 or end_y > self.world.height - 1 or end_x < 0 or end_y < 0: - return - - self.world.obstacles[self.x][self.y].remove(self) - self.x = end_x - self.y = end_y - self.world.obstacles[end_x][end_y].append(self) - diff --git a/domain/entities/vacuum.py b/domain/entities/vacuum.py index 1f8c9c8..3d05dfa 100644 --- a/domain/entities/vacuum.py +++ b/domain/entities/vacuum.py @@ -3,21 +3,7 @@ from domain.world import World class Vacuum(Entity): - def __init__(self, x: int, y: int, world: World): + def __init__(self, x: int, y: int): super().__init__(x, y, 'VACUUM') - self.world = world self.battery = 100 # TODO add more properties - - def move(self, dx, dy): - end_x = self.x + dx - end_y = self.y + dy - - if end_x > self.world.width - 1 or end_y > self.world.height - 1 or end_x < 0 or end_y < 0: - return - - if self.world.is_obstacle_at(end_x, end_y): - return - - self.x = end_x - self.y = end_y diff --git a/domain/world.py b/domain/world.py index 35722b3..d760e2f 100644 --- a/domain/world.py +++ b/domain/world.py @@ -11,34 +11,20 @@ class World: self.obstacles = [ [[] for j in range(height)] for i in range(width) ] - self.entities = [] self.vacuum = None self.cat = None - # move: update position from (start_x, start_y) to (end_x, end_y) - # def move(self, entity: Entity, end_x: int, end_y: int): - # # no change - # if entity.x == end_x and entity.y == end_y: - # return - # - # # check if object moves beyond border - # if end_x > self.width - 1 or end_y > self.height - 1 or end_x < 0 or end_y < 0: - # print("Cannot move object beyond board") - # return - # - # # check if destination is empty - # # if self.is_obstacle_at(end_x, end_y): - # # print( - # # f"Cannot move object to ({end_x}, {end_y}): position already occupied" - # # ) - # # return - # - # # change position in array - # self.grid[entity.x][entity.y].remove(entity) - # self.grid[end_x][end_y].append(entity) - # entity.x = end_x - # entity.y = end_y + def add_entity(self, entity: Entity): + if entity.type == "PEEL": + self.dust[entity.x][entity.y].append(entity) + elif entity.type == "VACUUM": + self.vacuum = entity + elif entity.type == "CAT": + self.cat = entity + self.obstacles[entity.x][entity.y].append(entity) + else: + self.obstacles[entity.x][entity.y].append(entity) def is_obstacle_at(self, x: int, y: int) -> bool: return bool(self.obstacles[x][y]) diff --git a/main.py b/main.py index f692a8d..6c2f933 100644 --- a/main.py +++ b/main.py @@ -3,6 +3,8 @@ from random import randint import pygame from Interface.vacuum_render import initial_draw +from domain.commands.random_cat_move_command import RandomCatMoveCommand +from domain.commands.vacuum_move_command import VacuumMoveCommand from domain.entities.cat import Cat from domain.entities.entity import Entity from domain.entities.vacuum import Vacuum @@ -19,19 +21,9 @@ class Main: self.renderer = Renderer(800, 800, tiles_x, tiles_y) - self.world = World(tiles_x, tiles_y) - for _ in range(10): - temp_x = randint(0, tiles_x - 1) - temp_y = randint(0, tiles_y - 1) - self.world.dust[temp_x][temp_y].append(Entity(temp_x, temp_y, "PEEL")) - self.world.vacuum = Vacuum(1, 1, self.world) - self.world.cat = Cat(7, 8, self.world) - self.world.obstacles[7][8].append(self.world.cat) - self.world.obstacles[2][8].append(Entity(2, 8, "PLANT1")) - self.world.obstacles[4][1].append(Entity(4, 1, "PLANT1")) - self.world.obstacles[3][4].append(Entity(3, 4, "PLANT2")) - self.world.obstacles[8][8].append(Entity(8, 8, "PLANT2")) - self.world.obstacles[9][3].append(Entity(9, 3, "PLANT3")) + self.world = generate_world(tiles_x, tiles_y) + + self.commands = [] self.clock = pygame.time.Clock() self.running = True @@ -52,45 +44,37 @@ class Main: self.running = False if event.type == pygame.KEYDOWN: if event.key == pygame.K_LEFT: - self.world.vacuum.move(-1, 0) + self.commands.append(VacuumMoveCommand(self.world, self.world.vacuum, (-1, 0))) if event.key == pygame.K_RIGHT: - self.world.vacuum.move(1, 0) + self.commands.append(VacuumMoveCommand(self.world, self.world.vacuum, (1, 0))) if event.key == pygame.K_UP: - self.world.vacuum.move(0, -1) + self.commands.append(VacuumMoveCommand(self.world, self.world.vacuum, (0, -1))) if event.key == pygame.K_DOWN: - self.world.vacuum.move(0, 1) + self.commands.append(VacuumMoveCommand(self.world, self.world.vacuum, (0, 1))) def update(self): - now = pygame.time.get_ticks() - # region cat random movement - cat = self.world.cat - if now - cat.last_tick >= cat.cooldown: - if not cat.busy: - while True: - cat.direction = randint(0, 3) - if not ((cat.direction == 0 and cat.y == 0) - or (cat.direction == 1 and cat.x == self.world.width - 1) - or (cat.direction == 2 and cat.y == self.world.height - 1) - or (cat.direction == 3 and cat.x == 0)): - break + self.commands.append(RandomCatMoveCommand(self.world, self.world.cat)) - if cat.direction == 0: # up - if cat.busy: - cat.move(0, - 1) - cat.busy = not cat.busy - if cat.direction == 1: # right - if cat.busy: - cat.move(1, 0) - cat.busy = not cat.busy - if cat.direction == 2: # down - if cat.busy: - cat.move(0, 1) - cat.busy = not cat.busy - if cat.direction == 3: # left - if cat.busy: - cat.move(-1, 0) - cat.busy = not cat.busy - cat.last_tick = pygame.time.get_ticks() + for command in self.commands: + command.run() + self.commands.clear() + + +def generate_world(tiles_x: int, tiles_y: int) -> World: + world = World(tiles_x, tiles_y) + for _ in range(10): + temp_x = randint(0, tiles_x - 1) + temp_y = randint(0, tiles_y - 1) + world.add_entity(Entity(temp_x, temp_y, "PEEL")) + world.vacuum = Vacuum(1, 1) + world.cat = Cat(7, 8) + world.add_entity(world.cat) + world.add_entity(Entity(2, 8, "PLANT1")) + world.add_entity(Entity(4, 1, "PLANT1")) + world.add_entity(Entity(3, 4, "PLANT2")) + world.add_entity(Entity(8, 8, "PLANT2")) + world.add_entity(Entity(9, 3, "PLANT3")) + return world if __name__ == "__main__": diff --git a/Interface/images/cat/standing_back.png b/media/sprites/cat/standing_back.png similarity index 100% rename from Interface/images/cat/standing_back.png rename to media/sprites/cat/standing_back.png diff --git a/Interface/images/cat/standing_front.png b/media/sprites/cat/standing_front.png similarity index 100% rename from Interface/images/cat/standing_front.png rename to media/sprites/cat/standing_front.png diff --git a/Interface/images/cat/standing_left.png b/media/sprites/cat/standing_left.png similarity index 100% rename from Interface/images/cat/standing_left.png rename to media/sprites/cat/standing_left.png diff --git a/Interface/images/cat/standing_right.png b/media/sprites/cat/standing_right.png similarity index 100% rename from Interface/images/cat/standing_right.png rename to media/sprites/cat/standing_right.png diff --git a/Interface/images/plants/plant1.png b/media/sprites/plants/plant1.png similarity index 100% rename from Interface/images/plants/plant1.png rename to media/sprites/plants/plant1.png diff --git a/Interface/images/plants/plant2.png b/media/sprites/plants/plant2.png similarity index 100% rename from Interface/images/plants/plant2.png rename to media/sprites/plants/plant2.png diff --git a/Interface/images/plants/plant3.png b/media/sprites/plants/plant3.png similarity index 100% rename from Interface/images/plants/plant3.png rename to media/sprites/plants/plant3.png diff --git a/view/renderer.py b/view/renderer.py index d3c4c15..bfe1dde 100644 --- a/view/renderer.py +++ b/view/renderer.py @@ -5,7 +5,8 @@ import pygame from pygame import Color from domain.entities.cat import Cat -from domain.world import World, Entity +from domain.entities.entity import Entity +from domain.world import World class Renderer: @@ -40,19 +41,19 @@ class Renderer: (self.tile_width, self.tile_height)), "PEEL": pygame.transform.scale(pygame.image.load("media/sprites/peel.webp"), (self.tile_width, self.tile_height)), - "CAT_FRONT": pygame.transform.scale(pygame.image.load("Interface/images/cat/standing_front.png"), + "CAT_FRONT": pygame.transform.scale(pygame.image.load("media/sprites/cat/standing_front.png"), (self.tile_width, self.tile_height)), - "CAT_BACK": pygame.transform.scale(pygame.image.load("Interface/images/cat/standing_back.png"), + "CAT_BACK": pygame.transform.scale(pygame.image.load("media/sprites/cat/standing_back.png"), (self.tile_width, self.tile_height)), - "CAT_LEFT": pygame.transform.scale(pygame.image.load("Interface/images/cat/standing_left.png"), + "CAT_LEFT": pygame.transform.scale(pygame.image.load("media/sprites/cat/standing_left.png"), (self.tile_width, self.tile_height)), - "CAT_RIGHT": pygame.transform.scale(pygame.image.load("Interface/images/cat/standing_right.png"), + "CAT_RIGHT": pygame.transform.scale(pygame.image.load("media/sprites/cat/standing_right.png"), (self.tile_width, self.tile_height)), - "PLANT1": pygame.transform.scale(pygame.image.load("Interface/images/plants/plant1.png"), + "PLANT1": pygame.transform.scale(pygame.image.load("media/sprites/plants/plant1.png"), (self.tile_width + self.tile_width / 4, self.tile_height + self.tile_height / 4)), - "PLANT2": pygame.transform.scale(pygame.image.load("Interface/images/plants/plant2.png"), + "PLANT2": pygame.transform.scale(pygame.image.load("media/sprites/plants/plant2.png"), (self.tile_width + self.tile_width / 4, self.tile_height + self.tile_height / 4)), - "PLANT3": pygame.transform.scale(pygame.image.load("Interface/images/plants/plant3.png"), + "PLANT3": pygame.transform.scale(pygame.image.load("media/sprites/plants/plant3.png"), (self.tile_width + self.tile_width / 4, self.tile_height + self.tile_height / 4)), }