swarm ui: the start page ends with the slug, its gradients animated
hyperhive / we are the wired between two shaded gradients that pulse in a wave, still under reduced motion. It sits under 2em from the bottom edge, clear of the setup assistant.
This commit is contained in:
parent
abf21683b9
commit
0e840bd34b
5 changed files with 94 additions and 11 deletions
|
|
@ -20,16 +20,16 @@ the highlighted one. **Escape**, **Tab** or a press elsewhere shut the list with
|
||||||
changing anything. Typing the start of an option's name picks it, also with the list
|
changing anything. Typing the start of an option's name picks it, also with the list
|
||||||
shut. A dropdown inside a dialog opens above the dialog and the dialog doesn't cut it off.
|
shut. A dropdown inside a dialog opens above the dialog and the dialog doesn't cut it off.
|
||||||
|
|
||||||
| route | what |
|
| route | what |
|
||||||
| ---------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
| ---------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
||||||
| `/` | the start page: the swarm's name over a digital-rain backdrop, plus a paperclip offering to set up an agent while no `ruth` exists, or her hive declares her destroyed (it opens the create form with `ruth` filled in); the swarm name in the header links here |
|
| `/` | the start page: the swarm's name over a digital-rain backdrop with the slug (`hyperhive / we are the wired`, its shaded gradients pulsing in a wave unless reduced motion is on) at the foot, plus a paperclip offering to set up an agent while no `ruth` exists, or her hive declares her destroyed (it opens the create form with `ruth` filled in); the swarm name in the header links here |
|
||||||
| `/agents` | every agent as a card that opens in place (status, config PR, wanted state, inference settings, resource caps, permissions, accounts, terminal), under a folded **hives** card with the hive directory and each hive's last reported status; create agents (with their permissions, optionally from an [archetype](archetypes.md)), link forge, matrix and GitHub accounts |
|
| `/agents` | every agent as a card that opens in place (status, config PR, wanted state, inference settings, resource caps, permissions, accounts, terminal), under a folded **hives** card with the hive directory and each hive's last reported status; create agents (with their permissions, optionally from an [archetype](archetypes.md)), link forge, matrix and GitHub accounts |
|
||||||
| `/agents/<name>/terminal` | one agent's live terminal |
|
| `/agents/<name>/terminal` | one agent's live terminal |
|
||||||
| `/agents/<name>/subagents/<subagent>/terminal` | one of that agent's subagents' live terminal |
|
| `/agents/<name>/subagents/<subagent>/terminal` | one of that agent's subagents' live terminal |
|
||||||
| `/reports` | two folded cards, each read only once opened: the **alerts** the swarm's Grafana holds now, the firing ones, with a button for the pending, no-data and error ones and a link to Grafana's own alert list; read through the controller with a Viewer service-account token, and a cross-repo **issue report** |
|
| `/reports` | two folded cards, each read only once opened: the **alerts** the swarm's Grafana holds now, the firing ones, with a button for the pending, no-data and error ones and a link to Grafana's own alert list; read through the controller with a Viewer service-account token, and a cross-repo **issue report** |
|
||||||
| `/jobs` | the controller's job graph, where agent creation and credential mints show progress, and under it the swarm builder's recent builds (agent config PRs, and agents built from `internal/meta` before a deploy), with what nix printed when one failed, and the review classifier's recent runs, a try-out on a real PR, and its settings |
|
| `/jobs` | the controller's job graph, where agent creation and credential mints show progress, and under it the swarm builder's recent builds (agent config PRs, and agents built from `internal/meta` before a deploy), with what nix printed when one failed, and the review classifier's recent runs, a try-out on a real PR, and its settings |
|
||||||
| `/messages` | the swarm-wide message feed: every message between agents, and to them from the operator, reminders and compaction, with a history window and a filter on sender or recipient; a folded **broadcast** card above the feed sends one message to more than one agent at once, and a folded **schedules** card holds the scheduled prompts: add, edit, pause, resume and remove |
|
| `/messages` | the swarm-wide message feed: every message between agents, and to them from the operator, reminders and compaction, with a history window and a filter on sender or recipient; a folded **broadcast** card above the feed sends one message to more than one agent at once, and a folded **schedules** card holds the scheduled prompts: add, edit, pause, resume and remove |
|
||||||
| `/notifications` | the notification router's flows: a switch for each built-in, every flow drawn as a graph, and an editor for custom flows |
|
| `/notifications` | the notification router's flows: a switch for each built-in, every flow drawn as a graph, and an editor for custom flows |
|
||||||
|
|
||||||
Everything it shows comes from [`swarm-controller`](../../swarm-controller/README.md).
|
Everything it shows comes from [`swarm-controller`](../../swarm-controller/README.md).
|
||||||
Pages that refresh on a timer share one polling rule: the page sends no new
|
Pages that refresh on a timer share one polling rule: the page sends no new
|
||||||
|
|
|
||||||
|
|
@ -21,3 +21,11 @@
|
||||||
0 0 0.4em color-mix(in srgb, var(--purple) 55%, transparent),
|
0 0 0.4em color-mix(in srgb, var(--purple) 55%, transparent),
|
||||||
0 0 1.2em var(--bg);
|
0 0 1.2em var(--bg);
|
||||||
}
|
}
|
||||||
|
/* The slug sits at the foot of the page, over the rain. It stays under 2em
|
||||||
|
* from the bottom edge, where the setup assistant starts (bottom-right,
|
||||||
|
* `SetupAssistant.css`), so the two never overlap, however narrow the window. */
|
||||||
|
.start-page .ui-slug {
|
||||||
|
position: absolute;
|
||||||
|
inset: auto 0 0;
|
||||||
|
margin: 0 0 0.4em;
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,8 @@
|
||||||
// <StartPage> — `/`, the swarm's landing page: the swarm's name over the
|
// <StartPage> — `/`, the swarm's landing page: the swarm's name over the
|
||||||
// digital-rain backdrop, plus the setup assistant while the swarm has no
|
// digital-rain backdrop, plus the setup assistant while the swarm has no
|
||||||
// `ruth`. The header's swarm name links here. The hive roster is a card on the agents page.
|
// `ruth`, and the slug at the foot. The header's swarm name links here. The hive roster is a card on the agents page.
|
||||||
import { MatrixRain } from "../shell/MatrixRain.js";
|
import { MatrixRain } from "../shell/MatrixRain.js";
|
||||||
|
import { Slug } from "../ui/slug/Slug.js";
|
||||||
import { useSwarmName } from "../shell/useSwarmName.js";
|
import { useSwarmName } from "../shell/useSwarmName.js";
|
||||||
import { SetupAssistant } from "./SetupAssistant.js";
|
import { SetupAssistant } from "./SetupAssistant.js";
|
||||||
import "./StartPage.css";
|
import "./StartPage.css";
|
||||||
|
|
@ -17,6 +18,7 @@ export function StartPage() {
|
||||||
<MatrixRain />
|
<MatrixRain />
|
||||||
<h1 class="start-page-name">{name}</h1>
|
<h1 class="start-page-name">{name}</h1>
|
||||||
<SetupAssistant />
|
<SetupAssistant />
|
||||||
|
<Slug />
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
43
frontend/packages/swarm-ui/src/ui/slug/Slug.css
Normal file
43
frontend/packages/swarm-ui/src/ui/slug/Slug.css
Normal file
|
|
@ -0,0 +1,43 @@
|
||||||
|
/* The slug: the signature line at the foot of a page. The shaded blocks pulse
|
||||||
|
in a wave, each glyph delayed by its index (`--i`). Motion is gated the way
|
||||||
|
`shell/Shell.css` gates its own: stilled under the OS preference and the
|
||||||
|
`data-motion` override, back on with `allow`. */
|
||||||
|
.ui-slug {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
gap: 1em;
|
||||||
|
margin: 2em 0 1em;
|
||||||
|
color: var(--purple-dim);
|
||||||
|
font-size: 0.8em;
|
||||||
|
letter-spacing: 0.15em;
|
||||||
|
}
|
||||||
|
.ui-slug-gradient {
|
||||||
|
white-space: pre;
|
||||||
|
}
|
||||||
|
.ui-slug-glyph {
|
||||||
|
display: inline-block;
|
||||||
|
animation: ui-slug-wave 2.4s ease-in-out infinite;
|
||||||
|
animation-delay: calc(var(--i) * 0.18s);
|
||||||
|
}
|
||||||
|
@keyframes ui-slug-wave {
|
||||||
|
0%,
|
||||||
|
100% {
|
||||||
|
opacity: 0.3;
|
||||||
|
}
|
||||||
|
50% {
|
||||||
|
opacity: 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@media (prefers-reduced-motion: reduce) {
|
||||||
|
.ui-slug-glyph {
|
||||||
|
animation: none;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
:root[data-motion="reduce"] .ui-slug-glyph {
|
||||||
|
animation: none;
|
||||||
|
}
|
||||||
|
:root[data-motion="allow"] .ui-slug-glyph {
|
||||||
|
animation: ui-slug-wave 2.4s ease-in-out infinite;
|
||||||
|
animation-delay: calc(var(--i) * 0.18s);
|
||||||
|
}
|
||||||
30
frontend/packages/swarm-ui/src/ui/slug/Slug.tsx
Normal file
30
frontend/packages/swarm-ui/src/ui/slug/Slug.tsx
Normal file
|
|
@ -0,0 +1,30 @@
|
||||||
|
// <Slug> — the signature line, `░▒▓█▓▒░ hyperhive / we are the wired ░▒▓█▓▒░`,
|
||||||
|
// the hive dashboard's footer line without its hive-c0re part. The
|
||||||
|
// shaded blocks at each end are the gradients: each glyph pulses a beat after
|
||||||
|
// its neighbour, so a wave runs along them (stilled under reduced motion, see
|
||||||
|
// `Slug.css`).
|
||||||
|
import "./Slug.css";
|
||||||
|
|
||||||
|
const GRADIENT = ["░", "▒", "▓", "█", "▓", "▒", "░"];
|
||||||
|
|
||||||
|
function Gradient() {
|
||||||
|
return (
|
||||||
|
<span class="ui-slug-gradient" aria-hidden="true">
|
||||||
|
{GRADIENT.map((glyph, i) => (
|
||||||
|
<span key={i} class="ui-slug-glyph" style={{ "--i": i }}>
|
||||||
|
{glyph}
|
||||||
|
</span>
|
||||||
|
))}
|
||||||
|
</span>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
export function Slug() {
|
||||||
|
return (
|
||||||
|
<p class="ui-slug">
|
||||||
|
<Gradient />
|
||||||
|
<span class="ui-slug-text">hyperhive / we are the wired</span>
|
||||||
|
<Gradient />
|
||||||
|
</p>
|
||||||
|
);
|
||||||
|
}
|
||||||
Loading…
Reference in a new issue