@groeponline/pi-wishcraft 1.3.1 → 1.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +2 -0
- package/ROADMAP.md +22 -127
- package/docs/design/vnext-release-plan.md +3 -1
- package/package.json +1 -1
- package/src/config/parse.ts +12 -6
- package/src/config/settings-registry.ts +118 -0
- package/src/config/structural-presets.ts +6 -1
- package/src/core/frontmatter.ts +5 -2
- package/src/extension/contrib/appearance.ts +91 -0
- package/src/extension/contrib/registry.ts +42 -0
- package/src/extension/contrib/types.ts +20 -0
- package/src/extension/core/state.ts +5 -4
- package/src/extension/hooks/hooks-config.ts +6 -1
- package/src/extension/hooks/index.ts +11 -5
- package/src/extension/session/read-hints.ts +6 -2
- package/src/extension/settings/wishcraft-config-items.ts +14 -110
- package/src/extension/settings/wishcraft-config.ts +19 -17
- package/src/extension/skills/inline-invocation.ts +35 -11
- package/src/extension/skills/skill-registry.ts +41 -2
- package/src/extension/ui/deck/routes.ts +17 -2
- package/src/motion/catalog.ts +14 -11
- package/src/motion/policy.ts +3 -2
- package/src/signal/render.ts +49 -6
package/src/signal/render.ts
CHANGED
|
@@ -18,8 +18,9 @@ import { mergeSegmentsWithCustomItems } from "../config/powerline-config.ts";
|
|
|
18
18
|
import { renderSegment } from "../segments/index.ts";
|
|
19
19
|
import { ansi, colorEnabled, getFgAnsiCode } from "../theme/colors.ts";
|
|
20
20
|
import { getSeparator } from "../theme/separators.ts";
|
|
21
|
-
import { frameAt, getMotion } from "../motion/index.ts";
|
|
21
|
+
import { frameAt, getMotion, sweepPosition, trailGlyph } from "../motion/index.ts";
|
|
22
22
|
import type { SignalRuntime } from "./controller.ts";
|
|
23
|
+
import { getContributedSignalSources } from "../extension/contrib/registry.ts";
|
|
23
24
|
|
|
24
25
|
export interface SignalRenderOptions {
|
|
25
26
|
separatorStyle: StatusLineSeparatorStyle;
|
|
@@ -50,7 +51,10 @@ export function renderSignal(
|
|
|
50
51
|
},
|
|
51
52
|
);
|
|
52
53
|
const left = renderModules(merged.leftSegments, ctx);
|
|
53
|
-
const right =
|
|
54
|
+
const right = [
|
|
55
|
+
...renderModules(merged.rightSegments, ctx),
|
|
56
|
+
...renderContributedSources(ctx),
|
|
57
|
+
];
|
|
54
58
|
const secondary = renderModules(merged.secondarySegments, ctx);
|
|
55
59
|
const separator = getSeparator(options.separatorStyle).left;
|
|
56
60
|
|
|
@@ -91,11 +95,27 @@ export function renderActivity(
|
|
|
91
95
|
const open = spec.caps.leftOpen ?? "";
|
|
92
96
|
const close = spec.caps.leftClose ?? "";
|
|
93
97
|
const dim = getFgAnsiCode("sep");
|
|
98
|
+
const hot = getFgAnsiCode("accent");
|
|
94
99
|
const reset = colorEnabled() ? ansi.reset : "";
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
100
|
+
// ponytail: vivid sweep — 12-char rail with travelling head + 6-char trail, not a single glyph
|
|
101
|
+
const RAIL_WIDTH = 12;
|
|
102
|
+
let railInner: string;
|
|
103
|
+
if (!runtime.active) {
|
|
104
|
+
railInner = "━".repeat(RAIL_WIDTH);
|
|
105
|
+
} else {
|
|
106
|
+
const pos = sweepPosition(runtime.tick, RAIL_WIDTH, true);
|
|
107
|
+
let built = "";
|
|
108
|
+
for (let i = 0; i < RAIL_WIDTH; i++) {
|
|
109
|
+
const dist = Math.abs(i - pos);
|
|
110
|
+
if (dist === 0) built += glyph;
|
|
111
|
+
else if (dist <= 6) built += trailGlyph(dist, ascii);
|
|
112
|
+
else built += "━";
|
|
113
|
+
}
|
|
114
|
+
railInner = built;
|
|
115
|
+
}
|
|
116
|
+
const railColor = runtime.active ? hot : dim;
|
|
117
|
+
const rail = `${spec.separators.left}${railInner}${spec.separators.right}`;
|
|
118
|
+
return `${railColor}${open}${rail}${close}${reset} ${label}`;
|
|
99
119
|
}
|
|
100
120
|
|
|
101
121
|
function fitLanes(
|
|
@@ -164,6 +184,29 @@ function joinModules(modules: Module[], separator: string, width: number): strin
|
|
|
164
184
|
return fitted.length ? ` ${fitted.map((module) => module.content).join(sep)} ` : "";
|
|
165
185
|
}
|
|
166
186
|
|
|
187
|
+
const ANSI_CONTROL_RE = /\x1B(?:\][^\x07]*(?:\x07|\x1B\\)|\[[0-?]*[ -/]*[@-~]|[@-_])|\x9B[0-?]*[ -/]*[@-~]|\x9D[^\x07]*(?:\x07|\x1B\\)/g;
|
|
188
|
+
|
|
189
|
+
function stripAnsiControls(text: string): string {
|
|
190
|
+
return text.replace(ANSI_CONTROL_RE, "");
|
|
191
|
+
}
|
|
192
|
+
|
|
193
|
+
function renderContributedSources(ctx: SegmentContext): Module[] {
|
|
194
|
+
const out: Module[] = [];
|
|
195
|
+
for (const src of getContributedSignalSources()) {
|
|
196
|
+
try {
|
|
197
|
+
const raw = src.render?.(ctx);
|
|
198
|
+
if (!raw || typeof raw !== "string") continue;
|
|
199
|
+
const content = raw.trim();
|
|
200
|
+
if (!stripAnsiControls(content).trim()) continue;
|
|
201
|
+
// ponytail: fault-isolated — a throwing or empty source never takes down Signal
|
|
202
|
+
out.push({ content, width: visibleWidth(content) });
|
|
203
|
+
} catch {
|
|
204
|
+
// skip failing contribution
|
|
205
|
+
}
|
|
206
|
+
}
|
|
207
|
+
return out;
|
|
208
|
+
}
|
|
209
|
+
|
|
167
210
|
function styledSeparator(separator: string): string {
|
|
168
211
|
const color = getFgAnsiCode("sep");
|
|
169
212
|
const reset = colorEnabled() ? ansi.reset : "";
|