feat(game): add game restard option

This commit is contained in:
Kristofers Solo 2024-01-03 02:24:48 +02:00
parent 4b02daf12b
commit 97a64b44b6
5 changed files with 77 additions and 64 deletions

3
src/path.py Normal file
View File

@ -0,0 +1,3 @@
from pathlib import Path
BASE_PATH = Path(__file__).resolve().parent.parent

View File

@ -1,5 +1,4 @@
from .game import Game from .game import Game
from .header import Header
from .menu import Menu from .menu import Menu
__all__ = ["Header", "Menu", "Game"] __all__ = ["Menu", "Game"]

View File

@ -2,25 +2,36 @@ import pygame
from loguru import logger from loguru import logger
from py2048 import Config from py2048 import Config
from py2048.objects import Board from py2048.objects import Board, Button, ScoreLabel
from py2048.utils import Direction, setup_logger from py2048.utils import Direction, Position, Size, setup_logger
from .header import Header
class Game: class Game:
def __init__(self) -> None: def __init__(self) -> None:
self.header = Header() self.rect = pygame.Rect(0, 0, *Config.HEADER.size)
self.labels = self._create_labels()
self.buttons = self._create_buttons()
self.board = Board() self.board = Board()
def update_score(self, new_score: int) -> None:
"""Updates the score to `new_score`."""
self.score.update_score(new_score)
def draw(self, surface: pygame.Surface) -> None: def draw(self, surface: pygame.Surface) -> None:
surface.fill(Config.COLORSCHEME.BG) surface.fill(Config.COLORSCHEME.BG)
self.board.draw(surface) self.board.draw(surface)
self.header.draw(surface) self.labels.draw(surface)
self.buttons.draw(surface)
pygame.display.flip() pygame.display.flip()
def handle_events(self, event: pygame.Event) -> None: def handle_events(self, event: pygame.Event) -> None:
if event.type == pygame.KEYDOWN: if event.type == pygame.MOUSEBUTTONDOWN:
for button in self.buttons:
button.on_click(Position(*event.pos))
elif event.type == pygame.MOUSEMOTION:
for button in self.buttons:
button.on_hover(Position(*event.pos))
elif event.type == pygame.KEYDOWN:
if event.key in (pygame.K_LEFT, pygame.K_a, pygame.K_h): if event.key in (pygame.K_LEFT, pygame.K_a, pygame.K_h):
self.move_left() self.move_left()
elif event.key in (pygame.K_RIGHT, pygame.K_d, pygame.K_l): elif event.key in (pygame.K_RIGHT, pygame.K_d, pygame.K_l):
@ -33,7 +44,14 @@ class Game:
def move(self, direction: Direction) -> None: def move(self, direction: Direction) -> None:
"""Moved the board in the given direction and updates the score.""" """Moved the board in the given direction and updates the score."""
self.board.move(direction) self.board.move(direction)
self.header.update(self.board.score) self.update_score(self.board.score)
if self.board.is_game_over():
logger.info("Game over!")
self.restart()
def restart(self) -> None:
self.board.reset()
self.update_score(0)
def move_up(self) -> None: def move_up(self) -> None:
self.move(Direction.UP) self.move(Direction.UP)
@ -46,3 +64,49 @@ class Game:
def move_right(self) -> None: def move_right(self) -> None:
self.move(Direction.RIGHT) self.move(Direction.RIGHT)
def _create_labels(self) -> pygame.sprite.Group:
size = Size(60, 40)
self.score = ScoreLabel(
value=0,
text="Score",
size=size,
position=Position(
Config.SCREEN.size.width - Config.TILE.size // 2 - size.width * 2 - 10,
10,
),
bg_color=Config.COLORSCHEME.BOARD_BG,
font_color=Config.COLORSCHEME.LIGHT_TEXT,
font_size=16,
border_radius=2,
)
highscore = ScoreLabel(
value=2048,
text="Best",
size=size,
position=Position(
Config.SCREEN.size.width - Config.TILE.size // 2 - size.width, 10
),
bg_color=Config.COLORSCHEME.BOARD_BG,
font_color=Config.COLORSCHEME.LIGHT_TEXT,
font_size=16,
border_radius=2,
)
return pygame.sprite.Group(self.score, highscore)
def _create_buttons(self) -> pygame.sprite.Group:
reset = Button(
position=(10, 10),
bg_color=Config.COLORSCHEME.BOARD_BG,
font_color=Config.COLORSCHEME.LIGHT_TEXT,
hover_color=Config.COLORSCHEME.TILE_0,
size=(100, 30),
text="New Game",
border_radius=Config.TILE.border.radius,
action=self.restart,
font_size=16,
border_width=2,
)
return pygame.sprite.Group(reset)

View File

@ -1,49 +0,0 @@
import pygame
from py2048 import Config
from py2048.objects import ScoreLabel
from py2048.utils import Position, Size
class Header:
def __init__(self) -> None:
self.rect = pygame.Rect(0, 0, *Config.HEADER.size)
self.labels = self._create_labels()
def _create_labels(self) -> pygame.sprite.Group:
size = Size(60, 40)
self.score = ScoreLabel(
value=0,
text="Score",
size=size,
position=Position(
Config.SCREEN.size.width - Config.TILE.size // 2 - size.width * 2 - 10,
10,
),
bg_color=Config.COLORSCHEME.BOARD_BG,
font_color=Config.COLORSCHEME.LIGHT_TEXT,
font_size=16,
border_radius=2,
)
highscore = ScoreLabel(
value=2048,
text="Best",
size=size,
position=Position(
Config.SCREEN.size.width - Config.TILE.size // 2 - size.width, 10
),
bg_color=Config.COLORSCHEME.BOARD_BG,
font_color=Config.COLORSCHEME.LIGHT_TEXT,
font_size=16,
border_radius=2,
)
return pygame.sprite.Group(self.score, highscore)
def draw(self, surface: pygame.Surface) -> None:
self.labels.draw(surface)
def update(self, new_score: int) -> None:
"""Updates the score to `new_score`."""
self.score.update_score(new_score)

View File

@ -1,13 +1,10 @@
from pathlib import Path
from loguru import logger from loguru import logger
from path import BASE_PATH
from .collections import Board, Font, Header, Position, Screen, Size, Tile from .collections import Board, Font, Header, Position, Screen, Size, Tile
from .color import ColorScheme from .color import ColorScheme
from .enums import Direction from .enums import Direction
BASE_PATH = Path(__file__).resolve().parent.parent.parent.parent
def setup_logger() -> None: def setup_logger() -> None:
logger.add( logger.add(
@ -20,7 +17,6 @@ def setup_logger() -> None:
__all__ = [ __all__ = [
"BASE_PATH",
"Board", "Board",
"ColorScheme", "ColorScheme",
"Direction", "Direction",