-
Notifications
You must be signed in to change notification settings - Fork 0
/
oppu.py
160 lines (118 loc) · 5.43 KB
/
oppu.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
from tkinter import filedialog as fd
from ttkthemes import ThemedTk
from itertools import product
from random import choices
from tkinter import ttk
from os import getcwd
import tkinter as tk
from questions import load_questions
class Oppu(ThemedTk):
def __init__(self):
ThemedTk.__init__(self, themebg=True, fonts=True)
# Setup:
self.eval('tk::PlaceWindow . center')
self.title('Oppu-Chan')
self.geometry('240x240')
self.minsize(240, 240)
self._set_icon()
# Menu Bar:
self.menu_bar = tk.Menu(self)
self.file_menu = tk.Menu(self.menu_bar, tearoff=0)
self.file_menu.add_command(label='Open...', command=self.load_question, accelerator='Ctrl+O')
self.file_menu.add_command(label='Difficulty', command=self.select_difficulty)
self.file_menu.add_command(label='Change Theme', command=self.change_theme)
self.file_menu.add_separator()
self.file_menu.add_command(label='Exit', command=self.quit, accelerator='Ctrl+E')
self.menu_bar.add_cascade(label='File', menu=self.file_menu)
self.config(menu=self.menu_bar)
# Variables:
self.questions = load_questions('questions/katakana.ans')
self.current_question = ''.join(choices(list(self.questions.keys()), k=1))
self.streak, self.difficulty = 0, 1
self.dark_theme_enabled = True
# Widgets:
self.streak_label, self.correct_label, self.question_label, self.answer_button, self.text_input = [None] * 5
self.streak_separator = None
self._create_widgets()
# Theme:
self.dark_theme()
# Button Commands:
def answer_command(self, event=None):
string_answer, answer = '', []
for character in self.current_question:
answer.append(self.questions[character])
answers = [''.join(x) for x in list(product(*answer))]
if self.text_input.get().upper() in answers:
self.correct_label.config(text=f"Correct!", foreground='#228B22')
self.streak += self.difficulty
self.streak_label.config(text=f"Streak: {self.streak}")
else:
self.correct_label.config(text=f"Incorrect... That was {''.join(answers[0]).title()}.",
foreground='#ff3232')
self.streak = 0
self.streak_label.config(text=f"Streak: 0")
self.correct_label.pack(side=tk.TOP, pady=1)
self.text_input.delete(0, tk.END)
self.change_question()
def change_question(self):
self.current_question = ''.join(choices(list(self.questions.keys()), k=self.difficulty))
self.question_label.config(text=f"{self.current_question}")
# Menu Commands:
def load_question(self):
filetypes = (('Question Files', '*.ans'),)
filename = fd.askopenfilename(title='Open a file', initialdir=getcwd(), filetypes=filetypes)
self.questions = load_questions(filename)
self.change_question()
def select_difficulty(self):
selector = tk.Toplevel()
selector.geometry("300x100")
selector.minsize(300, 100)
selector.focus()
self.eval(f'tk::PlaceWindow {str(selector)} center')
difficulty_label = ttk.Label(selector, text=f"{self.difficulty}")
def control_difficulty(value=None):
self.difficulty = round(float(value))
difficulty_label.config(text=f"{self.difficulty}")
scale = ttk.Scale(selector, from_=1, to=5, value=self.difficulty, orient=tk.HORIZONTAL,
command=control_difficulty)
def on_ok():
self.change_question()
selector.destroy()
ok_button = ttk.Button(selector, text='Ok', command=on_ok)
scale.pack(fill='x', padx=10, pady=10)
difficulty_label.pack()
ok_button.pack()
self.difficulty = scale.get()
# Themes:
def change_theme(self):
self.light_theme() if self.dark_theme_enabled else self.dark_theme()
self.dark_theme_enabled = not self.dark_theme_enabled
self.update()
def dark_theme(self):
self.set_theme('equilux')
def light_theme(self):
self.set_theme('plastik')
# Helpers:
def _set_icon(self):
try:
self.iconbitmap('icon.ico')
except tk.TclError:
print(f"[Error]: The icon file could not be file within the project's directory.")
def _create_widgets(self):
self.streak_label = ttk.Label(self, text=f"Streak: {self.streak}")
self.streak_label.pack(side=tk.TOP, pady=3)
self.streak_separator = tk.Frame(self, bg='#bababa', height=1, bd=0)
self.streak_separator.pack(fill='x')
self.correct_label = ttk.Label(self)
self.question_label = ttk.Label(self, text=f"{self.current_question}")
self.question_label.config(font=("Consolas", 32))
self.question_label.pack(pady=30)
self.answer_button = ttk.Button(self, text="Answer", command=self.answer_command)
self.answer_button.pack(side=tk.BOTTOM, pady=5)
self.text_input = ttk.Entry(self)
self.text_input.bind('<Return>', self.answer_command)
self.text_input.pack(side=tk.BOTTOM, pady=5)
self.text_input.focus()
if __name__ == '__main__':
app = Oppu()
app.mainloop()