diff --git a/tagstudio/src/cli/ts_cli.py b/tagstudio/src/cli/ts_cli.py index 30e14ae9..723e8ef2 100644 --- a/tagstudio/src/cli/ts_cli.py +++ b/tagstudio/src/cli/ts_cli.py @@ -23,6 +23,7 @@ from src.core.ts_core import * from src.core.utils.web import * from src.core.utils.fs import * from src.core.library import * +from src.qt.helpers.file_opener import open_file WHITE_FG = '\033[37m' WHITE_BG = '\033[47m' @@ -352,8 +353,8 @@ class CliDriver: if not os.path.isfile(external_preview_path): temp = self.external_preview_default temp.save(external_preview_path) - if os.path.isfile(external_preview_path): - os.startfile(external_preview_path) + + open_file(external_preview_path) def set_external_preview_default(self) -> None: """Sets the external preview to its default image.""" @@ -1703,11 +1704,9 @@ class CliDriver: elif (com[0].lower() == 'open' or com[0].lower() == 'o'): if len(com) > 1: if com[1].lower() == 'location' or com[1].lower() == 'l': - args = ['explorer', '/select,', filename] - subprocess.call(args) + open_file(filename, True) else: - if os.path.isfile(filename): - os.startfile(filename) + open_file(filename) # refresh=False # self.scr_browse_entries_gallery(index) # Add Field ============================================================ @@ -2152,9 +2151,8 @@ class CliDriver: # Open ============================================================= elif (com[0].lower() == 'open' or com[0].lower() == 'o'): for match in self.lib.missing_matches[filename]: - fn = f'{os.path.normpath(self.lib.library_dir + "/" + match + "/" + entry.filename)}' - if os.path.isfile(fn): - os.startfile(fn) + fn = os.path.normpath(self.lib.library_dir + "/" + match + "/" + entry.filename) + open_file(fn) refresh = False # clear() # return self.scr_choose_missing_match(index, clear_scr=False) @@ -2274,10 +2272,9 @@ class CliDriver: elif (com[0].lower() == 'open' or com[0].lower() == 'o'): # for match in self.lib.missing_matches[filename]: # fn = f'{os.path.normpath(self.lib.library_dir + "/" + match + "/" + entry_1.filename)}' - # if os.path.isfile(fn): - # os.startfile(fn) - os.startfile(dupe[0]) - os.startfile(dupe[1]) + # open_file(fn) + open_file(dupe[0]) + open_file(dupe[1]) # clear() # return self.scr_resolve_dupe_files(index, clear_scr=False) # Mirror Entries =================================================== @@ -2385,8 +2382,7 @@ class CliDriver: # Open with Default Application ======================================== if (com[0].lower() == 'open' or com[0].lower() == 'o'): - if os.path.isfile(filename): - os.startfile(filename) + open_file(filename) # self.scr_edit_entry_tag_box(entry_index, field_index) # return # Close View =========================================================== diff --git a/tagstudio/src/qt/helpers/__init__.py b/tagstudio/src/qt/helpers/__init__.py index f66a6473..a79b66ab 100644 --- a/tagstudio/src/qt/helpers/__init__.py +++ b/tagstudio/src/qt/helpers/__init__.py @@ -1,4 +1,3 @@ -from .open_file import open_file -from .file_opener import FileOpenerHelper, FileOpenerLabel +from .file_opener import open_file, FileOpenerHelper, FileOpenerLabel from .function_iterator import FunctionIterator -from .custom_runnable import CustomRunnable \ No newline at end of file +from .custom_runnable import CustomRunnable diff --git a/tagstudio/src/qt/helpers/file_opener.py b/tagstudio/src/qt/helpers/file_opener.py index e6703f11..25f5d1dd 100644 --- a/tagstudio/src/qt/helpers/file_opener.py +++ b/tagstudio/src/qt/helpers/file_opener.py @@ -5,6 +5,9 @@ import logging import os import subprocess +import shutil +import sys +import traceback from PySide6.QtWidgets import QLabel @@ -15,7 +18,49 @@ INFO = f'[INFO]' logging.basicConfig(format="%(message)s", level=logging.INFO) -class FileOpenerHelper(): +def open_file(path: str, file_manager: bool = False): + logging.info(f'Opening file: {path}') + if not os.path.exists(path): + logging.error(f'File not found: {path}') + return + try: + if sys.platform == "win32": + normpath = os.path.normpath(path) + if file_manager: + command_name = "explorer" + command_args = [f"/select,{normpath}"] + else: + command_name = "start" + # first parameter is for title, NOT filepath + command_args = ["", normpath] + subprocess.Popen([command_name] + command_args, shell=True, close_fds=True, creationflags=subprocess.CREATE_NEW_PROCESS_GROUP | subprocess.CREATE_BREAKAWAY_FROM_JOB) + else: + if sys.platform == "darwin": + command_name = "open" + command_args = [path] + if file_manager: + # will reveal in Finder + command_args.append("-R") + else: + if file_manager: + command_name = "dbus-send" + # might not be guaranteed to launch default? + command_args = ["--session", "--dest=org.freedesktop.FileManager1", "--type=method_call", + "/org/freedesktop/FileManager1", "org.freedesktop.FileManager1.ShowItems", + f"array:string:file://{path}", "string:"] + else: + command_name = "xdg-open" + command_args = [path] + command = shutil.which(command_name) + if command is not None: + subprocess.Popen([command] + command_args, close_fds=True) + else: + logging.info(f"Could not find {command_name} on system PATH") + except: + traceback.print_exc() + + +class FileOpenerHelper: def __init__(self, filepath:str): self.filepath = filepath @@ -23,26 +68,10 @@ class FileOpenerHelper(): self.filepath = filepath def open_file(self): - if os.path.exists(self.filepath): - os.startfile(self.filepath) - logging.info(f'Opening file: {self.filepath}') - else: - logging.error(f'File not found: {self.filepath}') + open_file(self.filepath) def open_explorer(self): - if os.path.exists(self.filepath): - logging.info(f'Opening file: {self.filepath}') - if os.name == 'nt': # Windows - command = f'explorer /select,"{self.filepath}"' - subprocess.run(command, shell=True) - else: # macOS and Linux - command = f'nautilus --select "{self.filepath}"' # Adjust for your Linux file manager if different - if subprocess.run(command, shell=True).returncode == 0: - file_loc = os.path.dirname(self.filepath) - file_loc = os.path.normpath(file_loc) - os.startfile(file_loc) - else: - logging.error(f'File not found: {self.filepath}') + open_file(self.filepath, True) class FileOpenerLabel(QLabel): diff --git a/tagstudio/src/qt/helpers/open_file.py b/tagstudio/src/qt/helpers/open_file.py deleted file mode 100644 index f2e070e4..00000000 --- a/tagstudio/src/qt/helpers/open_file.py +++ /dev/null @@ -1,49 +0,0 @@ -# Copyright (C) 2024 Travis Abendshien (CyanVoxel). -# Licensed under the GPL-3.0 License. -# Created for TagStudio: https://github.com/CyanVoxel/TagStudio - - -import logging -import os -import sys -import traceback -import shutil -import subprocess - - -def open_file(path: str, file_manager: bool = False): - try: - if sys.platform == "win32": - normpath = os.path.normpath(path) - if file_manager: - command_name = "explorer" - command_args = [f"/select,{normpath}"] - else: - command_name = "start" - # first parameter is for title, NOT filepath - command_args = ["", normpath] - subprocess.Popen([command_name] + command_args, shell=True, close_fds=True, creationflags=subprocess.CREATE_NEW_PROCESS_GROUP | subprocess.CREATE_BREAKAWAY_FROM_JOB) - else: - if sys.platform == "darwin": - command_name = "open" - command_args = [path] - if file_manager: - # will reveal in Finder - command_args.append("-R") - else: - if file_manager: - command_name = "dbus-send" - # might not be guaranteed to launch default? - command_args = ["--session", "--dest=org.freedesktop.FileManager1", "--type=method_call", - "/org/freedesktop/FileManager1", "org.freedesktop.FileManager1.ShowItems", - f"array:string:file://{path}", "string:"] - else: - command_name = "xdg-open" - command_args = [path] - command = shutil.which(command_name) - if command is not None: - subprocess.Popen([command] + command_args, close_fds=True) - else: - logging.info(f"Could not find {command_name} on system PATH") - except: - traceback.print_exc() \ No newline at end of file