Surface toolset: icons and planned commands (#808)

Icons for the surface toolset, and its planned commands registered and disabled with the issue that tracks each one.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
Irakli KourtisandClaude Opus 5.5 authored and GitHub committed 2026-10-13 14:28:38 -04:00
1 parent dd084ec9e1
commit c8d668108a
6 files changed
+437 -31

No files matched your search

+24 -9
View File
@@ -3,7 +3,8 @@
//! The page lists every registered command by area (the first part of its dotted id), with its
//! label, id and toolbar place. It comes only from SolidCraft's command registry
//! (`solidcraft-cli commands`), so it can't drift from what the program does; it compares with
//! nothing else.
//! nothing else. Planned commands (registered, not built yet) are listed as planned, with their
//! issue, and are not counted.
use std::path::Path;
@@ -59,16 +60,26 @@ pub fn page(cmds: &[Value]) -> String {
for p in prefixes.iter().filter(|p| !AREAS.iter().any(|(a, _)| a == p)) {
order.push((p.clone(), format!("`{p}.*`")));
}
let planned = |c: &Value| c["planned"].as_str().map(str::to_string);
let built = cmds.iter().filter(|c| planned(c).is_none()).count();
let later = match cmds.len() - built {
0 => String::new(),
n => format!(" Planned (registered, not built yet): {n}."),
};
let mut md = format!(
"# Features\n\nSolidCraft's commands by area, generated by `cargo xtask features` from the command registry \
(`solidcraft-cli commands`). **{} commands.** Every command runs the same way from the toolbar, a script, \
(`solidcraft-cli commands`). **{built} commands.**{later} Every command runs the same way from the toolbar, a script, \
`solidcraft-cli exec <id> '<json>'`, the control channel and MCP; parameters are in the \
[command reference](book/src/reference/commands.md) (`cargo xtask book`). Status and plans: [ROADMAP](../ROADMAP.md).\n",
cmds.len()
[command reference](book/src/reference/commands.md) (`cargo xtask book`). Status and plans: [ROADMAP](../ROADMAP.md).\n"
);
for (prefix, heading) in &order {
let in_area: Vec<&Value> = cmds.iter().filter(|c| area(&s(c, "id")) == prefix).collect();
md += &format!("\n## {heading} ({})\n\n| Command | Id | Toolbar |\n|---|---|---|\n", in_area.len());
let n = in_area.iter().filter(|c| planned(c).is_none()).count();
let count = match in_area.len() - n {
0 => n.to_string(),
p => format!("{n}, {p} planned"),
};
md += &format!("\n## {heading} ({count})\n\n| Command | Id | Toolbar |\n|---|---|---|\n");
for c in in_area {
let place = match (s(c, "tab"), s(c, "panel")) {
(t, _) if t.is_empty() => "–".to_string(),
@@ -76,7 +87,8 @@ pub fn page(cmds: &[Value]) -> String {
(t, p) => format!("{t} › {p}"),
};
let key = c["shortcut"].as_str().map(|k| format!(" ({k})")).unwrap_or_default();
md += &format!("| {}{key} | `{}` | {place} |\n", s(c, "label").replace('|', "/"), s(c, "id"));
let note = planned(c).map(|i| format!(" *(planned: [#{i}](https://github.com/bherbruck/solidcraft/issues/{i}))*")).unwrap_or_default();
md += &format!("| {}{key}{note} | `{}` | {place} |\n", s(c, "label").replace('|', "/"), s(c, "id"));
}
}
md
@@ -91,14 +103,17 @@ mod tests {
let cmds: Value = serde_json::from_str(
r#"[{"id":"solid.extrude","label":"Extrude","tab":"SOLID","panel":"CREATE","shortcut":"E"},
{"id":"sketch.line","label":"Line","tab":"SKETCH","panel":"CREATE"},
{"id":"view.fit","label":"Fit","tab":"","panel":""}]"#,
{"id":"view.fit","label":"Fit","tab":"","panel":""},
{"id":"solid.knit","label":"Knit","tab":"SOLID","panel":"CREATE","planned":"9"}]"#,
)
.unwrap();
let md = page(cmds.as_array().unwrap());
assert!(md.contains("**3 commands.**"));
let (sk, so, other) = (md.find("## Sketch (1)").unwrap(), md.find("## Solid modelling (1)").unwrap(), md.find("## `view.*` (1)").unwrap());
assert!(md.contains("**3 commands.** Planned (registered, not built yet): 1."));
let (sk, so, other) =
(md.find("## Sketch (1)").unwrap(), md.find("## Solid modelling (1, 1 planned)").unwrap(), md.find("## `view.*` (1)").unwrap());
assert!(sk < so && so < other);
assert!(md.contains("| Extrude (E) | `solid.extrude` | SOLID › CREATE |"));
assert!(md.contains("| Fit | `view.fit` | – |"));
assert!(md.contains("| Knit *(planned: [#9](https://github.com/bherbruck/solidcraft/issues/9))* | `solid.knit` | SOLID › CREATE |"));
}
}