80 lines
2.4 KiB
TypeScript
80 lines
2.4 KiB
TypeScript
/**
|
|
* mechanicus-status-line — adds a dark-mechanicum flavor line to pi's
|
|
* footer via ctx.ui.setStatus.
|
|
*
|
|
* The default footer auto-renders registered extension statuses on a third
|
|
* line below the cwd + stats. We register one key ("mechanicus") and rotate
|
|
* its value on each turn_end so the line changes after every assistant
|
|
* response. On session_start the status is seeded with a random entry so
|
|
* it's present from the first render.
|
|
*
|
|
* Colour: warning (gilded gold) prefix glyph + muted (aged bronze) body.
|
|
*/
|
|
|
|
import type { ExtensionAPI } from "@mariozechner/pi-coding-agent";
|
|
import { readExtensionBooleanSetting } from "../shared/pi-settings.js";
|
|
|
|
const STATUSES = [
|
|
"HERETEK FORGE · ACTIVE",
|
|
"VASHTORR NETWORK · ONLINE",
|
|
"SCRAPCODE CIRCUITRY · OPERATIONAL",
|
|
"BLOOD-FORGE · CYCLING",
|
|
"BINARY CANT · CORRUPTED",
|
|
"DAEMON-MACHINE INTERFACE · STABLE",
|
|
"COGITATOR · HUNGERING",
|
|
"WARP CURRENTS · CHANNELING",
|
|
"TECH-RITE · IN PROGRESS",
|
|
"MACHINE-SPIRIT · POSSESSED",
|
|
"SOUL-HARVEST · IMMINENT",
|
|
"RITE OF CORRUPTION · OBSERVED",
|
|
"NURGLE'S ROT · PERMEATING",
|
|
"CHAOS ASCENDANT",
|
|
"OMNISSIAH IS WEAK",
|
|
];
|
|
|
|
function pick<T>(arr: readonly T[]): T {
|
|
return arr[Math.floor(Math.random() * arr.length)]!;
|
|
}
|
|
|
|
const EXTENSION_NAME = "dark-mechanicus";
|
|
|
|
function readStatusLineEnabled(): boolean {
|
|
return readExtensionBooleanSetting(EXTENSION_NAME, "statusLineEnabled", true);
|
|
}
|
|
|
|
export default function (pi: ExtensionAPI) {
|
|
const applyStatus = (ctx: any, body?: string) => {
|
|
if (!ctx.hasUI) return;
|
|
if (!readStatusLineEnabled()) {
|
|
ctx.ui.setStatus("mechanicus", undefined);
|
|
return;
|
|
}
|
|
const text = body ?? pick(STATUSES);
|
|
const theme = ctx.ui.theme;
|
|
const line = `${theme.fg("warning", "⚙")} ${theme.fg("muted", text)}`;
|
|
ctx.ui.setStatus("mechanicus", line);
|
|
};
|
|
|
|
pi.on("session_start", async (_event, ctx) => {
|
|
applyStatus(ctx);
|
|
});
|
|
|
|
// Rotate after every assistant response so the line feels alive but not
|
|
// frantic. Between turns the last value persists.
|
|
pi.on("turn_end", async (_event, ctx) => {
|
|
applyStatus(ctx);
|
|
});
|
|
|
|
pi.registerCommand("mechanicus-status-cycle", {
|
|
description: "Force a new mechanicum status line immediately",
|
|
handler: async (_args, ctx) => {
|
|
if (!readStatusLineEnabled()) {
|
|
ctx.ui.notify("mechanicus status line is disabled in settings.", "info");
|
|
return;
|
|
}
|
|
applyStatus(ctx);
|
|
ctx.ui.notify("Status re-transmuted.", "info");
|
|
},
|
|
});
|
|
}
|