anvilsign in

collin/anvil · 76f9fe52

ui: svg folder and file icons in the tree view

Collin Richards · 2026-06-10 08:12 UTC · 76f9fe529616fae8231551d4bdc13c12aea7e1a1 · parent b056637e · browse files

modifiedcrates/anvil-web/src/ui.rs+14 −2
⋯ 102 unchanged lines
103103 .box .row a.fc-msg { flex:1; margin-left:24px; overflow:hidden; text-overflow:ellipsis; white-space:nowrap; text-align:left; color:var(--muted); font-size:13px; }
104104 .box .row a.fc-msg:hover { color:var(--accent); }
105105 .box .row .fc-time { margin-left:16px; white-space:nowrap; color:var(--muted); font-size:13px; }
106-.icon { width:16px; color:var(--muted); }
106+.icon { width:16px; flex:none; display:inline-flex; align-items:center; justify-content:center; color:var(--muted); }
107+.icon.dir { color:#54aeff; }
107108 table.code { border-collapse:collapse; width:100%; font:12px/1.45 ui-monospace,SFMono-Regular,Menlo,Consolas,monospace; }
108109 table.code td { padding:0 10px; vertical-align:top; white-space:pre; }
109110 table.code td.ln { text-align:right; color:var(--muted); user-select:none; width:1%; border-right:1px solid var(--border); background:var(--code-bg); }
⋯ 76 unchanged lines
186187
187188 /// Clipboard icon for the clone "copy" button.
188189 const CLIPBOARD_SVG: &str = r#"<svg viewBox="0 0 16 16" width="15" height="15" fill="currentColor" aria-hidden="true"><path d="M10 1.5H6a.5.5 0 0 0-.5.5v1H4A1.5 1.5 0 0 0 2.5 4.5v9A1.5 1.5 0 0 0 4 15h8a1.5 1.5 0 0 0 1.5-1.5v-9A1.5 1.5 0 0 0 12 3h-1.5V2a.5.5 0 0 0-.5-.5zm-3.5 1h3v1h-3v-1zM4 4.5h8v9H4v-9z"/></svg>"#;
190+
191+/// Filled folder icon for directory entries in the tree view.
192+const FOLDER_SVG: &str = r#"<svg viewBox="0 0 16 16" width="16" height="16" fill="currentColor" aria-hidden="true"><path d="M1.75 1A1.75 1.75 0 0 0 0 2.75v10.5C0 14.216.784 15 1.75 15h12.5A1.75 1.75 0 0 0 16 13.25v-8.5A1.75 1.75 0 0 0 14.25 3H7.5a.25.25 0 0 1-.2-.1l-.9-1.2C6.07 1.26 5.55 1 5 1H1.75Z"/></svg>"#;
193+
194+/// Outline file icon for blob entries in the tree view.
195+const FILE_SVG: &str = r#"<svg viewBox="0 0 16 16" width="16" height="16" fill="currentColor" aria-hidden="true"><path d="M2 1.75C2 .784 2.784 0 3.75 0h6.586c.464 0 .909.184 1.237.513l2.914 2.914c.329.328.513.773.513 1.237v9.586A1.75 1.75 0 0 1 13.25 16h-9.5A1.75 1.75 0 0 1 2 14.25Zm1.75-.25a.25.25 0 0 0-.25.25v12.5c0 .138.112.25.25.25h9.5a.25.25 0 0 0 .25-.25V6h-2.75A1.75 1.75 0 0 1 9 4.25V1.5Zm6.75.062V4.25c0 .138.112.25.25.25h2.688l-.011-.013-2.914-2.914-.013-.011Z"/></svg>"#;
196+
189197 /// Delegated handlers for the clone widget: protocol toggle + copy-to-clipboard.
190198 /// Registered once on `document`, so it survives htmx body swaps.
191199 const CLONE_JS: &str = r#"
⋯ 876 unchanged lines
10681076 @let kind = if e.is_dir { "tree" } else { "blob" };
10691077 div.row {
10701078 a.entry href=(format!("/{owner}/{repo}/{kind}/{rev}/{child}")) {
1071- span.icon { (if e.is_dir { "[ ]" } else { "·" }) }
1079+ @if e.is_dir {
1080+ span.icon.dir { (PreEscaped(FOLDER_SVG)) }
1081+ } @else {
1082+ span.icon { (PreEscaped(FILE_SVG)) }
1083+ }
10721084 (e.name) @if e.is_dir { "/" }
10731085 }
10741086 @if let Some(c) = latest.get(&e.name) {
⋯ 491 unchanged lines