Finished settings menu and automatic note loads

Implemented the settings menu to the main window so the settings are
applied. Moved the double layout option to the settings instead of the
right click menu. Also implemented a system to automatically load the
notes that were active when SplitNotes was closed last time.
This commit is contained in:
Joelnir
2016-02-18 21:34:02 +01:00
parent af125173c4
commit d314860608
10 changed files with 135 additions and 97 deletions
+2 -1
View File
@@ -1,4 +1,5 @@
*.pyc
TESTING.py
.idea
__pycache__
__pycache__
resources/config.cfg
Binary file not shown.
Binary file not shown.
Binary file not shown.
+6 -5
View File
@@ -64,7 +64,7 @@ TEXT_FILES = [
]
# Default content of config.cfg file
DEFAULT_CONFIG = "notes=\nfont_size=12\nfont=arial\ntext_color=#FFFFFF\nbackground_color=#000000\nserver_port=16834"
DEFAULT_CONFIG = "notes=\nfont_size=12\nfont=arial\ntext_color=#000000\nbackground_color=#FFFFFF\ndouble_layout=False\nserver_port=16834"
# Required settings
REQUIRED_SETTINGS = ("notes",
@@ -72,13 +72,14 @@ REQUIRED_SETTINGS = ("notes",
"font_size",
"text_color",
"background_color",
"server_port"
"server_port",
"double_layout"
)
# Settings window options
SETTINGS_WINDOW = {"TITLE": "Settings",
"WIDTH": 360,
"HEIGHT": 280,
"HEIGHT": 330,
"CANCEL": "Cancel",
"SAVE": "Save"}
@@ -88,12 +89,12 @@ SETTINGS_OPTIONS = {"FONT": "Font",
"TEXT_COLOR": "Text Color",
"BG_COLOR": "Background Color",
"SERVER_PORT": "LiveSplit Server port",
"DEFAULT_SERVER_PORT": "(Default is 16834)"}
"DEFAULT_SERVER_PORT": "(Default is 16834)",
"DOUBLE_LAYOUT": "Use double layout"}
# Fonts that can be selected
AVAILABLE_FONTS = ("arial",
"courier new",
"comic sans",
"fixedsys",
"ms sans serif",
"ms serif",
+4 -4
View File
@@ -8,9 +8,9 @@ import config
import select # used for checking if socket has data pending
def ls_connect(ls_socket, call_func, window):
def ls_connect(ls_socket, call_func, window, server_port):
"""Connects given socket to the livesplit server."""
con_thread = Thread(target=try_connection, args=(ls_socket, call_func, window))
con_thread = Thread(target=try_connection, args=(ls_socket, call_func, window, server_port))
con_thread.start()
@@ -19,7 +19,7 @@ def init_socket():
return socket.socket()
def try_connection(ls_socket, call_func, window):
def try_connection(ls_socket, call_func, window, server_port):
"""
Tries to connect given socket to ls.
If connection is successful given "call_func"
@@ -27,7 +27,7 @@ def try_connection(ls_socket, call_func, window):
(made to be ran in a separate thread)
"""
try:
ls_socket.connect((config.HOST, config.PORT))
ls_socket.connect((config.HOST, server_port))
except:
return False
+73 -72
View File
@@ -9,16 +9,15 @@ import sys
import config
import ls_connection as con
import note_reader as noter
import setting_handler as settings
import setting_handler
runtime_info = {
"ls_connected": False,
"timer_running": False,
"icon_active": False,
"active_split": -1,
"notes": [],
"double_layout": False,
"big_font": False
"server_port": 0,
"force_reset": False
}
root = tkinter.Tk()
@@ -41,9 +40,14 @@ def update(window, com_socket, text1, text2):
"""
Function to loop along tkinter mainloop.
"""
if not runtime_info["ls_connected"]:
if runtime_info["force_reset"]:
#boolean flag to force a connection reset
com_socket = reset_connection(com_socket, window, text1, text2)
runtime_info["force_reset"] = False
elif not runtime_info["ls_connected"]:
# try connecting to ls
con.ls_connect(com_socket, server_found, window)
con.ls_connect(com_socket, server_found, window, runtime_info["server_port"])
else:
# is_connected
if runtime_info["notes"]:
@@ -105,7 +109,7 @@ def update_GUI(window, com_socket, text1, text2):
if runtime_info["notes"]:
set_title_notes(window, index, split_name)
update_notes(window, text1, text2, index)
update_notes(text1, text2, index)
else:
update_title(config.DEFAULT_WINDOW["TITLE"], window)
@@ -139,6 +143,7 @@ def reset_connection(com_socket, window, text1, text2):
# Close old and return a fresh socket
con.close_socket(com_socket)
return con.init_socket()
@@ -153,12 +158,10 @@ def server_found(window):
def update_icon(active, window):
"""Updates icon of window depending on "active" variable"""
if active and not runtime_info["icon_active"]:
if active:
window.tk.call('wm', 'iconphoto', window._w, green_icon)
runtime_info["icon_active"] = True
elif runtime_info["icon_active"]:
else:
window.tk.call('wm', 'iconphoto', window._w, red_icon)
runtime_info["icon_active"] = False
def update_title(name, window):
@@ -205,16 +208,6 @@ def show_popup(event, menu):
menu.post(event.x_root, event.y_root)
def menu_change_layout(window, box1, box2, popup):
"""Menu option for changing layout selected."""
if runtime_info["double_layout"]:
set_single_layout(window, box1, box2)
popup.entryconfig(0, label=config.MENU_OPTIONS["DOUBLE"])
else:
set_double_layout(window, box1, box2)
popup.entryconfig(0, label=config.MENU_OPTIONS["SINGLE"])
def menu_load_notes(window, text1, text2, com_socket):
"""Menu selected load notes option."""
load_notes(window, text1, text2, com_socket)
@@ -232,6 +225,11 @@ def load_notes(window, text1, text2, com_socket):
# Notes loaded correctly
runtime_info["notes"] = notes
# Save notes to settings
settings = setting_handler.load_settings()
settings["notes"] = file
setting_handler.save_settings(settings)
split_c = len(notes)
show_info(("Notes Loaded",
("Loaded notes with " + str(split_c) + " splits.")))
@@ -244,10 +242,9 @@ def load_notes(window, text1, text2, com_socket):
else:
show_info(config.ERRORS["NOTES_EMPTY"], True)
def show_info(info, warning=False):
"""
Displays an infor popup window.
Displays an info popup window.
if warning is True window has a warning triangle.
"""
if warning:
@@ -256,7 +253,7 @@ def show_info(info, warning=False):
messagebox.showinfo(info[0], info[1])
def update_notes(window, text1, text2, index):
def update_notes(text1, text2, index):
"""
Displays notes with the given index in given text widgets.
If index is lower than 0, displays notes for index 0.
@@ -279,7 +276,7 @@ def update_notes(window, text1, text2, index):
if index <= max_index:
text1.insert(tkinter.END, runtime_info["notes"][index])
# cand disply notes for index+1
# cant disply notes for index+1
if index < max_index:
text2.insert(tkinter.END, runtime_info["notes"][index + 1])
@@ -298,7 +295,10 @@ def left_arrow(window, com_socket, text1, text2):
def change_preview(window, com_socket, text1, text2, move):
"""move is either 1 for next or -1 for previous."""
"""
Chnges notes that are currently displayed.
Move is either 1 for next or -1 for previous.
"""
if runtime_info["notes"] and (not runtime_info["timer_running"]):
max_index = (len(runtime_info["notes"]) - 1)
index = runtime_info["active_split"]
@@ -334,34 +334,31 @@ def set_title_notes(window, index, split_name=False):
update_title(title, window)
def menu_font_size(text_font, menu):
if runtime_info["big_font"]:
runtime_info["big_font"] = False
menu.entryconfig(1, label=config.MENU_OPTIONS["BIG"])
def menu_open_settings(root_wnd, box1, box2, text1, text2):
setting_handler.edit_settings(root_wnd,
(lambda settings: apply_settings(settings,
root_wnd,
box1,box2,
text1, text2)))
def apply_settings(settings, window, box1, box2, text1, text2):
#Server port change
if not (runtime_info["server_port"] == int(settings["server_port"])):
runtime_info["server_port"] = int(settings["server_port"])
runtime_info["force_reset"] = True
text_font = (settings["font"], int(settings["font_size"]))
if setting_handler.decode_boolean_setting(settings["double_layout"]):
set_double_layout(window, box1, box2)
else:
runtime_info["big_font"] = True
menu.entryconfig(1, label=config.MENU_OPTIONS["SMALL"])
set_single_layout(window, box1, box2)
update_font_size(text_font)
def menu_open_settings(root_wnd, apply_method, text1, text2):
settings.edit_settings(root_wnd, (lambda settings: apply_settings(settings, text1, text2)))
def apply_settings(config, text1, text2):
# TODO apply all settings to the root window
print("Applying settings")
print(config)
def update_font_size(text_font):
if runtime_info["big_font"]:
font_size = config.FONT["BIG"]
else:
font_size = config.FONT["SMALL"]
text_font.config(size=font_size)
text1.config(font=text_font)
text2.config(font=text_font)
text1.config(fg=settings["text_color"], bg=settings["background_color"])
text2.config(fg=settings["text_color"], bg=settings["background_color"])
def init_UI(root):
@@ -370,6 +367,10 @@ def init_UI(root):
# Create communication socket
com_socket = con.init_socket()
# Load Settings
settings = setting_handler.load_settings()
runtime_info["server_port"] = int(settings["server_port"])
# Graphical components
root.geometry(str(config.DEFAULT_WINDOW["WIDTH"]) + "x" + str(config.DEFAULT_WINDOW["HEIGHT"]))
@@ -392,6 +393,7 @@ def init_UI(root):
text1.config(state=tkinter.DISABLED)
text1.pack(fill=tkinter.BOTH, expand=True)
text2 = tkinter.Text(
box2,
yscrollcommand=scroll2.set,
@@ -406,44 +408,43 @@ def init_UI(root):
scroll2.config(command=text2.yview)
# Set font and color for text
text_font = font.Font(
family=config.FONT["NAME"],
size=config.FONT["SMALL"]
)
text_font = (settings["font"], int(settings["font_size"]))
text1.config(font=text_font)
text2.config(font=text_font)
text1.config(fg=config.COLOR["TEXT"], bg=config.COLOR["TEXT_BG"])
text2.config(fg=config.COLOR["TEXT"], bg=config.COLOR["TEXT_BG"])
text1.config(fg=settings["text_color"], bg=settings["background_color"])
text2.config(fg=settings["text_color"], bg=settings["background_color"])
set_single_layout(root, box1, box2)
if setting_handler.decode_boolean_setting(settings["double_layout"]):
set_double_layout(root, box1, box2)
else:
set_single_layout(root, box1, box2)
# create popup menu
popup = tkinter.Menu(root, tearoff=0)
popup.add_command(
label=config.MENU_OPTIONS["DOUBLE"],
command=(
lambda: menu_change_layout(root, box1, box2, popup)
)
) # Needs to be at index 0
popup.add_command(
label=config.MENU_OPTIONS["BIG"],
command=(
lambda: menu_font_size(text_font, popup)
)
) # Needs to be at index 1
popup.add_command(
label=config.MENU_OPTIONS["LOAD"],
command=(lambda: menu_load_notes(root, text1, text2, com_socket))
)
popup.add_command(
label=config.MENU_OPTIONS["SETTINGS"],
command=(lambda: menu_open_settings(root, apply_settings, text1, text2))
command=(lambda: menu_open_settings(root, box1, box2, text1, text2))
)
# Set default window icon and title
root.tk.call('wm', 'iconphoto', root._w, red_icon)
update_title(config.DEFAULT_WINDOW["TITLE"], root)
# Check if notes can be loaded from settings
settings = setting_handler.load_settings()
if settings["notes"] and noter.file_exists(settings["notes"]):
notes = noter.get_notes(settings["notes"])
if notes:
runtime_info["notes"] = notes
update_GUI(root, com_socket, text1, text2)
# Event binds
root.bind("<Configure>", (lambda e: adjust_content(root, box1, box2)))
root.bind("<Button-3>", (lambda e: show_popup(e, popup)))
+4
View File
@@ -120,3 +120,7 @@ def select_file():
return file
else:
return False
def file_exists(file):
return path.isfile(file)
+7 -6
View File
@@ -1,6 +1,7 @@
notes=
font=times new roman
font_size=12
server_port=34
background_color=#4d73f4
text_color=#ff8080
notes=C:/Users/Joel/Documents/EA Games/Mirror's Edge/TdGame/Config/TdEngine.ini
server_port=16834
text_color=#000000
double_layout=True
font_size=11
font=ms sans serif
background_color=#ffffff
+39 -9
View File
@@ -18,6 +18,7 @@ settings_icon_path = os.path.join(
config.ICONS["SETTINGS"]
)
def load_settings():
"""
Tries to load settings from file.
@@ -65,10 +66,11 @@ def format_settings(file_rows):
for row in file_rows:
row = row.strip("\n")
parts = row.split("=")
parts = row.split("=", 1)
if len(parts) == SETTING_PART_LENGTH:
settings[parts[0]] = parts[1]
# Strip to remove whitespace at end and beginning
settings[parts[0].strip()] = parts[1].strip()
return settings
@@ -115,6 +117,10 @@ def validate_settings(settings):
if not (settings["font"] in config.AVAILABLE_FONTS):
return False
if not ((settings["double_layout"] == "True") or
(settings["double_layout"] == "False")):
return False
return True
@@ -156,6 +162,9 @@ def edit_settings(root_wnd, apply_method):
bg_color_label = tkinter.Label(settings_wnd,
text=config.SETTINGS_OPTIONS["BG_COLOR"],
font=config.GUI_FONT)
layout_label = tkinter.Label(settings_wnd,
text=config.SETTINGS_OPTIONS["DOUBLE_LAYOUT"],
font=config.GUI_FONT)
port_label = tkinter.Label(settings_wnd,
text=config.SETTINGS_OPTIONS["SERVER_PORT"],
font=config.GUI_FONT)
@@ -163,6 +172,7 @@ def edit_settings(root_wnd, apply_method):
text=config.SETTINGS_OPTIONS["DEFAULT_SERVER_PORT"],
font=config.GUI_FONT)
# Font Selection
selected_font = tkinter.StringVar(settings_wnd)
selected_font.set(settings["font"])
@@ -211,7 +221,6 @@ def edit_settings(root_wnd, apply_method):
def bg_color_selection():
choosen_color = colorchooser.askcolor()
if choosen_color[1]:
print(choosen_color)
settings["background_color"] = choosen_color[1]
bg_color.configure(background=settings["background_color"])
@@ -223,6 +232,13 @@ def edit_settings(root_wnd, apply_method):
port_entry = tkinter.Entry(settings_wnd, width=6, font=config.GUI_FONT)
port_entry.insert(0, settings["server_port"])
# Double Layout Selection
double_layout = tkinter.BooleanVar()
double_layout_btn = tkinter.Checkbutton(settings_wnd, variable=double_layout)
if decode_boolean_setting(settings["double_layout"]):
double_layout_btn.select()
# Save and cancel buttons
def control_and_save():
errors_found = False
@@ -232,6 +248,8 @@ def edit_settings(root_wnd, apply_method):
chosen_font_size = font_size_entry.get()
chosen_port = port_entry.get()
settings["double_layout"] = encode_boolean_setting(double_layout.get())
if not validate_font_size(chosen_font_size):
msgbox.showerror(config.ERRORS["FONT_SIZE"][0], config.ERRORS["FONT_SIZE"][1])
errors_found = True
@@ -265,17 +283,19 @@ def edit_settings(root_wnd, apply_method):
font_size_label.place(x=15, y=55)
text_color_label.place(x=15, y=95)
bg_color_label.place(x=15, y=135)
port_label.place(x=15, y=175)
default_port_label.place(x=15, y=200)
layout_label.place(x=15, y=175)
port_label.place(x=15, y=215)
default_port_label.place(x=15, y=240)
font_dropdown.place(x=178, y=15)
font_size_entry.place(x=180, y=55)
text_color.place(x=180, y=95)
bg_color.place(x=180, y=135)
port_entry.place(x=180, y=175)
double_layout_btn.place(x=180, y=175)
port_entry.place(x=180, y=215)
save_btn.place(x=110, y=230)
cancel_btn.place(x=190, y=230)
save_btn.place(x=110, y=280)
cancel_btn.place(x=190, y=280)
def validate_color(color):
@@ -314,4 +334,14 @@ def save_settings(settings):
for key in settings.keys():
file_content += key + "=" + settings[key] + "\n"
set_settings_file_content(file_content)
set_settings_file_content(file_content)
def decode_boolean_setting(setting):
return setting == "True"
def encode_boolean_setting(value):
if value:
return "True"
else:
return "False"