Compare commits

...
Sign in to create a new pull request.

74 commits

Author SHA1 Message Date
f86f2e5dce added last part of tutorial 2024-03-10 18:42:40 +01:00
fc3773150a - 2024-03-10 16:19:57 +01:00
04547161a3 picture 2024-03-10 16:05:15 +01:00
93bbb0eb84 Stoorryy 2024-03-10 16:05:09 +01:00
4e976c3895 wuhu 2024-03-10 15:14:21 +01:00
e540693def story yea yea 2024-03-10 15:06:44 +01:00
248fc2a112 fix fix 2024-03-10 14:30:20 +01:00
726c5ee2a2 storyline 2024-03-10 14:23:22 +01:00
bb8ec349dd Merge branch 'main' of https://git.spafi.eu/Lyzzy/game 2024-03-10 13:04:29 +01:00
4d40e44e2d starting to add some storyline, added Rat 2024-03-10 12:58:59 +01:00
2a2d7b2765 Merge pull request 'Development' (#11) from InfoProjekt/game:Development into main
Reviewed-on: #11
2024-03-10 11:51:09 +00:00
4a47efe94d Merge pull request 'changed NPC talk key to f and resolved merge conflicts' (#77) from Spafi/game:main into Development
Reviewed-on: InfoProjekt/game#77
2024-03-10 11:46:45 +00:00
SpagettiFisch
4ccc2dde11 Merge branch 'main' of https://git.spafi.eu/Spafi/game
Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-10 12:42:41 +01:00
SpagettiFisch
67a0937c4b changed NPC talking key to f
Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-10 12:42:09 +01:00
01c3aeae4a Merge pull request 'Development' (#10) from InfoProjekt/game:Development into main
Reviewed-on: #10
2024-03-10 09:32:18 +00:00
3232096d66 Merge pull request 'changed stuff' (#76) from Spafi/game:main into Development
Reviewed-on: InfoProjekt/game#76
2024-03-10 08:27:07 +00:00
e8d81dfb11 Merge pull request 'InfoProjekt-Development3' (#6) from InfoProjekt-Development3 into main
Reviewed-on: Spafi/game#6
2024-03-10 08:26:52 +00:00
SpagettiFisch
0032f8b2e1 Merge branch 'Development' of https://git.spafi.eu/InfoProjekt/game into InfoProjekt-Development3
Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-10 09:23:59 +01:00
SpagettiFisch
b1b7b21aa2 changed stuff
Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-10 09:17:22 +01:00
523b34615b Merge pull request 'Changed Book and fixed NPC convo' (#75) from Lyzzy/game:main into Development
Reviewed-on: InfoProjekt/game#75
2024-03-10 08:16:42 +00:00
3fe22ff6ac updated convo, still weird tho 2024-03-09 21:27:54 +01:00
9147971be8 added house 2024-03-09 20:14:40 +01:00
52d3ec6e8d fixed that herberts attributes stay the same 2024-03-09 16:26:53 +01:00
c17b65d2f3 added village somehow 2024-03-09 15:54:19 +01:00
67f1e081fa added village 2024-03-09 14:00:00 +01:00
2970e5cecd fixed Convo 2024-03-09 12:03:59 +01:00
614654692f changed Book and Convo, renamed Speech 2024-03-09 11:11:28 +01:00
1f38a04004 Merge pull request 'Development' (#9) from InfoProjekt/game:Development into main
Reviewed-on: #9
2024-03-09 09:06:05 +00:00
d85c6ec22c Merge pull request 'fixed wall colision' (#74) from Spafi/game:main into Development
Reviewed-on: InfoProjekt/game#74
2024-03-08 07:36:57 +00:00
SpagettiFisch
bd5ff8b3fe fixed wall colision
added object collision for mobs

Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-08 08:36:13 +01:00
091726b8ca Merge pull request 'attack now with left mouse click' (#73) from Spafi/game:main into Development
Reviewed-on: InfoProjekt/game#73
2024-03-07 20:05:46 +00:00
SpagettiFisch
31a9742a9c attack now with left mouse click
emter conversaton now with f
no change to leave conversation

Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-07 20:50:09 +01:00
4d228bf6e0 test2 2024-03-07 16:44:38 +01:00
956c25769c test 2024-03-07 16:41:11 +01:00
569b3394a0 Merge pull request 'Development' (#8) from InfoProjekt/game:Development into main
Reviewed-on: #8
2024-03-07 15:35:48 +00:00
9396218a11 Merge pull request 'main' (#72) from Spafi/game:main into Development
Reviewed-on: InfoProjekt/game#72
2024-03-07 14:27:03 +00:00
321dac7cca wrong location
Signed-off-by: Spafi <spafi@noreply.git.spafi.eu>
2024-03-07 14:26:57 +00:00
abfa24ced8 wrong location
Signed-off-by: Spafi <spafi@noreply.git.spafi.eu>
2024-03-07 14:26:52 +00:00
11c7a9037b wrong location
Signed-off-by: Spafi <spafi@noreply.git.spafi.eu>
2024-03-07 14:26:45 +00:00
9c36e8d570 wrong location
Signed-off-by: Spafi <spafi@noreply.git.spafi.eu>
2024-03-07 14:26:36 +00:00
SpagettiFisch
a68bba70bb image files changed
new mob sprites
relocated all image files
disabled collision between player and npcs and mobs

Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-07 14:57:18 +01:00
SpagettiFisch
b7fb7e1f1e Merge branch 'main' of https://git.spafi.eu/Lyzzy/game
Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-07 13:56:24 +01:00
SpagettiFisch
5010609378 relocated image files
changed room generation

Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-07 13:55:01 +01:00
73165bd33e speech and fireplace 2024-03-07 12:52:41 +00:00
b368fe4665 zombie speech and fireplace 2024-03-07 12:52:17 +00:00
af5204857b some fixes
forgot what i did
2024-03-07 09:43:33 +00:00
1d03d60ac2 Merge pull request 'new river sprite file added' (#67) from Spafi/game:main into Development
Reviewed-on: InfoProjekt/game#67
2024-03-07 08:51:52 +00:00
SpagettiFisch
c3c44bbc71 new river sprite file added
new idea lol

Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-07 09:50:10 +01:00
a41ee41fba Merge pull request 'main' (#66) from jaffa/game:main into Development
Reviewed-on: InfoProjekt/game#66
2024-03-07 08:24:16 +00:00
47c93f61dc Upload files to "art/sprite files" 2024-03-07 08:18:47 +00:00
1fd852e31e Merge pull request 'Development' (#1) from InfoProjekt/game:Development into main
Reviewed-on: jaffa/game#1
2024-03-07 08:13:31 +00:00
f21d980352 Merge pull request 'doubled image size' (#65) from Spafi/game:main into Development
Reviewed-on: InfoProjekt/game#65
2024-03-07 06:51:08 +00:00
SpagettiFisch
1b6ccb17b0 Merge branch 'Development' of https://git.spafi.eu/InfoProjekt/game 2024-03-07 07:49:49 +01:00
SpagettiFisch
6034a8382f changed image size
Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-07 07:49:16 +01:00
SpagettiFisch
746982641a Merge https://git.spafi.eu/InfoProjekt/game 2024-03-07 07:46:26 +01:00
b3c7d87926 Merge pull request 'Added Label class' (#64) from Lyzzy/game:main into Development
Reviewed-on: InfoProjekt/game#64
2024-03-07 06:45:57 +00:00
41f8b76b90 added Label class
Label class in classes, added text to book, changed wind spell a bit but dunno if really good
2024-03-06 17:40:02 +00:00
96c0a691b7 empty image cuz im stupid 2024-03-06 17:36:57 +00:00
25f04f994f added Label class
added Label class in classes and added text to book, changed wind attack a bit but idk if good
2024-03-06 17:35:27 +00:00
e2ec301fce Merge pull request 'Development' (#6) from InfoProjekt/game:Development into main
Reviewed-on: #6
2024-03-06 15:44:25 +00:00
55b50531f9 Merge pull request 'wind slash spell' (#63) from Spafi/game:main into Development
Reviewed-on: InfoProjekt/game#63
2024-03-06 14:29:34 +00:00
SpagettiFisch
c9a98fb94c added new icons for spell selection inside the book
Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-06 14:27:06 +01:00
SpagettiFisch
501e84181f added a new missile
new to character: wind slash attack
added projectile lifetime (in frames, maybe change to 5*fps later)

Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-06 14:26:32 +01:00
0564d778a1 Merge pull request 'updated the button class -> can now take any arguments for the onClick Function' (#62) from Spafi/game:main into Development
Reviewed-on: InfoProjekt/game#62
2024-03-06 11:12:00 +00:00
SpagettiFisch
953edca694 updated the button class -> can now take any arguments for the onClick Function
changed all buttons according to this

Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-06 12:10:59 +01:00
96b15fd425 Merge pull request 'manual merge of lyzzys updates into Development' (#60) from Spafi/game:main into Development
Reviewed-on: InfoProjekt/game#60
2024-03-06 06:45:56 +00:00
SpagettiFisch
ef3a617e4d Merge branch 'main' of https://git.spafi.eu/Spafi/game; branch 'main' of https://git.spafi.eu/Lyzzy/game 2024-03-06 07:42:45 +01:00
4cfb4b92f0 Dateien nach "/" hochladen 2024-03-05 15:48:06 +00:00
44793f22a5 Merge pull request 'Collisions fixed' (#58) from Spafi/game:main into Development
Reviewed-on: InfoProjekt/game#58
2024-03-04 16:18:33 +00:00
SpagettiFisch
3ad2ad6478 optimized collision with npcs and mobs
added wall collision
enabled hitboxes for object and wall highlighting

Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-04 17:15:19 +01:00
SpagettiFisch
0cd9444222 Merge branch 'Development' of https://git.spafi.eu/InfoProjekt/game
Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-03 13:36:15 +01:00
SpagettiFisch
d86f8c360b fixed bug which stopped movement if colliding with projectiles
Signed-off-by: SpagettiFisch <63868515+SpagettiFisch@users.noreply.github.com>
2024-03-03 13:31:01 +01:00
6fce7e0fd2 Merge pull request 'Development' (#57) from Development into main
Reviewed-on: InfoProjekt/game#57
2024-03-03 12:28:45 +00:00
cb9a7e6ff5 Merge pull request 'mobs can die, main can attack, book object added to main, npc object added' (#56) from Lyzzy/game:main into Development
Reviewed-on: InfoProjekt/game#56
2024-03-03 12:21:58 +00:00
47 changed files with 1020 additions and 554 deletions

1
.idea/ideas.txt generated
View file

@ -38,6 +38,7 @@ Story:
Henker Henker
armer Bauer armer Bauer
"Hexe" "Hexe"
Patrice, fragt nach Lightning Anschluss -> Lightning Spell freigeschaltet
Ziel(e) Ziel(e)
-> Zurückkommen -> Zurückkommen

View file

Binary file not shown.

After

Width:  |  Height:  |  Size: 255 B

View file

Before

Width:  |  Height:  |  Size: 131 KiB

After

Width:  |  Height:  |  Size: 131 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 771 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 954 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 11 KiB

View file

Before

Width:  |  Height:  |  Size: 2.3 MiB

After

Width:  |  Height:  |  Size: 2.3 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.8 KiB

Binary file not shown.

Binary file not shown.

Before

Width:  |  Height:  |  Size: 11 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 11 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 11 KiB

BIN
art/images/box/empty.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 68 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 581 B

View file

Before

Width:  |  Height:  |  Size: 635 B

After

Width:  |  Height:  |  Size: 635 B

View file

Before

Width:  |  Height:  |  Size: 644 B

After

Width:  |  Height:  |  Size: 644 B

BIN
art/images/box/thinks.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 433 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 106 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 77 KiB

View file

Before

Width:  |  Height:  |  Size: 128 KiB

After

Width:  |  Height:  |  Size: 128 KiB

View file

Before

Width:  |  Height:  |  Size: 450 B

After

Width:  |  Height:  |  Size: 450 B

View file

Before

Width:  |  Height:  |  Size: 433 B

After

Width:  |  Height:  |  Size: 433 B

View file

Before

Width:  |  Height:  |  Size: 462 B

After

Width:  |  Height:  |  Size: 462 B

View file

Before

Width:  |  Height:  |  Size: 438 B

After

Width:  |  Height:  |  Size: 438 B

View file

Before

Width:  |  Height:  |  Size: 441 B

After

Width:  |  Height:  |  Size: 441 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 477 B

View file

Before

Width:  |  Height:  |  Size: 674 B

After

Width:  |  Height:  |  Size: 674 B

View file

Before

Width:  |  Height:  |  Size: 5.9 KiB

After

Width:  |  Height:  |  Size: 5.9 KiB

View file

Before

Width:  |  Height:  |  Size: 2.1 KiB

After

Width:  |  Height:  |  Size: 2.1 KiB

BIN
art/images/people/rat.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 197 B

View file

Before

Width:  |  Height:  |  Size: 654 B

After

Width:  |  Height:  |  Size: 654 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 505 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 588 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 120 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 11 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 11 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 11 KiB

View file

Before

Width:  |  Height:  |  Size: 255 B

After

Width:  |  Height:  |  Size: 255 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 87 B

View file

Before

Width:  |  Height:  |  Size: 495 B

After

Width:  |  Height:  |  Size: 495 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 400 B

View file

@ -1,230 +1,308 @@
import pygame import pygame
pygame.font.init() pygame.font.init()
fonts = { fonts = {
'medieval': 'medieval.ttf', 'medieval': 'medieval.ttf',
'minecraft': 'Minecraft Evenings.otf', 'minecraft': 'Minecraft Evenings.otf',
'3dpixel': '3D-Pixel.ttf', '3dpixel': '3D-Pixel.ttf',
'8bit': '8bitlim.ttf', '8bit': '8bitlim.ttf',
'8bito': '8blimro.ttf', '8bito': '8blimro.ttf',
'arcade': 'ARCADECLASSIC.ttf', 'arcade': 'ARCADECLASSIC.ttf',
'modern_game': 'astron boy video.otf', 'modern_game': 'astron boy video.otf',
'modern': 'astron boy.otf', 'modern': 'astron boy.otf',
'wonder': 'Beyond Wonderland.ttf', 'wonder': 'Beyond Wonderland.ttf',
'curved': 'Digitag.ttf', 'curved': 'Digitag.ttf',
'simple': 'DisposableDroidBB.ttf', 'simple': 'DisposableDroidBB.ttf',
'rounded': 'dpcomic.ttf', 'rounded': 'dpcomic.ttf',
'playfull': 'Endalian Script.ttf', 'playfull': 'Endalian Script.ttf',
'blocky': 'FREAKSOFNATURE.ttf', 'blocky': 'FREAKSOFNATURE.ttf',
'catchy': 'Future TimeSplitters.otf', 'catchy': 'Future TimeSplitters.otf',
'simple_wide': 'Halo3.ttf', 'simple_wide': 'Halo3.ttf',
'simple_fat': 'INVASION2000.ttf', 'simple_fat': 'INVASION2000.ttf',
'very_gamy': 'ka1.ttf', 'very_gamy': 'ka1.ttf',
'simple_round': 'Karma Suture.otf', 'simple_round': 'Karma Suture.otf',
'mono': 'manaspc.ttf', 'mono': 'manaspc.ttf',
'damaged': 'Merchant Copy.ttf', 'damaged': 'Merchant Copy.ttf',
'big_natural': 'MorialCitadel.TTF', 'big_natural': 'MorialCitadel.TTF',
'spacy': 'nasalization-rg.otf', 'spacy': 'nasalization-rg.otf',
'sci-fi': 'neuropol.otf', 'sci-fi': 'neuropol.otf',
'hollow_big_edge': 'papercut.ttf', 'hollow_big_edge': 'papercut.ttf',
'space_shuttle': 'pdark.ttf', 'space_shuttle': 'pdark.ttf',
'thin': 'PixelFJVerdana12pt.ttf', 'thin': 'PixelFJVerdana12pt.ttf',
'random': 'Seattle Avenue.ttf', 'random': 'Seattle Avenue.ttf',
'pixel': 'yoster.ttf' 'pixel': 'yoster.ttf'
} }
class Button(): class Button():
def __init__(self, x, y, width, height, font, font_size, buttonText='Button', onclickFunction=None, onePress=False): def __init__(self, x, y, width, height, image, font, font_size, buttonText='', onclickFunction=None, onePress=False, attributes=None):
self.font = pygame.font.Font(f'fonts/{fonts[font]}', font_size) self.font = pygame.font.Font(f'fonts/{fonts[font]}', font_size)
self.x = x self.x = x
self.y = y self.y = y
self.width = width self.width = width
self.height = height self.height = height
self.onclickFunction = onclickFunction self.attributes = attributes
self.onePress = onePress self.onclickFunction = onclickFunction
self.alreadyPressed = False self.onePress = onePress
self.alreadyPressed = False
with open('art/images/textbox.png', 'r') as tb:
self.box = pygame.image.load(tb) with open(f'art/images/box/{image}', 'r') as tb:
self.box = pygame.transform.scale(self.box, (width, height)) self.box = pygame.image.load(tb)
self.box = pygame.transform.scale(self.box, (width, height))
self.buttonRect = pygame.Rect(self.x, self.y, self.width, self.height)
self.buttonRect = pygame.Rect(self.x, self.y, self.width, self.height)
self.buttonSurf = self.font.render(buttonText, True, '#baab80')
self.buttonSurf = self.font.render(buttonText, True, '#baab80')
def process(self, screen, clock, running, background, isblack, WIDTH, HEIGHT):
mousePos = pygame.mouse.get_pos() def update(self, screen):
if self.buttonRect.collidepoint(mousePos): mousePos = pygame.mouse.get_pos()
if pygame.mouse.get_pressed(num_buttons=3)[0]: if self.buttonRect.collidepoint(mousePos):
if self.onePress: if pygame.mouse.get_pressed(3)[0]:
self.onclickFunction() if self.onePress:
elif not self.alreadyPressed: self.onclickFunction()
if 'play' in str(self.onclickFunction): elif not self.alreadyPressed:
self.onclickFunction(screen, clock, running, background, isblack, WIDTH, HEIGHT) if self.attributes:
self.alreadyPressed = True self.onclickFunction(*self.attributes)
else: self.alreadyPressed = True
self.onclickFunction() else:
self.alreadyPressed = True self.onclickFunction()
else: self.alreadyPressed = True
self.alreadyPressed = False else:
self.box.blit(self.buttonSurf, [ self.alreadyPressed = False
self.buttonRect.width/2 - self.buttonSurf.get_rect().width/2, self.box.blit(self.buttonSurf, [
self.buttonRect.height/2 - self.buttonSurf.get_rect().height/2 self.buttonRect.width/2 - self.buttonSurf.get_rect().width/2,
]) self.buttonRect.height/2 - self.buttonSurf.get_rect().height/2
screen.blit(self.box, self.buttonRect) ])
screen.blit(self.box, self.buttonRect)
class DropDown(): class Label():
def __init__(self, x, y, width, height, font, font_size, color_menu, color_option, main, options): def __init__(self, x, y, width, height, text, font='simple', font_size=20, font_color = '#1e90ff', sprite = 'label.png') -> None:
self.rect = pygame.Rect(x, y, width, height) self.x = x
self.font = pygame.font.Font(f'fonts/{fonts[font]}', font_size) self.y = y
self.main = main self.width = width
self.options = options self.height = height
self.draw_menu = False self.font = pygame.font.Font(f'fonts/{fonts[font]}', font_size)
self.menu_active = False self.font_color = font_color
self.active_option = -1 self.text = text
self.hidden = False
with open('art/images/textbox.png', 'r') as tb: self.sprite = sprite
self.box = pygame.image.load(tb) with open(f'art/images/box/{sprite}', 'r') as tb:
self.box = pygame.transform.scale(self.box, (width, height)) self.box = pygame.image.load(tb)
self.box = pygame.transform.scale(self.box, (width, height))
def draw(self, screen):
#pygame.draw.rect(screen, self.color_menu[self.menu_active], self.rect, 0)
surface = self.font.render(self.main, 1, (0, 0, 0)) def draw(self, screen):
self.box.blit(surface, [ if self.hidden:
self.rect.width/2 - surface.get_rect().width/2, return
self.rect.height/2 - surface.get_rect().height/2 with open(f'art/images/box/{self.sprite}', 'r') as tb:
]) self.box = pygame.image.load(tb)
screen.blit(self.box, surface.get_rect(center = self.rect.center)) self.box = pygame.transform.scale(self.box, (self.width,self.height))
self.labelRect = pygame.Rect(self.x, self.y, self.width, self.height)
if self.draw_menu: self.labelSurf = self.font.render(self.text, True, self.font_color)
for i, text in enumerate(self.options): self.box.blit(self.labelSurf, [
rect = self.rect.copy() self.labelRect.width / 2 - self.labelSurf.get_rect().width / 2,
rect.y += (i+1) * self.rect.height self.labelRect.height / 2 - self.labelSurf.get_rect().height / 2
rect.x = self.rect.x ])
#pygame.draw.rect(screen, self.color_option[1 if i == self.active_option else 0], rect, 0) screen.blit(self.box, self.labelRect)
#msg = self.font.render(text, 1, (0, 0, 0))
#screen.blit(msg, msg.get_rect(center = rect.center))
surface = self.font.render(text, 1, (0, 0, 0))
self.box.blit(surface, [ class DropDown():
rect.width/2 - surface.get_rect().width/2, def __init__(self, x, y, width, height, font, font_size, color_menu, color_option, main, options):
rect.height/2 - surface.get_rect().height/2 self.rect = pygame.Rect(x, y, width, height)
]) self.font = pygame.font.Font(f'fonts/{fonts[font]}', font_size)
screen.blit(self.box, rect) self.main = main
self.options = options
def update(self, event_list): self.draw_menu = False
mpos = pygame.mouse.get_pos() self.menu_active = False
self.menu_active = self.rect.collidepoint(mpos) self.active_option = -1
self.active_option = -1
for i in range(len(self.options)): with open('art/images/box/textbox.png', 'r') as tb:
rect = self.rect.copy() self.box = pygame.image.load(tb)
rect.y += (i+1) * self.rect.height self.box = pygame.transform.scale(self.box, (width, height))
if rect.collidepoint(mpos):
self.active_option = i def draw(self, screen):
break #pygame.draw.rect(screen, self.color_menu[self.menu_active], self.rect, 0)
surface = self.font.render(self.main, 1, (0, 0, 0))
if not self.menu_active and self.active_option == -1: self.box.blit(surface, [
self.draw_menu = False self.rect.width/2 - surface.get_rect().width/2,
#self.draw_menu = True self.rect.height/2 - surface.get_rect().height/2
#return -1 ])
if pygame.mouse.get_pressed(num_buttons=3)[0]: screen.blit(self.box, surface.get_rect(center = self.rect.center))
if self.menu_active:
self.draw_menu = not self.draw_menu if self.draw_menu:
elif self.draw_menu and self.active_option >= 0: for i, text in enumerate(self.options):
self.draw_menu = False rect = self.rect.copy()
return self.active_option rect.y += (i+1) * self.rect.height
return -1 rect.x = self.rect.x
#pygame.draw.rect(screen, self.color_option[1 if i == self.active_option else 0], rect, 0)
#msg = self.font.render(text, 1, (0, 0, 0))
class GameObjects(): #screen.blit(msg, msg.get_rect(center = rect.center))
def __init__(self, name:str, _type:str, bg, objects:list, WIDTH, HEIGHT) -> None: surface = self.font.render(text, 1, (0, 0, 0))
self.name = name self.box.blit(surface, [
self.type = _type rect.width/2 - surface.get_rect().width/2,
self.background = bg rect.height/2 - surface.get_rect().height/2
if bg != None: ])
with open(bg, 'r') as bg: screen.blit(self.box, rect)
self.background = pygame.transform.scale(pygame.image.load(bg), [WIDTH, HEIGHT])
self.objects = objects def update(self, event_list):
mpos = pygame.mouse.get_pos()
self.menu_active = self.rect.collidepoint(mpos)
class Scene(GameObjects): self.active_option = -1
def __init__(self, name:str, _type:str, bg, objects:list | None, WIDTH, HEIGHT, level:list) -> None: for i in range(len(self.options)):
super().__init__(name, _type, bg, objects, WIDTH, HEIGHT) rect = self.rect.copy()
self.level = level rect.y += (i+1) * self.rect.height
self.current_level = 0 if rect.collidepoint(mpos):
self.active_option = i
def update(self, change:bool): break
if change:
self.current_level += 1 if not self.menu_active and self.active_option == -1:
self.level[self.current_level].update() self.draw_menu = False
if isinstance(self.objects, list): #self.draw_menu = True
for obj in self.objects: #return -1
obj.update() if pygame.mouse.get_pressed(num_buttons=3)[0]:
if self.menu_active:
def draw(self, screen): self.draw_menu = not self.draw_menu
if isinstance(self.objects, list): elif self.draw_menu and self.active_option >= 0:
for obj in self.objects: self.draw_menu = False
obj.draw(screen) return self.active_option
self.level[self.current_level].draw(screen) return -1
class Stage(GameObjects): class GameObjects():
def __init__(self, name: str, _type: str, bg, objects: list, WIDTH, HEIGHT, stage:str, rooms:list) -> None: def __init__(self, name:str, _type:str, bg, objects:list, WIDTH, HEIGHT) -> None:
super().__init__(name, _type, bg, objects, WIDTH, HEIGHT) self.name = name
self.stage = stage self.type = _type
self.rooms = rooms self.background = bg
self.current = 0 if bg != None:
if WIDTH != None and HEIGHT != None:
def update(self): with open(bg, 'r') as bg:
for room in self.rooms: self.background = pygame.transform.scale(pygame.image.load(bg), [WIDTH, HEIGHT])
if room.id == self.current: else:
room.update() with open(bg, 'r') as bg:
keys = pygame.key.get_pressed() self.background = pygame.transform.scale2x(pygame.image.load(bg))
if keys[pygame.K_RIGHT]: self.objects = objects
self.current += 1
if self.current >= len(self.rooms): def update(self, objects):
return 1 return
def draw(self, screen):
def draw(self, screen): return
for room in self.rooms:
if room.id == self.current: class Scene(GameObjects):
room.draw(screen) def __init__(self, name:str, _type:str, bg, objects:list, WIDTH, HEIGHT, level:list) -> None:
super().__init__(name, _type, bg, objects, WIDTH, HEIGHT)
class Room(GameObjects): self.level = level
def __init__(self, name:str, _type:str, bg, objects:list, WIDTH, HEIGHT, exits:list, id:int) -> None: self.current_level = 0
super().__init__(name, _type, bg, objects, WIDTH, HEIGHT) self.update()
self.exits = exits
self.id = id def update(self, change:bool=False, objects=None):
if self.type == 'normal' or self.type == 'boss': if change:
self.locked = True self.current_level += 1
else: self.level[self.current_level].update(objects)
self.locked = False self.background = self.level[self.current_level].background
"""if isinstance(self.objects, list):
self.objects.append(self.genWalls(WIDTH, HEIGHT)) for obj in self.objects[0] + self.objects[1] + self.objects[2]:
obj.update()"""
def genWalls(self, WIDTH, HEIGHT):
walls = [] def draw(self, screen):
walls.append(pygame.Rect(0, 0, 4, HEIGHT)) if isinstance(self.objects, list):
walls.append(pygame.Rect(WIDTH - 4, 0, 4, HEIGHT)) for obj in self.objects[0] + self.objects[1] + self.objects[2] + self.objects[3]:
walls.append(pygame.Rect(0, 0, WIDTH, 4)) obj.draw(screen)
walls.append(pygame.Rect(0, HEIGHT - 4, WIDTH, 4)) self.level[self.current_level].draw(screen)
return walls
def getObjects(self):
def update(self): return self.level[self.current_level].getObjects()
pass
def draw(self, screen): class Stage(GameObjects):
screen.blit(self.background, (32, 32)) def __init__(self, name: str, _type: str, bg, objects: list, WIDTH, HEIGHT, stage:str, rooms:list) -> None:
if isinstance(self.objects, list): super().__init__(name, _type, bg, objects, WIDTH, HEIGHT)
for obj in self.objects[0]: self.stage = stage
obj.draw(screen) self.rooms = rooms
self.current = 0
class Obstacle(GameObjects):
def __init__(self, name: str, _type: str, bg, collision: bool, x: int, y: int, hidden: bool=False, objects: list = None, WIDTH=None, HEIGHT=None) -> None: def update(self, objects):
super().__init__(name, _type, bg, objects, WIDTH, HEIGHT) for room in self.rooms:
self.collision = collision if room.id == self.current:
self.rect = pygame.Rect((x, y), self.background.get_size()) room.update(objects)
self.background = room.background
def draw(self, screen): keys = pygame.key.get_pressed()
screen.blit(self.background, self.rect) if keys[pygame.K_RIGHT]:
self.current += 1
if self.current >= len(self.rooms):
return 1
def draw(self, screen):
for room in self.rooms:
if room.id == self.current:
room.draw(screen)
def getObjects(self):
for room in self.rooms:
if room.id == self.current:
return room.getObjects()
class Room(GameObjects):
def __init__(self, name:str, _type:str, bg, objects:list, WIDTH, HEIGHT, exits:list, id:int) -> None:
super().__init__(name, _type, bg, objects, WIDTH, HEIGHT)
self.exits = exits
self.id = id
if self.type == 'normal' or self.type == 'boss':
self.locked = True
else:
self.locked = False
[self.objects[4].append(wall) for wall in self.genWalls(WIDTH, HEIGHT)]
def genWalls(self, WIDTH, HEIGHT):
walls = []
walls.append(Obstacle('wall_l', 'wall', None, True, 32, 32, True, WIDTH=4, HEIGHT=HEIGHT))
walls.append(Obstacle('wall_r', 'wall', None, True, WIDTH + 28, 32, True, WIDTH=4, HEIGHT=HEIGHT))
walls.append(Obstacle('wall_t', 'wall', None, True, 32, 32, True, WIDTH=WIDTH, HEIGHT=4))
walls.append(Obstacle('wall_b', 'wall', None, True, 32, HEIGHT + 28, True, WIDTH=WIDTH, HEIGHT=4))
return walls
def update(self, objects):
if objects is not None:
self.objects = objects
if not self.objects[1]:
self.locked = False
return
def draw(self, screen):
screen.blit(self.background, (32, 32))
if isinstance(self.objects, list):
for obj in self.objects[3] + self.objects[0] + self.objects[1] + self.objects[2]:
obj.draw(screen)
def getObjects(self):
return self.objects
class Obstacle(GameObjects):
def __init__(self, name: str, _type: str, bg, collision: bool, x: int, y: int, hidden: bool=False, objects: list = None, WIDTH=None, HEIGHT=None) -> None:
super().__init__(name, _type, bg, objects, WIDTH, HEIGHT)
self.collision = collision
self.hidden = hidden
self.width = WIDTH
self.height = HEIGHT
if self.background is not None:
self.rect = pygame.Rect((x, y), self.background.get_size())
else:
self.rect = pygame.Rect(x, y, WIDTH, HEIGHT)
def draw(self, screen):
if not self.hidden:
screen.blit(self.background, self.rect)
else:
pygame.draw.rect(screen, '#e7f8e0', self.rect, 2)
class Door(GameObjects):
def __init__(self, name: str, _type: str, bg, objects: list, WIDTH, HEIGHT, x: int, y: int, islocked=True) -> None:
super().__init__(name, _type, bg, objects, WIDTH, HEIGHT)
self.rect = pygame.Rect((x, y), self.background.get_size())
self.locked = islocked
def draw(self, screen):
screen.blit(self.background, self.rect)
def update(self, islocked=True):
self.locked = islocked

621
main.py
View file

@ -1,214 +1,407 @@
import pygame import pygame
import sys import sys
import json import json
import time import time
import random import random
from classes import * from classes import *
from viecher import * from viecher import *
fps = 60 fps = 60
def setUp(config): def setUp(config):
pygame.init() pygame.init()
if config["fullscreen"]: if config["fullscreen"]:
screen = pygame.display.set_mode(config["res"], pygame.FULLSCREEN) screen = pygame.display.set_mode(config["res"], pygame.FULLSCREEN)
else: else:
screen = pygame.display.set_mode(config["res"]) screen = pygame.display.set_mode(config["res"])
clock = pygame.time.Clock() clock = pygame.time.Clock()
pygame.display.set_caption('Between The Pages')
return screen, clock, True, True, "start.png", [] return screen, clock, True, True, "start.png", []
def readConfig(): def readConfig():
with open('config.json', 'r') as c: with open('config.json', 'r') as c:
json_data = c.read() json_data = c.read()
return json.loads(json_data) return json.loads(json_data)
def quitGame(): def quitGame():
#save progress somehow, if needed #save progress somehow, if needed
pygame.quit() pygame.quit()
quit() quit()
def genRooms(WIDTH, HEIGHT, type:str): def genRooms(WIDTH, HEIGHT, type:str, objects:list):
room_objects = [Obstacle('dirt', 'boulder', 'art/images/dirt2.png', False, 32, 32, WIDTH=WIDTH - 64, HEIGHT=HEIGHT - 64)] room_objects = []
room_objects.append(Obstacle('river', 'water', 'art/images/river1.png', True, 32, 32, WIDTH=WIDTH - 64, HEIGHT=HEIGHT - 64)) #room_objects = [Obstacle('dirt', 'boulder', 'art/images/dirt2.png', False, 32, 32, WIDTH=WIDTH - 64, HEIGHT=HEIGHT - 64)]
rooms = [ room_objects.append(Obstacle('river', 'water', 'art/images/background/river.png', True, random.randint(32, round(WIDTH * 0.75)), 32, WIDTH=96, HEIGHT=round(HEIGHT * 0.66)))
Room(type, 'normal', f'art/images/{type}.png', [[room_objects[i] for i in range(0, random.randint(0, len(room_objects)))]], WIDTH - 64, HEIGHT - 64, [True, True, True, False], 0), room_backgrounds = [f'art/images/background/{type}{i}.png' for i in range(1)]
Room(type, 'normal', f'art/images/{type}.png', [], WIDTH - 64, HEIGHT - 64, [True, True, True, False], 1), rooms = [
Room(type, 'normal', f'art/images/{type}.png', [], WIDTH - 64, HEIGHT - 64, [True, True, True, False], 2), Room(type, 'normal', room_backgrounds[random.randint(0, 0)], [objects[0], objects[1], objects[2], objects[3], objects[4] + [room_objects[random.randint(0, 0)] for i in range(0, random.randint(0, 1))]], WIDTH - 64, HEIGHT - 64, [True, True, True, True], j)
] for j in range(random.randint(5, 10))
return rooms ]
#rooms =Room(type, 'normal', room_backgrounds[random.randint(0, 4)], [objects[0], objects[1], objects[2], [room_objects[random.randint(0, len(room_objects) - 1)] for i in range(0, random.randint(0, 1))]], WIDTH - 64, HEIGHT - 64, [True, True, True, True], j)
def play(screen, clock, running, background, isblack, WIDTH, HEIGHT):
main = [MainCharacter('Herbert', 100, 'oldman.png', 500, 500, 20, 5, 1, 1, 50)] return rooms
mobs = [Skeleton(i, random.randint(40, 60), 'reddy.png', random.randint(20,1000), random.randint(20,700), 5, 1, 1, 1, 200) for i in range(0,random.randint(2, 8))]
others = [] def play(screen, clock, running, background, isblack, WIDTH, HEIGHT):
npcs = [NPC('name', 100, 'reddy.png', 1, 200, 200)] main = [herbert]
objects = [main, mobs, npcs, others] mobs = [Skeleton('skeleton', random.randint(40, 60), random.randint(50, WIDTH - 50), random.randint(50, HEIGHT - 50), 5, 1, 1, 1, 200) for i in range(0,random.randint(2, 5))]+[Zombie('zombie', random.randint(40, 60), random.randint(50, WIDTH-50), random.randint(50, HEIGHT-50), 5, 1, 1, 1, 25) for i in range(0,random.randint(2, 5))]
freeze = False #Gameplay is freezed in certain situations weapons = []
others = []
while running: npcs = []
screen.fill('#000000') objects = [main, mobs, npcs, weapons, others]
events = pygame.event.get() level = []
for event in events: rooms = genRooms(WIDTH, HEIGHT, 'grass', objects)
if event.type == pygame.QUIT: level.append(Stage('blau', 'normal', None, [], WIDTH, HEIGHT, 'blue', rooms))
quitGame() scene = Scene('test', 'normal', None, None, WIDTH, HEIGHT, level)
elif event.type == pygame.KEYDOWN: freeze = False #Gameplay is freezed in certain situations
if event.key == pygame.K_e: #when book is open gameplay is freezed
freeze = not freeze while running:
# RENDER YOUR GAME HERE screen.fill('#000000')
"""with open(background, 'r') as i: events = pygame.event.get()
bg = pygame.image.load(i) for event in events:
bg = pygame.transform.scale(bg, (WIDTH, HEIGHT)) if event.type == pygame.QUIT:
# fill the screen with an image to clear the screen quitGame()
screen.blit(bg, (0, 0)) elif event.type == pygame.KEYDOWN:
""" if event.key == pygame.K_e: #when book is open gameplay is freezed
if not freeze: freeze = not freeze
for thing in objects[0]: # RENDER YOUR GAME HERE
thing.book.hidden = not freeze """with open(background, 'r') as i:
if not thing.update(pygame.key.get_pressed(), objects): bg = pygame.image.load(i)
menu(screen, clock, running, background, isblack, WIDTH, HEIGHT) bg = pygame.transform.scale(bg, (WIDTH, HEIGHT))
thing.draw(screen) # fill the screen with an image to clear the screen
screen.blit(bg, (0, 0))
for mob in objects[1]: """
mob.update(objects) if not freeze:
mob.draw(screen) objects = scene.getObjects()
screen.blit(scene.background, (32, 32))
for npc in objects[2]:
npc.update(pygame.key.get_pressed(), objects) for thing in objects[4]:
npc.draw(screen) thing.draw(screen)
for thing in objects[3]: for weapon in objects[3]:
thing.update(objects) weapon.update(objects)
thing.draw(screen) weapon.draw(screen)
else:
objects[0][0].book.hidden = not freeze for thing in objects[0]:
objects[0][0].book.draw(screen) thing.book.hidden = not freeze
objects[0][0].book.update() result = thing.update(pygame.key.get_pressed(), pygame.mouse.get_pos(), objects)
# flip() the display to put your work on screen if result == 'village':
pygame.display.flip() village(screen, clock, running, background, isblack, WIDTH, HEIGHT)
elif result == 'play':
clock.tick(fps) # limits FPS to 60 play(screen, clock, running, background, isblack, WIDTH, HEIGHT)
else:
def options(screen, clock, running, background, isblack, WIDTH, HEIGHT): thing.draw(screen)
objects = []
# List that is displayed while selecting the window resolution level for mob in objects[1]:
resolution = [("1920x1080", "1920x1080"), mob.update(objects)
("1920x1200", "1920x1200"), mob.draw(screen)
("1280x720", "1280x720"),
("2560x1440", "2560x1440"), for npc in objects[2]:
("3840x2160", "3840x2160")] npc.update(pygame.key.get_pressed(), objects)
npc.draw(screen)
# This function displays the currently selected options
objects[0][0].book.addspell('windslash')
def printSettings(): scene.update(False, objects)
print("\n\n")
# getting the data using "get_input_data" method of the Menu class else:
settingsData = settings.get_input_data() objects[0][0].book.hidden = not freeze
objects[0][0].book.draw(screen)
for key in settingsData.keys(): objects[0][0].book.update()
print(f"{key}\t:\t{settingsData[key]}") # flip() the display to put your work on screen
pygame.display.flip()
while running:
for event in pygame.event.get(): clock.tick(fps) # limits FPS to 60
if event.type == pygame.QUIT:
running = False def village(screen, clock, running, background, isblack, WIDTH, HEIGHT):
# RENDER YOUR GAME HERE main = [herbert]
with open(background, 'r') as i: mobs = []
bg = pygame.image.load(i) weapons = []
bg = pygame.transform.scale(bg, (WIDTH, HEIGHT)) others = [Obstacle('fireplace', 'interactable', 'art/images/background/fireplace.png', False, 200, 500),
# fill the screen with an image to clear the screen Obstacle('house', 'Interactable', 'art/images/background/house.png', False, 500, 150, WIDTH=180, HEIGHT=160)]
screen.blit(bg, (0, 0)) npcs = [NPC('oldlady', 100, 'people/oldlady.png', 0, 200, 200)]
for obj in objects: objects = [main, mobs, npcs, weapons, others]
obj.process(screen) room = Room('village', 'village', 'art/images/background/village.png', objects, WIDTH - 64, HEIGHT - 64, [True, True, True, True], 0)
freeze = True #Gameplay is freezed in certain situations
# flip() the display to put your work on screen main[0].health.health = 20
pygame.display.flip()
while running:
clock.tick(60) # limits FPS to 60 screen.fill('#000000')
events = pygame.event.get()
def menu(screen, clock, running, background, isblack, WIDTH, HEIGHT): for event in events:
objects = [] if event.type == pygame.QUIT:
objects.append(Button(WIDTH / 2 - 80, HEIGHT / 2, 160, 64, 'medieval', 48, "Play", play)) quitGame()
#objects.append(Button(WIDTH / 2 - 80, HEIGHT / 2 - 72, 160, 64, 'medieval', 48, "Options", uwu)) elif event.type == pygame.KEYDOWN:
objects.append(Button(WIDTH / 2 - 80, HEIGHT / 2 + 72, 160, 64, 'medieval', 48, "Exit game", quitGame)) if event.key == pygame.K_e: #when book is open gameplay is freezed
while running: freeze = not freeze
for event in pygame.event.get(): # RENDER YOUR GAME HERE
if event.type == pygame.QUIT: """with open(background, 'r') as i:
running = False bg = pygame.image.load(i)
quitGame() bg = pygame.transform.scale(bg, (WIDTH, HEIGHT))
# RENDER YOUR GAME HERE # fill the screen with an image to clear the screen
with open(f'art/images/{background}', 'r') as i: screen.blit(bg, (0, 0))
bg = pygame.image.load(i) """
bg = pygame.transform.scale(bg, (WIDTH, HEIGHT)) if not freeze:
# fill the screen with an image to clear the screen objects = room.getObjects()
screen.blit(bg, (0, 0)) screen.blit(room.background, (32, 32))
for obj in objects:
obj.process(screen, clock, running, background, isblack, WIDTH, HEIGHT) for thing in objects[4]:
thing.draw(screen)
# flip() the display to put your work on screen
pygame.display.flip() for weapon in objects[3]:
weapon.update(objects)
clock.tick(60) # limits FPS to 60 weapon.draw(screen)
def test(screen, clock, running, background, isblack, WIDTH, HEIGHT): for thing in objects[0]:
level = [] thing.book.hidden = not freeze
rooms = genRooms(WIDTH, HEIGHT, 'grass') result = thing.update(pygame.key.get_pressed(), pygame.mouse.get_pos(), objects)
level.append(Stage('blau', 'normal', None, [], WIDTH, HEIGHT, 'blue', rooms)) if result == 'village':
menu(screen, clock, running, background, isblack, WIDTH, HEIGHT)
level.append(Stage('rot', 'normal', None, [], WIDTH, HEIGHT, 'red', [ elif result == 'play':
Room('red1', 'normal', 'art/images/grass.png', [], WIDTH, HEIGHT, [True, True, True, False], 0), play(screen, clock, running, background, isblack, WIDTH, HEIGHT)
Room('red2', 'normal', 'art/images/grass.png', [], WIDTH, HEIGHT, [True, True, True, False], 1), elif result == 'house':
Room('red3', 'normal', 'art/images/grass.png', [], WIDTH, HEIGHT, [True, True, True, False], 2), house(screen, clock, running, background, isblack, WIDTH, HEIGHT)
])) else:
thing.draw(screen)
scene = Scene('test', 'normal', None, None, WIDTH, HEIGHT, level)
for mob in objects[1]:
# RENDER YOUR GAME HERE mob.update(objects)
while True: mob.draw(screen)
for event in pygame.event.get():
if event.type == pygame.QUIT: for npc in objects[2]:
running = False npc.update(pygame.key.get_pressed(), objects)
quitGame() npc.draw(screen)
screen.fill('#000000')
scene.update(False) room.update(objects)
scene.draw(screen)
# flip() the display to put your work on screen else:
pygame.display.flip() objects[0][0].book.hidden = not freeze
objects[0][0].book.draw(screen)
clock.tick(60) # limits FPS to 60 objects[0][0].book.update()
# flip() the display to put your work on screen
def main(): pygame.display.flip()
config = readConfig()
screen, clock, running, isblack, background, objects = setUp(config["screen"]) clock.tick(fps) # limits FPS to
WIDTH, HEIGHT = screen.get_size()
#objects.append(Button(WIDTH / 2 - 80, HEIGHT / 2 - 72, 160, 64, 'medieval', 48, "Play", play)) def house(screen, clock, running, background, isblack, WIDTH, HEIGHT):
#objects.append(Button(WIDTH / 2 - 80, HEIGHT / 2, 160, 64, 'medieval', 48, "Options", uwu)) main = [herbert]
#objects.append(Button(WIDTH / 2 - 80, HEIGHT / 2 + 72, 160, 64, 'medieval', 48, "Exit game", quitGame)) mobs = []
menu(screen, clock, running, background, isblack, WIDTH, HEIGHT) weapons = []
test(screen, clock, running, background, isblack, WIDTH, HEIGHT) others = []
npcs = [NPC('elder', 100, 'people/reddy.png', 0, 200, 200)]
"""while running: objects = [main, mobs, npcs, weapons, others]
for event in pygame.event.get(): room = Room('house', 'house', 'art/images/background/insideHouse.png', objects, WIDTH - 64, HEIGHT - 64, [True, True, True, True], 0)
if event.type == pygame.QUIT: freeze = False #Gameplay is freezed in certain situations
running = False
#menu(screen, clock, running, background, isblack, WIDTH, HEIGHT) while running:
if not isblack: screen.fill('#000000')
with open(background, 'r') as i: events = pygame.event.get()
bg = pygame.image.load(i) for event in events:
bg = pygame.transform.scale(bg, (WIDTH, HEIGHT)) if event.type == pygame.QUIT:
# fill the screen with a color to wipe away anything from last frame quitGame()
screen.blit(bg, (0, 0)) elif event.type == pygame.KEYDOWN:
if event.key == pygame.K_e: #when book is open gameplay is freezed
# RENDER YOUR GAME HERE freeze = not freeze
# RENDER YOUR GAME HERE
else: """with open(background, 'r') as i:
for obj in objects: bg = pygame.image.load(i)
obj.process(screen, clock, running, background, isblack, WIDTH, HEIGHT) bg = pygame.transform.scale(bg, (WIDTH, HEIGHT))
# flip() the display to put your work on screen # fill the screen with an image to clear the screen
pygame.display.flip() screen.blit(bg, (0, 0))
"""
clock.tick(60) # limits FPS to 60""" if not freeze:
objects = room.getObjects()
pygame.quit() screen.blit(room.background, (32, 32))
if __name__ == '__main__': for thing in objects[4]:
main() thing.draw(screen)
# for weapon in objects[3]:
# weapon.update(objects)
# weapon.draw(screen)
for thing in objects[0]:
thing.book.hidden = not freeze
result = thing.update(pygame.key.get_pressed(), pygame.mouse.get_pos(), objects)
if result == 'village':
menu(screen, clock, running, background, isblack, WIDTH, HEIGHT)
elif result == 'play':
play(screen, clock, running, background, isblack, WIDTH, HEIGHT)
elif result == 'wall':
village(screen, clock, running, background, isblack, WIDTH, HEIGHT)
else:
thing.draw(screen)
for npc in objects[2]:
npc.update(pygame.key.get_pressed(), objects)
npc.draw(screen)
objects[0][0].book.addspell('windslash')
room.update(objects)
else:
objects[0][0].book.hidden = not freeze
objects[0][0].book.draw(screen)
objects[0][0].book.update()
# flip() the display to put your work on screen
pygame.display.flip()
clock.tick(fps) # limits FPS to
def options(screen, clock, running, background, isblack, WIDTH, HEIGHT):
objects = []
# List that is displayed while selecting the window resolution level
resolution = [("1920x1080", "1920x1080"),
("1920x1200", "1920x1200"),
("1280x720", "1280x720"),
("2560x1440", "2560x1440"),
("3840x2160", "3840x2160")]
# This function displays the currently selected options
def printSettings():
print("\n\n")
# getting the data using "get_input_data" method of the Menu class
settingsData = settings.get_input_data()
for key in settingsData.keys():
print(f"{key}\t:\t{settingsData[key]}")
while running:
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
# RENDER YOUR GAME HERE
with open(background, 'r') as i:
bg = pygame.image.load(i)
bg = pygame.transform.scale(bg, (WIDTH, HEIGHT))
# fill the screen with an image to clear the screen
screen.blit(bg, (0, 0))
for obj in objects:
obj.process(screen)
# flip() the display to put your work on screen
pygame.display.flip()
clock.tick(60) # limits FPS to 60
def menu(screen, clock, running, background, isblack, WIDTH, HEIGHT):
objects = []
objects.append(Button(WIDTH / 2 - 80, HEIGHT / 2, 160, 64, 'textbox.png', 'medieval', 48, "Play", village, attributes=[screen, clock, running, background, isblack, WIDTH, HEIGHT]))
#objects.append(Button(WIDTH / 2 - 80, HEIGHT / 2 - 72, 160, 64, 'textbox.png', 'medieval', 48, "Options", uwu))
objects.append(Button(WIDTH / 2 - 80, HEIGHT / 2 + 72, 160, 64, 'textbox.png', 'medieval', 48, "Exit game", quitGame))
while running:
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
quitGame()
# RENDER YOUR GAME HERE
with open(f'art/images/background/{background}', 'r') as i:
bg = pygame.image.load(i)
bg = pygame.transform.scale(bg, (WIDTH, HEIGHT))
# fill the screen with an image to clear the screen
screen.blit(bg, (0, 0))
for obj in objects:
obj.update(screen)
# flip() the display to put your work on screen
pygame.display.flip()
clock.tick(60) # limits FPS to 60
def test(screen, clock, running, background, isblack, WIDTH, HEIGHT):
main = [MainCharacter('Herbert', 100, 'oldman.png', 500, 500, 20, 5, 1, 1, 50)]
mobs = [Skeleton(i, random.randint(40, 60), 'reddy.png', random.randint(20,1000), random.randint(20,700), 5, 1, 1, 1, 200) for i in range(0,random.randint(2, 8))]
others = []
npcs = [NPC('name', 100, 'reddy.png', 1, 200, 200)]
objects = [main, mobs, npcs, others]
level = []
rooms = genRooms(WIDTH, HEIGHT, 'grass', objects)
level.append(Stage('blau', 'normal', None, [], WIDTH, HEIGHT, 'blue', rooms))
freeze = False #Gameplay is freezed in certain situations
#level.append(Stage('rot', 'normal', None, [], WIDTH, HEIGHT, 'red', [
# Room('red1', 'normal', 'art/images/grass.png', [], WIDTH, HEIGHT, [True, True, True, False], 0),
# Room('red2', 'normal', 'art/images/grass.png', [], WIDTH, HEIGHT, [True, True, True, False], 1),
# Room('red3', 'normal', 'art/images/grass.png', [], WIDTH, HEIGHT, [True, True, True, False], 2),
# ]))
scene = Scene('test', 'normal', None, None, WIDTH, HEIGHT, level)
# RENDER YOUR GAME HERE
while True:
screen.fill('#000000')
events = pygame.event.get()
for event in events:
if event.type == pygame.QUIT:
running = False
quitGame()
elif event.type == pygame.KEYDOWN:
if event.key == pygame.K_e: #when book is open gameplay is freezed
freeze = not freeze
if not freeze:
objects = scene.getObjects()
for thing in objects[0]:
thing.book.hidden = not freeze
if not thing.update(pygame.key.get_pressed(), objects):
menu(screen, clock, running, background, isblack, WIDTH, HEIGHT)
thing.draw(screen)
for mob in objects[1]:
mob.update(objects)
mob.draw(screen)
for npc in objects[2]:
npc.update(pygame.key.get_pressed(), objects)
npc.draw(screen)
for thing in objects[3]:
thing.update(objects)
thing.draw(screen)
else:
objects[0][0].book.hidden = not freeze
objects[0][0].book.draw(screen)
objects[0][0].book.update()
# flip() the display to put your work on screen
pygame.display.flip()
clock.tick(60) # limits FPS to 60
def main():
config = readConfig()
screen, clock, running, isblack, background, objects = setUp(config["screen"])
WIDTH, HEIGHT = screen.get_size()
#objects.append(Button(WIDTH / 2 - 80, HEIGHT / 2 - 72, 160, 64, 'textbox.png', 'medieval', 48, "Play", play))
#objects.append(Button(WIDTH / 2 - 80, HEIGHT / 2, 160, 64, 'textbox.png', 'medieval', 48, "Options", uwu))
#objects.append(Button(WIDTH / 2 - 80, HEIGHT / 2 + 72, 160, 64, 'textbox.png', 'medieval', 48, "Exit game", quitGame))
menu(screen, clock, running, background, isblack, WIDTH, HEIGHT)
test(screen, clock, running, background, isblack, WIDTH, HEIGHT)
"""while running:
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
#menu(screen, clock, running, background, isblack, WIDTH, HEIGHT)
if not isblack:
with open(background, 'r') as i:
bg = pygame.image.load(i)
bg = pygame.transform.scale(bg, (WIDTH, HEIGHT))
# fill the screen with a color to wipe away anything from last frame
screen.blit(bg, (0, 0))
# RENDER YOUR GAME HERE
else:
for obj in objects:
obj.process(screen, clock, running, background, isblack, WIDTH, HEIGHT)
# flip() the display to put your work on screen
pygame.display.flip()
clock.tick(60) # limits FPS to 60"""
pygame.quit()
if __name__ == '__main__':
herbert = MainCharacter('Herbert', 100, 'people/oldman.png', 500, 500, 20, 5, 1, 1, 50)
main()

View file

@ -1,4 +1,8 @@
import pygame as pg import pygame as pg
from classes import *
from main import *
import random
vec = pg.math.Vector2 vec = pg.math.Vector2
fps = 60 fps = 60
@ -41,7 +45,7 @@ class Objects():
self.name = name self.name = name
self.speed = ms self.speed = ms
with open(f'art/images/{sprite}') as i: with open(f'art/images/{sprite}') as i:
self.sprite = pg.image.load(i) self.sprite = pg.transform.scale2x(pg.image.load(i))
self.x = x self.x = x
self.y = y self.y = y
self.hidden = False self.hidden = False
@ -52,60 +56,85 @@ class Objects():
return return
self.rect.x, self.rect.y = self.x, self.y self.rect.x, self.rect.y = self.x, self.y
screen.blit(self.sprite, self.rect) screen.blit(self.sprite, self.rect)
pg.draw.rect(screen, '#ef0120', self.rect, 2)
class NPC(Objects): class NPC(Objects):
def __init__(self, name, ms, sprite, convo_act, x, y) -> None: def __init__(self, name, ms, sprite, convo_scene, x, y) -> None:
self.talking = False
self.hidden = True
super().__init__(name, ms, sprite, x, y) super().__init__(name, ms, sprite, x, y)
self.conversation = Convo('Hello, you can shoot fireballs with f now.', convo_act, 'person') self.talking = False
self.hidden = False
self.conversation = Convo(self, convo_scene)
self.lastUpdate = pg.time.get_ticks()
def talk(self, objects): def talk(self, objects):
self.talking = True self.talking = True
objects[0][0].talking = True objects[0][0].talking = True
self.conversation.hidden = False
def draw(self, screen): def draw(self, screen):
super().draw(screen) super().draw(screen)
if self.talking == True: if self.talking:
self.conversation.draw(screen) self.conversation.draw(screen)
def update(self, keys, objects): def update(self, keys, objects):
if self.talking: if self.name == 'oldlady':
self.conversation.update(keys, objects) if self.conversation.convo_scene==0 and 'rat' in objects[0][0].killed and objects[1]==[]:
self.conversation.convo_scene=1
if self.lastUpdate + 200 < pg.time.get_ticks():
if self.talking:
self.conversation.update(keys, objects)
self.lastUpdate = pg.time.get_ticks()
else:
touches = pg.sprite.spritecollideany(self, objects[0])
if touches is not None and keys[pg.K_f] and isinstance(touches, MainCharacter):
self.talk(objects)
self.lastUpdate = pg.time.get_ticks()
class Convo():
def __init__(self, text, convo_act, person, x = 140, y = 600, width = 1000, height = 100, font='simple', font_size = 20) -> None:
self.x = x
self.y = y
self.width = width
self.height = height
self.hidden = False
self.font = pg.font.Font(f'fonts/{fonts[font]}', font_size)
with open('art/images/label.png', 'r') as tb:
self.box = pg.image.load(tb)
self.box = pg.transform.scale(self.box, (width, height))
self.labelRect = pg.Rect(self.x, self.y, self.width, self.height)
self.labelSurf = self.font.render(text, True, '#1E90FF')
class Convo(Label):
def __init__(self, npc, convo_scene, text='', x = 140, y = 600, width = 1000, height = 100, font='simple', font_size = 20) -> None:
super().__init__(x, y, width, height, text, font, font_size)
self.convo_act=0
self.npc = npc
self.convo_scene = convo_scene
self.convos = [
['oldlady', 0, ['There are so many rats here.', 'I wish someone would to something against that.','An experienced fighter could kill them.', 'For them it only takes a mouseclick.']],
['oldlady', 1, ['Oh, did you kill all the rats?', 'You must be the chosen one!', 'It would be nice if you would go and talk to the village elder.']],
['elder', 0, ['Who are you?', 'You want to help us?', 'We have a serious problem with monsters.', 'One day they appeared out of nowhere and started attacking.', 'When you jump into the portal over there,', 'You will be send to a place with monsters.', 'PLEASE help us!']],
['elder', 1, ['Who are you?', 'You want to help us?', 'We have a serious problem with monsters.', 'One day they appeared out of nowhere and started attacking.', 'When you jump into the portal over there,', 'You will be send to a place with monsters.', 'PLEASE help us!']]
]
def draw(self, screen): def draw(self, screen):
if self.hidden: self.text = self.findConversation()[2][self.convo_act]
return super().draw(screen)
self.box.blit(self.labelSurf, [
self.labelRect.width/2 - self.labelSurf.get_rect().width/2,
self.labelRect.height/2 - self.labelSurf.get_rect().height/2 def findConversation(self):
]) for convo in self.convos:
screen.blit(self.box, self.labelRect) if convo[0] == self.npc.name and convo[1] == self.convo_scene:
return convo
return ['ERROR']
def update(self, keys, objects): def update(self, keys, objects):
if keys[pg.K_SPACE]: if keys[pg.K_f]:
objects[0][0].book.addspell('fireball') convo = self.findConversation()
self.talking = False if self.convo_act+1 < len(convo[2]):
objects[0][0].talking = False self.text = convo[2][self.convo_act]
self.hidden = True self.convo_act += 1
else:
if convo[0] == 'oldlady':
if convo[1] == 0:
for i in range(0,5):
objects[1].append(Rat('rat', random.randint(150,250), 800, 400+i*20, 1, 1, 1, 100, 25))
elif convo[1] == 1:
objects[0][0].level.level = 5
while 'rat' in objects[0][0].killed: objects[0][0].killed.remove('rat')
if convo[0] == 'elder':
if convo[1] == 0:
objects[4].append(Obstacle('portal', 'interactable', 'art/images/background/portal.png', False, 700, 300))
self.convo_scene += 1
self.convo_act = 0
self.npc.talking = False
objects[0][0].talking = False
class Fighter(Objects): class Fighter(Objects):
@ -122,13 +151,16 @@ class Fighter(Objects):
class MainCharacter(Fighter): class MainCharacter(Fighter):
def __init__(self, name, ms, sprite, x, y, health, damage, level, asp, atr) -> None: def __init__(self, name, ms, sprite, x, y, health, damage, level, asp, atr, killed =[]) -> None:
super().__init__(name, ms, sprite, x, y, health, damage, level, asp, atr) super().__init__(name, ms, sprite, x, y, health, damage, level, asp, atr)
self.book = Book(0, 0, [], None, None) self.book = Book(0, 0, [], None, None)
self.talking = False self.talking = False
self.level = Level(1000, 38, level, 150, 40, f'will to live: {level}%', 'simple', 20) self.level = Level(1000, 38, 150, 40, level, f'will to live: {level}%', 'simple', 20, )
self.health = Hearts(health, sprite=['fullheart.png', 'fullheart.png', 'fullheart.png', 'fullheart.png', 'fullheart.png'], x=900, y= 50, hurtCooldown=self.hurtCooldown) self.health = Hearts(health, sprite=['fullheart.png', 'fullheart.png', 'fullheart.png', 'fullheart.png', 'fullheart.png'], x=900, y= 50, hurtCooldown=self.hurtCooldown)
self.thinks = Thinks(self.x+20, self.y-50, 150, 100, 'brr I\'m freezing')
self.freezing = True
self.killed = killed #amount of mobs that were killed
def draw(self, screen): def draw(self, screen):
if self.hidden: if self.hidden:
return return
@ -137,11 +169,30 @@ class MainCharacter(Fighter):
self.health.draw(screen) self.health.draw(screen)
self.level.draw(screen) self.level.draw(screen)
self.book.draw(screen) self.book.draw(screen)
pg.draw.rect(screen, '#e900fa', self.rect, 2)
if self.thinks.hidden == False:
self.thinks.draw(screen, self.x+20, self.y-100)
def hurt(self, damage, objects): def hurt(self, damage, objects):
if not self.talking: if not self.talking:
self.health.hurt(damage) self.health.hurt(damage)
def obstacle_interaction(self, objects):
touches = pg.sprite.spritecollideany(self, objects[4])
if touches is not None:
if touches.name == 'fireplace':
self.freezing = False
elif touches.name == 'portal' and self.level.level != 1:
return 'play'
elif touches.name == 'house' and self.level.level != 1:
self.x = 500
self.y = 400
return 'house'
elif 'wall' in touches.name:
return 'wall'
else:
return True
def walk(self, keys, objects): def walk(self, keys, objects):
moveto = vec(0, 0) moveto = vec(0, 0)
if keys[pg.K_w] or keys[pg.K_UP]: if keys[pg.K_w] or keys[pg.K_UP]:
@ -154,33 +205,68 @@ class MainCharacter(Fighter):
moveto += vec(1, 0) moveto += vec(1, 0)
if not moveto == vec(0, 0): if not moveto == vec(0, 0):
moveto.scale_to_length(self.speed) moveto.scale_to_length(self.speed)
self.x += moveto[0] / fps self.x += moveto[0] / fps
self.y += moveto[1] / fps self.y += moveto[1] / fps
touches = pg.sprite.spritecollideany(self, objects[1] + objects[2]) touches = pg.sprite.spritecollideany(self, objects[2] + objects[4])
if touches is not None: if touches is not None and not isinstance(touches, Weapons):
self.x -= moveto[0]*1.5 / fps #change later if isinstance(touches, Obstacle):
self.y -= moveto[1]*1.5 / fps #change later if not touches.collision:
if isinstance(touches, NPC): # print(touches.name)
touches.talk(objects) return
if touches.type == 'wall':
if touches.name == 'wall_l':
self.x += (2 + (self.x - touches.rect.x))
elif touches.name == 'wall_r':
self.x -= (2 + self.rect.width - (touches.rect.x - self.x))
if touches.name == 'wall_t':
self.y += (2 + (self.y - touches.rect.y))
elif touches.name == 'wall_b':
self.y -= (2 + self.rect.height - (touches.rect.y - self.y))
return
elif isinstance(touches, NPC):
return
if self.x <= touches.rect.x: self.x -= (self.rect.width - (touches.rect.x - self.x))
elif self.x > touches.rect.x: self.x += (self.rect.width - (self.x - touches.rect.x - touches.rect.width * 0.66))
#if self.y <= touches.y: pass
#elif self.y > touches.y: pass
#self.x -= moveto[0] * 2 / fps
#self.y -= moveto[1] * 2 / fps
"""
if self.x <= 32:
self.x = 33
elif self.x >= objects[3][0].width - 32:
self.x = objects[3][0].width - 32 - self.rect.width + 1
if self.y <= 32:
self.y = 33
elif self.y >= objects[3][0].height - 32:
self.y = objects[3][0].height - 32 - self.rect.height + 1
"""
def attack(self, obj, moveto = vec(0,1)): def attack(self, obj, mouse):
if self.lastAttack + self.attack_speed * 1000 < pg.time.get_ticks(): if self.lastAttack + self.attack_speed * 1000 < pg.time.get_ticks():
moveto = mouse - vec(self.x, self.y)
if self.book.current_sp == 'fireball': if self.book.current_sp == 'fireball':
weapon = Fireball('fb1', 100, self.x, self.y, moveto, 5) weapon = Fireball('fb1', 100, self.x, self.y, moveto, 5)
elif self.book.current_sp == 'windslash':
weapon = Windslash('ws1', 100, self.x, self.y, moveto, 10)
else: else:
return weapon = Punch('punch', 100, self.x, self.y, moveto, 1, Mobs, life_ticks=500)
obj[3].append(weapon) obj[3].append(weapon)
self.lastAttack = pg.time.get_ticks() self.lastAttack = pg.time.get_ticks()
def update(self, keys, objects): def update(self, keys, mouse, objects):
if not self.talking: if not self.talking:
self.walk(keys, objects) self.walk(keys, objects)
if keys[pg.K_f]: if pg.mouse.get_pressed()[0]:
self.attack(objects) self.attack(objects, vec(mouse))
self.thinks.update(objects, self)
if self.health.health <= 0: if self.health.health <= 0:
return False return 'village'
else: else:
return True return self.obstacle_interaction(objects)
class Hearts(): class Hearts():
def __init__(self, health, sprite, x, y, hurtCooldown) -> None: def __init__(self, health, sprite, x, y, hurtCooldown) -> None:
@ -192,7 +278,7 @@ class Hearts():
self.hidden = False self.hidden = False
self.sprite=[] self.sprite=[]
for parts in sprite: for parts in sprite:
with open(f'art/images/{parts}') as i: with open(f'art/images/main_attributes/{parts}') as i:
self.sprite.append(pg.image.load(i)) self.sprite.append(pg.image.load(i))
self.rect = [] self.rect = []
for each in self.sprite: for each in self.sprite:
@ -226,66 +312,105 @@ class Hearts():
sprite.append('noheart.png') sprite.append('noheart.png')
self.sprite = [] self.sprite = []
for parts in sprite: for parts in sprite:
with open(f'art/images/{parts}') as i: with open(f'art/images/main_attributes/{parts}') as i:
self.sprite.append(pg.image.load(i)) self.sprite.append(pg.image.load(i))
class Level(): class Level(Label):
def __init__(self, x, y, level, width, height, text, font, font_size) -> None: def __init__(self, x, y, width, height, level, text, font='simple', font_size=20, font_color='#1e90ff', sprite='label.png') -> None:
super().__init__(x, y, width, height, text, font, font_size, font_color, sprite)
self.level = level
def draw(self, screen):
self.text = f'will to live: {self.level}%'
super().draw(screen)
class Thinks(Label):
def __init__(self, x, y, width, height, text, font='simple', font_size=15, font_color='#000000', sprite='thinks.png') -> None:
super().__init__(x, y, width, height, text, font, font_size, font_color, sprite)
self.scene = 0
def draw(self, screen, x, y):
if self.hidden:
return
self.x = x self.x = x
self.y = y self.y = y
self.level = level super().draw(screen)
self.width = width
self.height = height def update(self, objects, main):
self.font = pg.font.Font(f'fonts/{fonts[font]}', font_size) if not self.hidden:
self.hidden = False if self.scene == 0 and not main.freezing:
with open('art/images/label.png', 'r') as tb: self.scene = 1
self.box = pg.image.load(tb) self.hidden = True
self.box = pg.transform.scale(self.box, (width, height)) elif self.scene == 1 and main.talking:
self.labelRect = pg.Rect(self.x, self.y, self.width, self.height) self.scene = 2
self.labelSurf = self.font.render(text, True, '#1E90FF') self.hidden = True
if self.scene == 1:
def draw(self, screen): touches = pg.sprite.spritecollideany(main, objects[2])
self.box.blit(self.labelSurf, [ if touches is not None and isinstance(touches, NPC):
self.labelRect.width / 2 - self.labelSurf.get_rect().width / 2, self.text = 'I should press \"f\"'
self.labelRect.height / 2 - self.labelSurf.get_rect().height / 2 self.hidden = False
]) else:
screen.blit(self.box, self.labelRect) self.hidden = False
self.text = 'the lady over there'
class Book(): class Book():
def __init__(self, x, y, spells, current_spell, current_shield) -> None: def __init__(self, x, y, spells, current_spell, current_shield) -> None:
with open(f'art/images/book.png') as i: with open(f'art/images/main_attributes/book.png') as i:
self.sprite = pg.image.load(i) self.sprite = pg.image.load(i)
self.sprite = pg.transform.scale(self.sprite, (1280, 720)) self.sprite = pg.transform.scale(self.sprite, (1280, 720))
self.x = x self.x = x
self.y = y self.y = y
self.hidden = True self.hidden = False
self.rect = pg.Rect(self.x, self.y, self.sprite.get_width(), self.sprite.get_height()) self.rect = pg.Rect(self.x, self.y, self.sprite.get_width(), self.sprite.get_height())
self.sp_list = spells self.sp_list = spells
self.current_sp = current_spell self.current_sp = current_spell
self.text_left = ["Dear User, ", "in case you fell on the ground too hard,", "here is a quick reminder:",
"You are a homeless person. One cold day","you went to the library to warm up yourself.",
"There you got bored and found and opened me.", "This lead to you being thrown into this world.",
"But you can find a way out of here again."]
self.text_right = ["This book will help you to survive.", "You can open and close me when pressing e.",
"Click on a picture to choose your spell.",
"Talk to fairies to unlock new spells!"]
self.buttons=[]
self.buttons_y = 400
self.buttons_x = 800
def draw(self, screen): def draw(self, screen):
if self.hidden: if self.hidden:
return return
self.rect.x, self.rect.y = self.x, self.y self.rect.x, self.rect.y = self.x, self.y
screen.blit(self.sprite, self.rect) screen.blit(self.sprite, self.rect)
text_left_y = 100
text_right_y = 100
for text in self.text_left:
label = Label(100, text_left_y, 500, 50, text, font_color='#000000', sprite='empty.png')
label.draw(screen)
text_left_y += 50
for text in self.text_right:
label = Label(680, text_right_y, 500, 50, text, font_color='#000000', sprite='empty.png')
label.draw(screen)
text_right_y += 50
for button in self.buttons:
button.update(screen)
def addspell(self, spell): def addspell(self, spell):
if spell not in self.sp_list: if spell not in self.sp_list:
self.sp_list.append(spell) self.sp_list.append(spell)
self.current_sp = spell self.current_sp = spell
self.buttons.append(Button(self.buttons_x, self.buttons_y, 58, 50, f'{spell}_icon.png', 'medieval', 23, attributes=[spell], onclickFunction=self.update_spell))
self.buttons_y += 100
def update_spell(self, spell):
self.current_sp = spell
def update(self): def update(self):
pass pass
class Mobs(Fighter): class Mobs(Fighter):
def __init__(self, name, ms, sprite, x, y, health, damage, level, asp, atr, drops) -> None: def __init__(self, name, ms, sprite, x, y, health, damage, level, asp, atr, drops) -> None:
super().__init__(name, ms, sprite, x, y, health, damage, level, asp, atr) super().__init__(name, ms, sprite, x, y, health, damage, level, asp, atr)
self.drops = drops * (self.level / 2) self.drops = drops * (self.level / 2)
class Skeleton(Mobs):
def __init__(self, name, ms, sprite, x, y, health, damage, level, asp, atr, drops=0) -> None:
super().__init__(name, ms, sprite, x, y, health, damage, level, asp, atr, drops)
def chase(self, obj): def chase(self, obj):
x = obj[0][0].x x = obj[0][0].x
@ -295,67 +420,136 @@ class Skeleton(Mobs):
moveto.scale_to_length(self.speed) moveto.scale_to_length(self.speed)
self.x += moveto[0] / fps self.x += moveto[0] / fps
self.y += moveto[1] / fps self.y += moveto[1] / fps
touches = pg.sprite.spritecollideany(self, obj[4])
if touches is not None and not isinstance(touches, Weapons):
if isinstance(touches, Obstacle):
if not touches.collision:
return
if touches.type == 'wall':
if touches.name == 'wall_l':
self.x += (2 + (self.x - touches.rect.x))
elif touches.name == 'wall_r':
self.x -= (2 + self.rect.width - (touches.rect.x - self.x))
if touches.name == 'wall_t':
self.y += (2 + (self.y - touches.rect.y))
elif touches.name == 'wall_b':
self.y -= (2 + self.rect.height - (touches.rect.y - self.y))
if self.x <= touches.rect.x: self.x -= (self.rect.width - (touches.rect.x - self.x))
elif self.x > touches.rect.x: self.x += (self.rect.width - (self.x - touches.rect.x - touches.rect.width * 0.66))
else: else:
self.attack(moveto, obj) self.attack(moveto, obj)
def hurt(self, damage, objects):
self.health -= damage
if self.health <= 0:
objects[0][0].killed.append(self.name)
self.hidden = True
objects[1].remove(self)
def update(self, obj):
self.chase(obj)
class Skeleton(Mobs):
def __init__(self, name, ms, x, y, health, damage, level, asp, atr, sprite = 'people/skeleton.png', drops=0) -> None:
super().__init__(name, ms, sprite, x, y, health, damage, level, asp, atr, drops)
def attack(self, moveto, obj): def attack(self, moveto, obj):
if self.lastAttack + self.attack_speed * 1000 < pg.time.get_ticks(): if self.lastAttack + self.attack_speed * 1000 < pg.time.get_ticks():
obj[3].append(Arrow("arrow", 200, self.x, self.y, moveto, self.damage)) obj[3].append(Arrow("arrow", 200, self.x, self.y, moveto, self.damage))
self.lastAttack = pg.time.get_ticks() self.lastAttack = pg.time.get_ticks()
def hurt(self, damage, objects):
self.health -= damage
if self.health <= 0:
self.hidden = True
objects[1].remove(self)
def update(self, obj): class Zombie(Mobs):
self.chase(obj) def __init__(self, name, ms, x, y, health, damage, level, asp, atr, sprite='people/zombie.png', drops=0) -> None:
super().__init__(name, ms, sprite, x, y, health, damage, level, asp, atr, drops)
def attack(self, moveto, obj):
if self.lastAttack + self.attack_speed * 1000 < pg.time.get_ticks():
obj[3].append(Punch('punch', 100, self.x, self.y, moveto, self.damage, MainCharacter))
self.lastAttack = pg.time.get_ticks()
class Rat(Mobs):
def __init__(self, name, ms, x, y, health, damage, level, asp, atr, sprite='people/rat.png', drops=0) -> None:
super().__init__(name, ms, sprite, x, y, health, damage, level, asp, atr, drops)
def attack(self, moveto, obj):
if self.lastAttack + self.attack_speed * 1000 < pg.time.get_ticks():
obj[3].append(Punch('punch', 100, self.x, self.y, moveto, self.damage, MainCharacter))
self.lastAttack = pg.time.get_ticks()
class Weapons(Objects): class Weapons(Objects):
def __init__(self, name, ms, sprite, x, y, moveto, damage) -> None: def __init__(self, name, ms, sprite, x, y, moveto, damage, life_ticks) -> None:
super().__init__(name, ms, sprite, x, y) super().__init__(name, ms, sprite, x, y)
self.moveto = moveto self.moveto = moveto
self.damage = damage self.damage = damage
self.life_ticks= life_ticks
self.spawn_tick = pg.time.get_ticks()
pos = vec(1,0) pos = vec(1,0)
angle = pos.angle_to(moveto) angle = pos.angle_to(moveto)
with open(f'art/images/{sprite}') as i:
self.sprite = pg.transform.rotate(pg.image.load(i), -angle) self.sprite = pg.transform.rotate(self.sprite, -angle)
def die(self, objects, kills): def die(self, objects, kills):
touches = pg.sprite.spritecollideany(self, objects[0] + objects[1]) touches = pg.sprite.spritecollideany(self, objects[0] + objects[1])
if touches is not None and isinstance(touches, kills): if touches is not None and isinstance(touches, kills):
touches.hurt(self.damage, objects) touches.hurt(self.damage, objects)
self.hidden = True
if self in objects[3]:
objects[3].remove(self)
def move(self, objects):
self.moveto.scale_to_length(self.speed)
self.x += self.moveto[0] / fps
self.y += self.moveto[1] / fps
if pg.time.get_ticks() - self.spawn_tick > self.life_ticks:
self.hidden = True self.hidden = True
objects[3].remove(self) objects[3].remove(self)
class Spells(Weapons): class Spells(Weapons):
def __init__(self, name, ms, sprite, x, y, moveto, damage) -> None: def __init__(self, name, ms, sprite, x, y, moveto, damage, life_ticks) -> None:
super().__init__(name, ms, sprite, x, y, moveto, damage) super().__init__(name, ms, sprite, x, y, moveto, damage, life_ticks)
class Fireball(Spells): class Fireball(Spells):
def __init__(self, name, ms, x, y, moveto, damage, sprite = 'fireball.png') -> None: def __init__(self, name, ms, x, y, moveto, damage, sprite = 'weapons/fireball.png', life_ticks=5000) -> None:
super().__init__(name, ms, sprite, x, y, moveto, damage) super().__init__(name, ms, sprite, x, y, moveto, damage, life_ticks)
def move(self):
self.moveto.scale_to_length(self.speed)
self.x += self.moveto[0] / fps
self.y += self.moveto[1] / fps
def update(self, objects): def update(self, objects):
self.move() self.move(objects)
self.die(objects, Mobs) self.die(objects, Mobs)
class Arrow(Weapons):
def __init__(self, name, ms, x, y, moveto, damage, sprite = 'arrow.png') -> None:
super().__init__(name, ms, sprite, x, y, moveto, damage)
def move(self): class Windslash(Spells):
self.moveto.scale_to_length(self.speed) def __init__(self, name, ms, x, y, moveto, damage, sprite = 'weapons/windslash.png', life_ticks=1000) -> None:
self.x += self.moveto[0] / fps super().__init__(name, ms, sprite, x, y, moveto, damage, life_ticks)
self.y += self.moveto[1] / fps
def update(self, objects): def update(self, objects):
self.move() self.move(objects)
self.die(objects, Mobs)
def move(self, objects):
super().move(objects)
self.moveto = self.moveto.rotate(5)
class Arrow(Weapons):
def __init__(self, name, ms, x, y, moveto, damage, sprite = 'weapons/arrow.png', life_ticks=5000) -> None:
super().__init__(name, ms, sprite, x, y, moveto, damage, life_ticks)
def update(self, objects):
self.move(objects)
self.die(objects, MainCharacter) self.die(objects, MainCharacter)
class Punch(Weapons):
def __init__(self, name, ms, x, y, moveto, damage, kills, sprite = 'weapons/empty.png', life_ticks=100) -> None:
super().__init__(name, ms, sprite, x, y, moveto, damage, life_ticks)
self.kills = kills
def update(self, objects):
self.move(objects)
self.die(objects, self.kills)