@clipkit/patterns 1.0.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/LICENSE +201 -0
- package/README.md +84 -0
- package/dist/anchor-default.d.ts +4 -0
- package/dist/anchor-default.d.ts.map +1 -0
- package/dist/anchor-default.js +34 -0
- package/dist/anchor-default.js.map +1 -0
- package/dist/bar-chart-row.d.ts +43 -0
- package/dist/bar-chart-row.d.ts.map +1 -0
- package/dist/bar-chart-row.js +143 -0
- package/dist/bar-chart-row.js.map +1 -0
- package/dist/beat-sync.d.ts +101 -0
- package/dist/beat-sync.d.ts.map +1 -0
- package/dist/beat-sync.js +145 -0
- package/dist/beat-sync.js.map +1 -0
- package/dist/camera-orbit.d.ts +22 -0
- package/dist/camera-orbit.d.ts.map +1 -0
- package/dist/camera-orbit.js +32 -0
- package/dist/camera-orbit.js.map +1 -0
- package/dist/cta-outro.d.ts +18 -0
- package/dist/cta-outro.d.ts.map +1 -0
- package/dist/cta-outro.js +44 -0
- package/dist/cta-outro.js.map +1 -0
- package/dist/data-scenes.d.ts +66 -0
- package/dist/data-scenes.d.ts.map +1 -0
- package/dist/data-scenes.js +188 -0
- package/dist/data-scenes.js.map +1 -0
- package/dist/flow-line.d.ts +27 -0
- package/dist/flow-line.d.ts.map +1 -0
- package/dist/flow-line.js +53 -0
- package/dist/flow-line.js.map +1 -0
- package/dist/glass-panel.d.ts +24 -0
- package/dist/glass-panel.d.ts.map +1 -0
- package/dist/glass-panel.js +32 -0
- package/dist/glass-panel.js.map +1 -0
- package/dist/header-bar.d.ts +36 -0
- package/dist/header-bar.d.ts.map +1 -0
- package/dist/header-bar.js +108 -0
- package/dist/header-bar.js.map +1 -0
- package/dist/hero-reveal.d.ts +17 -0
- package/dist/hero-reveal.d.ts.map +1 -0
- package/dist/hero-reveal.js +47 -0
- package/dist/hero-reveal.js.map +1 -0
- package/dist/index.d.ts +21 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +43 -0
- package/dist/index.js.map +1 -0
- package/dist/intro-card.d.ts +23 -0
- package/dist/intro-card.d.ts.map +1 -0
- package/dist/intro-card.js +123 -0
- package/dist/intro-card.js.map +1 -0
- package/dist/kinetic-headline.d.ts +18 -0
- package/dist/kinetic-headline.d.ts.map +1 -0
- package/dist/kinetic-headline.js +39 -0
- package/dist/kinetic-headline.js.map +1 -0
- package/dist/layers.d.ts +13 -0
- package/dist/layers.d.ts.map +1 -0
- package/dist/layers.js +19 -0
- package/dist/layers.js.map +1 -0
- package/dist/liquid-morph.d.ts +62 -0
- package/dist/liquid-morph.d.ts.map +1 -0
- package/dist/liquid-morph.js +113 -0
- package/dist/liquid-morph.js.map +1 -0
- package/dist/lit-surface.d.ts +38 -0
- package/dist/lit-surface.d.ts.map +1 -0
- package/dist/lit-surface.js +63 -0
- package/dist/lit-surface.js.map +1 -0
- package/dist/lower-third.d.ts +26 -0
- package/dist/lower-third.d.ts.map +1 -0
- package/dist/lower-third.js +101 -0
- package/dist/lower-third.js.map +1 -0
- package/dist/morph-shape.d.ts +42 -0
- package/dist/morph-shape.d.ts.map +1 -0
- package/dist/morph-shape.js +57 -0
- package/dist/morph-shape.js.map +1 -0
- package/dist/pie-card.d.ts +35 -0
- package/dist/pie-card.d.ts.map +1 -0
- package/dist/pie-card.js +168 -0
- package/dist/pie-card.js.map +1 -0
- package/dist/promo.d.ts +38 -0
- package/dist/promo.d.ts.map +1 -0
- package/dist/promo.js +61 -0
- package/dist/promo.js.map +1 -0
- package/dist/ranked-list.d.ts +38 -0
- package/dist/ranked-list.d.ts.map +1 -0
- package/dist/ranked-list.js +130 -0
- package/dist/ranked-list.js.map +1 -0
- package/dist/stat-block.d.ts +26 -0
- package/dist/stat-block.d.ts.map +1 -0
- package/dist/stat-block.js +92 -0
- package/dist/stat-block.js.map +1 -0
- package/dist/theme.d.ts +36 -0
- package/dist/theme.d.ts.map +1 -0
- package/dist/theme.js +75 -0
- package/dist/theme.js.map +1 -0
- package/dist/tilted-showcase.d.ts +29 -0
- package/dist/tilted-showcase.d.ts.map +1 -0
- package/dist/tilted-showcase.js +106 -0
- package/dist/tilted-showcase.js.map +1 -0
- package/dist/trend-pill.d.ts +33 -0
- package/dist/trend-pill.d.ts.map +1 -0
- package/dist/trend-pill.js +83 -0
- package/dist/trend-pill.js.map +1 -0
- package/dist/zoom-rig.d.ts +27 -0
- package/dist/zoom-rig.d.ts.map +1 -0
- package/dist/zoom-rig.js +46 -0
- package/dist/zoom-rig.js.map +1 -0
- package/package.json +36 -0
package/dist/theme.d.ts
ADDED
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
import type { FontFace } from '@clipkit/protocol';
|
|
2
|
+
export type ThemeName = 'mux' | 'minimal' | 'cinematic';
|
|
3
|
+
export type ColorName = 'pink' | 'green' | 'blue' | 'lavender' | 'purple' | 'yellow' | 'gray';
|
|
4
|
+
export interface ColorPalette {
|
|
5
|
+
/** Light background tint — used for body fills and pill interiors. */
|
|
6
|
+
bg: string;
|
|
7
|
+
/** Mid-weight accent — borders, dividers, secondary text. */
|
|
8
|
+
accent: string;
|
|
9
|
+
/** Dark accent — top borders, big headline text, pill borders + text. */
|
|
10
|
+
accentDark: string;
|
|
11
|
+
/** Color of the foreground "measure" bar (white in Mux). */
|
|
12
|
+
measure: string;
|
|
13
|
+
/** Primary body text color (black-ish). */
|
|
14
|
+
text: string;
|
|
15
|
+
/** Secondary / muted text. */
|
|
16
|
+
textMuted: string;
|
|
17
|
+
}
|
|
18
|
+
export interface Theme {
|
|
19
|
+
sansFont: string;
|
|
20
|
+
monoFont: string;
|
|
21
|
+
/** Display/serif face for big hero wordmarks (falls back to sansFont). */
|
|
22
|
+
displayFont?: string;
|
|
23
|
+
/** Webfonts to register on the Source so non-system faces actually load. */
|
|
24
|
+
fontFaces?: FontFace[];
|
|
25
|
+
/** When true, the theme's canvas is dark — patterns pick light defaults. */
|
|
26
|
+
dark?: boolean;
|
|
27
|
+
palettes: Record<ColorName, ColorPalette>;
|
|
28
|
+
}
|
|
29
|
+
export declare const THEMES: Record<ThemeName, Theme>;
|
|
30
|
+
export declare function getPalette(theme: ThemeName, color: ColorName): ColorPalette;
|
|
31
|
+
export declare function getFonts(theme: ThemeName): {
|
|
32
|
+
sans: string;
|
|
33
|
+
mono: string;
|
|
34
|
+
display: string;
|
|
35
|
+
};
|
|
36
|
+
//# sourceMappingURL=theme.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"theme.d.ts","sourceRoot":"","sources":["../src/theme.ts"],"names":[],"mappings":"AAWA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAElD,MAAM,MAAM,SAAS,GAAG,KAAK,GAAG,SAAS,GAAG,WAAW,CAAC;AACxD,MAAM,MAAM,SAAS,GACjB,MAAM,GACN,OAAO,GACP,MAAM,GACN,UAAU,GACV,QAAQ,GACR,QAAQ,GACR,MAAM,CAAC;AAEX,MAAM,WAAW,YAAY;IAC3B,sEAAsE;IACtE,EAAE,EAAE,MAAM,CAAC;IACX,6DAA6D;IAC7D,MAAM,EAAE,MAAM,CAAC;IACf,yEAAyE;IACzE,UAAU,EAAE,MAAM,CAAC;IACnB,4DAA4D;IAC5D,OAAO,EAAE,MAAM,CAAC;IAChB,2CAA2C;IAC3C,IAAI,EAAE,MAAM,CAAC;IACb,8BAA8B;IAC9B,SAAS,EAAE,MAAM,CAAC;CACnB;AAED,MAAM,WAAW,KAAK;IACpB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;IACjB,0EAA0E;IAC1E,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,4EAA4E;IAC5E,SAAS,CAAC,EAAE,QAAQ,EAAE,CAAC;IACvB,4EAA4E;IAC5E,IAAI,CAAC,EAAE,OAAO,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC,SAAS,EAAE,YAAY,CAAC,CAAC;CAC3C;AAaD,eAAO,MAAM,MAAM,EAAE,MAAM,CAAC,SAAS,EAAE,KAAK,CAgD3C,CAAC;AAEF,wBAAgB,UAAU,CAAC,KAAK,EAAE,SAAS,EAAE,KAAK,EAAE,SAAS,GAAG,YAAY,CAE3E;AAED,wBAAgB,QAAQ,CAAC,KAAK,EAAE,SAAS,GAAG;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,MAAM,CAAA;CAAE,CAG1F"}
|
package/dist/theme.js
ADDED
|
@@ -0,0 +1,75 @@
|
|
|
1
|
+
// Pattern theming.
|
|
2
|
+
//
|
|
3
|
+
// Each pattern accepts a `theme` (named bundle) + a `color` (named accent
|
|
4
|
+
// inside that theme) and reads its palette via getPalette(theme, color).
|
|
5
|
+
// Patterns DON'T accept arbitrary color overrides; if you need a custom
|
|
6
|
+
// look, copy the pattern source and tweak it. Same model as shadcn.
|
|
7
|
+
//
|
|
8
|
+
// To add a theme, extend THEMES below. To add a color within a theme,
|
|
9
|
+
// extend that theme's palette map. Patterns will pick it up automatically
|
|
10
|
+
// as long as the color name is listed in ColorName.
|
|
11
|
+
const MUX_BLACK = '#252525';
|
|
12
|
+
const MUX_GRAY = '#8e8e8e';
|
|
13
|
+
const WHITE = '#ffffff';
|
|
14
|
+
// Cinematic webfonts (fontsource CDN) — Inter for UI, Playfair for the wordmark.
|
|
15
|
+
const INTER = (w) => `https://cdn.jsdelivr.net/npm/@fontsource/inter/files/inter-latin-${w}-normal.woff2`;
|
|
16
|
+
const PLAYFAIR = (w) => `https://cdn.jsdelivr.net/npm/@fontsource/playfair-display/files/playfair-display-latin-${w}-normal.woff2`;
|
|
17
|
+
const CINE_BG = '#0a0e16', CINE_TEXT = '#f2f5fb', CINE_MUTE = '#8a98b8';
|
|
18
|
+
const cinePalette = (accent, accentDark) => ({ bg: CINE_BG, accent, accentDark, measure: WHITE, text: CINE_TEXT, textMuted: CINE_MUTE });
|
|
19
|
+
export const THEMES = {
|
|
20
|
+
mux: {
|
|
21
|
+
sansFont: 'Helvetica Neue, Helvetica, Arial, sans-serif',
|
|
22
|
+
monoFont: 'Menlo, Monaco, Consolas, monospace',
|
|
23
|
+
palettes: {
|
|
24
|
+
pink: { bg: '#ffecf6', accent: '#fb2491', accentDark: '#d91377', measure: WHITE, text: MUX_BLACK, textMuted: MUX_GRAY },
|
|
25
|
+
green: { bg: '#eaf9e4', accent: '#1FC3A8', accentDark: '#17A089', measure: WHITE, text: MUX_BLACK, textMuted: MUX_GRAY },
|
|
26
|
+
blue: { bg: '#e5f4ff', accent: '#1CA0FD', accentDark: '#0B85DB', measure: WHITE, text: MUX_BLACK, textMuted: MUX_GRAY },
|
|
27
|
+
lavender: { bg: '#f5e4ff', accent: '#9620D8', accentDark: '#6e15a0', measure: WHITE, text: MUX_BLACK, textMuted: MUX_GRAY },
|
|
28
|
+
purple: { bg: '#f5e4ff', accent: '#9620D8', accentDark: '#6e15a0', measure: WHITE, text: MUX_BLACK, textMuted: MUX_GRAY },
|
|
29
|
+
yellow: { bg: '#FFF8E0', accent: '#FED32F', accentDark: '#E99001', measure: WHITE, text: MUX_BLACK, textMuted: MUX_GRAY },
|
|
30
|
+
gray: { bg: '#f5f5f5', accent: '#8e8e8e', accentDark: '#383838', measure: WHITE, text: MUX_BLACK, textMuted: MUX_GRAY },
|
|
31
|
+
},
|
|
32
|
+
},
|
|
33
|
+
minimal: {
|
|
34
|
+
sansFont: 'system-ui, -apple-system, sans-serif',
|
|
35
|
+
monoFont: 'monospace',
|
|
36
|
+
palettes: {
|
|
37
|
+
pink: { bg: '#fafafa', accent: '#d4d4d4', accentDark: '#525252', measure: WHITE, text: '#0a0a0a', textMuted: '#737373' },
|
|
38
|
+
green: { bg: '#fafafa', accent: '#d4d4d4', accentDark: '#525252', measure: WHITE, text: '#0a0a0a', textMuted: '#737373' },
|
|
39
|
+
blue: { bg: '#fafafa', accent: '#d4d4d4', accentDark: '#525252', measure: WHITE, text: '#0a0a0a', textMuted: '#737373' },
|
|
40
|
+
lavender: { bg: '#fafafa', accent: '#d4d4d4', accentDark: '#525252', measure: WHITE, text: '#0a0a0a', textMuted: '#737373' },
|
|
41
|
+
purple: { bg: '#fafafa', accent: '#d4d4d4', accentDark: '#525252', measure: WHITE, text: '#0a0a0a', textMuted: '#737373' },
|
|
42
|
+
yellow: { bg: '#fafafa', accent: '#d4d4d4', accentDark: '#525252', measure: WHITE, text: '#0a0a0a', textMuted: '#737373' },
|
|
43
|
+
gray: { bg: '#fafafa', accent: '#d4d4d4', accentDark: '#525252', measure: WHITE, text: '#0a0a0a', textMuted: '#737373' },
|
|
44
|
+
},
|
|
45
|
+
},
|
|
46
|
+
cinematic: {
|
|
47
|
+
sansFont: 'Inter',
|
|
48
|
+
monoFont: 'Menlo, Monaco, monospace',
|
|
49
|
+
displayFont: 'Playfair Display',
|
|
50
|
+
dark: true,
|
|
51
|
+
fontFaces: [
|
|
52
|
+
{ family: 'Inter', weight: 400, src: INTER(400) },
|
|
53
|
+
{ family: 'Inter', weight: 700, src: INTER(700) },
|
|
54
|
+
{ family: 'Inter', weight: 800, src: INTER(800) },
|
|
55
|
+
{ family: 'Playfair Display', weight: 700, src: PLAYFAIR(700) },
|
|
56
|
+
],
|
|
57
|
+
palettes: {
|
|
58
|
+
pink: cinePalette('#ff5fae', '#c93d84'),
|
|
59
|
+
green: cinePalette('#2fe6b0', '#17a085'),
|
|
60
|
+
blue: cinePalette('#5fd0ff', '#2a93d4'),
|
|
61
|
+
lavender: cinePalette('#b58cff', '#7d54d4'),
|
|
62
|
+
purple: cinePalette('#9b6cff', '#6e3fd0'),
|
|
63
|
+
yellow: cinePalette('#f0c987', '#c79a4f'),
|
|
64
|
+
gray: cinePalette('#9fb0d8', '#5a6b8f'),
|
|
65
|
+
},
|
|
66
|
+
},
|
|
67
|
+
};
|
|
68
|
+
export function getPalette(theme, color) {
|
|
69
|
+
return THEMES[theme].palettes[color];
|
|
70
|
+
}
|
|
71
|
+
export function getFonts(theme) {
|
|
72
|
+
const t = THEMES[theme];
|
|
73
|
+
return { sans: t.sansFont, mono: t.monoFont, display: t.displayFont ?? t.sansFont };
|
|
74
|
+
}
|
|
75
|
+
//# sourceMappingURL=theme.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"theme.js","sourceRoot":"","sources":["../src/theme.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import type { Element } from '@clipkit/protocol';
|
|
2
|
+
import { type ColorName, type ThemeName } from './theme.js';
|
|
3
|
+
export interface TiltedShowcaseProps {
|
|
4
|
+
/** Used as the id prefix for every produced element. */
|
|
5
|
+
id: string;
|
|
6
|
+
/** Screenshot URL shown inside the frame (object-fit: cover). */
|
|
7
|
+
source: string;
|
|
8
|
+
/** Accent color slot — drives the frame's top border. */
|
|
9
|
+
color: ColorName;
|
|
10
|
+
theme?: ThemeName;
|
|
11
|
+
/** Center of the card in canvas px. */
|
|
12
|
+
x: number;
|
|
13
|
+
y: number;
|
|
14
|
+
/** Card size in px (chrome bar included). Default 720×480. */
|
|
15
|
+
width?: number;
|
|
16
|
+
height?: number;
|
|
17
|
+
/**
|
|
18
|
+
* Peak y-rotation in degrees; the card swings ±tilt (ping-pong) over
|
|
19
|
+
* its lifetime. Default 22. Pass 0 for a static straight-on card.
|
|
20
|
+
*/
|
|
21
|
+
tilt?: number;
|
|
22
|
+
/** Push the card toward (+) / away from (−) the camera, px. Default 0. */
|
|
23
|
+
z?: number;
|
|
24
|
+
time: number;
|
|
25
|
+
duration: number;
|
|
26
|
+
layer: number;
|
|
27
|
+
}
|
|
28
|
+
export declare function tiltedShowcase(props: TiltedShowcaseProps): Element;
|
|
29
|
+
//# sourceMappingURL=tilted-showcase.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"tilted-showcase.d.ts","sourceRoot":"","sources":["../src/tilted-showcase.ts"],"names":[],"mappings":"AASA,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,mBAAmB,CAAC;AAEjD,OAAO,EAAc,KAAK,SAAS,EAAE,KAAK,SAAS,EAAE,MAAM,YAAY,CAAC;AAExE,MAAM,WAAW,mBAAmB;IAClC,wDAAwD;IACxD,EAAE,EAAE,MAAM,CAAC;IACX,iEAAiE;IACjE,MAAM,EAAE,MAAM,CAAC;IACf,yDAAyD;IACzD,KAAK,EAAE,SAAS,CAAC;IACjB,KAAK,CAAC,EAAE,SAAS,CAAC;IAClB,uCAAuC;IACvC,CAAC,EAAE,MAAM,CAAC;IACV,CAAC,EAAE,MAAM,CAAC;IACV,8DAA8D;IAC9D,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB;;;OAGG;IACH,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,0EAA0E;IAC1E,CAAC,CAAC,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;IACjB,KAAK,EAAE,MAAM,CAAC;CACf;AAED,wBAAgB,cAAc,CAAC,KAAK,EAAE,mBAAmB,GAAG,OAAO,CAgGlE"}
|
|
@@ -0,0 +1,106 @@
|
|
|
1
|
+
// TiltedShowcase — the promo-video signature shot: a screenshot (or UI
|
|
2
|
+
// mock) inside a browser-chrome frame, tilted back in 3D and gently
|
|
3
|
+
// swinging. Pair with a Source-level `camera: { perspective }` for
|
|
4
|
+
// converging perspective; without one the tilt is affine.
|
|
5
|
+
//
|
|
6
|
+
// COMPONENT pattern: returns ONE `clip: true` group, so the §4.4.3
|
|
7
|
+
// flattening rule projects the whole framed card as a unit — and it
|
|
8
|
+
// expands to plain primitives only.
|
|
9
|
+
import { assignLayers } from './layers.js';
|
|
10
|
+
import { getPalette } from './theme.js';
|
|
11
|
+
export function tiltedShowcase(props) {
|
|
12
|
+
const { id, source, color, x, y, time, duration, layer } = props;
|
|
13
|
+
const theme = props.theme ?? 'mux';
|
|
14
|
+
const palette = getPalette(theme, color);
|
|
15
|
+
const W = props.width ?? 720;
|
|
16
|
+
const H = props.height ?? 480;
|
|
17
|
+
const tilt = props.tilt ?? 22;
|
|
18
|
+
const CHROME = 44;
|
|
19
|
+
const children = [
|
|
20
|
+
{
|
|
21
|
+
id: `${id}-frame`,
|
|
22
|
+
type: 'shape',
|
|
23
|
+
shape: 'rectangle',
|
|
24
|
+
x: W / 2,
|
|
25
|
+
y: H / 2,
|
|
26
|
+
x_anchor: '50%',
|
|
27
|
+
y_anchor: '50%',
|
|
28
|
+
width: W,
|
|
29
|
+
height: H,
|
|
30
|
+
fill_color: '#161B22',
|
|
31
|
+
border_radius: 14,
|
|
32
|
+
},
|
|
33
|
+
{
|
|
34
|
+
id: `${id}-chrome`,
|
|
35
|
+
type: 'shape',
|
|
36
|
+
shape: 'rectangle',
|
|
37
|
+
x: W / 2,
|
|
38
|
+
y: CHROME / 2,
|
|
39
|
+
x_anchor: '50%',
|
|
40
|
+
y_anchor: '50%',
|
|
41
|
+
width: W,
|
|
42
|
+
height: CHROME,
|
|
43
|
+
fill_color: '#21262E',
|
|
44
|
+
},
|
|
45
|
+
{ id: `${id}-d1`, type: 'shape', shape: 'ellipse', x: 26, y: CHROME / 2, x_anchor: '50%', y_anchor: '50%', width: 12, height: 12, fill_color: '#EF4444' },
|
|
46
|
+
{ id: `${id}-d2`, type: 'shape', shape: 'ellipse', x: 48, y: CHROME / 2, x_anchor: '50%', y_anchor: '50%', width: 12, height: 12, fill_color: '#F5B50F' },
|
|
47
|
+
{ id: `${id}-d3`, type: 'shape', shape: 'ellipse', x: 70, y: CHROME / 2, x_anchor: '50%', y_anchor: '50%', width: 12, height: 12, fill_color: '#22C55E' },
|
|
48
|
+
{
|
|
49
|
+
id: `${id}-accent`,
|
|
50
|
+
type: 'shape',
|
|
51
|
+
shape: 'rectangle',
|
|
52
|
+
x: W / 2,
|
|
53
|
+
y: CHROME + 1,
|
|
54
|
+
x_anchor: '50%',
|
|
55
|
+
y_anchor: '50%',
|
|
56
|
+
width: W,
|
|
57
|
+
height: 2,
|
|
58
|
+
fill_color: palette.accent,
|
|
59
|
+
},
|
|
60
|
+
{
|
|
61
|
+
id: `${id}-shot`,
|
|
62
|
+
type: 'image',
|
|
63
|
+
source,
|
|
64
|
+
x: W / 2,
|
|
65
|
+
y: CHROME + (H - CHROME) / 2,
|
|
66
|
+
x_anchor: '50%',
|
|
67
|
+
y_anchor: '50%',
|
|
68
|
+
width: W,
|
|
69
|
+
height: H - CHROME,
|
|
70
|
+
fit: 'cover',
|
|
71
|
+
},
|
|
72
|
+
];
|
|
73
|
+
return {
|
|
74
|
+
id,
|
|
75
|
+
type: 'group',
|
|
76
|
+
layer,
|
|
77
|
+
time,
|
|
78
|
+
duration,
|
|
79
|
+
x,
|
|
80
|
+
y,
|
|
81
|
+
x_anchor: '50%',
|
|
82
|
+
y_anchor: '50%',
|
|
83
|
+
width: W,
|
|
84
|
+
height: H,
|
|
85
|
+
clip: true,
|
|
86
|
+
...(props.z !== undefined ? { z: props.z } : {}),
|
|
87
|
+
...(tilt !== 0
|
|
88
|
+
? {
|
|
89
|
+
keyframe_animations: [{
|
|
90
|
+
property: 'y_rotation',
|
|
91
|
+
loop: 'ping-pong',
|
|
92
|
+
keyframes: [
|
|
93
|
+
{ time: 0, value: -tilt },
|
|
94
|
+
{ time: Math.max(0.1, duration / 2), value: tilt, easing: 'ease-in-out' },
|
|
95
|
+
],
|
|
96
|
+
}],
|
|
97
|
+
}
|
|
98
|
+
: {}),
|
|
99
|
+
animations: [
|
|
100
|
+
{ type: 'fade-in', duration: 0.5 },
|
|
101
|
+
{ type: 'fade-out', time: 'end', duration: 0.4 },
|
|
102
|
+
],
|
|
103
|
+
elements: assignLayers(children),
|
|
104
|
+
};
|
|
105
|
+
}
|
|
106
|
+
//# sourceMappingURL=tilted-showcase.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"tilted-showcase.js","sourceRoot":"","sources":["../src/tilted-showcase.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import type { Element } from '@clipkit/protocol';
|
|
2
|
+
import { type ColorName, type ThemeName } from './theme.js';
|
|
3
|
+
export interface TrendPillProps {
|
|
4
|
+
/** Unique id prefix; pattern appends -border / -inner / -text. */
|
|
5
|
+
id: string;
|
|
6
|
+
/** Center x in canvas pixels. */
|
|
7
|
+
cx: number;
|
|
8
|
+
/** Center y in canvas pixels. */
|
|
9
|
+
cy: number;
|
|
10
|
+
/**
|
|
11
|
+
* Signed percentage. Positive renders as "+X.X% FROM LAST MONTH",
|
|
12
|
+
* negative as "-X.X% FROM LAST MONTH".
|
|
13
|
+
*/
|
|
14
|
+
delta: number;
|
|
15
|
+
/** Color slot — determines border, bg, and text colors. */
|
|
16
|
+
color: ColorName;
|
|
17
|
+
/** Theme bundle. Default 'mux'. */
|
|
18
|
+
theme?: ThemeName;
|
|
19
|
+
/** Pill width in pixels. Default 460. */
|
|
20
|
+
width?: number;
|
|
21
|
+
/** Pill height in pixels. Default 60. */
|
|
22
|
+
height?: number;
|
|
23
|
+
/** Scene-local start time in seconds. */
|
|
24
|
+
time: number;
|
|
25
|
+
/** Duration in seconds. */
|
|
26
|
+
duration: number;
|
|
27
|
+
/** Starting layer index; pattern uses layerBase..layerBase+2. */
|
|
28
|
+
layerBase: number;
|
|
29
|
+
}
|
|
30
|
+
export declare function trendPill(props: TrendPillProps): Element[];
|
|
31
|
+
/** Convenience — signed percentage change from previous → current. */
|
|
32
|
+
export declare function trendPct(current: number, previous: number): number;
|
|
33
|
+
//# sourceMappingURL=trend-pill.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"trend-pill.d.ts","sourceRoot":"","sources":["../src/trend-pill.ts"],"names":[],"mappings":"AAMA,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,mBAAmB,CAAC;AACjD,OAAO,EAAwB,KAAK,SAAS,EAAE,KAAK,SAAS,EAAE,MAAM,YAAY,CAAC;AAElF,MAAM,WAAW,cAAc;IAC7B,kEAAkE;IAClE,EAAE,EAAE,MAAM,CAAC;IACX,iCAAiC;IACjC,EAAE,EAAE,MAAM,CAAC;IACX,iCAAiC;IACjC,EAAE,EAAE,MAAM,CAAC;IACX;;;OAGG;IACH,KAAK,EAAE,MAAM,CAAC;IACd,2DAA2D;IAC3D,KAAK,EAAE,SAAS,CAAC;IACjB,mCAAmC;IACnC,KAAK,CAAC,EAAE,SAAS,CAAC;IAClB,yCAAyC;IACzC,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,yCAAyC;IACzC,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,yCAAyC;IACzC,IAAI,EAAE,MAAM,CAAC;IACb,2BAA2B;IAC3B,QAAQ,EAAE,MAAM,CAAC;IACjB,iEAAiE;IACjE,SAAS,EAAE,MAAM,CAAC;CACnB;AAED,wBAAgB,SAAS,CAAC,KAAK,EAAE,cAAc,GAAG,OAAO,EAAE,CA2E1D;AAED,sEAAsE;AACtE,wBAAgB,QAAQ,CAAC,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,MAAM,CAGlE"}
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
// TrendPill — small "+X.X% FROM LAST MONTH" pill with a colored border.
|
|
2
|
+
//
|
|
3
|
+
// Renders as three stacked elements: an outer rectangle in the accent
|
|
4
|
+
// color, a slightly smaller inner rectangle in the body background, and
|
|
5
|
+
// uppercase monospace text on top. Animates in with fade + slide-up.
|
|
6
|
+
import { getFonts, getPalette } from './theme.js';
|
|
7
|
+
export function trendPill(props) {
|
|
8
|
+
const { id, cx, cy, delta, color, time, duration, layerBase, } = props;
|
|
9
|
+
const theme = props.theme ?? 'mux';
|
|
10
|
+
const width = props.width ?? 460;
|
|
11
|
+
const height = props.height ?? 60;
|
|
12
|
+
const palette = getPalette(theme, color);
|
|
13
|
+
const fonts = getFonts(theme);
|
|
14
|
+
const sign = delta >= 0 ? '+' : '-';
|
|
15
|
+
const text = `${sign}${Math.abs(delta).toFixed(1)}% FROM LAST MONTH`;
|
|
16
|
+
const slide = [
|
|
17
|
+
{ type: 'fade-in', duration: 0.4 },
|
|
18
|
+
{ type: 'slide-up-in', duration: 0.6, easing: 'ease-out-cubic' },
|
|
19
|
+
];
|
|
20
|
+
return [
|
|
21
|
+
{
|
|
22
|
+
id: `${id}-border`,
|
|
23
|
+
type: 'shape',
|
|
24
|
+
layer: layerBase,
|
|
25
|
+
time,
|
|
26
|
+
duration,
|
|
27
|
+
shape: 'rectangle',
|
|
28
|
+
x: cx,
|
|
29
|
+
y: cy,
|
|
30
|
+
x_anchor: '50%',
|
|
31
|
+
y_anchor: '50%',
|
|
32
|
+
width,
|
|
33
|
+
height,
|
|
34
|
+
fill_color: palette.accentDark,
|
|
35
|
+
border_radius: 12,
|
|
36
|
+
animations: slide,
|
|
37
|
+
},
|
|
38
|
+
{
|
|
39
|
+
id: `${id}-inner`,
|
|
40
|
+
type: 'shape',
|
|
41
|
+
layer: layerBase + 1,
|
|
42
|
+
time,
|
|
43
|
+
duration,
|
|
44
|
+
shape: 'rectangle',
|
|
45
|
+
x: cx,
|
|
46
|
+
y: cy,
|
|
47
|
+
x_anchor: '50%',
|
|
48
|
+
y_anchor: '50%',
|
|
49
|
+
width: width - 6,
|
|
50
|
+
height: height - 6,
|
|
51
|
+
fill_color: palette.bg,
|
|
52
|
+
border_radius: 10,
|
|
53
|
+
animations: slide,
|
|
54
|
+
},
|
|
55
|
+
{
|
|
56
|
+
id: `${id}-text`,
|
|
57
|
+
type: 'text',
|
|
58
|
+
layer: layerBase + 2,
|
|
59
|
+
time,
|
|
60
|
+
duration,
|
|
61
|
+
text,
|
|
62
|
+
x: cx,
|
|
63
|
+
// Nudged 4 px so uppercase glyphs look optically centered (geometric
|
|
64
|
+
// centering of uppercase text appears slightly too high).
|
|
65
|
+
y: cy + 4,
|
|
66
|
+
x_anchor: '50%',
|
|
67
|
+
y_anchor: '50%',
|
|
68
|
+
font_family: fonts.mono,
|
|
69
|
+
font_size: 26,
|
|
70
|
+
font_weight: '600',
|
|
71
|
+
letter_spacing: 1.5,
|
|
72
|
+
fill_color: palette.accentDark,
|
|
73
|
+
animations: slide,
|
|
74
|
+
},
|
|
75
|
+
];
|
|
76
|
+
}
|
|
77
|
+
/** Convenience — signed percentage change from previous → current. */
|
|
78
|
+
export function trendPct(current, previous) {
|
|
79
|
+
if (previous === 0)
|
|
80
|
+
return current === 0 ? 0 : 100;
|
|
81
|
+
return ((current - previous) / previous) * 100;
|
|
82
|
+
}
|
|
83
|
+
//# sourceMappingURL=trend-pill.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"trend-pill.js","sourceRoot":"","sources":["../src/trend-pill.ts"],"names":[],"mappings":"AAAA,wEAAwE;AACxE,EAAE;AACF,sEAAsE;AACtE,wEAAwE;AACxE,qEAAqE;AAGrE,OAAO,EAAE,QAAQ,EAAE,UAAU,EAAkC,MAAM,YAAY,CAAC;AA8BlF,MAAM,UAAU,SAAS,CAAC,KAAqB;IAC7C,MAAM,EACJ,EAAE,EAAE,EAAE,EAAE,EAAE,EAAE,KAAK,EAAE,KAAK,EAAE,IAAI,EAAE,QAAQ,EAAE,SAAS,GACpD,GAAG,KAAK,CAAC;IACV,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,IAAI,KAAK,CAAC;IACnC,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,IAAI,GAAG,CAAC;IACjC,MAAM,MAAM,GAAG,KAAK,CAAC,MAAM,IAAI,EAAE,CAAC;IAElC,MAAM,OAAO,GAAG,UAAU,CAAC,KAAK,EAAE,KAAK,CAAC,CAAC;IACzC,MAAM,KAAK,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAC;IAE9B,MAAM,IAAI,GAAG,KAAK,IAAI,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,GAAG,CAAC;IACpC,MAAM,IAAI,GAAG,GAAG,IAAI,GAAG,IAAI,CAAC,GAAG,CAAC,KAAK,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,mBAAmB,CAAC;IAErE,MAAM,KAAK,GAAG;QACZ,EAAE,IAAI,EAAE,SAAkB,EAAE,QAAQ,EAAE,GAAG,EAAE;QAC3C,EAAE,IAAI,EAAE,aAAsB,EAAE,QAAQ,EAAE,GAAG,EAAE,MAAM,EAAE,gBAAyB,EAAE;KACnF,CAAC;IAEF,OAAO;QACL;YACE,EAAE,EAAE,GAAG,EAAE,SAAS;YAClB,IAAI,EAAE,OAAO;YACb,KAAK,EAAE,SAAS;YAChB,IAAI;YACJ,QAAQ;YACR,KAAK,EAAE,WAAW;YAClB,CAAC,EAAE,EAAE;YACL,CAAC,EAAE,EAAE;YACL,QAAQ,EAAE,KAAK;YACf,QAAQ,EAAE,KAAK;YACf,KAAK;YACL,MAAM;YACN,UAAU,EAAE,OAAO,CAAC,UAAU;YAC9B,aAAa,EAAE,EAAE;YACjB,UAAU,EAAE,KAAK;SAClB;QACD;YACE,EAAE,EAAE,GAAG,EAAE,QAAQ;YACjB,IAAI,EAAE,OAAO;YACb,KAAK,EAAE,SAAS,GAAG,CAAC;YACpB,IAAI;YACJ,QAAQ;YACR,KAAK,EAAE,WAAW;YAClB,CAAC,EAAE,EAAE;YACL,CAAC,EAAE,EAAE;YACL,QAAQ,EAAE,KAAK;YACf,QAAQ,EAAE,KAAK;YACf,KAAK,EAAE,KAAK,GAAG,CAAC;YAChB,MAAM,EAAE,MAAM,GAAG,CAAC;YAClB,UAAU,EAAE,OAAO,CAAC,EAAE;YACtB,aAAa,EAAE,EAAE;YACjB,UAAU,EAAE,KAAK;SAClB;QACD;YACE,EAAE,EAAE,GAAG,EAAE,OAAO;YAChB,IAAI,EAAE,MAAM;YACZ,KAAK,EAAE,SAAS,GAAG,CAAC;YACpB,IAAI;YACJ,QAAQ;YACR,IAAI;YACJ,CAAC,EAAE,EAAE;YACL,qEAAqE;YACrE,0DAA0D;YAC1D,CAAC,EAAE,EAAE,GAAG,CAAC;YACT,QAAQ,EAAE,KAAK;YACf,QAAQ,EAAE,KAAK;YACf,WAAW,EAAE,KAAK,CAAC,IAAI;YACvB,SAAS,EAAE,EAAE;YACb,WAAW,EAAE,KAAK;YAClB,cAAc,EAAE,GAAG;YACnB,UAAU,EAAE,OAAO,CAAC,UAAU;YAC9B,UAAU,EAAE,KAAK;SAClB;KACF,CAAC;AACJ,CAAC;AAED,sEAAsE;AACtE,MAAM,UAAU,QAAQ,CAAC,OAAe,EAAE,QAAgB;IACxD,IAAI,QAAQ,KAAK,CAAC;QAAE,OAAO,OAAO,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC;IACnD,OAAO,CAAC,CAAC,OAAO,GAAG,QAAQ,CAAC,GAAG,QAAQ,CAAC,GAAG,GAAG,CAAC;AACjD,CAAC"}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import type { Element } from '@clipkit/protocol';
|
|
2
|
+
export interface ZoomShot {
|
|
3
|
+
/** The world point to centre, in canvas coords. */
|
|
4
|
+
focal: [number, number];
|
|
5
|
+
/** Zoom factor (1 = whole frame). */
|
|
6
|
+
scale: number;
|
|
7
|
+
/** Time (seconds, rig-local) this shot is reached. The first shot is the
|
|
8
|
+
* starting pose and should usually be `at: 0`. */
|
|
9
|
+
at: number;
|
|
10
|
+
}
|
|
11
|
+
export interface ZoomRigProps {
|
|
12
|
+
/** Id prefix for the wrapper group. */
|
|
13
|
+
id: string;
|
|
14
|
+
/** The world content (absolute canvas coords). */
|
|
15
|
+
elements: Element[];
|
|
16
|
+
/** Framing keyframes. ≥1; reached in order, eased between. */
|
|
17
|
+
shots: ZoomShot[];
|
|
18
|
+
canvasWidth: number;
|
|
19
|
+
canvasHeight: number;
|
|
20
|
+
/** Ease between shots (cubic in-out). Default true; false = linear. */
|
|
21
|
+
ease?: boolean;
|
|
22
|
+
time: number;
|
|
23
|
+
duration: number;
|
|
24
|
+
track: number;
|
|
25
|
+
}
|
|
26
|
+
export declare function zoomRig(props: ZoomRigProps): Element;
|
|
27
|
+
//# sourceMappingURL=zoom-rig.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"zoom-rig.d.ts","sourceRoot":"","sources":["../src/zoom-rig.ts"],"names":[],"mappings":"AAoBA,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,mBAAmB,CAAC;AAEjD,MAAM,WAAW,QAAQ;IACvB,mDAAmD;IACnD,KAAK,EAAE,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IACxB,qCAAqC;IACrC,KAAK,EAAE,MAAM,CAAC;IACd;uDACmD;IACnD,EAAE,EAAE,MAAM,CAAC;CACZ;AAED,MAAM,WAAW,YAAY;IAC3B,uCAAuC;IACvC,EAAE,EAAE,MAAM,CAAC;IACX,kDAAkD;IAClD,QAAQ,EAAE,OAAO,EAAE,CAAC;IACpB,8DAA8D;IAC9D,KAAK,EAAE,QAAQ,EAAE,CAAC;IAClB,WAAW,EAAE,MAAM,CAAC;IACpB,YAAY,EAAE,MAAM,CAAC;IACrB,uEAAuE;IACvE,IAAI,CAAC,EAAE,OAAO,CAAC;IACf,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;IACjB,KAAK,EAAE,MAAM,CAAC;CACf;AAED,wBAAgB,OAAO,CAAC,KAAK,EAAE,YAAY,GAAG,OAAO,CA6BpD"}
|
package/dist/zoom-rig.js
ADDED
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
// zoomRig — a continuous "camera" move done with a group transform (the
|
|
2
|
+
// motion-graphics "infinite zoom" rig, not the 2.5D scene camera). Wraps your
|
|
3
|
+
// world content in one group and animates its scale + position so a sequence of
|
|
4
|
+
// SHOTS frames different points of the scene: push in on A, pan to B, pull back
|
|
5
|
+
// out — all as one continuous move, every transition a real camera gesture
|
|
6
|
+
// rather than a cut.
|
|
7
|
+
//
|
|
8
|
+
// The math (verified against the compositor): for a full-frame group anchored at
|
|
9
|
+
// its centre, a world point (fx, fy) lands at screen centre at zoom S when
|
|
10
|
+
// group.x = cx - S·(fx - cx), group.y = cy - S·(fy - cy)
|
|
11
|
+
// where (cx, cy) is the canvas centre. We solve that PER SHOT and emit it as
|
|
12
|
+
// `keyframe_animations` for scale/x/y (the runtime interpolates + eases between
|
|
13
|
+
// shots). Keyframed group transforms anchor at the group centre and correctly
|
|
14
|
+
// carry nested children — including clipped groups (a `flowLine`) and `svg`
|
|
15
|
+
// (a `morphShape`) — which expression-valued group x/y do NOT.
|
|
16
|
+
//
|
|
17
|
+
// Put it around content authored in ABSOLUTE canvas coordinates (the same space
|
|
18
|
+
// every other pattern uses). Keep shot scales ≥ 1 (S < 1 reveals outside the
|
|
19
|
+
// world). Pair with `motion_blur` on the Source to sell the fast push/pull.
|
|
20
|
+
export function zoomRig(props) {
|
|
21
|
+
const { id, elements, shots, canvasWidth: W, canvasHeight: H, time, duration, track } = props;
|
|
22
|
+
const easing = (props.ease ?? true) ? 'ease-in-out' : undefined;
|
|
23
|
+
const cx = W / 2;
|
|
24
|
+
const cy = H / 2;
|
|
25
|
+
// Solve the framing transform at each shot; the runtime eases between them.
|
|
26
|
+
const key = (value) => shots.map((s, i) => ({ time: Math.max(0, s.at), value: value(s), ...(i > 0 && easing ? { easing } : {}) }));
|
|
27
|
+
const animations = [
|
|
28
|
+
{ property: 'scale', keyframes: key((s) => s.scale) },
|
|
29
|
+
{ property: 'x', keyframes: key((s) => cx - s.scale * (s.focal[0] - cx)) },
|
|
30
|
+
{ property: 'y', keyframes: key((s) => cy - s.scale * (s.focal[1] - cy)) },
|
|
31
|
+
];
|
|
32
|
+
return {
|
|
33
|
+
id,
|
|
34
|
+
type: 'group',
|
|
35
|
+
track,
|
|
36
|
+
time,
|
|
37
|
+
duration,
|
|
38
|
+
x: cx,
|
|
39
|
+
y: cy,
|
|
40
|
+
width: W,
|
|
41
|
+
height: H,
|
|
42
|
+
keyframe_animations: animations,
|
|
43
|
+
elements,
|
|
44
|
+
};
|
|
45
|
+
}
|
|
46
|
+
//# sourceMappingURL=zoom-rig.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"zoom-rig.js","sourceRoot":"","sources":["../src/zoom-rig.ts"],"names":[],"mappings":"AAAA,wEAAwE;AACxE,8EAA8E;AAC9E,gFAAgF;AAChF,gFAAgF;AAChF,2EAA2E;AAC3E,qBAAqB;AACrB,EAAE;AACF,iFAAiF;AACjF,2EAA2E;AAC3E,4DAA4D;AAC5D,6EAA6E;AAC7E,gFAAgF;AAChF,8EAA8E;AAC9E,4EAA4E;AAC5E,+DAA+D;AAC/D,EAAE;AACF,gFAAgF;AAChF,6EAA6E;AAC7E,4EAA4E;AA8B5E,MAAM,UAAU,OAAO,CAAC,KAAmB;IACzC,MAAM,EAAE,EAAE,EAAE,QAAQ,EAAE,KAAK,EAAE,WAAW,EAAE,CAAC,EAAE,YAAY,EAAE,CAAC,EAAE,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE,GAAG,KAAK,CAAC;IAC9F,MAAM,MAAM,GAAG,CAAC,KAAK,CAAC,IAAI,IAAI,IAAI,CAAC,CAAC,CAAC,CAAC,aAAa,CAAC,CAAC,CAAC,SAAS,CAAC;IAChE,MAAM,EAAE,GAAG,CAAC,GAAG,CAAC,CAAC;IACjB,MAAM,EAAE,GAAG,CAAC,GAAG,CAAC,CAAC;IAEjB,4EAA4E;IAC5E,MAAM,GAAG,GAAG,CAAC,KAA8B,EAAE,EAAE,CAC7C,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,IAAI,EAAE,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,EAAE,KAAK,EAAE,KAAK,CAAC,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC,GAAG,CAAC,IAAI,MAAM,CAAC,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC;IAE9G,MAAM,UAAU,GAAG;QACjB,EAAE,QAAQ,EAAE,OAAO,EAAE,SAAS,EAAE,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,KAAK,CAAC,EAAE;QACrD,EAAE,QAAQ,EAAE,GAAG,EAAE,SAAS,EAAE,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,EAAE,GAAG,CAAC,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC,CAAC,EAAE;QAC1E,EAAE,QAAQ,EAAE,GAAG,EAAE,SAAS,EAAE,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,EAAE,GAAG,CAAC,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC,CAAC,EAAE;KAC3E,CAAC;IAEF,OAAO;QACL,EAAE;QACF,IAAI,EAAE,OAAO;QACb,KAAK;QACL,IAAI;QACJ,QAAQ;QACR,CAAC,EAAE,EAAE;QACL,CAAC,EAAE,EAAE;QACL,KAAK,EAAE,CAAC;QACR,MAAM,EAAE,CAAC;QACT,mBAAmB,EAAE,UAAU;QAC/B,QAAQ;KACE,CAAC;AACf,CAAC"}
|
package/package.json
ADDED
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@clipkit/patterns",
|
|
3
|
+
"version": "1.0.0",
|
|
4
|
+
"description": "Authoring-time pattern library for Clipkit — composable motion-graphics units that emit primitive Source elements.",
|
|
5
|
+
"license": "Apache-2.0",
|
|
6
|
+
"repository": { "type": "git", "url": "git+https://github.com/clipkit-video/clipkit.git", "directory": "packages/patterns" },
|
|
7
|
+
"homepage": "https://clipkit.dev",
|
|
8
|
+
"bugs": "https://github.com/clipkit-video/clipkit/issues",
|
|
9
|
+
"type": "module",
|
|
10
|
+
"main": "./dist/index.js",
|
|
11
|
+
"types": "./dist/index.d.ts",
|
|
12
|
+
"exports": {
|
|
13
|
+
".": {
|
|
14
|
+
"import": "./dist/index.js",
|
|
15
|
+
"types": "./dist/index.d.ts"
|
|
16
|
+
}
|
|
17
|
+
},
|
|
18
|
+
"files": [
|
|
19
|
+
"dist",
|
|
20
|
+
"README.md",
|
|
21
|
+
"LICENSE"
|
|
22
|
+
],
|
|
23
|
+
"scripts": {
|
|
24
|
+
"build": "tsc",
|
|
25
|
+
"dev": "tsc --watch",
|
|
26
|
+
"typecheck": "tsc --noEmit",
|
|
27
|
+
"clean": "rm -rf dist"
|
|
28
|
+
},
|
|
29
|
+
"dependencies": {
|
|
30
|
+
"@clipkit/music-analysis": "^1.0.0",
|
|
31
|
+
"@clipkit/protocol": "^1.0.0"
|
|
32
|
+
},
|
|
33
|
+
"devDependencies": {
|
|
34
|
+
"typescript": "^5.7.3"
|
|
35
|
+
}
|
|
36
|
+
}
|