From e22dee6d7038f2339397fb446c33a0252e466b20 Mon Sep 17 00:00:00 2001 From: Savathun Date: Fri, 21 Nov 2025 17:22:59 -0700 Subject: [PATCH 01/16] fix plugin icons not showing up when building with mob by embedding svgs instead --- games/baldursgate3/plugins/bg3_tool_plugin.py | 16 +++---- .../plugins/check_for_lslib_updates_plugin.py | 4 +- .../plugins/convert_jsons_to_yaml_plugin.py | 3 +- games/baldursgate3/plugins/icons.py | 42 ++++++++++++++++++ games/baldursgate3/plugins/icons/ui-next.ico | Bin 110588 -> 0 bytes .../baldursgate3/plugins/icons/ui-refresh.ico | Bin 115044 -> 0 bytes .../baldursgate3/plugins/icons/ui-update.ico | Bin 120408 -> 0 bytes .../plugins/reparse_pak_metadata_plugin.py | 3 +- 8 files changed, 56 insertions(+), 12 deletions(-) create mode 100644 games/baldursgate3/plugins/icons.py delete mode 100644 games/baldursgate3/plugins/icons/ui-next.ico delete mode 100644 games/baldursgate3/plugins/icons/ui-refresh.ico delete mode 100644 games/baldursgate3/plugins/icons/ui-update.ico diff --git a/games/baldursgate3/plugins/bg3_tool_plugin.py b/games/baldursgate3/plugins/bg3_tool_plugin.py index d77c5fc..31db4ec 100644 --- a/games/baldursgate3/plugins/bg3_tool_plugin.py +++ b/games/baldursgate3/plugins/bg3_tool_plugin.py @@ -1,19 +1,19 @@ -from pathlib import Path - -from PyQt6.QtCore import QCoreApplication -from PyQt6.QtGui import QIcon - import mobase +from PyQt6.QtCore import QCoreApplication +from PyQt6.QtGui import QIcon, QPixmap class BG3ToolPlugin(mobase.IPluginTool, mobase.IPlugin): - icon_file = desc = sub_name = "" - + desc = sub_name = "" + icon_bytes: bytes def __init__(self): mobase.IPluginTool.__init__(self) mobase.IPlugin.__init__(self) self._pluginName = self._displayName = "BG3 Tools" self._pluginVersion = mobase.VersionInfo(1, 0, 0) + pixmap = QPixmap() + pixmap.loadFromData(self.icon_bytes, "SVG") + self.qicon = QIcon(pixmap) def init(self, organizer: mobase.IOrganizer) -> bool: self._organizer = organizer @@ -41,7 +41,7 @@ def settings(self) -> list[mobase.PluginSetting]: return [] def icon(self) -> QIcon: - return QIcon(str(Path(__file__).parent / "icons" / self.icon_file)) + return self.qicon def description(self) -> str: return QCoreApplication.translate(self._pluginName, self.desc) diff --git a/games/baldursgate3/plugins/check_for_lslib_updates_plugin.py b/games/baldursgate3/plugins/check_for_lslib_updates_plugin.py index bc4df8c..a72be68 100644 --- a/games/baldursgate3/plugins/check_for_lslib_updates_plugin.py +++ b/games/baldursgate3/plugins/check_for_lslib_updates_plugin.py @@ -1,8 +1,8 @@ from .bg3_tool_plugin import BG3ToolPlugin - +from .icons import download class BG3ToolCheckForLsLibUpdates(BG3ToolPlugin): - icon_file = "ui-update.ico" + icon_bytes = download sub_name = "Check For LsLib Updates" desc = "Check to see if there has been a new release of LSLib and create download dialog if so." diff --git a/games/baldursgate3/plugins/convert_jsons_to_yaml_plugin.py b/games/baldursgate3/plugins/convert_jsons_to_yaml_plugin.py index 58a51bb..f9c84cc 100644 --- a/games/baldursgate3/plugins/convert_jsons_to_yaml_plugin.py +++ b/games/baldursgate3/plugins/convert_jsons_to_yaml_plugin.py @@ -6,10 +6,11 @@ from PyQt6.QtWidgets import QApplication from .bg3_tool_plugin import BG3ToolPlugin +from .icons import exchange class BG3ToolConvertJsonsToYaml(BG3ToolPlugin): - icon_file = "ui-next.ico" + icon_bytes = exchange sub_name = "Convert JSONS to YAML" desc = "Convert all jsons in active mods to yaml immediately." diff --git a/games/baldursgate3/plugins/icons.py b/games/baldursgate3/plugins/icons.py new file mode 100644 index 0000000..adc1023 --- /dev/null +++ b/games/baldursgate3/plugins/icons.py @@ -0,0 +1,42 @@ +refresh = b""" + + + + + + + +""" + +exchange = b""" + + + + + + + + + + +""" + +download = b""" + + + + + + + + + + +""" diff --git a/games/baldursgate3/plugins/icons/ui-next.ico b/games/baldursgate3/plugins/icons/ui-next.ico deleted file mode 100644 index 1ef6e3b2fa1479d0c2c92a183d941e6d39fa9ba5..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 110588 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 z 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 S^=DpVALXQ#rD`NhLjEtO^(lV< diff --git a/games/baldursgate3/plugins/reparse_pak_metadata_plugin.py b/games/baldursgate3/plugins/reparse_pak_metadata_plugin.py index 4f75371..f32a8a0 100644 --- a/games/baldursgate3/plugins/reparse_pak_metadata_plugin.py +++ b/games/baldursgate3/plugins/reparse_pak_metadata_plugin.py @@ -1,8 +1,9 @@ from .bg3_tool_plugin import BG3ToolPlugin +from .icons import refresh class BG3ToolReparsePakMetadata(BG3ToolPlugin): - icon_file = "ui-refresh.ico" + icon_bytes = refresh sub_name = "Reparse Pak Metadata" desc = "Force reparsing mod metadata immediately." From c3dfec98613fcb857929b8434a424eb97d2fc799 Mon Sep 17 00:00:00 2001 From: Savathun Date: Fri, 21 Nov 2025 17:26:37 -0700 Subject: [PATCH 02/16] gate yaml import in bg3_file_mapper to ensure its only imported if user is using the functionality --- games/baldursgate3/bg3_file_mapper.py | 6 +++--- games/baldursgate3/plugins/convert_jsons_to_yaml_plugin.py | 2 +- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/games/baldursgate3/bg3_file_mapper.py b/games/baldursgate3/bg3_file_mapper.py index ba0b987..be8e3ba 100644 --- a/games/baldursgate3/bg3_file_mapper.py +++ b/games/baldursgate3/bg3_file_mapper.py @@ -1,11 +1,9 @@ import functools -import json import os from pathlib import Path from typing import Callable, Optional -import yaml -from PyQt6.QtCore import QDir, qDebug, qInfo, qWarning +from PyQt6.QtCore import QDir, qDebug, qInfo, qWarning, QLoggingCategory from PyQt6.QtWidgets import QApplication import mobase @@ -77,6 +75,8 @@ def map_files( if not converted_path.exists() or os.path.getmtime( file ) > os.path.getmtime(converted_path): + import json + import yaml with open(file, "r") as yaml_file: with open(converted_path, "w") as json_file: json.dump( diff --git a/games/baldursgate3/plugins/convert_jsons_to_yaml_plugin.py b/games/baldursgate3/plugins/convert_jsons_to_yaml_plugin.py index f9c84cc..628bc71 100644 --- a/games/baldursgate3/plugins/convert_jsons_to_yaml_plugin.py +++ b/games/baldursgate3/plugins/convert_jsons_to_yaml_plugin.py @@ -40,7 +40,6 @@ def display(self): def _convert_jsons_in_dir_to_yaml(path: Path): - import yaml for file in list(path.rglob("*.json")): converted_path = file.parent / file.name.replace(".json", ".yaml") @@ -48,6 +47,7 @@ def _convert_jsons_in_dir_to_yaml(path: Path): if not converted_path.exists() or os.path.getmtime(file) > os.path.getmtime( converted_path ): + import yaml with open(file, "r") as json_file: with open(converted_path, "w") as yaml_file: yaml.dump( From 80e8264bf7fd6726c57a64b85cb082f2b097d1fc Mon Sep 17 00:00:00 2001 From: Savathun Date: Fri, 21 Nov 2025 17:28:53 -0700 Subject: [PATCH 03/16] bail out of mapping function early if modlist is empty --- games/baldursgate3/bg3_file_mapper.py | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/games/baldursgate3/bg3_file_mapper.py b/games/baldursgate3/bg3_file_mapper.py index be8e3ba..545774f 100644 --- a/games/baldursgate3/bg3_file_mapper.py +++ b/games/baldursgate3/bg3_file_mapper.py @@ -27,12 +27,13 @@ def mappings(self) -> list[mobase.Mapping]: qInfo("creating custom bg3 mappings") self.current_mappings.clear() active_mods = self._utils.active_mods() - doc_dir = Path(self.doc_dir().path()) + if not active_mods: + return [] progress = self._utils.create_progress_window( "Mapping files to documents folder", len(active_mods) + 1 ) - docs_path_mods = doc_dir / "Mods" - docs_path_se = doc_dir / "Script Extender" + docs_path_mods = self.doc_path / "Mods" + docs_path_se = self.doc_path / "Script Extender" for mod in active_mods: modpath = Path(mod.absolutePath()) self.map_files(modpath, dest=docs_path_mods, pattern="*.pak", rel=False) @@ -45,7 +46,7 @@ def mappings(self) -> list[mobase.Mapping]: self.map_files(self._utils.overwrite_path) self.create_mapping( self._utils.modsettings_path, - doc_dir / "PlayerProfiles" / "Public" / self._utils.modsettings_path.name, + self.doc_path / "PlayerProfiles" / "Public" / self._utils.modsettings_path.name, ) progress.setValue(len(active_mods) + 1) QApplication.processEvents() From 662df8e98c5bf175e93da63a123a9ba87141a7ac Mon Sep 17 00:00:00 2001 From: Savathun Date: Fri, 21 Nov 2025 17:31:45 -0700 Subject: [PATCH 04/16] ensure spacing is consistent in generated modsettings.xml by creating a function to share the creating of the xml strings for ModuleShortDesc --- games/baldursgate3/bg3_utils.py | 47 +++++++++++++++++--------------- games/baldursgate3/pak_parser.py | 21 ++++++-------- 2 files changed, 34 insertions(+), 34 deletions(-) diff --git a/games/baldursgate3/bg3_utils.py b/games/baldursgate3/bg3_utils.py index a61890c..53f1efa 100644 --- a/games/baldursgate3/bg3_utils.py +++ b/games/baldursgate3/bg3_utils.py @@ -26,31 +26,34 @@ "ScriptExtender", } +def get_node_string(folder: str = "", md5: str = "", name: str = "", publish_handle: str = "0", uuid: str = "", version64: str = "0") -> str: + return f""" + + + + + + + + """ class BG3Utils: - _mod_settings_xml_start = """ - - - - - - - - - - - - - - - """ + _mod_settings_xml_start = f"""\ + + + + + + + + """ + get_node_string(folder="GustavX", name="GustavX", uuid="cb555efe-2d9e-131f-8195-a89329d218ea", version64="36028797018963968") _mod_settings_xml_end = """ - - - - - - """ + + + + + +""" def __init__(self, name: str): self.main_window = None diff --git a/games/baldursgate3/pak_parser.py b/games/baldursgate3/pak_parser.py index 826e124..5f2acf2 100644 --- a/games/baldursgate3/pak_parser.py +++ b/games/baldursgate3/pak_parser.py @@ -274,18 +274,15 @@ def metadata_to_ini( def get_module_short_desc(config: configparser.ConfigParser, file: Path) -> str: + if not config.has_section(file.name): + return "" + section: configparser.SectionProxy = config[file.name] return ( "" - if not config.has_section(file.name) - or "override" in config[file.name].keys() - or "Name" not in config[file.name].keys() - else f""" - - - - - - - - """ + if "override" in section.keys() + or "Name" not in section.keys() + else + bg3_utils.get_node_string(folder=section["Folder"], md5=section["MD5"], name=section["Name"], + publish_handle=section["PublishHandle"], uuid=section["UUID"], + version64=section["Version64"]) ) From fff5fb3afbe69aa406c5387be4f94c828106bf8a Mon Sep 17 00:00:00 2001 From: Savathun Date: Fri, 21 Nov 2025 17:33:05 -0700 Subject: [PATCH 05/16] dont do diffing if file doesnt exist or debug logging is not enabled --- games/game_baldursgate3.py | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/games/game_baldursgate3.py b/games/game_baldursgate3.py index fcc4497..0288f78 100644 --- a/games/game_baldursgate3.py +++ b/games/game_baldursgate3.py @@ -8,7 +8,7 @@ from PyQt6.QtCore import ( qDebug, - qInfo, + qInfo, QLoggingCategory, ) import mobase @@ -180,10 +180,10 @@ def _on_finished_run(self, exec_path: str, exit_code: int): if "bin/bg3" not in exec_path: return self.utils.log_dir.mkdir(parents=True, exist_ok=True) - if self.utils.log_diff: + if QLoggingCategory.defaultCategory().isDebugEnabled() and self.utils.log_diff and self.utils.modsettings_backup.exists() and self.utils.modsettings_path.exists(): for x in difflib.unified_diff( - open(self.utils.modsettings_backup).readlines(), - open(self.utils.modsettings_path).readlines(), + self.utils.modsettings_backup.open().readlines(), + self.utils.modsettings_path.open().readlines(), fromfile=str(self.utils.modsettings_backup), tofile=str(self.utils.modsettings_path), lineterm="", From a4bba4349a7796852911443cf25dd02dd0c94175 Mon Sep 17 00:00:00 2001 From: Savathun Date: Fri, 21 Nov 2025 17:33:56 -0700 Subject: [PATCH 06/16] ensure dialog boxes are exec'd so the user can see them --- games/baldursgate3/lslib_retriever.py | 2 ++ 1 file changed, 2 insertions(+) diff --git a/games/baldursgate3/lslib_retriever.py b/games/baldursgate3/lslib_retriever.py index 5a031f0..ee1122c 100644 --- a/games/baldursgate3/lslib_retriever.py +++ b/games/baldursgate3/lslib_retriever.py @@ -86,6 +86,7 @@ def reporthook(block_num: int, block_size: int, total_size: int) -> None: err.setText( "LSLib tools are required for the proper generation of the modsettings.xml file, file will not be generated" ) + err.exec() return False else: progress = self._utils.create_progress_window( @@ -106,6 +107,7 @@ def reporthook(block_num: int, block_size: int, total_size: int) -> None: new_msg.setText( self._utils.tr("Latest version of LSLib already downloaded!") ) + new_msg.exec() except Exception as e: qDebug(f"Download failed: {e}") From 2dce6339fc14965b9b08a780fc4990878dbbae26 Mon Sep 17 00:00:00 2001 From: Savathun Date: Fri, 21 Nov 2025 17:37:30 -0700 Subject: [PATCH 07/16] mv log.txt files to logs dir, only make one logging statement for file moving --- games/game_baldursgate3.py | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-) diff --git a/games/game_baldursgate3.py b/games/game_baldursgate3.py index 0288f78..19b38d1 100644 --- a/games/game_baldursgate3.py +++ b/games/game_baldursgate3.py @@ -189,12 +189,24 @@ def _on_finished_run(self, exec_path: str, exit_code: int): lineterm="", ): qDebug(x) + moved = {} for path in self.utils.overwrite_path.rglob("*.log"): try: - qDebug(f"moving {path} to {self.utils.log_dir}") - shutil.move(path, self.utils.log_dir / path.name) + moved[str(path.relative_to(Path.home()))] = str((self.utils.log_dir / path.name).relative_to(Path.home())) + path.replace(self.utils.log_dir / path.name) except PermissionError as e: qDebug(str(e)) + for path in self.utils.overwrite_path.rglob("*log.txt"): + dest = self.utils.log_dir / path.name + if path.name == "log.txt": + dest = self.utils.log_dir / f"{path.parent.name}-{path.name}" + try: + moved[str(path.relative_to(Path.home()))] = str(dest.relative_to(Path.home())) + path.replace(dest) + except PermissionError as e: + qDebug(str(e)) + if QLoggingCategory.defaultCategory().isDebugEnabled() and len(moved) > 0: + qDebug(f"moved log files to logs dir: {moved}") days = self.utils.get_setting("delete_levelcache_folders_older_than_x_days") if type(days) is int and days >= 0: cutoff_time = datetime.datetime.now() - datetime.timedelta(days=days) From e6dd9d0c9248d75b0e102f06c42d331befea1502 Mon Sep 17 00:00:00 2001 From: Savathun Date: Fri, 21 Nov 2025 17:38:51 -0700 Subject: [PATCH 08/16] remove empty folders left behind by plugin in documents dir when executable finishes, log folders removed --- games/game_baldursgate3.py | 22 ++++++++++++++-------- 1 file changed, 14 insertions(+), 8 deletions(-) diff --git a/games/game_baldursgate3.py b/games/game_baldursgate3.py index 19b38d1..da8ff51 100644 --- a/games/game_baldursgate3.py +++ b/games/game_baldursgate3.py @@ -211,17 +211,23 @@ def _on_finished_run(self, exec_path: str, exit_code: int): if type(days) is int and days >= 0: cutoff_time = datetime.datetime.now() - datetime.timedelta(days=days) qDebug(f"cleaning folders in overwrite/LevelCache older than {cutoff_time}") + removed = set() for path in self.utils.overwrite_path.glob("LevelCache/*"): if ( datetime.datetime.fromtimestamp(os.path.getmtime(path)) < cutoff_time ): shutil.rmtree(path, ignore_errors=True) - qDebug("cleaning empty dirs from overwrite directory") - for folder in sorted( - list(os.walk(self.utils.overwrite_path))[1:], reverse=True - ): - try: - os.rmdir(folder[0]) - except OSError: - pass + removed.add(path) + if QLoggingCategory.defaultCategory().isDebugEnabled() and len(removed) > 0: + qDebug(f"cleaned the following folders due to them being older than {cutoff_time}: {removed}") + for fdir in {self.utils.overwrite_path, self.doc_path}: + removed = set() + for folder in sorted(list(fdir.walk(top_down=False)))[:-1]: + try: + folder[0].rmdir() + removed.add(folder[0].relative_to(Path.home())) + except OSError: + pass + if QLoggingCategory.defaultCategory().isDebugEnabled() and len(removed) > 0: + qDebug(f"cleaned empty dirs from {fdir.relative_to(Path.home())} {removed}") From f175709f38e8168ac211802701f02a33a9378929 Mon Sep 17 00:00:00 2001 From: Savathun Date: Fri, 21 Nov 2025 17:40:28 -0700 Subject: [PATCH 09/16] add conversion of yamls in bin folder that wont get mapped to the documents directory --- games/baldursgate3/bg3_file_mapper.py | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/games/baldursgate3/bg3_file_mapper.py b/games/baldursgate3/bg3_file_mapper.py index 545774f..b492a24 100644 --- a/games/baldursgate3/bg3_file_mapper.py +++ b/games/baldursgate3/bg3_file_mapper.py @@ -38,6 +38,8 @@ def mappings(self) -> list[mobase.Mapping]: modpath = Path(mod.absolutePath()) self.map_files(modpath, dest=docs_path_mods, pattern="*.pak", rel=False) self.map_files(modpath / "Script Extender", dest=docs_path_se) + if self._utils.convert_yamls_to_json: + self.map_files(modpath / "bin", only_convert=True) progress.setValue(progress.value() + 1) QApplication.processEvents() if progress.wasCanceled(): @@ -59,6 +61,7 @@ def map_files( dest: Optional[Path] = None, pattern: str = "*", rel: bool = True, + only_convert: bool = False ): dest = dest if dest else self.doc_path dest_func: Callable[[Path], str] = ( @@ -89,8 +92,10 @@ def map_files( qWarning(f"Error accessing file {converted_path}: {e}") elif file.name.endswith(".json"): found_jsons.add(file) - else: + elif not only_convert: self.create_mapping(file, dest / dest_func(file)) + if only_convert: + return for file in found_jsons: self.create_mapping(file, dest / dest_func(file)) From 31a844f0cf8ccfa3561d2a3db20f8b2062344810 Mon Sep 17 00:00:00 2001 From: Savathun Date: Fri, 21 Nov 2025 17:43:18 -0700 Subject: [PATCH 10/16] ensure all directories are created when they are needed --- games/baldursgate3/bg3_file_mapper.py | 2 ++ games/baldursgate3/bg3_utils.py | 20 ++++++++++++++------ 2 files changed, 16 insertions(+), 6 deletions(-) diff --git a/games/baldursgate3/bg3_file_mapper.py b/games/baldursgate3/bg3_file_mapper.py index b492a24..c0e1890 100644 --- a/games/baldursgate3/bg3_file_mapper.py +++ b/games/baldursgate3/bg3_file_mapper.py @@ -100,6 +100,8 @@ def map_files( self.create_mapping(file, dest / dest_func(file)) def create_mapping(self, file: Path, dest: Path): + bg3_utils.create_dir_if_needed(dest) + self.current_mappings.append( mobase.Mapping( source=str(file), diff --git a/games/baldursgate3/bg3_utils.py b/games/baldursgate3/bg3_utils.py index 53f1efa..180860c 100644 --- a/games/baldursgate3/bg3_utils.py +++ b/games/baldursgate3/bg3_utils.py @@ -92,28 +92,28 @@ def convert_yamls_to_json(self): @functools.cached_property def log_dir(self): - return Path(self._organizer.basePath()) / "logs" + return create_dir_if_needed(Path(self._organizer.basePath()) / "logs") @functools.cached_property def modsettings_backup(self): - return self.plugin_data_path / "temp" / "modsettings.lsx" + return create_dir_if_needed(self.plugin_data_path / "temp" / "modsettings.lsx") @functools.cached_property def modsettings_path(self): - return Path(self._organizer.profilePath()) / "modsettings.lsx" + return create_dir_if_needed(Path(self._organizer.profilePath()) / "modsettings.lsx") @functools.cached_property def plugin_data_path(self) -> Path: """Gets the path to the data folder for the current plugin.""" - return Path(self._organizer.pluginDataPath(), self._name).absolute() + return create_dir_if_needed(Path(self._organizer.pluginDataPath(), self._name).absolute()) @functools.cached_property def tools_dir(self): - return self.plugin_data_path / "tools" + return create_dir_if_needed(self.plugin_data_path / "tools") @functools.cached_property def overwrite_path(self): - return Path(self._organizer.overwritePath()) + return create_dir_if_needed(Path(self._organizer.overwritePath())) def active_mods(self) -> list[mobase.IModInterface]: modlist = self._organizer.modList() @@ -237,9 +237,17 @@ def retrieve_mod_metadata_in_new_thread(mod: mobase.IModInterface): f"backing up generated file {self.modsettings_path} to {self.modsettings_backup}, " f"check the backup after the executable runs for differences with the file used by the game if you encounter issues" ) + self.modsettings_backup.parent.mkdir(parents=True, exist_ok=True) shutil.copy(self.modsettings_path, self.modsettings_backup) return True def on_mod_installed(self, mod: mobase.IModInterface) -> None: if self.lslib_retriever.download_lslib_if_missing(): self._pak_parser.get_metadata_for_files_in_mod(mod, True) + +def create_dir_if_needed(path: Path) -> Path: + if '.' not in path.name[1:]: + path.mkdir(parents=True, exist_ok=True) + else: + path.parent.mkdir(parents=True, exist_ok=True) + return path From fcf7033984ea72d5baee9c7df78212f2dc4bdc70 Mon Sep 17 00:00:00 2001 From: Savathun Date: Fri, 21 Nov 2025 17:44:10 -0700 Subject: [PATCH 11/16] add catch for oserror in pak parsing function --- games/baldursgate3/pak_parser.py | 24 ++++++++++++++---------- 1 file changed, 14 insertions(+), 10 deletions(-) diff --git a/games/baldursgate3/pak_parser.py b/games/baldursgate3/pak_parser.py index 5f2acf2..bd8f533 100644 --- a/games/baldursgate3/pak_parser.py +++ b/games/baldursgate3/pak_parser.py @@ -161,17 +161,21 @@ def _get_metadata_for_file( ) build_pak = True if pak_path.exists(): - pak_creation_time = os.path.getmtime(pak_path) - for root, _, files in os.walk(file): - for f in files: - file_path = os.path.join(root, f) - try: - if os.path.getmtime(file_path) > pak_creation_time: + try: + pak_creation_time = os.path.getmtime(pak_path) + for root, _, files in file.walk(): + for f in files: + file_path = root.joinpath(f) + try: + if os.path.getmtime(file_path) > pak_creation_time: + break + except OSError as e: + qDebug(f"Error accessing file {file_path}: {e}") break - except OSError as e: - qDebug(f"Error accessing file {file_path}: {e}") - break - else: + else: + build_pak = False + except OSError as e: + qDebug(f"Error accessing file {pak_path}: {e}") build_pak = False if build_pak: pak_path.unlink(missing_ok=True) From 4e4543205681500f54313de478a4b5bf421f9d27 Mon Sep 17 00:00:00 2001 From: Savathun Date: Fri, 21 Nov 2025 17:45:39 -0700 Subject: [PATCH 12/16] add a small sleep after creation of modsettings.xml to ensure the executable does not launch too fast to see it --- games/baldursgate3/bg3_utils.py | 2 ++ 1 file changed, 2 insertions(+) diff --git a/games/baldursgate3/bg3_utils.py b/games/baldursgate3/bg3_utils.py index 180860c..9330ff7 100644 --- a/games/baldursgate3/bg3_utils.py +++ b/games/baldursgate3/bg3_utils.py @@ -2,6 +2,7 @@ import shutil import typing from pathlib import Path +from time import sleep from PyQt6.QtCore import ( QCoreApplication, @@ -239,6 +240,7 @@ def retrieve_mod_metadata_in_new_thread(mod: mobase.IModInterface): ) self.modsettings_backup.parent.mkdir(parents=True, exist_ok=True) shutil.copy(self.modsettings_path, self.modsettings_backup) + sleep(0.5) return True def on_mod_installed(self, mod: mobase.IModInterface) -> None: From 0f62cec4b0d1f1edd6e399e031769ea68dfaeebf Mon Sep 17 00:00:00 2001 From: Savathun Date: Fri, 21 Nov 2025 17:47:32 -0700 Subject: [PATCH 13/16] create directories that should be sent to overwrite folder from the documents folder if they dont exist in the mapping function, log all directories mapped if debug is enabled --- games/baldursgate3/bg3_file_mapper.py | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/games/baldursgate3/bg3_file_mapper.py b/games/baldursgate3/bg3_file_mapper.py index c0e1890..0b77148 100644 --- a/games/baldursgate3/bg3_file_mapper.py +++ b/games/baldursgate3/bg3_file_mapper.py @@ -45,6 +45,13 @@ def mappings(self) -> list[mobase.Mapping]: if progress.wasCanceled(): qWarning("mapping canceled by user") return self.current_mappings + (self._utils.overwrite_path / 'Script Extender').mkdir(parents=True, exist_ok=True) + (self._utils.overwrite_path / 'Stats').mkdir(parents=True, exist_ok=True) + (self._utils.overwrite_path / 'Temp').mkdir(parents=True, exist_ok=True) + (self._utils.overwrite_path / 'LevelCache').mkdir(parents=True, exist_ok=True) + (self._utils.overwrite_path / 'Stats').mkdir(parents=True, exist_ok=True) + (self._utils.overwrite_path / 'Mods').mkdir(parents=True, exist_ok=True) + (self._utils.overwrite_path / 'GMCampaigns').mkdir(parents=True, exist_ok=True) self.map_files(self._utils.overwrite_path) self.create_mapping( self._utils.modsettings_path, @@ -53,6 +60,8 @@ def mappings(self) -> list[mobase.Mapping]: progress.setValue(len(active_mods) + 1) QApplication.processEvents() progress.close() + if QLoggingCategory.defaultCategory().isDebugEnabled(): + qDebug(f"resolved mappings: { {m.source: m.destination for m in self.current_mappings} }") return self.current_mappings def map_files( From eb0b8ad46cdedbb4a4e7e5478207bd5949367ef2 Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Sat, 22 Nov 2025 00:50:44 +0000 Subject: [PATCH 14/16] [pre-commit.ci] Auto fixes from pre-commit.com hooks. --- games/baldursgate3/bg3_file_mapper.py | 31 ++++++++++++------- games/baldursgate3/bg3_utils.py | 31 +++++++++++++++---- games/baldursgate3/pak_parser.py | 15 +++++---- games/baldursgate3/plugins/bg3_tool_plugin.py | 4 ++- .../plugins/check_for_lslib_updates_plugin.py | 1 + .../plugins/convert_jsons_to_yaml_plugin.py | 2 +- games/game_baldursgate3.py | 26 ++++++++++++---- 7 files changed, 79 insertions(+), 31 deletions(-) diff --git a/games/baldursgate3/bg3_file_mapper.py b/games/baldursgate3/bg3_file_mapper.py index 0b77148..2567287 100644 --- a/games/baldursgate3/bg3_file_mapper.py +++ b/games/baldursgate3/bg3_file_mapper.py @@ -3,7 +3,7 @@ from pathlib import Path from typing import Callable, Optional -from PyQt6.QtCore import QDir, qDebug, qInfo, qWarning, QLoggingCategory +from PyQt6.QtCore import QDir, QLoggingCategory, qDebug, qInfo, qWarning from PyQt6.QtWidgets import QApplication import mobase @@ -45,23 +45,30 @@ def mappings(self) -> list[mobase.Mapping]: if progress.wasCanceled(): qWarning("mapping canceled by user") return self.current_mappings - (self._utils.overwrite_path / 'Script Extender').mkdir(parents=True, exist_ok=True) - (self._utils.overwrite_path / 'Stats').mkdir(parents=True, exist_ok=True) - (self._utils.overwrite_path / 'Temp').mkdir(parents=True, exist_ok=True) - (self._utils.overwrite_path / 'LevelCache').mkdir(parents=True, exist_ok=True) - (self._utils.overwrite_path / 'Stats').mkdir(parents=True, exist_ok=True) - (self._utils.overwrite_path / 'Mods').mkdir(parents=True, exist_ok=True) - (self._utils.overwrite_path / 'GMCampaigns').mkdir(parents=True, exist_ok=True) + (self._utils.overwrite_path / "Script Extender").mkdir( + parents=True, exist_ok=True + ) + (self._utils.overwrite_path / "Stats").mkdir(parents=True, exist_ok=True) + (self._utils.overwrite_path / "Temp").mkdir(parents=True, exist_ok=True) + (self._utils.overwrite_path / "LevelCache").mkdir(parents=True, exist_ok=True) + (self._utils.overwrite_path / "Stats").mkdir(parents=True, exist_ok=True) + (self._utils.overwrite_path / "Mods").mkdir(parents=True, exist_ok=True) + (self._utils.overwrite_path / "GMCampaigns").mkdir(parents=True, exist_ok=True) self.map_files(self._utils.overwrite_path) self.create_mapping( self._utils.modsettings_path, - self.doc_path / "PlayerProfiles" / "Public" / self._utils.modsettings_path.name, + self.doc_path + / "PlayerProfiles" + / "Public" + / self._utils.modsettings_path.name, ) progress.setValue(len(active_mods) + 1) QApplication.processEvents() progress.close() if QLoggingCategory.defaultCategory().isDebugEnabled(): - qDebug(f"resolved mappings: { {m.source: m.destination for m in self.current_mappings} }") + qDebug( + f"resolved mappings: { {m.source: m.destination for m in self.current_mappings} }" + ) return self.current_mappings def map_files( @@ -70,7 +77,7 @@ def map_files( dest: Optional[Path] = None, pattern: str = "*", rel: bool = True, - only_convert: bool = False + only_convert: bool = False, ): dest = dest if dest else self.doc_path dest_func: Callable[[Path], str] = ( @@ -89,7 +96,9 @@ def map_files( file ) > os.path.getmtime(converted_path): import json + import yaml + with open(file, "r") as yaml_file: with open(converted_path, "w") as json_file: json.dump( diff --git a/games/baldursgate3/bg3_utils.py b/games/baldursgate3/bg3_utils.py index 9330ff7..958d173 100644 --- a/games/baldursgate3/bg3_utils.py +++ b/games/baldursgate3/bg3_utils.py @@ -27,7 +27,15 @@ "ScriptExtender", } -def get_node_string(folder: str = "", md5: str = "", name: str = "", publish_handle: str = "0", uuid: str = "", version64: str = "0") -> str: + +def get_node_string( + folder: str = "", + md5: str = "", + name: str = "", + publish_handle: str = "0", + uuid: str = "", + version64: str = "0", +) -> str: return f""" @@ -38,8 +46,9 @@ def get_node_string(folder: str = "", md5: str = "", name: str = "", publish_han """ + class BG3Utils: - _mod_settings_xml_start = f"""\ + _mod_settings_xml_start = """\ @@ -47,7 +56,12 @@ class BG3Utils: - """ + get_node_string(folder="GustavX", name="GustavX", uuid="cb555efe-2d9e-131f-8195-a89329d218ea", version64="36028797018963968") + """ + get_node_string( + folder="GustavX", + name="GustavX", + uuid="cb555efe-2d9e-131f-8195-a89329d218ea", + version64="36028797018963968", + ) _mod_settings_xml_end = """ @@ -101,12 +115,16 @@ def modsettings_backup(self): @functools.cached_property def modsettings_path(self): - return create_dir_if_needed(Path(self._organizer.profilePath()) / "modsettings.lsx") + return create_dir_if_needed( + Path(self._organizer.profilePath()) / "modsettings.lsx" + ) @functools.cached_property def plugin_data_path(self) -> Path: """Gets the path to the data folder for the current plugin.""" - return create_dir_if_needed(Path(self._organizer.pluginDataPath(), self._name).absolute()) + return create_dir_if_needed( + Path(self._organizer.pluginDataPath(), self._name).absolute() + ) @functools.cached_property def tools_dir(self): @@ -247,8 +265,9 @@ def on_mod_installed(self, mod: mobase.IModInterface) -> None: if self.lslib_retriever.download_lslib_if_missing(): self._pak_parser.get_metadata_for_files_in_mod(mod, True) + def create_dir_if_needed(path: Path) -> Path: - if '.' not in path.name[1:]: + if "." not in path.name[1:]: path.mkdir(parents=True, exist_ok=True) else: path.parent.mkdir(parents=True, exist_ok=True) diff --git a/games/baldursgate3/pak_parser.py b/games/baldursgate3/pak_parser.py index bd8f533..18598a9 100644 --- a/games/baldursgate3/pak_parser.py +++ b/games/baldursgate3/pak_parser.py @@ -283,10 +283,13 @@ def get_module_short_desc(config: configparser.ConfigParser, file: Path) -> str: section: configparser.SectionProxy = config[file.name] return ( "" - if "override" in section.keys() - or "Name" not in section.keys() - else - bg3_utils.get_node_string(folder=section["Folder"], md5=section["MD5"], name=section["Name"], - publish_handle=section["PublishHandle"], uuid=section["UUID"], - version64=section["Version64"]) + if "override" in section.keys() or "Name" not in section.keys() + else bg3_utils.get_node_string( + folder=section["Folder"], + md5=section["MD5"], + name=section["Name"], + publish_handle=section["PublishHandle"], + uuid=section["UUID"], + version64=section["Version64"], + ) ) diff --git a/games/baldursgate3/plugins/bg3_tool_plugin.py b/games/baldursgate3/plugins/bg3_tool_plugin.py index 31db4ec..fc258a6 100644 --- a/games/baldursgate3/plugins/bg3_tool_plugin.py +++ b/games/baldursgate3/plugins/bg3_tool_plugin.py @@ -1,11 +1,13 @@ -import mobase from PyQt6.QtCore import QCoreApplication from PyQt6.QtGui import QIcon, QPixmap +import mobase + class BG3ToolPlugin(mobase.IPluginTool, mobase.IPlugin): desc = sub_name = "" icon_bytes: bytes + def __init__(self): mobase.IPluginTool.__init__(self) mobase.IPlugin.__init__(self) diff --git a/games/baldursgate3/plugins/check_for_lslib_updates_plugin.py b/games/baldursgate3/plugins/check_for_lslib_updates_plugin.py index a72be68..b534e8a 100644 --- a/games/baldursgate3/plugins/check_for_lslib_updates_plugin.py +++ b/games/baldursgate3/plugins/check_for_lslib_updates_plugin.py @@ -1,6 +1,7 @@ from .bg3_tool_plugin import BG3ToolPlugin from .icons import download + class BG3ToolCheckForLsLibUpdates(BG3ToolPlugin): icon_bytes = download sub_name = "Check For LsLib Updates" diff --git a/games/baldursgate3/plugins/convert_jsons_to_yaml_plugin.py b/games/baldursgate3/plugins/convert_jsons_to_yaml_plugin.py index 628bc71..fde3431 100644 --- a/games/baldursgate3/plugins/convert_jsons_to_yaml_plugin.py +++ b/games/baldursgate3/plugins/convert_jsons_to_yaml_plugin.py @@ -40,7 +40,6 @@ def display(self): def _convert_jsons_in_dir_to_yaml(path: Path): - for file in list(path.rglob("*.json")): converted_path = file.parent / file.name.replace(".json", ".yaml") try: @@ -48,6 +47,7 @@ def _convert_jsons_in_dir_to_yaml(path: Path): converted_path ): import yaml + with open(file, "r") as json_file: with open(converted_path, "w") as yaml_file: yaml.dump( diff --git a/games/game_baldursgate3.py b/games/game_baldursgate3.py index da8ff51..dca7fb2 100644 --- a/games/game_baldursgate3.py +++ b/games/game_baldursgate3.py @@ -7,8 +7,9 @@ from typing import Any from PyQt6.QtCore import ( + QLoggingCategory, qDebug, - qInfo, QLoggingCategory, + qInfo, ) import mobase @@ -180,7 +181,12 @@ def _on_finished_run(self, exec_path: str, exit_code: int): if "bin/bg3" not in exec_path: return self.utils.log_dir.mkdir(parents=True, exist_ok=True) - if QLoggingCategory.defaultCategory().isDebugEnabled() and self.utils.log_diff and self.utils.modsettings_backup.exists() and self.utils.modsettings_path.exists(): + if ( + QLoggingCategory.defaultCategory().isDebugEnabled() + and self.utils.log_diff + and self.utils.modsettings_backup.exists() + and self.utils.modsettings_path.exists() + ): for x in difflib.unified_diff( self.utils.modsettings_backup.open().readlines(), self.utils.modsettings_path.open().readlines(), @@ -192,7 +198,9 @@ def _on_finished_run(self, exec_path: str, exit_code: int): moved = {} for path in self.utils.overwrite_path.rglob("*.log"): try: - moved[str(path.relative_to(Path.home()))] = str((self.utils.log_dir / path.name).relative_to(Path.home())) + moved[str(path.relative_to(Path.home()))] = str( + (self.utils.log_dir / path.name).relative_to(Path.home()) + ) path.replace(self.utils.log_dir / path.name) except PermissionError as e: qDebug(str(e)) @@ -201,7 +209,9 @@ def _on_finished_run(self, exec_path: str, exit_code: int): if path.name == "log.txt": dest = self.utils.log_dir / f"{path.parent.name}-{path.name}" try: - moved[str(path.relative_to(Path.home()))] = str(dest.relative_to(Path.home())) + moved[str(path.relative_to(Path.home()))] = str( + dest.relative_to(Path.home()) + ) path.replace(dest) except PermissionError as e: qDebug(str(e)) @@ -220,7 +230,9 @@ def _on_finished_run(self, exec_path: str, exit_code: int): shutil.rmtree(path, ignore_errors=True) removed.add(path) if QLoggingCategory.defaultCategory().isDebugEnabled() and len(removed) > 0: - qDebug(f"cleaned the following folders due to them being older than {cutoff_time}: {removed}") + qDebug( + f"cleaned the following folders due to them being older than {cutoff_time}: {removed}" + ) for fdir in {self.utils.overwrite_path, self.doc_path}: removed = set() for folder in sorted(list(fdir.walk(top_down=False)))[:-1]: @@ -230,4 +242,6 @@ def _on_finished_run(self, exec_path: str, exit_code: int): except OSError: pass if QLoggingCategory.defaultCategory().isDebugEnabled() and len(removed) > 0: - qDebug(f"cleaned empty dirs from {fdir.relative_to(Path.home())} {removed}") + qDebug( + f"cleaned empty dirs from {fdir.relative_to(Path.home())} {removed}" + ) From 172fba1ccd5723c76edc7aa2c5a9d30e2948d703 Mon Sep 17 00:00:00 2001 From: Savathun Date: Fri, 21 Nov 2025 17:57:45 -0700 Subject: [PATCH 15/16] lint --- games/baldursgate3/bg3_file_mapper.py | 3 ++- games/game_baldursgate3.py | 15 ++++++++------- 2 files changed, 10 insertions(+), 8 deletions(-) diff --git a/games/baldursgate3/bg3_file_mapper.py b/games/baldursgate3/bg3_file_mapper.py index 2567287..0ae6ef8 100644 --- a/games/baldursgate3/bg3_file_mapper.py +++ b/games/baldursgate3/bg3_file_mapper.py @@ -65,7 +65,8 @@ def mappings(self) -> list[mobase.Mapping]: progress.setValue(len(active_mods) + 1) QApplication.processEvents() progress.close() - if QLoggingCategory.defaultCategory().isDebugEnabled(): + cat = QLoggingCategory.defaultCategory() + if cat is not None and cat.isDebugEnabled(): qDebug( f"resolved mappings: { {m.source: m.destination for m in self.current_mappings} }" ) diff --git a/games/game_baldursgate3.py b/games/game_baldursgate3.py index dca7fb2..6baf03e 100644 --- a/games/game_baldursgate3.py +++ b/games/game_baldursgate3.py @@ -180,9 +180,10 @@ def _base_dlls(self) -> set[str]: def _on_finished_run(self, exec_path: str, exit_code: int): if "bin/bg3" not in exec_path: return + cat = QLoggingCategory.defaultCategory() self.utils.log_dir.mkdir(parents=True, exist_ok=True) if ( - QLoggingCategory.defaultCategory().isDebugEnabled() + cat is not None and cat.isDebugEnabled() and self.utils.log_diff and self.utils.modsettings_backup.exists() and self.utils.modsettings_path.exists() @@ -195,7 +196,7 @@ def _on_finished_run(self, exec_path: str, exit_code: int): lineterm="", ): qDebug(x) - moved = {} + moved: dict[str, str] = {} for path in self.utils.overwrite_path.rglob("*.log"): try: moved[str(path.relative_to(Path.home()))] = str( @@ -215,13 +216,13 @@ def _on_finished_run(self, exec_path: str, exit_code: int): path.replace(dest) except PermissionError as e: qDebug(str(e)) - if QLoggingCategory.defaultCategory().isDebugEnabled() and len(moved) > 0: + if cat is not None and cat.isDebugEnabled() and len(moved) > 0: qDebug(f"moved log files to logs dir: {moved}") days = self.utils.get_setting("delete_levelcache_folders_older_than_x_days") if type(days) is int and days >= 0: cutoff_time = datetime.datetime.now() - datetime.timedelta(days=days) qDebug(f"cleaning folders in overwrite/LevelCache older than {cutoff_time}") - removed = set() + removed: set[Path] = set() for path in self.utils.overwrite_path.glob("LevelCache/*"): if ( datetime.datetime.fromtimestamp(os.path.getmtime(path)) @@ -229,19 +230,19 @@ def _on_finished_run(self, exec_path: str, exit_code: int): ): shutil.rmtree(path, ignore_errors=True) removed.add(path) - if QLoggingCategory.defaultCategory().isDebugEnabled() and len(removed) > 0: + if cat is not None and cat.isDebugEnabled() and len(removed) > 0: qDebug( f"cleaned the following folders due to them being older than {cutoff_time}: {removed}" ) for fdir in {self.utils.overwrite_path, self.doc_path}: - removed = set() + removed: set[Path] = set() for folder in sorted(list(fdir.walk(top_down=False)))[:-1]: try: folder[0].rmdir() removed.add(folder[0].relative_to(Path.home())) except OSError: pass - if QLoggingCategory.defaultCategory().isDebugEnabled() and len(removed) > 0: + if cat is not None and cat.isDebugEnabled() and len(removed) > 0: qDebug( f"cleaned empty dirs from {fdir.relative_to(Path.home())} {removed}" ) From 43a896eac748996d4abc455a7636b49f254a04dc Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Sat, 22 Nov 2025 00:58:00 +0000 Subject: [PATCH 16/16] [pre-commit.ci] Auto fixes from pre-commit.com hooks. --- games/game_baldursgate3.py | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/games/game_baldursgate3.py b/games/game_baldursgate3.py index 6baf03e..560eec1 100644 --- a/games/game_baldursgate3.py +++ b/games/game_baldursgate3.py @@ -183,7 +183,8 @@ def _on_finished_run(self, exec_path: str, exit_code: int): cat = QLoggingCategory.defaultCategory() self.utils.log_dir.mkdir(parents=True, exist_ok=True) if ( - cat is not None and cat.isDebugEnabled() + cat is not None + and cat.isDebugEnabled() and self.utils.log_diff and self.utils.modsettings_backup.exists() and self.utils.modsettings_path.exists()