Rusfort ce26d54a5d Pre-Codebase-review commit :3
Codebase dedublication and Cleanup refactor

Documentation updated as well

Preferences update

Removed testfiles from repository
2025-05-03 13:19:25 +02:00

11 KiB

Developer Guide: GUI Internals

This document provides technical details about the implementation of the Graphical User Interface (GUI) for developers.

Framework

The GUI is built using PySide6, which provides Python bindings for the Qt framework.

Main Window (gui/main_window.py)

The MainWindow class acts as the central coordinator for the GUI application. It is responsible for:

  • Setting up the main application window structure and menu bar.
  • Instantiating and arranging the major GUI widgets:
    • MainPanelWidget (gui/main_panel_widget.py): Contains the core controls, preset selection, and the rule editor.
    • PresetEditorWidget (gui/preset_editor_widget.py): Handles preset loading, saving, and editing.
    • LogConsoleWidget (gui/log_console_widget.py): Displays application logs.
  • Instantiating key models and handlers:
    • UnifiedViewModel (gui/unified_view_model.py): The model for the rule hierarchy view.
    • LLMInteractionHandler (gui/llm_interaction_handler.py): Manages communication with the LLM service.
  • Connecting signals and slots between these components to orchestrate the application flow.
  • Handling top-level user interactions like drag-and-drop for loading sources (add_input_paths). This method now handles the "placeholder" state (no preset selected) by scanning directories or inspecting archives (ZIP) and creating placeholder SourceRule/AssetRule/FileRule objects to immediately populate the UnifiedViewModel with the file structure.
  • Initiating predictions based on the selected preset mode (Rule-Based or LLM) when presets change or sources are added.
  • Starting the processing task (_on_process_requested): This slot now filters the SourceRule list obtained from the UnifiedViewModel, excluding sources where no asset has a Target Asset name assigned, before emitting the start_backend_processing signal. It also manages enabling/disabling controls.
  • Managing the QThreadPool for running background prediction tasks (RuleBasedPredictionHandler, LLMPredictionHandler).
  • Implementing slots to handle results from background tasks:
    • _handle_prediction_completion(source_id, source_rule_list): Receives results from either prediction handler via the prediction_signal. It calls self.unified_view_model.update_rules_for_sources() to update the view model, preserving user overrides where possible. For LLM predictions, it also triggers processing the next item in the queue.
    • Slots to handle status updates from the LLM handler.

Threading and Background Tasks

To keep the UI responsive, prediction tasks run in background threads managed by a QThreadPool.

  • BasePredictionHandler (gui/base_prediction_handler.py): An abstract QRunnable base class defining the common interface and signals (prediction_signal, status_signal) for prediction tasks.
  • RuleBasedPredictionHandler (gui/prediction_handler.py): Inherits from BasePredictionHandler. Runs as a QRunnable in the thread pool when a rule-based preset is selected. Generates the SourceRule hierarchy based on preset rules and emits prediction_signal.
  • LLMPredictionHandler (gui/llm_prediction_handler.py): Inherits from BasePredictionHandler. Runs as a QRunnable in the thread pool when "- LLM Interpretation -" is selected. Interacts with LLMInteractionHandler, parses the response, generates the SourceRule hierarchy for a single input item, and emits prediction_signal and status_signal.
  • LLMInteractionHandler (gui/llm_interaction_handler.py): Manages the communication with the LLM service. This handler itself may perform network operations but typically runs synchronously within the LLMPredictionHandler's thread.

(Note: The actual processing via ProcessingEngine is now handled by main.ProcessingTask, which runs in a separate process managed outside the GUI's direct threading model, though the GUI initiates it).

Communication (Signals and Slots)

Communication between the MainWindow (main UI thread) and the background prediction tasks relies on Qt's signals and slots.

  • Prediction handlers (RuleBasedPredictionHandler, LLMPredictionHandler) emit signals from the BasePredictionHandler:
    • prediction_signal(source_id, source_rule_list): Indicates prediction for a source is complete.
    • status_signal(message): Provides status updates (primarily from LLM handler).
  • The MainWindow connects slots to these signals:
    • prediction_signal -> MainWindow._handle_prediction_completion(source_id, source_rule_list)
    • status_signal -> MainWindow._on_status_update(message) (updates status bar)
  • Signals from the UnifiedViewModel (dataChanged, layoutChanged) trigger updates in the QTreeView.
  • Signals from the UnifiedViewModel (targetAssetOverrideChanged) trigger the AssetRestructureHandler.

Preset Editor (gui/preset_editor_widget.py)

The PresetEditorWidget provides a dedicated interface for managing presets. It handles loading, displaying, editing, and saving preset .json files. It communicates with the MainWindow (e.g., via signals) when a preset is loaded or saved.

Unified Hierarchical View

The core rule editing interface is built around a QTreeView managed within the MainPanelWidget, using a custom model and delegates.

  • UnifiedViewModel (gui/unified_view_model.py): Implements QAbstractItemModel.
    • Wraps the RuleHierarchyModel to expose the SourceRule list (Source -> Asset -> File) to the QTreeView.
    • Provides data for display and flags for editing.
    • Handles setData requests: Validates input and updates the underlying RuleHierarchyModel. Crucially, it delegates complex restructuring (when target_asset_name_override changes) to the AssetRestructureHandler by emitting the targetAssetOverrideChanged signal.
    • Row Coloring: Provides data for Qt.ForegroundRole (text color) based on the item_type and the colors defined in config/app_settings.json. Provides data for Qt.BackgroundRole based on calculating a 30% darker shade of the parent asset's background color.
    • Caching: Caches configuration data (ASSET_TYPE_DEFINITIONS, FILE_TYPE_DEFINITIONS, color maps) in __init__ for performance.
    • update_rules_for_sources Method: Intelligently merges new prediction results or placeholder rules into the existing model data, preserving user overrides where applicable.
    • (Note: The previous concept of switching between "simple" and "detailed" display modes has been removed. The model always represents the full detailed structure.)
  • RuleHierarchyModel (gui/rule_hierarchy_model.py): A non-Qt model holding the actual list of SourceRule objects. Provides methods for accessing and modifying the hierarchy (used by UnifiedViewModel and AssetRestructureHandler).
  • AssetRestructureHandler (gui/asset_restructure_handler.py): Contains the logic to modify the RuleHierarchyModel when a file's target asset is changed. It listens for the targetAssetOverrideChanged signal from the UnifiedViewModel and uses methods on the RuleHierarchyModel (moveFileRule, createAssetRule, removeAssetRule) to perform the restructuring safely.
  • Delegates (gui/delegates.py): Custom QStyledItemDelegate implementations provide inline editors:
    • ComboBoxDelegate: For selecting predefined types (from Configuration).
    • LineEditDelegate: For free-form text editing.
    • SupplierSearchDelegate: For supplier names with auto-completion (using config/suppliers.json).

Data Flow Diagram (GUI Rule Management - Refactored):

graph TD
    subgraph MainWindow [MainWindow Coordinator]
        direction LR
        MW_Input[User Input (Drag/Drop, Preset Select)] --> MW(MainWindow);
        MW -- Initiates --> PredPool{QThreadPool};
        MW -- Connects Signals --> VM(UnifiedViewModel);
        MW -- Connects Signals --> ARH(AssetRestructureHandler);
        MW -- Owns/Manages --> MPW(MainPanelWidget);
        MW -- Owns/Manages --> PEW(PresetEditorWidget);
        MW -- Owns/Manages --> LCW(LogConsoleWidget);
        MW -- Owns/Manages --> LLMIH(LLMInteractionHandler);
    end

    subgraph MainPanel [MainPanelWidget]
        direction TB
        MPW_UI[UI Controls (Load, Predict, Process Btns)];
        MPW_UI --> MPW;
        MPW -- Contains --> REW(RuleEditorWidget);
    end

    subgraph RuleEditor [RuleEditorWidget]
        direction TB
        REW -- Contains --> TV(QTreeView - Rule View);
    end

    subgraph Prediction [Background Prediction]
        direction TB
        PredPool -- Runs --> RBP(RuleBasedPredictionHandler);
        PredPool -- Runs --> LLMP(LLMPredictionHandler);
        LLMP -- Uses --> LLMIH;
        RBP -- prediction_signal --> MW;
        LLMP -- prediction_signal --> MW;
        LLMP -- status_signal --> MW;
    end

    subgraph ModelView [Model/View Components]
        direction TB
        TV -- Sets Model --> VM;
        TV -- Displays Data From --> VM;
        TV -- Uses Delegates --> Del(Delegates);
        UserEdit[User Edits Rules] --> TV;
        TV -- setData --> VM;
        VM -- Wraps --> RHM(RuleHierarchyModel);
        VM -- dataChanged/layoutChanged --> TV;
        VM -- targetAssetOverrideChanged --> ARH;
        ARH -- Modifies --> RHM;
        Del -- Get/Set Data --> VM;
    end

    MW -- _handle_prediction_completion --> VM;
    MW -- Triggers Processing --> ProcTask(main.ProcessingTask);

    %% Connections between subgraphs
    MPW --> MW;
    PEW --> MW;
    LCW --> MW;
    VM --> MW;
    ARH --> MW;
    LLMIH --> MW;
    REW --> MPW;

Application Styling

The application style is explicitly set to 'Fusion' in gui/main_window.py. A custom QPalette adjusts default colors.

Logging (gui/log_console_widget.py)

The LogConsoleWidget displays logs captured by a custom QtLogHandler from Python's logging module.

Cancellation

The GUI provides a "Cancel" button. Cancellation logic for the actual processing is now likely handled within the main.ProcessingTask or the code that manages it, as the ProcessingHandler has been removed. The GUI button would signal this external task manager.

GUI Configuration Editor (gui/config_editor_dialog.py)

A dedicated dialog for editing config/app_settings.json.

  • Functionality: Loads config/app_settings.json, presents in tabs, allows editing basic fields, definitions tables (with color editing), and merge rules list/detail.
  • Limitations: Editing complex fields like IMAGE_RESOLUTIONS or full MAP_MERGE_RULES details might still be limited.
  • Integration: Launched by MainWindow ("Edit" -> "Preferences...").
  • Persistence: Saves changes to config/app_settings.json. Requires application restart for changes to affect processing logic loaded by the Configuration class.

The refactored GUI separates concerns into distinct widgets and handlers, coordinated by the MainWindow. Background tasks use QThreadPool and QRunnable. The UnifiedViewModel focuses on data presentation and simple edits, delegating complex restructuring to the AssetRestructureHandler.