Skip to content

Commit

Permalink
Reorganised homescreen methods and added more global settings
Browse files Browse the repository at this point in the history
Split the `_make_frames` and `_make_content` so they each have their own function to place themselves.

Added the layout for the `CrosswordBrowser` class which will let the user view all the available crosswords definition sets.

`change_appearance` and `change_scale` have been implemented to allow the user to switch appearance and increase or decrease scale with optionmenus.

Added some additional informational files for each crossword (all the files related to a crossword will now be stored in a folder with the crossword's name). This will help make the crosswords preview block in the crossword browser more informative.
  • Loading branch information
tomasvana10 committed Jan 14, 2024
1 parent e04054c commit 2a7c5a1
Show file tree
Hide file tree
Showing 9 changed files with 149 additions and 35 deletions.
Binary file added assets/images/cword_img_dark.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added assets/images/cword_img_light.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file removed assets/images/cword_showcase.png
Binary file not shown.
4 changes: 2 additions & 2 deletions src/config.ini
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
[m]
scale = 1.0
scale = 1.1
appearance = system
theme = dark-blue
language = bs
language = en

[misc]
first_time_launch = 0
Expand Down
2 changes: 1 addition & 1 deletion src/cword_gen.py
Original file line number Diff line number Diff line change
Expand Up @@ -433,6 +433,6 @@ def _load_attempts_db(file_path):

# You can also generate a single crossword:
# crossword = Crossword(definitions=definitions, word_count=10, name="Capitals")
# crossword.generate
# crossword.generate()

print(crossword)
File renamed without changes.
5 changes: 5 additions & 0 deletions src/cwords/capitals/info.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
{
"total_definitions": 100,
"difficulty": "easy",
"editable": 0
}
7 changes: 7 additions & 0 deletions src/cwords/capitals/scores.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
{
"1705134471": {
"time_s": 100.5,
"words_inserted": 30,
"mistakes": 3
}
}
166 changes: 134 additions & 32 deletions src/main.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,10 +16,14 @@
class Paths:
CONFIG_PATH = Path(__file__).resolve().parents[0] / "config.ini"
LOCALES_PATH = Path(__file__).resolve().parents[1] / "locales"
CWORD_IMG_PATH = Path(__file__).resolve().parents[1] / "assets/images/cword_showcase.png"

CWORD_IMG_LIGHT_PATH = Path(__file__).resolve().parents[1] / "assets/images/cword_img_light.png"
CWORD_IMG_DARK_PATH = Path(__file__).resolve().parents[1] / "assets/images/cword_img_dark.png"

class Colour:
class Global:
EXIT_BUTTON = "#ED3B4D"
EXIT_BUTTON_HOVER = "#BF0013"

class Light:
FRAME_L = "#B0BEC5"
FRAME_R = "#CFD8DC"
Expand All @@ -43,73 +47,165 @@ def __init__(self, lang_info, locale_):
self.lang_db, self.lang_options = lang_info
self.title("Crossword Puzzle - Home")
self.geometry("800x600")
self.base_eng_appearances = ["light", "dark", "system"]
self.cword_browser_opened = False
ctk.set_appearance_mode(cfg.get("m", "appearance"))
ctk.set_default_color_theme(cfg.get("m", "theme"))
ctk.set_widget_scaling(float(cfg.get("m", "scale")))

self.protocol("WM_DELETE_WINDOW", self._exit_handler)

self._make_frames()
self._place_frames()
self._make_content()
self._place_content()

def _make_frames(self):
self.main_frame = ctk.CTkFrame(self)
self.main_frame.pack(fill=tk.BOTH, expand=True)
self.main_frame.grid_columnconfigure(0, weight=1)
self.main_frame.grid_columnconfigure(1, weight=0)
self.main_frame.grid_rowconfigure(0, weight=1)
self.container = ctk.CTkFrame(self)
self.container.grid_columnconfigure(0, weight=1)
self.container.grid_columnconfigure(1, weight=0)
self.container.grid_rowconfigure(0, weight=1)

self.settings_frame = ctk.CTkFrame(self.main_frame,
self.settings_frame = ctk.CTkFrame(self.container,
fg_color=(Colour.Light.FRAME_R, Colour.Dark.FRAME_R),
corner_radius=0)
self.settings_frame.grid(row=0, column=1, sticky="nsew")

self.cword_opts_frame = ctk.CTkFrame(self.main_frame,
self.cword_opts_frame = ctk.CTkFrame(self.container,
fg_color=(Colour.Light.FRAME_L, Colour.Dark.FRAME_L),
corner_radius=0)

def _place_frames(self):
self.container.pack(fill=tk.BOTH, expand=True)
self.settings_frame.grid(row=0, column=1, sticky="nsew")
self.cword_opts_frame.grid(row=0, column=0, sticky="nsew")

def _make_content(self):
title = ctk.CTkLabel(self.cword_opts_frame, text="Crossword Puzzle", font=ctk.CTkFont(
self.title = ctk.CTkLabel(self.cword_opts_frame, text="Crossword Puzzle", font=ctk.CTkFont(
size=Style.TITLE_FONT["size"],
weight=Style.TITLE_FONT["weight"]))
title.place(relx=0.5, rely=0.1, anchor=tk.CENTER)

cword_img = ctk.CTkLabel(self.cword_opts_frame, text="",
image=ctk.CTkImage(Image.open(Paths.CWORD_IMG_PATH),
self.cword_img = ctk.CTkLabel(self.cword_opts_frame, text="",
image=ctk.CTkImage(light_image=Image.open(Paths.CWORD_IMG_LIGHT_PATH),
dark_image=Image.open(Paths.CWORD_IMG_DARK_PATH),
size=(453, 154)))
cword_img.place(relx=0.5, rely=0.3, anchor=tk.CENTER)

self.b_open_cword_browser = ctk.CTkButton(self.cword_opts_frame, text="View your crosswords",
command=self.open_cword_browser, width=175,
height=50)

self.b_close_app = ctk.CTkButton(self.cword_opts_frame, text="Exit the app",
command=self._exit_handler, width=175, height=50,
fg_color=Colour.Global.EXIT_BUTTON,
hover_color=Colour.Global.EXIT_BUTTON_HOVER)

settings_label = ctk.CTkLabel(self.settings_frame, text="Global Settings",
self.settings_label = ctk.CTkLabel(self.settings_frame, text="Global Settings",
font=ctk.CTkFont(size=Style.SUBHEADING_FONT["size"],
slant=Style.SUBHEADING_FONT["slant"]))
settings_label.place(relx=0.5, rely=0.1, anchor=tk.CENTER)

slant=Style.SUBHEADING_FONT["slant"]))

l_language_options = ctk.CTkLabel(self.settings_frame, text="Languages",
self.l_language_optionsmenu = ctk.CTkLabel(self.settings_frame, text="Languages",
font=ctk.CTkFont(size=Style.LABEL_FONT["size"],
weight=Style.LABEL_FONT["weight"]))
l_language_options.place(relx=0.5, rely=0.2, anchor=tk.CENTER)
self.language_optionsmenu = ctk.CTkOptionMenu(self.settings_frame, values=self.lang_options,
command=self._switch_lang)
command=self.switch_lang)
self.language_optionsmenu.set(self.locale_.language_name)
self.language_optionsmenu.place(relx=0.5, rely=0.26, anchor=tk.CENTER)

self.l_scale_optionmenu = ctk.CTkLabel(self.settings_frame, text="Size",
font=ctk.CTkFont(size=Style.LABEL_FONT["size"],
weight=Style.LABEL_FONT["weight"]))
self.scale_optionmenu = ctk.CTkOptionMenu(self.settings_frame,
values=[str(round(num * 0.1, 1)) for num in range(7, 21)],
command=self.change_scale)
self.scale_optionmenu.set(cfg.get("m", "scale"))

self.appearances = ["light", "dark", "system"] # make sure to mark for translation later
self.l_appearance_optionmenu = ctk.CTkLabel(self.settings_frame, text="Appearance",
font=ctk.CTkFont(size=Style.LABEL_FONT["size"],
weight=Style.LABEL_FONT["weight"]))
self.appearance_optionmenu = ctk.CTkOptionMenu(self.settings_frame, values=self.appearances,
command=self.change_appearance)
self.appearance_optionmenu.set(cfg.get("m", "appearance"))

def _place_content(self):
self.title.place(relx=0.5, rely=0.1, anchor="c")
self.cword_img.place(relx=0.5, rely=0.35, anchor="c")
self.b_open_cword_browser.place(relx=0.5, rely=0.65, anchor="c")
self.b_close_app.place(relx=0.5, rely=0.79, anchor="c")
self.settings_label.place(relx=0.5, rely=0.1, anchor="c")
self.l_language_optionsmenu.place(relx=0.5, rely=0.2, anchor="c")
self.language_optionsmenu.place(relx=0.5, rely=0.26, anchor="c")
self.l_scale_optionmenu.place(relx=0.5, rely=0.4, anchor="c")
self.scale_optionmenu.place(relx=0.5, rely=0.46, anchor="c")
self.l_appearance_optionmenu.place(relx=0.5, rely=0.6, anchor=tk.CENTER)
self.appearance_optionmenu.place(relx=0.5, rely=0.66, anchor=tk.CENTER)

def open_cword_browser(self):
self.cword_browser = CrosswordBrowser(self)

def reopen_app(self):
self.cword_browser.destroy()
self._make_frames()
self._place_frames()
self._make_content()
self._place_content()

def _exit_handler(self, restart=False):
if AppHelper._confirm_with_messagebox(exit_=True, restart=restart):
if AppHelper.confirm_with_messagebox(exit_=True, restart=restart):
self.destroy()
if restart:
AppHelper.start_app()

def _switch_lang(self, lang):
def change_appearance(self, appearance):
if appearance == cfg.get("m", "appearance"):
AppHelper.show_messagebox(same_appearance=True)
return

eng_appearance_name = self.base_eng_appearances[self.appearances.index(appearance)]
ctk.set_appearance_mode(eng_appearance_name)
AppHelper._update_config("m", "appearance", eng_appearance_name)

def change_scale(self, scale):
if scale == cfg.get("m", "scale"):
AppHelper.show_messagebox(same_scale=True)
return

ctk.set_widget_scaling(float(scale))
AppHelper._update_config("m", "scale", scale)

def switch_lang(self, lang):
if self.lang_db[lang] == cfg.get("m", "language"):
AppHelper._show_messagebox(same_lang=True)
AppHelper.show_messagebox(same_lang=True)
return

AppHelper._update_config("m", "language", self.lang_db[lang])
self._exit_handler(restart=True)


class CrosswordBrowser(ctk.CTkFrame):
def __init__(self, master):
super().__init__(master)
self.master.container.pack_forget()
self.pack(expand=True, fill=tk.BOTH)
self.grid_columnconfigure(0, weight=1)
self.grid_rowconfigure(0, weight=1)
self._make_content()
self._place_content()

def _make_content(self):
self.scroll_frame = ctk.CTkFrame(self, fg_color="red")

def _place_content(self):
self.scroll_frame.grid(row=0, column=0, sticky="ew")

def return_home(self):
self.pack_forget()
self.master.reopen_app()


class CrosswordPreviewBlock(ctk.CTkFrame):
def __init__(self):
...


class AppHelper:
@staticmethod
def start_app():
Expand All @@ -123,29 +219,35 @@ def start_app():
language = cfg.get("m", "language")
locale_ = Locale.parse(language)

# gettext.translation("messages", Paths.LOCALES_PATH, languages=[language]).install()
# gettext.translation("messages", localedir=Paths.LOCALES_PATH, languages=[locale_.language]).install()

app = Home(AppHelper._get_language_options(), locale_)
AppHelper._update_config("misc", "first_time_launch", "0")

app.mainloop()

@staticmethod
def _confirm_with_messagebox(exit_=False, restart=False):
def confirm_with_messagebox(exit_=False, restart=False):
if exit_ & restart:
if tk.messagebox.askyesno("Restart", "Do you want to restart the app?"):
if tk.messagebox.askyesno("Restart", "Are you sure you want to restart the app?"):
return True

if exit_ & ~restart:
if tk.messagebox.askyesno("Exit", "Do you want to exit the app?"):
if tk.messagebox.askyesno("Exit", "Are you sure you want to exit the app?"):
return True

return False

@staticmethod
def _show_messagebox(same_lang=False):
def show_messagebox(same_lang=False, same_scale=False, same_appearance=False):
if same_lang:
tk.messagebox.showerror("Error", "This language is already selected.")

if same_scale:
tk.messagebox.showerror("Error", "This size is already selected.")

if same_appearance:
tk.messagebox.showerror("Error", "This appearance is already selected.")

@staticmethod
def _update_config(section, option, value):
Expand All @@ -172,4 +274,4 @@ def _get_language_options():


if __name__ == "__main__":
AppHelper.start_app()
AppHelper.start_app()

0 comments on commit 2a7c5a1

Please sign in to comment.