refactor(ui): scaffold ModelState and ViewState types (improvise-3vr)

Step 1 of vb4 (Split AppState into ModelState + ViewState): introduce the
named slice types in src/ui/app.rs as empty structs, with doc comments
pointing at the follow-up issues that fill them in. App still owns every
field directly; subsequent steps migrate the fields.

A structural test locks in that both types are constructible.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
Edward Langley
2026-04-26 11:31:03 -07:00
parent 1181ffd0ab
commit f11d79f700
+22
View File
@@ -185,6 +185,19 @@ impl AppMode {
}
}
/// Document state slice: the workbook and its IO bookkeeping. Distinct from
/// `Workbook` itself (which is pure document semantics in `improvise-core`)
/// because `file_path` and `dirty` are persistence-layer concerns. Filled in
/// by improvise-x2c (vb4 step 2).
#[derive(Debug, Default)]
pub struct ModelState {}
/// UI session-state slice: mode, cursors, panels, buffers, navigation stacks,
/// and other per-session state that does not persist to disk. Filled in by
/// improvise-ew0 (vb4 step 3).
#[derive(Debug, Default)]
pub struct ViewState {}
pub struct App {
pub workbook: Workbook,
pub file_path: Option<PathBuf>,
@@ -472,6 +485,15 @@ impl App {
mod tests {
use super::*;
/// improvise-3vr: ModelState and ViewState are the named slices of App
/// state introduced by the vb4 refactor. Step 1 only requires that the
/// types exist and are constructible; subsequent steps move fields in.
#[test]
fn model_state_and_view_state_are_constructible() {
let _: ModelState = ModelState::default();
let _: ViewState = ViewState::default();
}
fn two_col_model() -> App {
let mut wb = Workbook::new("T");
wb.add_category("Row").unwrap(); // → Row axis