astro-magic-move 0.1.0 → 0.1.2
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/package.json +2 -2
- package/src/MagicMove.astro +24 -15
- package/styles/magic-move.css +5 -4
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "astro-magic-move",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.2",
|
|
4
4
|
"description": "Animated code morphing for Astro, powered by Shiki Magic Move. Build-time tokenization, zero-framework client JS, CSS-variable theming.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "MIT",
|
|
@@ -34,4 +34,4 @@
|
|
|
34
34
|
"shiki": "^3.0.0",
|
|
35
35
|
"shiki-magic-move": "^1.3.0"
|
|
36
36
|
}
|
|
37
|
-
}
|
|
37
|
+
}
|
package/src/MagicMove.astro
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
---
|
|
2
|
-
import type { MagicMoveProps } from "./types";
|
|
3
|
-
import { cssVarTheme } from "./theme";
|
|
4
2
|
import { createHighlighter, type HighlighterGeneric } from "shiki";
|
|
5
3
|
import { codeToKeyedTokens, createMagicMoveMachine } from "shiki-magic-move/core";
|
|
4
|
+
import { cssVarTheme } from "./theme";
|
|
5
|
+
import type { MagicMoveProps } from "./types";
|
|
6
6
|
|
|
7
7
|
interface Props extends MagicMoveProps {}
|
|
8
8
|
|
|
@@ -29,15 +29,14 @@ if (stepsProp) {
|
|
|
29
29
|
} else if (before != null && after != null) {
|
|
30
30
|
steps = [before, after];
|
|
31
31
|
} else {
|
|
32
|
-
throw new Error(
|
|
33
|
-
"[astro-magic-move] Provide either `before` + `after` or `steps` (min 2 items).",
|
|
34
|
-
);
|
|
32
|
+
throw new Error("[astro-magic-move] Provide either `before` + `after` or `steps` (min 2 items).");
|
|
35
33
|
}
|
|
36
34
|
|
|
37
35
|
// Module-level highlighter cache (survives HMR via globalThis)
|
|
38
36
|
const CACHE_KEY = "__astro_magic_move_hl";
|
|
39
37
|
type HLCache = Map<string, HighlighterGeneric<string, string>>;
|
|
40
|
-
const hlCache: HLCache = ((globalThis as Record<string, unknown>)[CACHE_KEY] ??=
|
|
38
|
+
const hlCache: HLCache = ((globalThis as Record<string, unknown>)[CACHE_KEY] ??=
|
|
39
|
+
new Map()) as HLCache;
|
|
41
40
|
|
|
42
41
|
let highlighter = hlCache.get(lang);
|
|
43
42
|
if (!highlighter) {
|
|
@@ -50,8 +49,7 @@ if (!highlighter) {
|
|
|
50
49
|
|
|
51
50
|
// Build the magic move machine and compile all steps at build time
|
|
52
51
|
const machine = createMagicMoveMachine(
|
|
53
|
-
(code) =>
|
|
54
|
-
codeToKeyedTokens(highlighter, code, { lang, theme: "css-variables" }, lineNumbers),
|
|
52
|
+
(code) => codeToKeyedTokens(highlighter, code, { lang, theme: "css-variables" }, lineNumbers),
|
|
55
53
|
{},
|
|
56
54
|
);
|
|
57
55
|
|
|
@@ -105,9 +103,12 @@ const stepsJson = JSON.stringify(compiledSteps);
|
|
|
105
103
|
animateContainer: true,
|
|
106
104
|
});
|
|
107
105
|
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
106
|
+
if (trigger === "auto") {
|
|
107
|
+
this.currentStep = -1;
|
|
108
|
+
} else {
|
|
109
|
+
this.renderer.replace(this.steps[0]);
|
|
110
|
+
this.currentStep = 0;
|
|
111
|
+
}
|
|
111
112
|
this.setupTrigger(trigger, threshold);
|
|
112
113
|
}
|
|
113
114
|
|
|
@@ -128,9 +129,7 @@ const stepsJson = JSON.stringify(compiledSteps);
|
|
|
128
129
|
});
|
|
129
130
|
break;
|
|
130
131
|
case "auto":
|
|
131
|
-
requestAnimationFrame(() =>
|
|
132
|
-
this.animateToStep(1);
|
|
133
|
-
});
|
|
132
|
+
requestAnimationFrame(() => this.autoPlay());
|
|
134
133
|
break;
|
|
135
134
|
}
|
|
136
135
|
}
|
|
@@ -148,7 +147,17 @@ const stepsJson = JSON.stringify(compiledSteps);
|
|
|
148
147
|
this.observer.observe(this);
|
|
149
148
|
}
|
|
150
149
|
|
|
151
|
-
private async
|
|
150
|
+
private async autoPlay() {
|
|
151
|
+
const duration = Number(this.dataset.duration ?? 800);
|
|
152
|
+
for (let i = 0; i < this.steps.length; i++) {
|
|
153
|
+
await this.animateToStep(i);
|
|
154
|
+
if (i < this.steps.length - 1) {
|
|
155
|
+
await new Promise((r) => setTimeout(r, duration + 200));
|
|
156
|
+
}
|
|
157
|
+
}
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
private async animateToStep(stepIndex: number) {
|
|
152
161
|
if (!this.renderer || stepIndex === this.currentStep) return;
|
|
153
162
|
if (stepIndex < 0 || stepIndex >= this.steps.length) return;
|
|
154
163
|
|
package/styles/magic-move.css
CHANGED
|
@@ -11,10 +11,11 @@ magic-move {
|
|
|
11
11
|
margin: 0;
|
|
12
12
|
overflow-x: auto;
|
|
13
13
|
overflow-y: hidden;
|
|
14
|
-
padding: 1rem
|
|
15
|
-
font-family:
|
|
16
|
-
"Liberation Mono", "Courier New",
|
|
17
|
-
|
|
14
|
+
padding: 0.75rem 1rem;
|
|
15
|
+
font-family:
|
|
16
|
+
ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", "Courier New",
|
|
17
|
+
monospace;
|
|
18
|
+
font-size: clamp(0.75rem, 2vw, 0.875rem);
|
|
18
19
|
line-height: 1.7;
|
|
19
20
|
text-align: left;
|
|
20
21
|
background: var(--shiki-background, #1e1e1e);
|