Skip to content

Commit

Permalink
Merge pull request #10 from ChenglongMa/dev-1.2.0-pbe-support
Browse files Browse the repository at this point in the history
Dev 1.2.0 pbe support
  • Loading branch information
ChenglongMa authored Jul 20, 2024
2 parents db8fbe0 + dd1fb23 commit 82d1577
Show file tree
Hide file tree
Showing 9 changed files with 185 additions and 162 deletions.
2 changes: 2 additions & 0 deletions build.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,8 @@ $InstallerArgsDebug = @(
".\src\assets\*.ico;.\assets",
# "--add-data",
# ".\src\assets\*.pdf;.\assets",
"--collect-data",
"sv_ttk",
"--paths",
".\src",
"--clean",
Expand Down
2 changes: 1 addition & 1 deletion metadata.yml
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
Version: 1.1.0
Version: 1.2.0
CompanyName: Chenglong Ma
FileDescription: A launcher for starting LOL in different languages
InternalName: LOLauncher
Expand Down
3 changes: 2 additions & 1 deletion requirements.txt
Original file line number Diff line number Diff line change
Expand Up @@ -6,4 +6,5 @@ watchdog>=4.0.1
pystray>=0.19.5
pillow>=10.3.0
keyboard>=0.13.5
mouse>=0.7.1
mouse>=0.7.1
sv_ttk>=2.6.0
Binary file modified src/assets/tray_icon.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
4 changes: 2 additions & 2 deletions src/main.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@

config = read_json(CONFIG_FILENAME) or {}
ui_config = read_json(GUI_CONFIG_FILENAME) or {}
setting_file = verify_metadata_file(config)
setting_files = verify_metadata_file(config)

app = App(setting_file, config, ui_config)
app = App(setting_files, config, ui_config)
app.run()
154 changes: 102 additions & 52 deletions src/ui/app.py

Large diffs are not rendered by default.

1 change: 1 addition & 0 deletions src/ui/quick_chat.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
import threading
import time
import tkinter as tk
from tkinter import ttk

import easygui
import keyboard
Expand Down
28 changes: 25 additions & 3 deletions src/ui/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,27 @@
from assets import get_asset
from utils import open_web

THEME_COLOR = {
"dark": {
"warning_bg": "#333333",
"warning_fg": "white",
"border": "#927934",
"border_inactive": "#463714",
"hover_bg": "#C89B3C",
"hover_fg": "#010A13",
"accent": "#C89B3C",
},
"light": {
"warning_bg": "#F0E6D2",
"warning_fg": "#010A13",
"border": "#927934",
"border_inactive": "#463714",
"hover_bg": "#C89B3C",
"hover_fg": "#010A13",
"accent": "blue",
}
}


def reset_list_box_colors(list_box, default_bg, default_fg):
for i in range(list_box.size()):
Expand All @@ -18,11 +39,12 @@ def open_asset(uri):
subprocess.run(['start', file_path], shell=True, check=False)


def create_warning_label(parent, normal_text, link_text, uri):
label = tk.Text(parent, height=1, background="#ffffe0", relief=tk.SOLID, borderwidth=1)
def create_warning_label(parent, normal_text, link_text, uri, theme="dark"):
label = tk.Text(parent, height=1, background=THEME_COLOR[theme]["warning_bg"], foreground=THEME_COLOR[theme]["warning_fg"], relief=tk.SOLID,
borderwidth=1)
label.insert(1.0, normal_text + " ", tk.CENTER)
label.insert(tk.END, link_text, "link")
label.tag_config("link", foreground="blue", underline=True)
label.tag_config("link", foreground=THEME_COLOR[theme]["accent"], underline=True)
label.tag_bind("link", "<Button-1>", lambda e: open_asset(uri))
label.tag_bind("link", "<Enter>", lambda e: label.config(cursor="hand2"))
label.tag_bind("link", "<Leave>", lambda e: label.config(cursor=""))
Expand Down
153 changes: 50 additions & 103 deletions src/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,11 +20,20 @@
from github import Github
from watchdog.events import FileSystemEventHandler

VERSION = '1.1.0'
VERSION = '1.2.0'
APP_NAME = 'LOLauncher'
REPO_NAME = 'ChenglongMa/LOLauncher'
DEFAULT_METADATA_DIR = r"C:\ProgramData\Riot Games\Metadata\league_of_legends.live\league_of_legends.live.product_settings.yaml"
DEFAULT_METADATA_FILE = f"{DEFAULT_METADATA_DIR}\\league_of_legends.live.product_settings.yaml"
SUPPORTED_PATCH_LINEs = ['live', 'pbe']
DEFAULT_PATCH_LINE = 'live'
DEFAULT_DRIVE = r"C:"
# DEFAULT_METADATA_DIR = rf"{DEFAULT_DRIVE}\ProgramData\Riot Games\Metadata\league_of_legends.live"
# DEFAULT_METADATA_FILE = f"{DEFAULT_METADATA_DIR}\\league_of_legends.live.product_settings.yaml"
# PBE_METADATA_DIR = rf"{DEFAULT_DRIVE}\ProgramData\Riot Games\Metadata\league_of_legends.pbe"
# PBE_METADATA_FILE = f"{PBE_METADATA_DIR}\\league_of_legends.pbe.product_settings.yaml"
METADATA_DIR_FORMAT = r"{drive}\ProgramData\Riot Games\Metadata\league_of_legends.{patch_line}"
METADATA_FILE_FORMAT = "league_of_legends.{patch_line}.product_settings.yaml"
DEFAULT_METADATA_DIR = METADATA_DIR_FORMAT.format(drive=DEFAULT_DRIVE, patch_line=DEFAULT_PATCH_LINE)
DEFAULT_METADATA_FILE = os.path.join(DEFAULT_METADATA_DIR, METADATA_FILE_FORMAT.format(patch_line=DEFAULT_PATCH_LINE))

LOCALE_CODES = {
"zh_CN": "简体中文(国服)",
Expand Down Expand Up @@ -79,14 +88,16 @@
########################################################################################
class FileWatcher(FileSystemEventHandler):

def __init__(self, file_path, selected_locale, msg_callback_fn=None):
self.file_path = file_path
def __init__(self, *watching_files, selected_locale, msg_callback_fn=None):
self.watching_files = filter_existing_files(watching_files)
print(f"Watching files: {self.watching_files}")
self.selected_locale = selected_locale
self.msg_callback_fn = msg_callback_fn or print
super().__init__()

def on_modified(self, event):
if event.src_path == self.file_path:
print(f'event type: {event.event_type} path : {event.src_path}')
if normalize_file_path(event.src_path) in self.watching_files:
print(f'File {event.src_path} has been modified')
content = read_yaml(event.src_path)
if not is_valid_settings(content):
Expand All @@ -95,7 +106,6 @@ def on_modified(self, event):
curr_locale = content['settings']['locale']
if curr_locale != self.selected_locale:
self.msg_callback_fn(f'正在将语言 {curr_locale} 更新为 {self.selected_locale} ...')
# print(f'Updating locale from {curr_locale} to {self.selected_locale} ...')
update_settings(event.src_path, self.selected_locale, self.msg_callback_fn)


Expand Down Expand Up @@ -145,66 +155,6 @@ def enum_windows_proc(hwnd, lparam):
return False # stop enumerating windows
return True # continue enumerating windows

print("Bringing to front and clicking")
enum_windows_proc = ctypes.WINFUNCTYPE(ctypes.c_bool, wintypes.HWND, wintypes.LPARAM)(enum_windows_proc)
ctypes.windll.user32.EnumWindows(enum_windows_proc, 0)


def bring_to_front(pid):
"""
Bring the window of the process to the front and set focus
:param pid: the process ID
:return: True if the window is already in the front or successfully brought to the front and focus, False otherwise
"""
foreground_window = ctypes.windll.user32.GetForegroundWindow()
pid_foreground_window = wintypes.DWORD()
ctypes.windll.user32.GetWindowThreadProcessId(foreground_window, ctypes.byref(pid_foreground_window))
if pid_foreground_window.value == pid:
# ctypes.windll.user32.SetFocus(foreground_window)
return True

def enum_windows_proc(hwnd, lparam):
pid_window = wintypes.DWORD()
ctypes.windll.user32.GetWindowThreadProcessId(hwnd, ctypes.byref(pid_window))
if pid_window.value == pid:
ctypes.windll.user32.SetForegroundWindow(hwnd)
ctypes.windll.user32.SetFocus(hwnd)
# Simulate Alt key press and release
ctypes.windll.user32.keybd_event(0x12, 0, 0, 0) # Alt key down
ctypes.windll.user32.keybd_event(0x12, 0, 2, 0) # Alt key up
return False # stop enumerating windows
return True # continue enumerating windows

enum_windows_proc = ctypes.WINFUNCTYPE(ctypes.c_bool, wintypes.HWND, wintypes.LPARAM)(enum_windows_proc)
ctypes.windll.user32.EnumWindows(enum_windows_proc, 0)


def bring_to_front2(pid):
"""
Bring the window of the process to the front and set focus
:param pid: the process ID
:return: True if the window is already in the front or successfully brought to the front and focus, False otherwise
"""
foreground_window = ctypes.windll.user32.GetForegroundWindow()
pid_foreground_window = wintypes.DWORD()
ctypes.windll.user32.GetWindowThreadProcessId(foreground_window, ctypes.byref(pid_foreground_window))
if pid_foreground_window.value == pid:
ctypes.windll.user32.SetFocus(foreground_window)
return True

def enum_windows_proc(hwnd, lparam):
pid_window = wintypes.DWORD()
ctypes.windll.user32.GetWindowThreadProcessId(hwnd, ctypes.byref(pid_window))
if pid_window.value == pid:
# Attach the input processing mechanism of the foreground window's thread to our thread
ctypes.windll.user32.AttachThreadInput(ctypes.windll.kernel32.GetCurrentThreadId(), pid_foreground_window.value, True)
ctypes.windll.user32.SetForegroundWindow(hwnd)
ctypes.windll.user32.SetFocus(hwnd)
# Detach the input processing mechanism after setting the focus
ctypes.windll.user32.AttachThreadInput(ctypes.windll.kernel32.GetCurrentThreadId(), pid_foreground_window.value, False)
return False # stop enumerating windows
return True # continue enumerating windows

enum_windows_proc = ctypes.WINFUNCTYPE(ctypes.c_bool, wintypes.HWND, wintypes.LPARAM)(enum_windows_proc)
ctypes.windll.user32.EnumWindows(enum_windows_proc, 0)

Expand Down Expand Up @@ -274,12 +224,19 @@ def check_for_updates(no_new_version_callback=None):
no_new_version_callback()


def normalize_file_path(file_path):
file_path = os.path.abspath(file_path)
file_path = os.path.realpath(file_path)
file_path = os.path.normpath(file_path)
return file_path


def filter_existing_files(file_paths):
return list(set(filter(os.path.exists, file_paths)))
return list(set(filter(os.path.exists, map(normalize_file_path, file_paths))))


def filter_valid_metadata_files(filenames):
return list(filter(is_valid_metadata_file, filenames))
def filter_valid_metadata_files(*file_paths):
return list(set(filter(is_valid_metadata_file, map(normalize_file_path, file_paths))))


def to_list(data):
Expand Down Expand Up @@ -342,11 +299,12 @@ def open_metadata_file_dialog(title, file_types, initial_dir=DEFAULT_METADATA_DI

def find_setting_files():
while True:
selected_file = open_metadata_file_dialog(title="请选择 league_of_legends.live.product_settings.yaml 文件",
selected_file = open_metadata_file_dialog(title="请选择 league_of_legends.[live|pbe].product_settings.yaml 文件",
file_types=[('Riot 配置文件', '*.yaml'), ('所有文件', '*.*')],
initial_dir=DEFAULT_METADATA_DIR, initial_file=DEFAULT_METADATA_FILE)
if selected_file:
return [selected_file]
selected_files = filter_valid_metadata_files(*to_list(selected_file))
if len(selected_files) > 0:
return selected_files
else:
decision = easygui.buttonbox(
"您要重新选择文件,还是退出?\n",
Expand All @@ -373,44 +331,33 @@ def is_valid_metadata_file(filename):
def detect_metadata_file():
print("Detecting metadata file...")
setting_files = []
filename_suffix = r"ProgramData\Riot Games\Metadata\league_of_legends.live\league_of_legends.live.product_settings.yaml"

filename_suffixes = [os.path.join(
METADATA_DIR_FORMAT.format(drive="", patch_line=patch_line),
METADATA_FILE_FORMAT.format(patch_line=patch_line)
) for patch_line in SUPPORTED_PATCH_LINEs]
for drive in get_drives():
filename = os.path.join(drive, filename_suffix)
if is_valid_metadata_file(filename):
print(f"Found metadata file: {filename}")
setting_files.append(filename)
for filename_suffix in filename_suffixes:
filename = os.path.join(drive, filename_suffix)
if is_valid_metadata_file(filename):
print(f"Found metadata file: {filename}")
setting_files.append(filename)
return setting_files


def verify_metadata_file(config) -> str:
setting_files = filter_valid_metadata_files(to_list(config.get('SettingFile', [])))
def verify_metadata_file(config) -> [str]:
setting_files = detect_metadata_file()
setting_files = filter_valid_metadata_files(*to_list(config.get('SettingFile', [])), *setting_files)
if not setting_files or len(setting_files) < 1:
print("开始尝试自动查找配置文件...")
setting_files = detect_metadata_file()
if not setting_files or len(setting_files) < 1:
decision = easygui.buttonbox("该文件通常位于:\n\n"
r"[系统盘]:\ProgramData\Riot Games\Metadata\league_of_legends.live"
r"\league_of_legends.live.product_settings.yaml",
"未找到配置文件,请手动选择", ["手动选择", "退出"])
if decision.lower() == '手动选择':
setting_files = find_setting_files()
else:
sys.exit()
if len(setting_files) > 1:
msg = "请从以下选项中选择一个配置文件"
title = "找到多个配置文件,请选择一个"
choice = easygui.choicebox(msg, title, setting_files)
setting_files = [choice]
if not is_valid_metadata_file(setting_files[0]):
decision = easygui.buttonbox("该文件通常位于:"
r"[系统盘]:\ProgramData\Riot Games\Metadata\league_of_legends.live"
r"\league_of_legends.live.product_settings.yaml",
"无效的配置文件,请重新选择", ["重新选择", "退出"])
if decision.lower() == '重新选择':
decision = easygui.buttonbox("该文件通常位于:\n\n"
rf"[系统盘]:{DEFAULT_METADATA_DIR}"
rf"{DEFAULT_METADATA_FILE}",
"未找到配置文件,请手动选择", ["手动选择", "退出"])
if decision.lower() == '手动选择':
setting_files = find_setting_files()
else:
sys.exit()
return setting_files[0]
return setting_files


def is_read_only(file_path):
Expand Down

0 comments on commit 82d1577

Please sign in to comment.