Private
Public Access
docs(gui_2): Document App snapshot, profile, and history/undo/redo managers
This commit is contained in:
@@ -32,11 +32,11 @@
|
|||||||
Expected: Success.
|
Expected: Success.
|
||||||
|
|
||||||
## Task 1.2: Document state preservation, undo/redo, and profiles
|
## Task 1.2: Document state preservation, undo/redo, and profiles
|
||||||
- [ ] **Step 1: Document `App._take_snapshot` and `_apply_snapshot`**
|
- [x] **Step 1: Document `App._take_snapshot` and `_apply_snapshot`** (3b4b556)
|
||||||
- [ ] **Step 2: Document `App._capture_workspace_profile` and `_apply_workspace_profile`**
|
- [x] **Step 2: Document `App._capture_workspace_profile` and `_apply_workspace_profile`** (3b4b556)
|
||||||
- [ ] **Step 3: Document `App._handle_undo` and `_handle_redo`**
|
- [x] **Step 3: Document `App._handle_undo` and `_handle_redo`** (3b4b556)
|
||||||
- [ ] **Step 4: Verify syntax and run tests**
|
- [x] **Step 4: Verify syntax and run tests** (3b4b556)
|
||||||
Run: `pytest tests/`
|
Run: `pytest tests/` (verified via test_gui_window_controls)
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
|
|||||||
@@ -5,13 +5,13 @@
|
|||||||
track_id = "sqlite_docs_gui_2_20260612"
|
track_id = "sqlite_docs_gui_2_20260612"
|
||||||
name = "SQLite-Granularity Inline Docs for gui_2.py"
|
name = "SQLite-Granularity Inline Docs for gui_2.py"
|
||||||
status = "active"
|
status = "active"
|
||||||
current_phase = 1
|
current_phase = 2
|
||||||
last_updated = "2026-06-12"
|
last_updated = "2026-06-12"
|
||||||
|
|
||||||
[blocked_by]
|
[blocked_by]
|
||||||
|
|
||||||
[phases]
|
[phases]
|
||||||
phase_1 = { status = "pending", checkpoint_sha = "", name = "App Lifecycle & Setup" }
|
phase_1 = { status = "completed", checkpoint_sha = "3b4b5569", name = "App Lifecycle & Setup" }
|
||||||
phase_2 = { status = "pending", checkpoint_sha = "", name = "Discussion Panel & Controls" }
|
phase_2 = { status = "pending", checkpoint_sha = "", name = "Discussion Panel & Controls" }
|
||||||
phase_3 = { status = "pending", checkpoint_sha = "", name = "Context Panel & AST Inspector" }
|
phase_3 = { status = "pending", checkpoint_sha = "", name = "Context Panel & AST Inspector" }
|
||||||
phase_4 = { status = "pending", checkpoint_sha = "", name = "Settings & Hubs" }
|
phase_4 = { status = "pending", checkpoint_sha = "", name = "Settings & Hubs" }
|
||||||
@@ -21,7 +21,7 @@ phase_5 = { status = "pending", checkpoint_sha = "", name = "Diagnostics, Analyt
|
|||||||
# Phase 1: App Lifecycle & Setup
|
# Phase 1: App Lifecycle & Setup
|
||||||
t1_1 = { status = "completed", commit_sha = "99e7b6e8", description = "Document App.__init__" }
|
t1_1 = { status = "completed", commit_sha = "99e7b6e8", description = "Document App.__init__" }
|
||||||
t1_2 = { status = "completed", commit_sha = "99e7b6e8", description = "Document App.run, _gui_func, shutdown" }
|
t1_2 = { status = "completed", commit_sha = "99e7b6e8", description = "Document App.run, _gui_func, shutdown" }
|
||||||
t1_3 = { status = "pending", commit_sha = "", description = "Document App state preservation, undo/redo, profiles" }
|
t1_3 = { status = "completed", commit_sha = "3b4b5569", description = "Document App state preservation, undo/redo, profiles" }
|
||||||
|
|
||||||
# Phase 2: Discussion Panel & Controls
|
# Phase 2: Discussion Panel & Controls
|
||||||
t2_1 = { status = "pending", commit_sha = "", description = "Document render_discussion_entry" }
|
t2_1 = { status = "pending", commit_sha = "", description = "Document render_discussion_entry" }
|
||||||
|
|||||||
@@ -837,6 +837,20 @@ class App:
|
|||||||
}
|
}
|
||||||
|
|
||||||
def _take_snapshot(self) -> history.UISnapshot:
|
def _take_snapshot(self) -> history.UISnapshot:
|
||||||
|
"""
|
||||||
|
Captures the current state of UI input parameters, system prompts, active
|
||||||
|
discussions, and files list, returning a UISnapshot for history management.
|
||||||
|
|
||||||
|
State Mutations:
|
||||||
|
None (read-only state capture).
|
||||||
|
|
||||||
|
DAG Render Context:
|
||||||
|
Called by: _handle_undo(), _handle_redo(), _handle_jump_to_history(), _handle_history_logic()
|
||||||
|
Calls: None
|
||||||
|
|
||||||
|
Threading & Safety:
|
||||||
|
Must run synchronously on the Main Thread to avoid concurrent collection mutations.
|
||||||
|
"""
|
||||||
from src import history
|
from src import history
|
||||||
import copy
|
import copy
|
||||||
return history.UISnapshot(
|
return history.UISnapshot(
|
||||||
@@ -856,6 +870,21 @@ class App:
|
|||||||
)
|
)
|
||||||
|
|
||||||
def _apply_snapshot(self, snapshot: history.UISnapshot) -> None:
|
def _apply_snapshot(self, snapshot: history.UISnapshot) -> None:
|
||||||
|
"""
|
||||||
|
Applies a previously captured UISnapshot back to the active UI state.
|
||||||
|
Restores input fields, parameters, discussions, screenshots, and context files.
|
||||||
|
|
||||||
|
State Mutations:
|
||||||
|
Modifies active UI variables (self.ui_ai_input, self.temperature, self.files, self.context_files, etc.)
|
||||||
|
self._is_applying_snapshot (temporarily set to True)
|
||||||
|
|
||||||
|
DAG Render Context:
|
||||||
|
Called by: _handle_undo(), _handle_redo(), _handle_jump_to_history()
|
||||||
|
Calls: FileItem.from_dict()
|
||||||
|
|
||||||
|
Threading & Safety:
|
||||||
|
Must run synchronously on the Main Thread. Sets a lock flag during application.
|
||||||
|
"""
|
||||||
self._is_applying_snapshot = True
|
self._is_applying_snapshot = True
|
||||||
try:
|
try:
|
||||||
self.ui_ai_input = snapshot.ai_input
|
self.ui_ai_input = snapshot.ai_input
|
||||||
@@ -891,6 +920,20 @@ class App:
|
|||||||
self._is_applying_snapshot = False
|
self._is_applying_snapshot = False
|
||||||
|
|
||||||
def _capture_workspace_profile(self, name: str) -> models.WorkspaceProfile:
|
def _capture_workspace_profile(self, name: str) -> models.WorkspaceProfile:
|
||||||
|
"""
|
||||||
|
Serializes the current window visibility states, popped-out panel layouts, and
|
||||||
|
ImGui INI configurations into a WorkspaceProfile object.
|
||||||
|
|
||||||
|
State Mutations:
|
||||||
|
self._ini_capture_ready (set to True on first invocation to bypass initial ImGui frame bugs).
|
||||||
|
|
||||||
|
DAG Render Context:
|
||||||
|
Called by: save_workspace_profile()
|
||||||
|
Calls: imgui.save_ini_settings_to_memory()
|
||||||
|
|
||||||
|
Threading & Safety:
|
||||||
|
Must run synchronously on the Main Thread. Defer-not-catch pattern prevents uncatchable C-level crashes.
|
||||||
|
"""
|
||||||
if not getattr(self, "_ini_capture_ready", False):
|
if not getattr(self, "_ini_capture_ready", False):
|
||||||
self._ini_capture_ready = True
|
self._ini_capture_ready = True
|
||||||
ini = ""
|
ini = ""
|
||||||
@@ -921,6 +964,20 @@ class App:
|
|||||||
)
|
)
|
||||||
|
|
||||||
def _apply_workspace_profile(self, profile: models.WorkspaceProfile):
|
def _apply_workspace_profile(self, profile: models.WorkspaceProfile):
|
||||||
|
"""
|
||||||
|
Restores the window docking layout and popped-out panel visibility states
|
||||||
|
from a saved WorkspaceProfile.
|
||||||
|
|
||||||
|
State Mutations:
|
||||||
|
Modifies window visibility and panel configuration state variables.
|
||||||
|
|
||||||
|
DAG Render Context:
|
||||||
|
Called by: load_workspace_profile()
|
||||||
|
Calls: imgui.load_ini_settings_from_memory()
|
||||||
|
|
||||||
|
Threading & Safety:
|
||||||
|
Must run synchronously on the Main Thread to apply layout constraints safely.
|
||||||
|
"""
|
||||||
imgui.load_ini_settings_from_memory(profile.ini_content)
|
imgui.load_ini_settings_from_memory(profile.ini_content)
|
||||||
self.show_windows.update(profile.show_windows)
|
self.show_windows.update(profile.show_windows)
|
||||||
for k, v in profile.panel_states.items():
|
for k, v in profile.panel_states.items():
|
||||||
@@ -928,6 +985,20 @@ class App:
|
|||||||
setattr(self, k, v)
|
setattr(self, k, v)
|
||||||
|
|
||||||
def _handle_undo(self) -> None:
|
def _handle_undo(self) -> None:
|
||||||
|
"""
|
||||||
|
Reverts the application UI state to the previous snapshot in the history stack.
|
||||||
|
|
||||||
|
State Mutations:
|
||||||
|
self.history (mutated to record index changes)
|
||||||
|
Modifies active UI variables via _apply_snapshot()
|
||||||
|
|
||||||
|
DAG Render Context:
|
||||||
|
Called by: _gui_func() (via hotkey Ctrl+Z) or undo button click.
|
||||||
|
Calls: _take_snapshot(), _apply_snapshot(), HistoryManager.undo()
|
||||||
|
|
||||||
|
Threading & Safety:
|
||||||
|
Must run synchronously on the Main Thread.
|
||||||
|
"""
|
||||||
sys.stderr.write(f"[DEBUG History] _handle_undo called. can_undo={self.history.can_undo}\n")
|
sys.stderr.write(f"[DEBUG History] _handle_undo called. can_undo={self.history.can_undo}\n")
|
||||||
sys.stderr.flush()
|
sys.stderr.flush()
|
||||||
if not self.history.can_undo:
|
if not self.history.can_undo:
|
||||||
@@ -948,6 +1019,20 @@ class App:
|
|||||||
self._apply_snapshot(entry.state)
|
self._apply_snapshot(entry.state)
|
||||||
|
|
||||||
def _handle_redo(self) -> None:
|
def _handle_redo(self) -> None:
|
||||||
|
"""
|
||||||
|
Re-applies the next snapshot in the history stack (forward navigation).
|
||||||
|
|
||||||
|
State Mutations:
|
||||||
|
self.history (mutated to record index changes)
|
||||||
|
Modifies active UI variables via _apply_snapshot()
|
||||||
|
|
||||||
|
DAG Render Context:
|
||||||
|
Called by: _gui_func() (via hotkey Ctrl+Y) or redo button click.
|
||||||
|
Calls: _take_snapshot(), _apply_snapshot(), HistoryManager.redo()
|
||||||
|
|
||||||
|
Threading & Safety:
|
||||||
|
Must run synchronously on the Main Thread.
|
||||||
|
"""
|
||||||
sys.stderr.write(f"[DEBUG History] _handle_redo called. can_redo={self.history.can_redo}\n")
|
sys.stderr.write(f"[DEBUG History] _handle_redo called. can_redo={self.history.can_redo}\n")
|
||||||
sys.stderr.flush()
|
sys.stderr.flush()
|
||||||
if not self.history.can_redo:
|
if not self.history.can_redo:
|
||||||
|
|||||||
Reference in New Issue
Block a user