Rearranged the display class files, related to issue #56.

This commit is contained in:
eichhornchen 2021-01-10 12:35:50 +01:00
parent 8d0d0883a3
commit 5eb7699301
9 changed files with 226 additions and 256 deletions

View File

@ -1,97 +0,0 @@
# Copyright (C) 2020-2021 by ÿnérant, eichhornchen, nicomarg, charlse
# SPDX-License-Identifier: GPL-3.0-or-later
import curses
from ..display.display import Box, Display
from ..game import Game
from ..resources import ResourceManager
from ..translations import gettext as _
class CreditsDisplay(Display):
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
self.box = Box(*args, **kwargs)
self.pad = self.newpad(1, 1)
self.ascii_art_displayed = False
def update(self, game: Game) -> None:
return
def display(self) -> None:
self.box.refresh(self.y, self.x, self.height, self.width)
self.box.display()
self.pad.erase()
messages = [
_("Credits"),
"",
"Squirrel Battle",
"",
_("Developers:"),
"Yohann \"ÿnérant\" D'ANELLO",
"Mathilde \"eichhornchen\" DÉPRÉS",
"Nicolas \"nicomarg\" MARGULIES",
"Charles \"charsle\" PEYRAT",
"",
_("Translators:"),
"Hugo \"ifugao\" JACOB (español)",
]
for i, msg in enumerate(messages):
self.addstr(self.pad, i + (self.height - len(messages)) // 2,
(self.width - len(msg)) // 2, msg,
bold=(i == 0), italic=(":" in msg))
if self.ascii_art_displayed:
self.display_ascii_art()
self.refresh_pad(self.pad, 0, 0, self.y + 1, self.x + 1,
self.height + self.y - 2,
self.width + self.x - 2)
def display_ascii_art(self) -> None:
with open(ResourceManager.get_asset_path("ascii-art-ecureuil.txt"))\
as f:
ascii_art = f.read().split("\n")
height, width = len(ascii_art), len(ascii_art[0])
y_offset, x_offset = (self.height - height) // 2,\
(self.width - width) // 2
for i, line in enumerate(ascii_art):
for j, c in enumerate(line):
bg_color = curses.COLOR_WHITE
fg_color = curses.COLOR_BLACK
bold = False
if c == ' ':
bg_color = curses.COLOR_BLACK
elif c == '' or c == '' or c == '':
bold = True
fg_color = curses.COLOR_WHITE
bg_color = curses.COLOR_BLACK
elif c == '|':
bold = True # c = '┃'
fg_color = (100, 700, 1000)
bg_color = curses.COLOR_BLACK
elif c == '':
fg_color = (700, 300, 0)
elif c == '':
fg_color = (700, 300, 0)
bg_color = curses.COLOR_BLACK
elif c == '':
fg_color = (350, 150, 0)
elif c == '':
fg_color = (0, 0, 0)
bg_color = curses.COLOR_BLACK
elif c == '':
c = ''
fg_color = (1000, 1000, 1000)
bg_color = curses.COLOR_BLACK
self.addstr(self.pad, y_offset + i, x_offset + j, c,
fg_color, bg_color, bold=bold)
def handle_click(self, y: int, x: int, attr: int, game: Game) -> None:
if self.pad.inch(y - 1, x - 1) != ord(" "):
self.ascii_art_displayed = True

View File

@ -290,3 +290,29 @@ class Box(Display):
self.refresh_pad(self.pad, 0, 0, self.y, self.x,
self.y + self.height - 1, self.x + self.width - 1)
class MessageDisplay(Display):
"""
A class to handle the display of popup messages.
"""
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
self.box = Box(fg_border_color=curses.COLOR_RED, *args, **kwargs)
self.message = ""
self.pad = self.newpad(1, 1)
def update(self, game: Game) -> None:
self.message = game.message
def display(self) -> None:
self.box.refresh(self.y - 1, self.x - 2,
self.height + 2, self.width + 4)
self.box.display()
self.pad.erase()
self.addstr(self.pad, 0, 0, self.message, bold=True)
self.refresh_pad(self.pad, 0, 0, self.y, self.x,
self.height + self.y - 1,
self.width + self.x - 1)

View File

@ -4,14 +4,11 @@
import curses
from typing import Any, List
from .creditsdisplay import CreditsDisplay
from .display import Display, HorizontalSplit, VerticalSplit
from .logsdisplay import LogsDisplay
from .mapdisplay import MapDisplay
from .menudisplay import ChestInventoryDisplay, MainMenuDisplay, \
PlayerInventoryDisplay, SettingsMenuDisplay, StoreInventoryDisplay
from .messagedisplay import MessageDisplay
from .statsdisplay import StatsDisplay
from .display import Display, HorizontalSplit, MessageDisplay, VerticalSplit
from .gamedisplay import LogsDisplay, MapDisplay, StatsDisplay
from .menudisplay import ChestInventoryDisplay, CreditsDisplay, \
MainMenuDisplay, PlayerInventoryDisplay, \
SettingsMenuDisplay, StoreInventoryDisplay
from .texturepack import TexturePack
from ..enums import DisplayActions
from ..game import Game, GameMode

View File

@ -7,10 +7,116 @@ from .display import Display
from ..entities.items import Monocle
from ..entities.player import Player
from ..game import Game
from ..interfaces import FightingEntity
from ..interfaces import FightingEntity, Logs, Map
from ..translations import gettext as _
class LogsDisplay(Display):
"""
A class to handle the display of the logs.
"""
logs: Logs
def __init__(self, *args) -> None:
super().__init__(*args)
self.pad = self.newpad(self.rows, self.cols)
def update(self, game: Game) -> None:
self.logs = game.logs
def display(self) -> None:
messages = self.logs.messages[-self.height:]
messages = messages[::-1]
self.pad.erase()
for i in range(min(self.height, len(messages))):
self.addstr(self.pad, self.height - i - 1, self.x,
messages[i][:self.width])
self.refresh_pad(self.pad, 0, 0, self.y, self.x,
self.y + self.height - 1, self.x + self.width - 1)
class MapDisplay(Display):
"""
A class to handle the display of the map.
"""
map: Map
def __init__(self, *args):
super().__init__(*args)
def update(self, game: Game) -> None:
self.map = game.map
self.pad = self.newpad(self.map.height,
self.pack.tile_width * self.map.width + 1)
def update_pad(self) -> None:
for j in range(len(self.map.tiles)):
for i in range(len(self.map.tiles[j])):
if not self.map.seen_tiles[j][i]:
continue
fg, bg = self.map.tiles[j][i].visible_color(self.pack) if \
self.map.visibility[j][i] else \
self.map.tiles[j][i].hidden_color(self.pack)
self.addstr(self.pad, j, self.pack.tile_width * i,
self.map.tiles[j][i].char(self.pack), fg, bg)
for e in self.map.entities:
if self.map.visibility[e.y][e.x]:
self.addstr(self.pad, e.y, self.pack.tile_width * e.x,
self.pack[e.name.upper()],
self.pack.entity_fg_color,
self.pack.entity_bg_color)
# Display Path map for debug purposes
# from squirrelbattle.entities.player import Player
# players = [ p for p in self.map.entities if isinstance(p,Player) ]
# player = players[0] if len(players) > 0 else None
# if player:
# for x in range(self.map.width):
# for y in range(self.map.height):
# if (y,x) in player.paths:
# deltay, deltax = (y - player.paths[(y, x)][0],
# x - player.paths[(y, x)][1])
# if (deltay, deltax) == (-1, 0):
# character = '↓'
# elif (deltay, deltax) == (1, 0):
# character = '↑'
# elif (deltay, deltax) == (0, -1):
# character = '→'
# else:
# character = '←'
# self.addstr(self.pad, y, self.pack.tile_width * x,
# character, self.pack.tile_fg_color,
# self.pack.tile_bg_color)
def display(self) -> None:
y, x = self.map.currenty, self.pack.tile_width * self.map.currentx
deltay, deltax = (self.height // 2) + 1, (self.width // 2) + 1
pminrow, pmincol = y - deltay, x - deltax
sminrow, smincol = max(-pminrow, 0), max(-pmincol, 0)
deltay, deltax = self.height - deltay, self.width - deltax
smaxrow = self.map.height - (y + deltay) + self.height - 1
smaxrow = min(smaxrow, self.height - 1)
smaxcol = self.pack.tile_width * self.map.width - \
(x + deltax) + self.width - 1
# Wrap perfectly the map according to the width of the tiles
pmincol = self.pack.tile_width * (pmincol // self.pack.tile_width)
smincol = self.pack.tile_width * (smincol // self.pack.tile_width)
smaxcol = self.pack.tile_width \
* (smaxcol // self.pack.tile_width + 1) - 1
smaxcol = min(smaxcol, self.width - 1)
pminrow = max(0, min(self.map.height, pminrow))
pmincol = max(0, min(self.pack.tile_width * self.map.width, pmincol))
self.pad.erase()
self.update_pad()
self.refresh_pad(self.pad, pminrow, pmincol, sminrow, smincol, smaxrow,
smaxcol)
class StatsDisplay(Display):
"""
A class to handle the display of the stats of the player.

View File

@ -1,31 +0,0 @@
# Copyright (C) 2020-2021 by ÿnérant, eichhornchen, nicomarg, charlse
# SPDX-License-Identifier: GPL-3.0-or-later
from squirrelbattle.display.display import Display
from squirrelbattle.game import Game
from squirrelbattle.interfaces import Logs
class LogsDisplay(Display):
"""
A class to handle the display of the logs.
"""
logs: Logs
def __init__(self, *args) -> None:
super().__init__(*args)
self.pad = self.newpad(self.rows, self.cols)
def update(self, game: Game) -> None:
self.logs = game.logs
def display(self) -> None:
messages = self.logs.messages[-self.height:]
messages = messages[::-1]
self.pad.erase()
for i in range(min(self.height, len(messages))):
self.addstr(self.pad, self.height - i - 1, self.x,
messages[i][:self.width])
self.refresh_pad(self.pad, 0, 0, self.y, self.x,
self.y + self.height - 1, self.x + self.width - 1)

View File

@ -1,87 +0,0 @@
# Copyright (C) 2020-2021 by ÿnérant, eichhornchen, nicomarg, charlse
# SPDX-License-Identifier: GPL-3.0-or-later
from .display import Display
from ..game import Game
from ..interfaces import Map
class MapDisplay(Display):
"""
A class to handle the display of the map.
"""
map: Map
def __init__(self, *args):
super().__init__(*args)
def update(self, game: Game) -> None:
self.map = game.map
self.pad = self.newpad(self.map.height,
self.pack.tile_width * self.map.width + 1)
def update_pad(self) -> None:
for j in range(len(self.map.tiles)):
for i in range(len(self.map.tiles[j])):
if not self.map.seen_tiles[j][i]:
continue
fg, bg = self.map.tiles[j][i].visible_color(self.pack) if \
self.map.visibility[j][i] else \
self.map.tiles[j][i].hidden_color(self.pack)
self.addstr(self.pad, j, self.pack.tile_width * i,
self.map.tiles[j][i].char(self.pack), fg, bg)
for e in self.map.entities:
if self.map.visibility[e.y][e.x]:
self.addstr(self.pad, e.y, self.pack.tile_width * e.x,
self.pack[e.name.upper()],
self.pack.entity_fg_color,
self.pack.entity_bg_color)
# Display Path map for debug purposes
# from squirrelbattle.entities.player import Player
# players = [ p for p in self.map.entities if isinstance(p,Player) ]
# player = players[0] if len(players) > 0 else None
# if player:
# for x in range(self.map.width):
# for y in range(self.map.height):
# if (y,x) in player.paths:
# deltay, deltax = (y - player.paths[(y, x)][0],
# x - player.paths[(y, x)][1])
# if (deltay, deltax) == (-1, 0):
# character = '↓'
# elif (deltay, deltax) == (1, 0):
# character = '↑'
# elif (deltay, deltax) == (0, -1):
# character = '→'
# else:
# character = '←'
# self.addstr(self.pad, y, self.pack.tile_width * x,
# character, self.pack.tile_fg_color,
# self.pack.tile_bg_color)
def display(self) -> None:
y, x = self.map.currenty, self.pack.tile_width * self.map.currentx
deltay, deltax = (self.height // 2) + 1, (self.width // 2) + 1
pminrow, pmincol = y - deltay, x - deltax
sminrow, smincol = max(-pminrow, 0), max(-pmincol, 0)
deltay, deltax = self.height - deltay, self.width - deltax
smaxrow = self.map.height - (y + deltay) + self.height - 1
smaxrow = min(smaxrow, self.height - 1)
smaxcol = self.pack.tile_width * self.map.width - \
(x + deltax) + self.width - 1
# Wrap perfectly the map according to the width of the tiles
pmincol = self.pack.tile_width * (pmincol // self.pack.tile_width)
smincol = self.pack.tile_width * (smincol // self.pack.tile_width)
smaxcol = self.pack.tile_width \
* (smaxcol // self.pack.tile_width + 1) - 1
smaxcol = min(smaxcol, self.width - 1)
pminrow = max(0, min(self.map.height, pminrow))
pmincol = max(0, min(self.pack.tile_width * self.map.width, pmincol))
self.pad.erase()
self.update_pad()
self.refresh_pad(self.pad, pminrow, pmincol, sminrow, smincol, smaxrow,
smaxcol)

View File

@ -282,3 +282,91 @@ class ChestInventoryDisplay(MenuDisplay):
self.menu.position = max(0, min(len(self.menu.values) - 1, y - 2))
game.is_in_chest_menu = True
game.handle_key_pressed(KeyValues.ENTER)
class CreditsDisplay(Display):
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
self.box = Box(*args, **kwargs)
self.pad = self.newpad(1, 1)
self.ascii_art_displayed = False
def update(self, game: Game) -> None:
return
def display(self) -> None:
self.box.refresh(self.y, self.x, self.height, self.width)
self.box.display()
self.pad.erase()
messages = [
_("Credits"),
"",
"Squirrel Battle",
"",
_("Developers:"),
"Yohann \"ÿnérant\" D'ANELLO",
"Mathilde \"eichhornchen\" DÉPRÉS",
"Nicolas \"nicomarg\" MARGULIES",
"Charles \"charsle\" PEYRAT",
"",
_("Translators:"),
"Hugo \"ifugao\" JACOB (español)",
]
for i, msg in enumerate(messages):
self.addstr(self.pad, i + (self.height - len(messages)) // 2,
(self.width - len(msg)) // 2, msg,
bold=(i == 0), italic=(":" in msg))
if self.ascii_art_displayed:
self.display_ascii_art()
self.refresh_pad(self.pad, 0, 0, self.y + 1, self.x + 1,
self.height + self.y - 2,
self.width + self.x - 2)
def display_ascii_art(self) -> None:
with open(ResourceManager.get_asset_path("ascii-art-ecureuil.txt"))\
as f:
ascii_art = f.read().split("\n")
height, width = len(ascii_art), len(ascii_art[0])
y_offset, x_offset = (self.height - height) // 2,\
(self.width - width) // 2
for i, line in enumerate(ascii_art):
for j, c in enumerate(line):
bg_color = curses.COLOR_WHITE
fg_color = curses.COLOR_BLACK
bold = False
if c == ' ':
bg_color = curses.COLOR_BLACK
elif c == '' or c == '' or c == '':
bold = True
fg_color = curses.COLOR_WHITE
bg_color = curses.COLOR_BLACK
elif c == '|':
bold = True # c = '┃'
fg_color = (100, 700, 1000)
bg_color = curses.COLOR_BLACK
elif c == '':
fg_color = (700, 300, 0)
elif c == '':
fg_color = (700, 300, 0)
bg_color = curses.COLOR_BLACK
elif c == '':
fg_color = (350, 150, 0)
elif c == '':
fg_color = (0, 0, 0)
bg_color = curses.COLOR_BLACK
elif c == '':
c = ''
fg_color = (1000, 1000, 1000)
bg_color = curses.COLOR_BLACK
self.addstr(self.pad, y_offset + i, x_offset + j, c,
fg_color, bg_color, bold=bold)
def handle_click(self, y: int, x: int, attr: int, game: Game) -> None:
if self.pad.inch(y - 1, x - 1) != ord(" "):
self.ascii_art_displayed = True

View File

@ -1,32 +0,0 @@
# Copyright (C) 2020-2021 by ÿnérant, eichhornchen, nicomarg, charlse
# SPDX-License-Identifier: GPL-3.0-or-later
import curses
from squirrelbattle.display.display import Box, Display
from squirrelbattle.game import Game
class MessageDisplay(Display):
"""
A class to handle the display of popup messages.
"""
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
self.box = Box(fg_border_color=curses.COLOR_RED, *args, **kwargs)
self.message = ""
self.pad = self.newpad(1, 1)
def update(self, game: Game) -> None:
self.message = game.message
def display(self) -> None:
self.box.refresh(self.y - 1, self.x - 2,
self.height + 2, self.width + 4)
self.box.display()
self.pad.erase()
self.addstr(self.pad, 0, 0, self.message, bold=True)
self.refresh_pad(self.pad, 0, 0, self.y, self.x,
self.height + self.y - 1,
self.width + self.x - 1)