From caf2c7b337248270375bedeb7e90d865b3cf0c0e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E9=9B=B7=E7=94=B5=E8=8A=BD=E8=A1=A3?= Date: Sun, 19 Apr 2026 17:42:23 -0400 Subject: [PATCH] Restore document center operational shell --- .../crates/app_ui/src/app_root/documents.rs | 139 ++++++++++++------ AgentCompany-Rust/prd.json | 4 +- AgentCompany-Rust/progress.txt | 2 + 3 files changed, 96 insertions(+), 49 deletions(-) diff --git a/AgentCompany-Rust/crates/app_ui/src/app_root/documents.rs b/AgentCompany-Rust/crates/app_ui/src/app_root/documents.rs index 10ef365a..d16eebb5 100644 --- a/AgentCompany-Rust/crates/app_ui/src/app_root/documents.rs +++ b/AgentCompany-Rust/crates/app_ui/src/app_root/documents.rs @@ -14,39 +14,25 @@ impl AppRoot { .flex() .flex_col() .gap_6() + .child(render_document_header(total_count, cx)) .child( div() - .flex() - .justify_between() - .items_center() + .grid() + .grid_cols(2) + .gap_4() .child( div() - .child( - div() - .text_2xl() - .text_color(theme::text_primary()) - .child("Document Center"), - ) - .child( - div() - .mt(px(6.0)) - .text_sm() - .text_color(theme::text_muted()) - .child(format!("{} items", total_count)), - ), + .gap_4() + .child(document_section_label("DOCUMENTS PROSE")) + .child(self.render_document_prose_list(cx, selected)) + .when(!work_products.is_empty(), |container| { + container + .child(document_section_label("WORK PRODUCTS")) + .child(render_work_products(work_products.as_slice())) + }), ) - .child(primary_button("Save draft", cx, |this, cx| { - this.create_document(cx) - })), + .child(self.render_document_editor_surface(selected)), ) - .child(document_section_label("DOCUMENTS PROSE")) - .child(self.render_document_prose_list(cx, selected)) - .when(!work_products.is_empty(), |container| { - container - .child(document_section_label("WORK PRODUCTS")) - .child(render_work_products(work_products.as_slice())) - }) - .child(self.render_document_editor(selected)) } fn render_document_prose_list( @@ -97,19 +83,20 @@ impl AppRoot { .flex() .justify_between() .items_center() + .gap_3() .child( div() .flex_1() .child( div() - .text_base() + .text_sm() .text_color(theme::text_primary()) .child(document.title.clone()), ) .child( div() .mt(px(4.0)) - .text_sm() + .text_xs() .text_color(theme::text_muted()) .child(format!( "{} · v{} · {}", @@ -125,7 +112,10 @@ impl AppRoot { }) } - fn render_document_editor(&self, selected: Option<&domain::Document>) -> impl IntoElement + '_ { + fn render_document_editor_surface( + &self, + selected: Option<&domain::Document>, + ) -> impl IntoElement + '_ { div() .rounded_lg() .border_1() @@ -139,26 +129,80 @@ impl AppRoot { .unwrap_or_else(|| "New document".to_string()), ), ) - .child(self.document_title_input.clone()) - .child(self.document_body_input.clone()) .when_some(selected, |container, document| { - container.child( - div() - .mt(px(12.0)) - .rounded_lg() - .border_1() - .border_color(theme::panel_inset_border()) - .bg(theme::panel_inset()) - .p_4() - .text_sm() - .line_height(px(22.0)) - .text_color(theme::text_secondary()) - .child(document.content.clone()), - ) + container + .child( + div() + .mt(px(8.0)) + .text_sm() + .text_color(theme::text_muted()) + .child(format!( + "{} · v{} · {}", + document.document_type.replace('_', " "), + document.version, + document.status + )), + ) + .child( + div() + .mt(px(16.0)) + .rounded_lg() + .border_1() + .border_color(theme::panel_inset_border()) + .bg(theme::panel_inset()) + .p_4() + .text_sm() + .line_height(px(22.0)) + .text_color(theme::text_secondary()) + .child(document.content.clone()), + ) }) + .child( + div() + .mt(px(20.0)) + .text_xs() + .text_color(theme::text_muted()) + .child("DRAFT EDITOR"), + ) + .child(div().mt(px(10.0)).child(self.document_title_input.clone())) + .child(div().mt(px(12.0)).child(self.document_body_input.clone())) + .child( + div().mt(px(14.0)).flex().justify_end().child( + div() + .text_xs() + .text_color(theme::text_muted()) + .child("Use the draft editor to create the next document revision."), + ), + ) } } +fn render_document_header(total_count: usize, cx: &mut Context) -> impl IntoElement { + div() + .flex() + .justify_between() + .items_center() + .child( + div() + .child( + div() + .text_2xl() + .text_color(theme::text_primary()) + .child("Document Center"), + ) + .child( + div() + .mt(px(6.0)) + .text_sm() + .text_color(theme::text_muted()) + .child(format!("{} items", total_count)), + ), + ) + .child(primary_button("Save draft", cx, |this, cx| { + this.create_document(cx) + })) +} + fn document_section_label(label: &'static str) -> impl IntoElement { div().text_xs().text_color(theme::text_muted()).child(label) } @@ -180,19 +224,20 @@ fn render_work_products<'a>(products: &'a [&'a domain::ArtifactRecord]) -> impl .flex() .justify_between() .items_center() + .gap_3() .child( div() .flex_1() .child( div() - .text_base() + .text_sm() .text_color(theme::text_primary()) .child(artifact.title.clone()), ) .child( div() .mt(px(4.0)) - .text_sm() + .text_xs() .text_color(theme::text_muted()) .child(format!( "{} · {} · {}", diff --git a/AgentCompany-Rust/prd.json b/AgentCompany-Rust/prd.json index 673ce601..b99c5ae6 100644 --- a/AgentCompany-Rust/prd.json +++ b/AgentCompany-Rust/prd.json @@ -262,8 +262,8 @@ "cargo test --workspace passes" ], "priority": 19, - "passes": false, - "notes": "Opened after strict current-directory-only source audit." + "passes": true, + "notes": "Passed: Document Center now restores a source-like shell with section header, prose list, work-product list, and a dedicated editor/inspector column while preserving the existing native save path." }, { "id": "US-020", diff --git a/AgentCompany-Rust/progress.txt b/AgentCompany-Rust/progress.txt index 3c34bafd..3f3e72e0 100644 --- a/AgentCompany-Rust/progress.txt +++ b/AgentCompany-Rust/progress.txt @@ -24,3 +24,5 @@ Started: 2026-04-19 - Completed US-017 runs shell remediation. Native runs now follow the original RunQueue + RunDetail grammar more closely: the queue is a dedicated left panel with filtering/search/list rows, the right side is a primary run detail column, and runtime events/artifacts/operator actions are preserved as secondary panels instead of dominating the main operational shell. - Completed US-018 approvals remediation. Native approvals now use a grouped review-list grammar closer to the original PendingReviewList surface instead of parallel summary cards, while the lower pending-approval inspector still preserves the real approve/reject chain. + +- Completed US-019 document-center remediation. Native documents now follow a source-like operational shell with section header, prose list, work-product list, and a dedicated editor/inspector column while keeping the current native draft-save path intact.