Train your typing using Typemania! A aesthetic typing test.

Initial commit

WillM 8c2fef7f

Changed files
+1023
__pycache__
save_data
src
+2
.gitattributes
··· 1 + # Auto detect text files and perform LF normalization 2 + * text=auto
__pycache__/client.cpython-39.pyc

This is a binary file and will not be displayed.

__pycache__/game.cpython-39.pyc

This is a binary file and will not be displayed.

__pycache__/input.cpython-39.pyc

This is a binary file and will not be displayed.

__pycache__/notification.cpython-39.pyc

This is a binary file and will not be displayed.

+61
client.py
··· 1 + import pygame, time 2 + from src.scripts.game import Game 3 + 4 + game = Game() 5 + 6 + game.initialize() 7 + 8 + game.typemania.switch_scene("main_screen") 9 + 10 + def begin_update(): 11 + game.begin_update() 12 + 13 + def update(): 14 + game.update() 15 + 16 + if game.typemania.current_scene == "main_screen": 17 + game.typemania.main_screen_scene.update() 18 + elif game.typemania.current_scene == "pack_selection": 19 + game.typemania.pack_selection_scene.update() 20 + elif game.typemania.current_scene == "typing_test": 21 + game.typemania.typing_test_scene.update() 22 + elif game.typemania.current_scene == "result_screen": 23 + game.typemania.result_screen_scene.update() 24 + 25 + def end_update(): 26 + game.end_update() 27 + 28 + def render(): 29 + game.main_surface.fill(game.color_handler.get_color_rgb("typemania.background")) 30 + 31 + if game.typemania.current_scene == "main_screen": 32 + game.typemania.main_screen_scene.render() 33 + elif game.typemania.current_scene == "pack_selection": 34 + game.typemania.pack_selection_scene.render() 35 + if game.typemania.current_scene == "typing_test": 36 + game.typemania.typing_test_scene.render() 37 + elif game.typemania.current_scene == "result_screen": 38 + game.typemania.result_screen_scene.render() 39 + 40 + game.render() 41 + 42 + def stop(): 43 + game.typemania.stop() 44 + 45 + while game.running: 46 + update_start_time = time.time() 47 + begin_update() 48 + 49 + update() 50 + 51 + end_update() 52 + update_end_time = time.time() 53 + 54 + render_start_time = time.time() 55 + render() 56 + render_end_time = time.time() 57 + 58 + game.main_loop_final(update_end_time - update_start_time, render_end_time - render_start_time) 59 + 60 + stop() 61 + pygame.quit()
+1
save_data/typemania_save.json
··· 1 + {"all_plays": [{"quote": "Thank you Mario! But our Princess is in another castle!", "net_wpm": 51, "wpm": 62, "errors": 11}]}
src/__pycache__/__init__.cpython-39.pyc

This is a binary file and will not be displayed.

+4
src/properties.json
··· 1 + { 2 + "id": "Typemania", 3 + "version": "Dev 1" 4 + }
+15
src/resources/main/assets/colors.json
··· 1 + { 2 + "notification.border": "#495b66", 3 + "notification.fill": "#c5d4de", 4 + "notification.text": "#272a2e", 5 + 6 + "options.background": "#141517", 7 + "options.text": "#ebeff5", 8 + 9 + "typemania.background": "#435560", 10 + "typemania.marker": "#6e7c7c", 11 + "typemania.text": "#c8c6a7", 12 + "typemania.dark_text": "#92967d", 13 + "typemania.result_screen_panels": "#576974", 14 + "typemania.result_screen_front": "#4d5f6a" 15 + }
src/resources/main/assets/fonts/default.ttf

This is a binary file and will not be displayed.

src/resources/main/assets/icon.ico

This is a binary file and will not be displayed.

src/resources/main/assets/icon.png

This is a binary file and will not be displayed.

src/resources/main/assets/sounds/error.ogg

This is a binary file and will not be displayed.

src/resources/main/assets/sounds/key_sound_0.ogg

This is a binary file and will not be displayed.

src/resources/main/assets/sounds/key_sound_1.ogg

This is a binary file and will not be displayed.

src/resources/main/assets/sounds/key_sound_2.ogg

This is a binary file and will not be displayed.

src/resources/main/assets/sounds/key_sound_3.ogg

This is a binary file and will not be displayed.

+8
src/resources/main/data/lang/en_US.json
··· 1 + { 2 + "typemania.main_screen.play": "Play", 3 + "typemania.main_screen.options": "Options", 4 + "typemania.main_screen.exit": "Exit", 5 + 6 + "typemania.options.show_fps": "Show FPS", 7 + "typemania.options.reset_save": "Reset Save" 8 + }
+8
src/resources/main/data/lang/sv_SE.json
··· 1 + { 2 + "typemania.main_screen.play": "Spela", 3 + "typemania.main_screen.options": "Installningar", 4 + "typemania.main_screen.exit": "Avsluta", 5 + 6 + "typemania.options.show_fps": "Visa FPS", 7 + "typemania.options.reset_save": "Aterstall sparfil" 8 + }
+9
src/resources/main/data/quote_packs/famous_quotes_1.json
··· 1 + { 2 + "display_name": "Famous Quotes", 3 + "quotes": [ 4 + {"quote": "The quick brown fox jumps over the lazy dog", "author": "The Boston Journal"}, 5 + {"quote": "I have no special talent. I am only passionately curious.", "author": "Albert Einstein"}, 6 + {"quote": "Dont count the days, make the days count.", "author": "Muhammad Ali"}, 7 + {"quote": "A delayed game is eventually good, a bad game is bad forever.", "author": "Shigeru Miyamoto"} 8 + ] 9 + }
+10
src/resources/main/data/quote_packs/video_game_quotes_1.json
··· 1 + { 2 + "display_name": "Videogame Quotes", 3 + "quotes": [ 4 + {"quote": "The right man in the wrong place can make all the difference in the world.", "author": "G-Man"}, 5 + {"quote": "Its time to kick ass and chew bubblegum. And im all outta gum.", "author": "Duke Nukem"}, 6 + {"quote": "Its dangerous to go alone. Take this.", "author": "Old man, TLOZ"}, 7 + {"quote": "...", "author": "Gordon Freeman"}, 8 + {"quote": "Thank you Mario! But our Princess is in another castle!", "author": "Toad"} 9 + ] 10 + }
src/resources/main/icon.ico

This is a binary file and will not be displayed.

src/resources/main/icon.png

This is a binary file and will not be displayed.

src/scripts/__init__.py

This is a binary file and will not be displayed.

src/scripts/__pycache__/__init__.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/__pycache__/colors.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/__pycache__/debug.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/__pycache__/fonts.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/__pycache__/game.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/__pycache__/input.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/__pycache__/lang.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/__pycache__/language.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/__pycache__/notification.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/__pycache__/options.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/__pycache__/sound.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/__pycache__/typemania.cpython-39.pyc

This is a binary file and will not be displayed.

+104
src/scripts/game.py
··· 1 + import pygame, os, json, pyautogui, sys, time 2 + 3 + from .modules.input import Input 4 + from .modules.notification import Notification_Handler 5 + from .modules.language import Language_Handler 6 + from .modules.colors import Color_Handler 7 + from .modules.fonts import Font_Handler 8 + from .modules.sound import Sound_Handler 9 + from .typemania.typemania import typemania 10 + 11 + from .options import options 12 + 13 + class Game: 14 + main_screen = pygame.display.set_mode((1920, 1080)) 15 + main_surface = pygame.Surface((1920, 1080)) 16 + 17 + game_speed = 1 18 + clock = pygame.time.Clock() 19 + 20 + running = True 21 + title = "Game" 22 + 23 + current_assetpack = "main" 24 + 25 + display_width, display_height = pyautogui.size() 26 + 27 + def stop(self): 28 + self.running = False 29 + 30 + def change_title(self, title): 31 + self.title = title 32 + pygame.display.set_caption(title) 33 + 34 + def __init__(self): 35 + self.input = Input() 36 + self.notification_handler = Notification_Handler(self) 37 + self.language_handler = Language_Handler(self) 38 + self.color_handler = Color_Handler(self) 39 + self.font_handler = Font_Handler(self) 40 + self.sound_handler = Sound_Handler(self) 41 + 42 + self.typemania = typemania(self) 43 + 44 + self.display_width, self.display_height = pyautogui.size() 45 + 46 + self.scene_options = options(self) 47 + 48 + self.show_debug = False 49 + 50 + self.previous_time = time.time() 51 + 52 + with open(os.path.join("src", "properties.json"), "r") as file: 53 + self.properties = json.load(file) 54 + 55 + self.change_title(self.properties["id"]) 56 + icon = pygame.image.load(os.path.join("src", "resources", self.current_assetpack, "assets", "icon.png")) 57 + pygame.display.set_icon(icon) 58 + 59 + def initialize(self): 60 + self.notification_handler.send("Successful Start", "Game started succesfully on version " + self.properties["version"]) 61 + self.change_title(self.properties["id"]) 62 + self.input.input_state = "game" 63 + 64 + def begin_update(self): 65 + 66 + # Calculate Delta Time 67 + now = time.time() 68 + self.delta_time = now - self.previous_time 69 + self.previous_time = now 70 + 71 + self.input.any_key_pressed = False 72 + for event in pygame.event.get(): 73 + if event.type == pygame.QUIT: 74 + self.stop() 75 + if event.type == pygame.KEYDOWN: 76 + self.input.any_key_pressed = True 77 + 78 + def update(self): 79 + self.scene_options.update() 80 + 81 + def end_update(self): 82 + self.notification_handler.update() 83 + 84 + self.input.check_keys() 85 + 86 + def render(self): 87 + self.scene_options.render() 88 + 89 + self.notification_handler.render() 90 + 91 + copyright_text = self.font_handler.get_font("default_15").render("willmexe © 2021", True, (self.color_handler.get_color_rgb("typemania.text"))) 92 + self.main_surface.blit(copyright_text, (self.display_width / 2 - copyright_text.get_width() / 2, self.display_height - self.font_handler.get_font_size("default_15") - 10)) 93 + 94 + def main_loop_final(self, update_time, render_time): 95 + if self.scene_options.show_fps == True: 96 + self.scene_options.fps_module.draw_stats(update_time, render_time) 97 + 98 + surf = self.main_surface 99 + if self.main_screen.get_width() != self.main_surface.get_width(): 100 + if self.main_screen.get_height() != self.main_surface.get_height(): 101 + surf = pygame.transform.scale(self.main_surface, (self.main_screen.get_width(), self.main_screen.get_height())) 102 + self.main_screen.blit(surf, (0, 0)) 103 + pygame.display.update() 104 + self.clock.tick(60)
src/scripts/modules/__pycache__/colors.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/modules/__pycache__/debug.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/modules/__pycache__/fonts.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/modules/__pycache__/input.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/modules/__pycache__/language.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/modules/__pycache__/notification.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/modules/__pycache__/sound.cpython-39.pyc

This is a binary file and will not be displayed.

+23
src/scripts/modules/colors.py
··· 1 + import json, os 2 + from colormap import hex2rgb 3 + 4 + class Color_Handler: 5 + def __init__(self, game): 6 + self.game = game 7 + 8 + def get_color_hex(self, color_link): 9 + with open(os.path.join("src", "resources", self.game.current_assetpack, "assets", "colors.json"), "r") as color_file: 10 + color_json = json.load(color_file) 11 + if color_link in color_json: 12 + return color_json[color_link] 13 + else: 14 + return "#00000" 15 + 16 + def get_color_rgb(self, color_link): 17 + with open(os.path.join("src", "resources", self.game.current_assetpack, "assets", "colors.json"), "r") as color_file: 18 + color_json = json.load(color_file) 19 + if color_link in color_json: 20 + return hex2rgb(color_json[color_link]) 21 + else: 22 + return (255, 69, 230) 23 +
+49
src/scripts/modules/fonts.py
··· 1 + import json, os, pygame 2 + pygame.font.init() 3 + 4 + class Font_Handler: 5 + 6 + fonts = { 7 + "Ariel": { 8 + "file": pygame.font.SysFont('Ariel', 35), 9 + "size": 35 10 + } 11 + } 12 + 13 + def load_font(self, font, size, name=""): 14 + font_file = pygame.font.Font(os.path.join("src", "resources", self.game.current_assetpack, "assets", "fonts", font + ".ttf"), size) 15 + if name == "": 16 + self.fonts[font] = { 17 + "file": font_file, 18 + "size": size 19 + } 20 + else: 21 + self.fonts[name] = { 22 + "file": font_file, 23 + "size": size 24 + } 25 + 26 + def get_font(self, font, bold=False, italic=False, underline=False): 27 + if font in self.fonts: 28 + font_file = self.fonts[font]["file"] 29 + 30 + font_file.bold = bold 31 + font_file.italic = italic 32 + font_file.underline = underline 33 + 34 + return font_file 35 + else: 36 + return self.fonts[list(self.fonts.keys())[0]]["file"] 37 + 38 + def get_font_size(self, font): 39 + if font in self.fonts: 40 + return self.fonts[font]["size"] 41 + else: 42 + return self.fonts[list(self.fonts.keys())[0]]["size"] 43 + 44 + def __init__(self, game): 45 + self.game = game 46 + 47 + self.load_font("default", 40) 48 + self.load_font("default", 18, "default_18") 49 + self.load_font("default", 15, "default_15")
+38
src/scripts/modules/input.py
··· 1 + import pygame, keyboard 2 + 3 + class Input: 4 + 5 + input_state = "main" 6 + 7 + record_keys = ["a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "n", "o", "p", "q", "r", "s", "t", "u", "v", "w", "x", "y", "z", 8 + "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", 9 + "UP", "DOWN", "LEFT", "RIGHT", 10 + "SPACE", "CTRL", "SHIFT", "ALT", "RETURN", "ESCAPE", "TAB", "BACKSPACE"] 11 + 12 + def set_input_state(self, state): 13 + self.input_state = state 14 + 15 + def check_keys(self): 16 + for key in self.record_keys: 17 + exec("self.key_" + key + " = " + str(keyboard.is_pressed(key))) 18 + 19 + def __init__(self): 20 + self.check_keys() 21 + 22 + self.any_key_pressed = False 23 + 24 + def is_pressed(self, key, input_state=""): 25 + if input_state != "": 26 + return bool(keyboard.is_pressed(key) and pygame.mouse.get_focused() and input_state == self.input_state) 27 + else: 28 + return bool(keyboard.is_pressed(key) and pygame.mouse.get_focused()) 29 + 30 + def is_just_pressed(self, key, input_state=""): 31 + exec("self.check_key = self.key_" + key) 32 + if input_state != "": 33 + return bool(self.check_key == False and keyboard.is_pressed(key) and input_state == self.input_state) 34 + else: 35 + return bool(self.check_key == False and keyboard.is_pressed(key)) 36 + 37 + def is_any_key_pressed(self): 38 + return self.any_key_pressed
+18
src/scripts/modules/language.py
··· 1 + import json, os 2 + 3 + class Language_Handler: 4 + current_language_id = "en_US" 5 + 6 + def __init__(self, game): 7 + self.game = game 8 + 9 + with open(os.path.join("src", "resources", self.game.current_assetpack, "data", "lang", self.current_language_id + ".json"), "r") as lang_file: 10 + self.lang_json = json.load(lang_file) 11 + 12 + def translatable_text(self, lang_file_link): 13 + if lang_file_link in self.lang_json: 14 + text = self.lang_json[lang_file_link] 15 + return text 16 + else: 17 + return lang_file_link 18 +
+54
src/scripts/modules/notification.py
··· 1 + import pygame 2 + from pygame import display 3 + 4 + class Notification_Handler: 5 + 6 + notifications = [] 7 + 8 + def __init__(self, game): 9 + self.game = game 10 + 11 + def send(self, title, message): 12 + print("[" + title + "] " + message) 13 + self.notifications.append({"title": title, "message": message, "time": 300}) 14 + 15 + def render(self): 16 + height = 0 17 + last_end_y = 22 18 + 19 + for index, notification in enumerate(self.notifications): 20 + display_text = [] 21 + current = "" 22 + message = notification["message"].split(" ") 23 + for index, word in enumerate(message): 24 + if current != "": 25 + current += " " + word 26 + else: 27 + current += word 28 + if index < len(message) - 1: 29 + if len(current + message[index + 1]) > 30: 30 + display_text.append(current) 31 + current = "" 32 + 33 + display_text.append(current) 34 + 35 + height = 32 + (15 * len(display_text)) 36 + pygame.draw.rect(self.game.main_surface, self.game.color_handler.get_color_rgb("notification.border"), ((self.game.main_surface.get_width() - 250, last_end_y), (230, height)), False, 10) 37 + pygame.draw.rect(self.game.main_surface, self.game.color_handler.get_color_rgb("notification.fill"), ((self.game.main_surface.get_width() - 246, last_end_y + 4), (222, height - 8)), False, 10) 38 + 39 + title_surface = self.game.font_handler.get_font("default_18", bold=True).render(notification["title"], True, self.game.color_handler.get_color_rgb("notification.text")) 40 + self.game.main_surface.blit(title_surface, (self.game.main_surface.get_width() - 241, last_end_y + 2)) 41 + 42 + for i, notif in enumerate(display_text): 43 + title_surface = self.game.font_handler.get_font("default_15").render(notif, True, self.game.color_handler.get_color_rgb("notification.text")) 44 + self.game.main_surface.blit(title_surface, (self.game.main_surface.get_width() - 241, last_end_y + (i * 14) + 20)) 45 + 46 + last_end_y = height + 20 + last_end_y 47 + 48 + def update(self): 49 + new_notif = self.notifications.copy() 50 + for index, notification in enumerate(self.notifications): 51 + self.notifications[index]["time"] -= 1 52 + if self.notifications[index]["time"] <= 0: 53 + new_notif.pop(new_notif.index(self.notifications[index])) 54 + self.notifications = new_notif
src/scripts/modules/options/__init__.py

This is a binary file and will not be displayed.

src/scripts/modules/options/__pycache__/__init__.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/modules/options/__pycache__/fps.cpython-39.pyc

This is a binary file and will not be displayed.

+36
src/scripts/modules/options/fps.py
··· 1 + import pygame, math 2 + 3 + class fps: 4 + 5 + def __init__(self, game): 6 + self.game = game 7 + 8 + self.update_filler_text = self.game.font_handler.get_font("default_18").render("Update: Fps ( ms)", True, self.game.color_handler.get_color_rgb("options.text")) 9 + self.render_filler_text = self.game.font_handler.get_font("default_18").render("Render: Fps ( ms)", True, self.game.color_handler.get_color_rgb("options.text")) 10 + self.total_filler_text = self.game.font_handler.get_font("default_18").render( "Total : Fps ( ms)", True, self.game.color_handler.get_color_rgb("options.text")) 11 + 12 + def draw_stats(self, update_time, draw_time): 13 + s = pygame.Surface((260, 90), pygame.SRCALPHA) 14 + pygame.draw.rect(s, self.game.color_handler.get_color_rgb("options.background"), ((0, 0), (270, 100)), False, 10) 15 + s.set_alpha(128) 16 + self.game.main_surface.blit(s, (self.game.display_width - 260, self.game.display_height - 90)) 17 + 18 + update_fps_text = self.game.font_handler.get_font("default_18").render(str(1 / max(update_time, 0.0001)).split(".")[0], True, self.game.color_handler.get_color_rgb("options.text")) 19 + render_fps_text = self.game.font_handler.get_font("default_18").render(str(1 / max(draw_time, 0.0001)).split(".")[0], True, self.game.color_handler.get_color_rgb("options.text")) 20 + total_fps_text = self.game.font_handler.get_font("default_18").render(str(1 / max(draw_time + update_time, 0.0001)).split(".")[0], True, self.game.color_handler.get_color_rgb("options.text")) 21 + 22 + update_time_text = self.game.font_handler.get_font("default_18").render(str(update_time * 1000)[0: 5], True, self.game.color_handler.get_color_rgb("options.text")) 23 + render_time_text = self.game.font_handler.get_font("default_18").render(str(draw_time * 1000)[0: 5], True, self.game.color_handler.get_color_rgb("options.text")) 24 + total_time_text = self.game.font_handler.get_font("default_18").render(str((draw_time + update_time) * 1000)[0: 5], True, self.game.color_handler.get_color_rgb("options.text")) 25 + 26 + self.game.main_surface.blit(self.update_filler_text, (self.game.display_width - 250, self.game.display_height - update_fps_text.get_height() - 10)) 27 + self.game.main_surface.blit(self.render_filler_text, (self.game.display_width - 250, self.game.display_height - render_fps_text.get_height() * 2 - 10)) 28 + self.game.main_surface.blit(self.total_filler_text, (self.game.display_width - 250, self.game.display_height - total_fps_text.get_height() * 3 - 10)) 29 + 30 + self.game.main_surface.blit(update_fps_text, (self.game.display_width - 182, self.game.display_height - update_fps_text.get_height() - 10)) 31 + self.game.main_surface.blit(render_fps_text, (self.game.display_width - 182, self.game.display_height - render_fps_text.get_height() * 2 - 10)) 32 + self.game.main_surface.blit(total_fps_text, (self.game.display_width - 182, self.game.display_height - total_fps_text.get_height() * 3 - 10)) 33 + 34 + self.game.main_surface.blit(update_time_text, (self.game.display_width - 90, self.game.display_height - update_time_text.get_height() - 10)) 35 + self.game.main_surface.blit(render_time_text, (self.game.display_width - 90, self.game.display_height - render_time_text.get_height() * 2 - 10)) 36 + self.game.main_surface.blit(total_time_text, (self.game.display_width - 90, self.game.display_height - total_time_text.get_height() * 3 - 10))
+17
src/scripts/modules/sound.py
··· 1 + import pygame, os 2 + pygame.mixer.init() 3 + 4 + class Sound_Handler: 5 + 6 + sounds = {} 7 + 8 + def __init__(self, game): 9 + self.game = game 10 + 11 + def load_sound(self, sound_id, sound_file): 12 + self.sounds[sound_id] = { 13 + "file": pygame.mixer.Sound(os.path.join("src", "resources", self.game.current_assetpack, "assets", "sounds", sound_file + ".ogg")) 14 + } 15 + 16 + def play_sound(self, sound_id): 17 + self.sounds[sound_id]["file"].play()
+81
src/scripts/options.py
··· 1 + import pygame 2 + from .modules.options.fps import fps 3 + 4 + class options: 5 + 6 + def __init__(self, game): 7 + self.game = game 8 + 9 + self.open = False 10 + 11 + self.show_fps = False 12 + 13 + self.fps_module = fps(game) 14 + 15 + self.menu_id = 0 16 + 17 + self.marker_target_y = 200 + (self.menu_id * 70) 18 + self.marker_y = self.marker_target_y 19 + 20 + self.marker_x = 90 21 + 22 + self.show_fps_text_surface = self.game.font_handler.get_font("default").render(self.game.language_handler.translatable_text("typemania.options.show_fps") + ": " + str(self.show_fps), True, (self.game.color_handler.get_color_rgb("typemania.text"))) 23 + self.reset_save_text_surface = self.game.font_handler.get_font("default").render(self.game.language_handler.translatable_text("typemania.options.reset_save"), True, (self.game.color_handler.get_color_rgb("typemania.text"))) 24 + 25 + self.marker_target_width = self.show_fps_text_surface.get_width() + 20 26 + self.marker_width = self.marker_target_width 27 + 28 + self.bg_target_x = -1000 29 + self.bg_x = self.bg_target_x 30 + 31 + def update(self): 32 + self.bg_x += (self.bg_target_x - self.bg_x) / 10 33 + if self.open: 34 + self.bg_target_x = 5 35 + self.game.input.input_state = "options" 36 + if self.game.input.is_pressed("esc"): 37 + self.open = False 38 + 39 + if self.game.input.is_just_pressed("DOWN"): 40 + self.menu_id += 1 41 + if self.game.input.is_just_pressed("UP"): 42 + self.menu_id -= 1 43 + 44 + self.show_fps_text_surface = self.game.font_handler.get_font("default").render(self.game.language_handler.translatable_text("typemania.options.show_fps") + ": " + str(self.show_fps), True, (self.game.color_handler.get_color_rgb("typemania.text"))) 45 + 46 + self.marker_target_y = 270 + (self.menu_id * 140) - 25 47 + self.marker_y += (self.marker_target_y - self.marker_y) / 8 48 + self.marker_width += (self.marker_target_width - self.marker_width) / 20 49 + 50 + if self.menu_id < 0: 51 + self.menu_id = 1 52 + if self.menu_id > 1: 53 + self.menu_id = 0 54 + 55 + if self.menu_id == 0: 56 + self.marker_target_width = self.show_fps_text_surface.get_width() + 20 57 + if self.menu_id == 1: 58 + self.marker_target_width = self.reset_save_text_surface.get_width() + 20 59 + 60 + if self.game.input.is_just_pressed("SPACE") or self.game.input.is_just_pressed("RETURN"): 61 + if self.menu_id == 0: 62 + self.show_fps = not self.show_fps 63 + if self.menu_id == 1: 64 + self.game.typemania.save_file = {"all_plays": []} 65 + self.game.notification_handler.send("Save File Reset", "Typemania save file has been reset from the options menu.") 66 + 67 + else: 68 + self.game.input.input_state = "game" 69 + self.bg_target_x = -1000 70 + 71 + if self.game.input.is_pressed("ctrl") and self.game.input.is_just_pressed("o"): 72 + self.open = not self.open 73 + 74 + def render(self): 75 + pygame.draw.rect(self.game.main_surface, self.game.color_handler.get_color_rgb("options.background"), ((self.bg_x, 5), (500, self.game.display_height - 10)), False, 5) 76 + 77 + if self.open: 78 + pygame.draw.rect(self.game.main_surface, self.game.color_handler.get_color_rgb("typemania.marker"), ((self.marker_x, self.marker_y), (self.marker_width, 5)), False, 5) 79 + 80 + self.game.main_surface.blit(self.show_fps_text_surface, (100, 200)) 81 + self.game.main_surface.blit(self.reset_save_text_surface, (100, 340))
src/scripts/typemania/__init__.py

This is a binary file and will not be displayed.

src/scripts/typemania/__pycache__/__init__.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/typemania/__pycache__/typemania.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/typemania/scenes/__init__.py

This is a binary file and will not be displayed.

src/scripts/typemania/scenes/__pycache__/__init__.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/typemania/scenes/__pycache__/scene_main_screen.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/typemania/scenes/__pycache__/scene_pack_selection.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/typemania/scenes/__pycache__/scene_result_screen.cpython-39.pyc

This is a binary file and will not be displayed.

src/scripts/typemania/scenes/__pycache__/scene_type_test.cpython-39.pyc

This is a binary file and will not be displayed.

+78
src/scripts/typemania/scenes/scene_main_screen.py
··· 1 + import pygame, random 2 + from colormap import hex2rgb 3 + pygame.init() 4 + pygame.font.init() 5 + 6 + class main_screen: 7 + 8 + def __init__(self, game): 9 + self.game = game 10 + 11 + self.play_text_surface = self.game.font_handler.get_font("default").render(self.game.language_handler.translatable_text("typemania.main_screen.play"), True, (self.game.color_handler.get_color_rgb("typemania.text"))) 12 + self.options_text_surface = self.game.font_handler.get_font("default").render(self.game.language_handler.translatable_text("typemania.main_screen.options"), True, (self.game.color_handler.get_color_rgb("typemania.text"))) 13 + self.exit_text_surface = self.game.font_handler.get_font("default").render(self.game.language_handler.translatable_text("typemania.main_screen.exit"), True, (self.game.color_handler.get_color_rgb("typemania.text"))) 14 + 15 + self.menu_id = 0 16 + 17 + self.marker_target_y = (self.game.display_height / 2) + (70 * self.menu_id) + 10 18 + self.marker_y = self.marker_target_y 19 + 20 + if self.menu_id == 0: 21 + self.marker_target_width = self.play_text_surface.get_width() 22 + if self.menu_id == 1: 23 + self.marker_target_width = self.options_text_surface.get_width() 24 + if self.menu_id == 2: 25 + self.marker_target_width = self.exit_text_surface.get_width() 26 + 27 + self.marker_target_x = (self.game.display_width / 2) - (self.marker_target_width / 2) - 10 28 + self.marker_target_width += 20 29 + 30 + self.marker_width = self.marker_target_width 31 + self.marker_x = self.marker_target_x 32 + 33 + self.marker_x = self.marker_target_x 34 + 35 + def update(self): 36 + 37 + if self.game.input.is_just_pressed("UP", "game"): 38 + self.menu_id -= 1 39 + if self.game.input.is_just_pressed("DOWN", "game"): 40 + self.menu_id += 1 41 + 42 + if self.game.input.is_just_pressed("SPACE", "game") or self.game.input.is_just_pressed("RETURN", "game"): 43 + if self.menu_id == 0: 44 + self.game.typemania.switch_scene("pack_selection") 45 + #self.game.typemania.start_quote(random.randint(0, len(self.game.typemania.quotes) - 1)) 46 + if self.menu_id == 1: 47 + self.game.scene_options.open = True 48 + if self.menu_id == 2: 49 + self.game.stop() 50 + 51 + if self.menu_id < 0: 52 + self.menu_id = 2 53 + if self.menu_id > 2: 54 + self.menu_id = 0 55 + 56 + self.marker_target_y = (self.game.display_height / 2) + (70 * self.menu_id) + 10 57 + self.marker_y += (self.marker_target_y - self.marker_y) / 8 58 + 59 + self.marker_width += (self.marker_target_width - self.marker_width) / 10 60 + self.marker_x += (self.marker_target_x - self.marker_x) / 10 61 + 62 + if self.menu_id == 0: 63 + self.marker_target_width = self.play_text_surface.get_width() 64 + if self.menu_id == 1: 65 + self.marker_target_width = self.options_text_surface.get_width() 66 + if self.menu_id == 2: 67 + self.marker_target_width = self.exit_text_surface.get_width() 68 + 69 + self.marker_target_x = (self.game.display_width / 2) - (self.marker_target_width / 2) - 10 70 + self.marker_target_width += 20 71 + 72 + def render(self): 73 + 74 + pygame.draw.rect(self.game.main_surface, (self.game.color_handler.get_color_rgb("typemania.marker")), ((self.marker_x, self.marker_y), (self.marker_width, 5)), False, 5) 75 + 76 + self.game.main_surface.blit(self.play_text_surface, (self.game.display_width / 2 - self.play_text_surface.get_width() / 2, self.game.display_height / 2 - self.game.font_handler.get_font_size("default_42"))) 77 + self.game.main_surface.blit(self.options_text_surface, (self.game.display_width / 2 - self.options_text_surface.get_width() / 2, self.game.display_height / 2 + self.game.font_handler.get_font_size("default_42"))) 78 + self.game.main_surface.blit(self.exit_text_surface, (self.game.display_width / 2 - self.exit_text_surface.get_width() / 2, self.game.display_height / 2 + self.game.font_handler.get_font_size("default_42") * 3))
+69
src/scripts/typemania/scenes/scene_pack_selection.py
··· 1 + import pygame, random, os, json 2 + from colormap import hex2rgb 3 + pygame.init() 4 + pygame.font.init() 5 + 6 + class pack_selection: 7 + 8 + def __init__(self, game): 9 + self.game = game 10 + 11 + self.menu_id = 0 12 + 13 + quote_packs = os.listdir(os.path.join('src', 'resources', self.game.current_assetpack, 'data', 'quote_packs')) 14 + fixed_quote_packs = [] 15 + 16 + for i in quote_packs: 17 + with open(os.path.join('src', 'resources', self.game.current_assetpack, 'data', 'quote_packs', i)) as file: 18 + fixed_quote_packs.append(json.load(file)) 19 + 20 + self.quote_packs = fixed_quote_packs 21 + 22 + self.quote_pack_target_y = [] 23 + self.quote_pack_y = [] 24 + for i in range(len(self.quote_packs)): 25 + self.quote_pack_target_y.append(self.game.display_height / 2 - ((i - self.menu_id) * 70)) 26 + self.quote_pack_y.append(self.game.display_height / 2 - ((i - self.menu_id) * 70)) 27 + 28 + self.marker_target_width = 0 29 + self.marker_width = self.marker_target_width 30 + 31 + self.marker_target_x = self.game.display_width / 2 32 + self.marker_x = self.marker_target_x 33 + self.marker_y = self.game.display_height / 2 + 50 34 + 35 + def update(self): 36 + if self.game.input.is_just_pressed("UP", "game"): 37 + self.menu_id += 1 38 + if self.game.input.is_just_pressed("DOWN", "game"): 39 + self.menu_id -= 1 40 + 41 + if self.game.input.is_just_pressed("RETURN", "game") or self.game.input.is_just_pressed("SPACE", "game"): 42 + self.game.typemania.quotes = self.quote_packs[self.menu_id]["quotes"] 43 + self.game.typemania.start_quote(random.randint(0, len(self.game.typemania.quotes) - 1)) 44 + 45 + if self.menu_id < 0: 46 + self.menu_id = len(self.quote_packs) - 1 47 + if self.menu_id > len(self.quote_packs) - 1: 48 + self.menu_id = 0 49 + 50 + for i in range(len(self.quote_packs)): 51 + self.quote_pack_target_y[i] = self.game.display_height / 2 - ((i - self.menu_id) * 70) 52 + self.quote_pack_y[i] += (self.quote_pack_target_y[i] - self.quote_pack_y[i]) / 10 53 + 54 + self.marker_width += (self.marker_target_width - self.marker_width) / 10 55 + self.marker_x += (self.marker_target_x - self.marker_x) / 10 56 + 57 + def render(self): 58 + 59 + pygame.draw.rect(self.game.main_surface, (self.game.color_handler.get_color_rgb("typemania.marker")), ((self.marker_x, self.marker_y), (self.marker_width, 5)), False, 5) 60 + 61 + for index, quote_pack in enumerate(self.quote_packs): 62 + text_surface = self.game.font_handler.get_font("default").render(quote_pack['display_name'], True, (self.game.color_handler.get_color_rgb("typemania.text"))) 63 + if self.menu_id - index == 0: 64 + self.marker_target_width = text_surface.get_width() + 20 65 + self.marker_target_x = self.game.display_width / 2 - text_surface.get_width() / 2 - 10 66 + else: 67 + text_surface.set_alpha(256 / (abs(self.menu_id - index) * 1)) 68 + 69 + self.game.main_surface.blit(text_surface, (self.game.display_width / 2 - text_surface.get_width() / 2, self.quote_pack_y[index]))
+121
src/scripts/typemania/scenes/scene_result_screen.py
··· 1 + import pygame, pyautogui 2 + from colormap import hex2rgb 3 + from pygame import display 4 + pygame.init() 5 + pygame.font.init() 6 + 7 + class result_screen: 8 + 9 + def __init__(self, game): 10 + self.game = game 11 + 12 + self.menu_id = 0 13 + 14 + self.marker_y = self.game.display_height - 70 15 + 16 + self.has_init = False 17 + 18 + self.wpm_target_x = self.game.display_width / 2 + 150 19 + self.wpm_x = self.game.display_width / 2 - 175 20 + 21 + self.avg_wpm_target_x = self.game.display_width / 2 + 400 22 + self.avg_wpm_x = self.game.display_width / 2 - 175 23 + 24 + self.err_target_x = self.game.display_width / 2 + 150 25 + self.err_x = self.game.display_width / 2 - 175 26 + 27 + self.time = 0 28 + 29 + def initialize(self): 30 + self.has_init = True 31 + self.display_quote = [] 32 + quote = '"' + self.game.typemania.quotes[self.quote]["quote"] + '"' 33 + message = quote.split(" ") 34 + current = "" 35 + for index, word in enumerate(message): 36 + if current != "": 37 + current += " " + word 38 + else: 39 + current += word 40 + if index < len(message) - 1: 41 + if len(current + message[index + 1]) > 30: 42 + self.display_quote.append(current) 43 + current = "" 44 + 45 + self.display_quote.append(current) 46 + 47 + self.back_text_surface = self.game.font_handler.get_font("default").render("Back", True, self.game.color_handler.get_color_rgb("typemania.text")) 48 + 49 + self.author_text_surface = self.game.font_handler.get_font("default").render("-" + self.game.typemania.quotes[self.quote]["author"], True, self.game.color_handler.get_color_rgb("typemania.text")) 50 + self.wpm_text_surface = self.game.font_handler.get_font("default").render("WPM: " + str(int(self.net_wpm)), True, self.game.color_handler.get_color_rgb("typemania.text")) 51 + self.err_text_surface = self.game.font_handler.get_font("default").render("Errors: " + str(self.errors), True, self.game.color_handler.get_color_rgb("typemania.text")) 52 + 53 + all_wpm_added = 0 54 + for score in self.game.typemania.save_file["all_plays"]: 55 + all_wpm_added += score["net_wpm"] 56 + 57 + avg_wpm = int(all_wpm_added / max(len(self.game.typemania.save_file["all_plays"]), 0.0000001)) 58 + self.avg_wpm_text_surface = self.game.font_handler.get_font("default").render("Avg. WPM: " + str(avg_wpm), True, self.game.color_handler.get_color_rgb("typemania.text")) 59 + 60 + self.back_text_surface = self.game.font_handler.get_font("default").render("Back", True, self.game.color_handler.get_color_rgb("typemania.text")) 61 + 62 + self.polysurf = pygame.Surface((self.game.display_height - 450, self.game.display_height - 450), pygame.SRCALPHA) 63 + #pygame.draw.rect(self.game.main_surface, self.game.color_handler.get_color_rgb("typemania.result_screen_front"), ((self.game.display_width / 2 - (self.game.display_height - 200) / 2, 100), (self.game.display_height - 200, self.game.display_height - 200))) 64 + pygame.draw.rect(self.polysurf, self.game.color_handler.get_color_rgb("typemania.result_screen_front"), ((0, 0), (self.game.display_height - 450, self.game.display_height - 450)), False, 40) 65 + 66 + self.has_init = True 67 + 68 + self.bg_y = 700 69 + self.bg_target_y = 100 70 + 71 + def reset(self): 72 + self.has_init = False 73 + self.time = 0 74 + self.avg_wpm_x = self.game.display_width / 2 - 175 75 + self.wpm_x = self.game.display_width / 2 - 175 76 + self.err_x = self.game.display_width / 2 - 175 77 + self.bg_y = -700 78 + 79 + def update(self): 80 + self.time += 1 81 + 82 + if self.has_init == False: 83 + self.initialize() 84 + 85 + self.bg_y += (self.bg_target_y - self.bg_y) / 20 86 + 87 + if self.time >= 90: 88 + self.bg_y = self.bg_target_y 89 + self.wpm_x += (self.wpm_target_x - self.wpm_x) / 20 90 + self.avg_wpm_x += (self.avg_wpm_target_x - self.avg_wpm_x) / 20 91 + self.err_x += (self.err_target_x - self.err_x) / 20 92 + 93 + if self.game.input.is_just_pressed("SPACE", "game"): 94 + self.reset() 95 + self.game.typemania.switch_scene("main_screen") 96 + 97 + def render(self): 98 + if self.has_init == False: 99 + self.initialize() 100 + 101 + if self.time >= 90: 102 + pygame.draw.rect(self.game.main_surface, self.game.color_handler.get_color_rgb("typemania.result_screen_panels"), ((self.wpm_x, self.game.display_height / 4 + 25), (350, 60)), False, 5) 103 + self.game.main_surface.blit(self.wpm_text_surface, (self.wpm_x + 110, self.game.display_height / 4 + 25)) 104 + 105 + pygame.draw.rect(self.game.main_surface, self.game.color_handler.get_color_rgb("typemania.result_screen_panels"), ((self.avg_wpm_x, self.game.display_height / 2 - 25), (350, 60)), False, 5) 106 + self.game.main_surface.blit(self.avg_wpm_text_surface, (self.avg_wpm_x + 55, self.game.display_height / 2 - 25)) 107 + 108 + pygame.draw.rect(self.game.main_surface, self.game.color_handler.get_color_rgb("typemania.result_screen_panels"), ((self.err_x, self.game.display_height - self.game.display_height / 4 - 75), (350, 60)), False, 5) 109 + self.game.main_surface.blit(self.err_text_surface, (self.err_x + 110, self.game.display_height - self.game.display_height / 4 - 75)) 110 + 111 + self.game.main_surface.blit(pygame.transform.rotate(self.polysurf, 45), (self.game.display_width / 2 - (self.game.display_height - 200) / 2, self.bg_y)) 112 + 113 + self.game.main_surface.blit(self.author_text_surface, (self.game.display_width / 2 - self.author_text_surface.get_width() / 2, self.game.display_height / 3 + 45 * len(self.display_quote) + 50 + self.bg_y)) 114 + 115 + for index, line in enumerate(self.display_quote): 116 + quote_text_surface = self.game.font_handler.get_font("default").render(line, True, self.game.color_handler.get_color_rgb("typemania.text")) 117 + self.game.main_surface.blit(quote_text_surface, (self.game.display_width / 2 - quote_text_surface.get_width() / 2, self.game.display_height / 3 + 45 * index + 20 + self.bg_y)) 118 + 119 + pygame.draw.rect(self.game.main_surface, self.game.color_handler.get_color_rgb("typemania.marker"), ((70, self.marker_y), (100, 5)), False, 5) 120 + 121 + self.game.main_surface.blit(self.back_text_surface, (70, self.game.display_height - 70 - self.back_text_surface.get_height()))
+158
src/scripts/typemania/scenes/scene_type_test.py
··· 1 + import pygame 2 + from colormap import hex2rgb 3 + pygame.init() 4 + pygame.font.init() 5 + 6 + class typing_test: 7 + 8 + def __init__(self, game): 9 + self.game = game 10 + 11 + self.marker_height = 5 12 + self.marker_width = 25 13 + self.marker_target_width = 25 14 + 15 + self.marker_x = 0 16 + self.marker_y = self.game.display_height / 2 - self.marker_height + 13 17 + 18 + self.marker_draw_x = self.marker_x 19 + self.marker_draw_y = self.marker_y 20 + 21 + self.type_this = "" 22 + self.typed_text = "" 23 + 24 + self.typed_entries = 0 25 + 26 + self.errors = 0 27 + self.wpm = 0 28 + 29 + self.done = False 30 + 31 + self.time = 1 32 + 33 + self.game.sound_handler.load_sound("error", "error") 34 + 35 + self.has_started = False 36 + 37 + self.next_letter = self.game.font_handler.get_font("default").render("H", True, self.game.color_handler.get_color_rgb("typemania.text")) 38 + 39 + self.black_cover_surf = pygame.Surface((1, 1), pygame.SRCALPHA) 40 + pygame.draw.rect(self.black_cover_surf, self.game.color_handler.get_color_rgb("options.background"), ((0, 0), (1, 1))) 41 + self.black_cover_surf.set_alpha(230) 42 + 43 + self.wpm = (self.typed_entries / 5) / (self.time / 60 / 60) 44 + self.net_wpm = self.wpm - (self.errors / max(int((self.time / 60) / 60), 1)) 45 + 46 + self.net_wpm = max(self.net_wpm, 0) 47 + 48 + self.wpm_surface = self.game.font_handler.get_font("default").render("WPM: " + str(int(self.net_wpm)), True, self.game.color_handler.get_color_rgb("typemania.text")) 49 + 50 + self.text = self.game.font_handler.get_font("default").render(self.type_this, True, self.game.color_handler.get_color_rgb("typemania.text")) 51 + self.typed_text_surface = self.game.font_handler.get_font("default").render(self.typed_text, True, self.game.color_handler.get_color_rgb("typemania.dark_text")) 52 + 53 + self.y_offset_when_done = 0 54 + self.y_offset_when_done_target = 700 55 + 56 + self.game_done = False 57 + 58 + def reset(self): 59 + self.has_started = False 60 + self.typed_text = "" 61 + 62 + self.typed_entries = 0 63 + 64 + self.errors = 0 65 + self.wpm = 0 66 + 67 + self.done = False 68 + self.game_done = False 69 + 70 + self.time = 1 71 + self.y_offset_when_done = 0 72 + 73 + def update(self): 74 + self.time += 1 75 + if self.has_started and not self.game_done: 76 + 77 + if self.game.input.is_any_key_pressed(): 78 + if len(self.type_this) != len(self.typed_text): 79 + if self.type_this[len(self.typed_text)].lower() == " ": 80 + exec('self.tmp_key = "SPACE"') 81 + else: 82 + exec('self.tmp_key = "' + self.type_this[len(self.typed_text)].lower() + '"') 83 + if self.game.input.is_pressed(self.tmp_key, "game"): 84 + self.game.typemania.play_key_sound() 85 + self.typed_text += self.type_this[len(self.typed_text)] 86 + if self.tmp_key != "SPACE": 87 + self.typed_entries += 1 88 + else: 89 + if not self.game.input.is_pressed("shift"): 90 + self.game.sound_handler.play_sound("error") 91 + self.errors += 1 92 + 93 + else: 94 + if self.game.input.is_pressed(self.type_this[0]): 95 + self.has_started = True 96 + self.game.typemania.play_key_sound() 97 + if len(self.type_this) != len(self.typed_text): 98 + self.typed_text += self.type_this[len(self.typed_text)] 99 + self.typed_entries += 1 100 + 101 + self.marker_draw_x += (self.marker_x - self.marker_draw_x) / 10 102 + self.marker_draw_y += (self.marker_y - self.marker_draw_y) / 10 103 + 104 + self.text = self.game.font_handler.get_font("default").render(self.type_this, True, self.game.color_handler.get_color_rgb("typemania.text")) 105 + self.typed_text_surface = self.game.font_handler.get_font("default").render(self.typed_text, True, self.game.color_handler.get_color_rgb("typemania.dark_text")) 106 + self.marker_x = self.game.display_width / 2 - self.text.get_width() / 2 + self.typed_text_surface.get_width() 107 + 108 + self.wpm_surface = self.game.font_handler.get_font("default").render("WPM: " + str(int(self.net_wpm)), True, self.game.color_handler.get_color_rgb("typemania.text")) 109 + 110 + if len(self.type_this) != len(self.typed_text): 111 + self.next_letter = self.game.font_handler.get_font("default").render(self.type_this[len(self.typed_text)], True, self.game.color_handler.get_color_rgb("typemania.text")) 112 + self.marker_target_width = self.next_letter.get_width() 113 + self.marker_width += (self.marker_target_width - self.marker_width) / 10 114 + 115 + if self.game_done: 116 + self.y_offset_when_done += (self.y_offset_when_done_target - self.y_offset_when_done) / 20 117 + 118 + if self.time >= 40: 119 + self.game.typemania.show_result_screen(self.quote, int(self.net_wpm), self.errors) 120 + self.reset() 121 + 122 + else: 123 + self.wpm = (self.typed_entries / 5) / (self.time / 60 / 60) 124 + self.net_wpm = self.wpm - (self.errors / max(int((self.time / 60) / 60), 1)) 125 + 126 + self.net_wpm = max(self.net_wpm, 0) 127 + 128 + 129 + if len(self.type_this) == len(self.typed_text): 130 + self.game.typemania.save_file['all_plays'].append({ 131 + "quote": self.game.typemania.quotes[self.quote]["quote"], 132 + "net_wpm": int(self.net_wpm), 133 + "wpm": int(self.wpm), 134 + "errors": self.errors 135 + }) 136 + #self.game.typemania.show_result_screen(self.quote, int(net_wpm), self.errors) 137 + self.time = 0 138 + self.game_done = True 139 + #self.reset() 140 + 141 + def render(self): 142 + 143 + self.game.main_surface.blit(self.text, (self.game.display_width / 2 - self.text.get_width() / 2, self.game.display_height / 2 - 42 + self.y_offset_when_done)) 144 + self.game.main_surface.blit(self.typed_text_surface, (self.game.display_width / 2 - self.text.get_width() / 2, self.game.display_height / 2 - 42 + self.y_offset_when_done)) 145 + 146 + if self.has_started: 147 + pygame.draw.rect(self.game.main_surface, self.game.color_handler.get_color_rgb("typemania.marker"), ((self.marker_draw_x, self.marker_draw_y + self.y_offset_when_done), (self.marker_width, self.marker_height)), False, 5) 148 + 149 + self.game.main_surface.blit(self.wpm_surface, (self.game.display_width / 2 - self.text.get_width() / 2, self.game.display_height / 2 - 126 + self.y_offset_when_done)) 150 + 151 + if not self.has_started: 152 + self.game.main_surface.blit(pygame.transform.scale(self.black_cover_surf, (self.game.main_surface.get_width(), self.game.main_surface.get_height())), (0, 0)) 153 + 154 + letter = self.type_this[0] 155 + if letter == 'I': 156 + letter = letter.lower() 157 + press_x_to_start = self.game.font_handler.get_font("default").render("Press '" + letter + "' to start", True, self.game.color_handler.get_color_rgb("typemania.text")) 158 + self.game.main_surface.blit(press_x_to_start, (self.game.display_width / 2 - press_x_to_start.get_width() / 2, 200))
+59
src/scripts/typemania/typemania.py
··· 1 + import json, pygame, random, os 2 + from .scenes.scene_main_screen import main_screen 3 + from .scenes.scene_result_screen import result_screen 4 + from .scenes.scene_type_test import typing_test 5 + from .scenes.scene_pack_selection import pack_selection 6 + 7 + pygame.mixer.init() 8 + 9 + class typemania: 10 + 11 + def __init__(self, game): 12 + self.game = game 13 + 14 + self.typing_test_scene = typing_test(self.game) 15 + self.result_screen_scene = result_screen(self.game) 16 + self.main_screen_scene = main_screen(self.game) 17 + self.pack_selection_scene = pack_selection(self.game) 18 + 19 + self.game.sound_handler.load_sound("key_sound_0", "key_sound_0") 20 + self.game.sound_handler.load_sound("key_sound_1", "key_sound_1") 21 + self.game.sound_handler.load_sound("key_sound_2", "key_sound_2") 22 + self.game.sound_handler.load_sound("key_sound_3", "key_sound_3") 23 + 24 + if not os.path.exists(os.path.join("save_data", "typemania_save.json")): 25 + with open(os.path.join("save_data", "typemania_save.json"), "w") as file: 26 + file.write('{"all_plays": []}') 27 + with open(os.path.join("save_data", "typemania_save.json"), "r") as file_save_file: 28 + self.save_file = json.load(file_save_file) 29 + 30 + quotes = [{'quote': 'The quick brown fox jumps over the lazy dog', 'author': 'The Boston Journal'}, 31 + {'quote': 'I have no special talent. I am only passionately curious.', 'author': 'Albert Einstein'}, 32 + {'quote': 'Dont count the days, make the days count.', 'author': 'Muhammad Ali'}] 33 + 34 + current_scene = "" 35 + 36 + clock = pygame.time.Clock() 37 + dt = 0 38 + 39 + def play_key_sound(self): 40 + random_int = random.randint(0, 3) 41 + self.game.sound_handler.play_sound("key_sound_" + str(random_int)) 42 + 43 + def switch_scene(self, scene): 44 + self.current_scene = scene 45 + 46 + def start_quote(self, quote): 47 + self.typing_test_scene.type_this = self.quotes[quote]["quote"] 48 + self.typing_test_scene.quote = quote 49 + self.switch_scene("typing_test") 50 + 51 + def show_result_screen(self, quote, net_wpm, errors): 52 + self.result_screen_scene.quote = quote 53 + self.result_screen_scene.net_wpm = net_wpm 54 + self.result_screen_scene.errors = errors 55 + self.switch_scene("result_screen") 56 + 57 + def stop(self): 58 + with open(os.path.join("save_data", "typemania_save.json"), "w") as file: 59 + file.write(str(self.save_file).replace("'", '"'))