@boxcc/maildeno-editor 0.0.0-stage → 0.4.14
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 +479 -0
- package/README.md +442 -2
- package/dist/DatePicker-AdfGW0Tw.js +5347 -0
- package/dist/DatePicker-aNFlsoOb.js +5347 -0
- package/dist/Dialog-By0JLN8s.js +6294 -0
- package/dist/HealthIndicator-BLID6Ty0.js +1216 -0
- package/dist/HealthIndicator-DfzqzPNw.js +1217 -0
- package/dist/PopperContent-N2nAEFeH.js +2538 -0
- package/dist/PopperContent-eLmz1Gjd.js +2578 -0
- package/dist/PreviewCanvas-D3SpILsV.js +534 -0
- package/dist/PreviewCanvas-PtW1UL1J.js +534 -0
- package/dist/RichTextEditor-D6DQqbJg.js +12218 -0
- package/dist/RichTextEditor-DDEfKPZm.js +12217 -0
- package/dist/RowPreviewChildren-BGnilx-K.js +4 -0
- package/dist/RowPreviewChildren-CalQWx1C.js +4 -0
- package/dist/RowPreviewLegacyComponent-Df_1HTly.js +403 -0
- package/dist/RowPreviewLegacyComponent-NECG3wpn.js +403 -0
- package/dist/RowPreviewRow-C2XAe5Xs.js +81 -0
- package/dist/RowPreviewRow-DG4AdMrv.js +81 -0
- package/dist/SavedRowsPanel-2JBfYdxN.js +492 -0
- package/dist/SavedRowsPanel-B6_VHQZm.js +493 -0
- package/dist/_plugin-vue_export-helper-Dj7HTbfw.js +8 -0
- package/dist/adapters/errors.d.ts +59 -0
- package/dist/adapters/localStorageAdapter.d.ts +6 -0
- package/dist/adapters/types.d.ts +151 -0
- package/dist/babel-DV7WPQI0.js +10043 -0
- package/dist/blocks/registry.d.ts +23 -0
- package/dist/blocks/types.d.ts +73 -0
- package/dist/borderRadius-CkSa1lQ9.js +75 -0
- package/dist/components/features/emailBuilder/EmailEditor.vue.d.ts +183 -0
- package/dist/composables/emailBuilder/export/logic/espLogicWrapper.d.ts +76 -0
- package/dist/composables/emailBuilder/persistence/useEmailBuilderPersistence.d.ts +38 -0
- package/dist/composables/emailBuilder/transform/pipeline/optimize.d.ts +100 -0
- package/dist/composables/system/useColorScheme.d.ts +16 -0
- package/dist/element-DQw3HLit.js +21540 -0
- package/dist/element.d.ts +6 -0
- package/dist/element.js +5 -0
- package/dist/esp/registry.d.ts +33 -0
- package/dist/estree-DY9POgc0.js +8195 -0
- package/dist/html-wb0gSX1o.js +7273 -0
- package/dist/index.d.ts +17 -0
- package/dist/index.js +15032 -0
- package/dist/init.d.ts +180 -0
- package/dist/init.js +143 -0
- package/dist/maildeno-editor.css +2 -0
- package/dist/merge-tags/registry.d.ts +33 -0
- package/dist/mergeTagDefinitions-Cler19nv.js +27 -0
- package/dist/standalone-DHvJ30Td.js +3554 -0
- package/dist/theme.d.ts +206 -0
- package/dist/types/assistant.d.ts +56 -0
- package/dist/useEmailBuilder-2yCUzRx2.js +4934 -0
- package/dist/useEmailBuilder-D3uV7dwL.js +4934 -0
- package/dist/useToast-D1GgDMqQ.js +194 -0
- package/dist/utils/border.d.ts +15 -0
- package/dist/utils/borderRadius.d.ts +10 -0
- package/dist/vue.runtime.esm-bundler-D2AjRP90.js +6117 -0
- package/package.json +100 -4
package/dist/init.d.ts
ADDED
|
@@ -0,0 +1,180 @@
|
|
|
1
|
+
import { PartialStorageAdapter } from './adapters/types';
|
|
2
|
+
import { AssistantMount } from './types/assistant';
|
|
3
|
+
import { ThemeOptions } from './theme';
|
|
4
|
+
/**
|
|
5
|
+
* The ergonomic, no-Vue-knowledge entry point. element.ts already provides
|
|
6
|
+
* everything this composes — a real custom element, complete CSS bundling,
|
|
7
|
+
* live theming via CSS variables — init() just wires it up with a plain
|
|
8
|
+
* options object and hands back a small handle instead of requiring the
|
|
9
|
+
* caller to know defineCustomElement, prop reflection, or DOM CustomEvent
|
|
10
|
+
* details themselves.
|
|
11
|
+
*/
|
|
12
|
+
export interface InitOptions {
|
|
13
|
+
/** A DOM element, or a CSS selector resolved via document.querySelector. */
|
|
14
|
+
container: HTMLElement | string;
|
|
15
|
+
templateId?: string;
|
|
16
|
+
storageAdapter?: PartialStorageAdapter;
|
|
17
|
+
theme?: ThemeOptions;
|
|
18
|
+
capabilities?: {
|
|
19
|
+
export?: Array<"html" | "mjml" | "react" | "json">;
|
|
20
|
+
};
|
|
21
|
+
onSendTestEmail?: (payload: {
|
|
22
|
+
to: string;
|
|
23
|
+
subject: string;
|
|
24
|
+
html: string;
|
|
25
|
+
}) => Promise<void> | void;
|
|
26
|
+
/**
|
|
27
|
+
* Name shown in the desktop-only notice's "Powered by" line. Omit for the
|
|
28
|
+
* package default; pass an empty string to drop the line entirely.
|
|
29
|
+
*
|
|
30
|
+
* Unlike storageAdapter/theme/onSendTestEmail this is a plain string, so
|
|
31
|
+
* the custom element accepts it as a `brand-name` attribute too —
|
|
32
|
+
* `<maildeno-editor brand-name="Acme">` works without any JavaScript.
|
|
33
|
+
* init() still sets it as a property below, for consistency with the
|
|
34
|
+
* other options rather than out of necessity.
|
|
35
|
+
*/
|
|
36
|
+
brandName?: string;
|
|
37
|
+
/**
|
|
38
|
+
* Replaces the saved-templates panel and its header button with version
|
|
39
|
+
* history. Requires an adapter implementing the version methods — see
|
|
40
|
+
* EditorStorageAdapter; the built-in localStorage adapter implements all
|
|
41
|
+
* of them, so this works with no backend.
|
|
42
|
+
*
|
|
43
|
+
* A boolean, so the custom element accepts it as a `versions` attribute
|
|
44
|
+
* too — attribute presence is truthy, matching how HTML booleans work.
|
|
45
|
+
*/
|
|
46
|
+
versions?: boolean;
|
|
47
|
+
/**
|
|
48
|
+
* Called after a successful save. Its presence is what reveals the Save
|
|
49
|
+
* button — omit it for a read-only or guest editor and the button, the
|
|
50
|
+
* save-status indicator and the autosave timer all disappear.
|
|
51
|
+
*
|
|
52
|
+
* The "save" event still fires alongside, so handle.on("save", …) keeps
|
|
53
|
+
* working; this option exists because a listener attached after mount
|
|
54
|
+
* can't retroactively decide whether the button should have rendered.
|
|
55
|
+
*/
|
|
56
|
+
onSave?: (payload: {
|
|
57
|
+
templateId: string | null;
|
|
58
|
+
}) => void;
|
|
59
|
+
/**
|
|
60
|
+
* Fills the editor's assistant drawer with your own UI.
|
|
61
|
+
*
|
|
62
|
+
* The editor supplies the drawer, its trigger button, open/close state,
|
|
63
|
+
* escape handling and shadow-DOM-safe positioning; `mount` receives the
|
|
64
|
+
* drawer's body element plus a small canvas API (getJson/setJson/
|
|
65
|
+
* getSelection/setSelection/onChange) and renders whatever it likes into
|
|
66
|
+
* it — React root, plain DOM, anything.
|
|
67
|
+
*
|
|
68
|
+
* Called on first open rather than at startup, and `unmount` on close, so
|
|
69
|
+
* a drawer the user never opens costs nothing.
|
|
70
|
+
*
|
|
71
|
+
* ```ts
|
|
72
|
+
* init({
|
|
73
|
+
* container: "#editor",
|
|
74
|
+
* assistant: {
|
|
75
|
+
* mount(el, editor) {
|
|
76
|
+
* el.innerHTML = "<button>Rewrite</button>";
|
|
77
|
+
* el.querySelector("button").onclick = async () => {
|
|
78
|
+
* const next = await myApi.rewrite(editor.getJson());
|
|
79
|
+
* editor.setJson(next);
|
|
80
|
+
* };
|
|
81
|
+
* },
|
|
82
|
+
* },
|
|
83
|
+
* });
|
|
84
|
+
* ```
|
|
85
|
+
*/
|
|
86
|
+
assistant?: AssistantMount;
|
|
87
|
+
/**
|
|
88
|
+
* Render inside a shadow root (default) or directly in the page.
|
|
89
|
+
*
|
|
90
|
+
* Shadow DOM isolates the editor's styles from the host page, which is
|
|
91
|
+
* usually what you want. Set false when you'd rather have predictable
|
|
92
|
+
* DOM behaviour than isolation: inside a shadow root `event.target` is
|
|
93
|
+
* retargeted to the host, `document.activeElement` returns the host,
|
|
94
|
+
* `document.querySelector` can't see in, and `@font-face`/`@property`
|
|
95
|
+
* are ignored. This package handles all of that internally, but a host
|
|
96
|
+
* page's own scripts — or a third-party library — may not, and that is
|
|
97
|
+
* not fixable from inside the editor. Light DOM is the escape hatch.
|
|
98
|
+
*
|
|
99
|
+
* The trade-off is real in both directions: with `shadowDom: false`,
|
|
100
|
+
* the host page's CSS can reach the editor and vice versa.
|
|
101
|
+
*/
|
|
102
|
+
shadowDom?: boolean;
|
|
103
|
+
}
|
|
104
|
+
export interface EditorHandle {
|
|
105
|
+
/** The underlying <maildeno-editor> element, for anything this handle
|
|
106
|
+
* doesn't wrap directly — it's a real DOM element, nothing hidden. */
|
|
107
|
+
readonly element: HTMLElement;
|
|
108
|
+
/** Vue's defineCustomElement dispatches emits as real DOM CustomEvents
|
|
109
|
+
* on the host element, with the emit payload in event.detail — this is
|
|
110
|
+
* just addEventListener with that unwrapping done for you. */
|
|
111
|
+
/**
|
|
112
|
+
* Additional listeners for the save event.
|
|
113
|
+
*
|
|
114
|
+
* Only ever fires when `onSave` was passed to init(): without it the editor
|
|
115
|
+
* has no Save button and never saves, so there is no event to hear. If you
|
|
116
|
+
* only want to observe saves, pass a no-op `onSave` to enable saving and do
|
|
117
|
+
* the work here.
|
|
118
|
+
*/
|
|
119
|
+
on(event: "save", handler: (payload: {
|
|
120
|
+
templateId: string | null;
|
|
121
|
+
}) => void): void;
|
|
122
|
+
off(event: "save", handler: (payload: {
|
|
123
|
+
templateId: string | null;
|
|
124
|
+
}) => void): void;
|
|
125
|
+
/** Re-themes live — sets the theme prop, which EmailEditor.vue's own
|
|
126
|
+
* watch(..., {immediate: true}) picks up via useHost(), the same
|
|
127
|
+
* mechanism that applies it on initial mount. Calling this again after
|
|
128
|
+
* mount is the actual "live" part, not just initial configuration. */
|
|
129
|
+
setTheme(theme: ThemeOptions): void;
|
|
130
|
+
/** Updates the name used by the header, saves and exports. Empty clears it. */
|
|
131
|
+
setTemplateName(name: string): void;
|
|
132
|
+
/** These four call EmailEditor.vue's defineExpose'd methods, which Vue's
|
|
133
|
+
* own defineCustomElement implementation forwards directly onto the
|
|
134
|
+
* custom element instance (confirmed: _instance.exposed is read and
|
|
135
|
+
* redefined as properties on the element itself, not something Vue-
|
|
136
|
+
* internal or requiring a $refs-style lookup). "prune" (default)
|
|
137
|
+
* evaluates against the current preview context; "wrap" always
|
|
138
|
+
* includes every ESP-conditional branch, matching the same two modes
|
|
139
|
+
* the Export dropdown itself offers. */
|
|
140
|
+
getHtml(mode?: "prune" | "wrap"): string | null;
|
|
141
|
+
getMjml(mode?: "prune" | "wrap"): string | null;
|
|
142
|
+
getReactEmail(mode?: "prune" | "wrap"): string | null;
|
|
143
|
+
getJson(): Record<string, unknown> | null;
|
|
144
|
+
/** The write side of getJson(). Accepts what getJson() returns, so
|
|
145
|
+
* setJson(getJson()) round-trips, plus the { canvas, content: { rows } }
|
|
146
|
+
* shape version APIs typically hand back.
|
|
147
|
+
*
|
|
148
|
+
* history defaults to "undoable" — one Ctrl+Z-able step, right for
|
|
149
|
+
* anything the user triggered. Pass "reset" when swapping which document
|
|
150
|
+
* is open, where undoing back into the previous document would be wrong. */
|
|
151
|
+
setJson(data: unknown, opts?: {
|
|
152
|
+
history?: "undoable" | "reset";
|
|
153
|
+
}): void;
|
|
154
|
+
/** The selected node, or null. `type` is the block type, so a host can
|
|
155
|
+
* branch on it without resolving the id against the tree itself. */
|
|
156
|
+
getSelection(): {
|
|
157
|
+
id: string;
|
|
158
|
+
type: string | null;
|
|
159
|
+
} | null;
|
|
160
|
+
/** Selects by id, or clears with null. Returns false if no node has that
|
|
161
|
+
* id. Does not touch history — selection is view state. */
|
|
162
|
+
setSelection(id: string | null): boolean;
|
|
163
|
+
/** Fires after each committed change. Returns an unsubscribe function.
|
|
164
|
+
* Keyed to history commits rather than raw mutations, so typing inside a
|
|
165
|
+
* text block produces one call, not one per keystroke. */
|
|
166
|
+
onChange(cb: () => void): () => void;
|
|
167
|
+
/** Removes the element from the DOM. Vue's custom element wrapper
|
|
168
|
+
* handles unmounting the internal app and cleaning up watchers/effects
|
|
169
|
+
* as part of its own disconnectedCallback — not reimplemented here. */
|
|
170
|
+
destroy(): void;
|
|
171
|
+
}
|
|
172
|
+
export declare function init(options: InitOptions): Promise<EditorHandle>;
|
|
173
|
+
export { registerBlock, getBlock, getAllBlocks } from './blocks/registry';
|
|
174
|
+
export { registerESPSyntax, getRegisteredCustomESPs } from './esp/registry';
|
|
175
|
+
export { registerMergeTags, getRegisteredMergeTagIds, } from './merge-tags/registry';
|
|
176
|
+
export { setEditorTheme, palette } from './theme';
|
|
177
|
+
export { createLocalStorageAdapter } from './adapters/localStorageAdapter';
|
|
178
|
+
export type { BlockDefinition } from './blocks/types';
|
|
179
|
+
export type { ThemeOptions, ThemeTokens } from './theme';
|
|
180
|
+
export type { EditorStorageAdapter, PartialStorageAdapter, TemplateSnapshot, TemplateSummary, SavedRow, } from './adapters/types';
|
package/dist/init.js
ADDED
|
@@ -0,0 +1,143 @@
|
|
|
1
|
+
import { O as o, at as c, i as u, st as g } from "./vue.runtime.esm-bundler-D2AjRP90.js";
|
|
2
|
+
import { G as f, a as T, i as H, n as v, r as S } from "./element-DQw3HLit.js";
|
|
3
|
+
import { D as w, K as A, O as C, c as N, k as J, l as M, m as I, p as R } from "./useEmailBuilder-2yCUzRx2.js";
|
|
4
|
+
var d = !1;
|
|
5
|
+
function p() {
|
|
6
|
+
if (!(d || typeof document > "u")) {
|
|
7
|
+
d = !0;
|
|
8
|
+
for (const e of f()) {
|
|
9
|
+
if (!e) continue;
|
|
10
|
+
const l = document.createElement("style");
|
|
11
|
+
l.setAttribute("data-maildeno-light-dom", ""), l.textContent = e, document.head.appendChild(l);
|
|
12
|
+
}
|
|
13
|
+
}
|
|
14
|
+
}
|
|
15
|
+
function h(e, l) {
|
|
16
|
+
p();
|
|
17
|
+
const t = c({ ...l }), i = /* @__PURE__ */ new Set(), a = g(null), r = document.createElement("div");
|
|
18
|
+
r.style.height = "100%", e.appendChild(r);
|
|
19
|
+
const n = u({ setup() {
|
|
20
|
+
return () => o(S, {
|
|
21
|
+
...t,
|
|
22
|
+
ref: a,
|
|
23
|
+
onSave: (s) => i.forEach((m) => m(s))
|
|
24
|
+
});
|
|
25
|
+
} });
|
|
26
|
+
return n.mount(r), {
|
|
27
|
+
element: r,
|
|
28
|
+
exposed: () => a.value ?? null,
|
|
29
|
+
setProp: (s, m) => {
|
|
30
|
+
t[s] = m;
|
|
31
|
+
},
|
|
32
|
+
addSaveHandler: (s) => i.add(s),
|
|
33
|
+
removeSaveHandler: (s) => i.delete(s),
|
|
34
|
+
destroy: () => {
|
|
35
|
+
n.unmount(), r.remove();
|
|
36
|
+
}
|
|
37
|
+
};
|
|
38
|
+
}
|
|
39
|
+
async function j(e) {
|
|
40
|
+
const l = typeof e.container == "string" ? document.querySelector(e.container) : e.container;
|
|
41
|
+
if (!l) throw new Error(`[maildeno-editor] init() couldn't find a container${typeof e.container == "string" ? ` matching "${e.container}"` : ""}.`);
|
|
42
|
+
if (e.shadowDom === !1) {
|
|
43
|
+
const a = h(l, {
|
|
44
|
+
templateId: e.templateId,
|
|
45
|
+
storageAdapter: e.storageAdapter,
|
|
46
|
+
theme: e.theme,
|
|
47
|
+
capabilities: e.capabilities,
|
|
48
|
+
onSendTestEmail: e.onSendTestEmail,
|
|
49
|
+
brandName: e.brandName,
|
|
50
|
+
versions: e.versions,
|
|
51
|
+
saveHandler: e.onSave,
|
|
52
|
+
assistant: e.assistant
|
|
53
|
+
});
|
|
54
|
+
await new Promise((n) => setTimeout(n, 0));
|
|
55
|
+
const r = (n, ...s) => {
|
|
56
|
+
const m = a.exposed()?.[n];
|
|
57
|
+
return typeof m == "function" ? m(...s) : null;
|
|
58
|
+
};
|
|
59
|
+
return {
|
|
60
|
+
element: a.element,
|
|
61
|
+
on: (n, s) => a.addSaveHandler(s),
|
|
62
|
+
off: (n, s) => a.removeSaveHandler(s),
|
|
63
|
+
setTheme: (n) => a.setProp("theme", n),
|
|
64
|
+
setTemplateName: (n) => {
|
|
65
|
+
r("setTemplateName", n);
|
|
66
|
+
},
|
|
67
|
+
getHtml: (n = "prune") => r("getHtml", n),
|
|
68
|
+
getMjml: (n = "prune") => r("getMjml", n),
|
|
69
|
+
getReactEmail: (n = "prune") => r("getReactEmail", n),
|
|
70
|
+
getJson: () => r("getJson"),
|
|
71
|
+
setJson: (n, s) => {
|
|
72
|
+
r("setJson", n, s);
|
|
73
|
+
},
|
|
74
|
+
getSelection: () => r("getSelection"),
|
|
75
|
+
setSelection: (n) => r("setSelection", n) ?? !1,
|
|
76
|
+
onChange: (n) => r("onChange", n) ?? (() => {
|
|
77
|
+
}),
|
|
78
|
+
destroy: () => a.destroy()
|
|
79
|
+
};
|
|
80
|
+
}
|
|
81
|
+
v();
|
|
82
|
+
const t = document.createElement("maildeno-editor");
|
|
83
|
+
e.templateId !== void 0 && (t.templateId = e.templateId), e.storageAdapter && (t.storageAdapter = e.storageAdapter), e.theme && (t.theme = e.theme), e.capabilities && (t.capabilities = e.capabilities), e.onSendTestEmail && (t.onSendTestEmail = e.onSendTestEmail), e.brandName !== void 0 && (t.brandName = e.brandName), e.versions !== void 0 && (t.versions = e.versions), e.assistant && (t.assistant = e.assistant), e.onSave && (t.saveHandler = e.onSave), l.appendChild(t), await new Promise((a) => setTimeout(a, 0));
|
|
84
|
+
const i = /* @__PURE__ */ new WeakMap();
|
|
85
|
+
return {
|
|
86
|
+
element: t,
|
|
87
|
+
on(a, r) {
|
|
88
|
+
const n = ((s) => r(Array.isArray(s.detail) ? s.detail[0] : s.detail));
|
|
89
|
+
i.set(r, n), t.addEventListener(a, n);
|
|
90
|
+
},
|
|
91
|
+
off(a, r) {
|
|
92
|
+
const n = i.get(r);
|
|
93
|
+
n && (t.removeEventListener(a, n), i.delete(r));
|
|
94
|
+
},
|
|
95
|
+
setTheme(a) {
|
|
96
|
+
t.theme = a;
|
|
97
|
+
},
|
|
98
|
+
setTemplateName(a) {
|
|
99
|
+
t.setTemplateName?.(a);
|
|
100
|
+
},
|
|
101
|
+
getHtml(a = "prune") {
|
|
102
|
+
return t.getHtml ? t.getHtml(a) : null;
|
|
103
|
+
},
|
|
104
|
+
getMjml(a = "prune") {
|
|
105
|
+
return t.getMjml ? t.getMjml(a) : null;
|
|
106
|
+
},
|
|
107
|
+
getReactEmail(a = "prune") {
|
|
108
|
+
return t.getReactEmail ? t.getReactEmail(a) : null;
|
|
109
|
+
},
|
|
110
|
+
getJson() {
|
|
111
|
+
return t.getJson ? t.getJson() : null;
|
|
112
|
+
},
|
|
113
|
+
setJson(a, r) {
|
|
114
|
+
t.setJson?.(a, r);
|
|
115
|
+
},
|
|
116
|
+
getSelection() {
|
|
117
|
+
return t.getSelection ? t.getSelection() : null;
|
|
118
|
+
},
|
|
119
|
+
setSelection(a) {
|
|
120
|
+
return t.setSelection ? t.setSelection(a) : !1;
|
|
121
|
+
},
|
|
122
|
+
onChange(a) {
|
|
123
|
+
return t.onChange ? t.onChange(a) : () => {
|
|
124
|
+
};
|
|
125
|
+
},
|
|
126
|
+
destroy() {
|
|
127
|
+
t.remove();
|
|
128
|
+
}
|
|
129
|
+
};
|
|
130
|
+
}
|
|
131
|
+
export {
|
|
132
|
+
A as createLocalStorageAdapter,
|
|
133
|
+
w as getAllBlocks,
|
|
134
|
+
C as getBlock,
|
|
135
|
+
N as getRegisteredCustomESPs,
|
|
136
|
+
R as getRegisteredMergeTagIds,
|
|
137
|
+
j as init,
|
|
138
|
+
H as palette,
|
|
139
|
+
J as registerBlock,
|
|
140
|
+
M as registerESPSyntax,
|
|
141
|
+
I as registerMergeTags,
|
|
142
|
+
T as setEditorTheme
|
|
143
|
+
};
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
.md-input[data-v-94ca4419]{width:100%;color:var(--md-text);background:var(--md-surface);border:1px solid var(--md-border);border-radius:.375rem;outline:none;padding:.325rem .625rem;font-size:13px;line-height:1.25rem;transition:border-color .15s,box-shadow .15s}.md-input[data-v-94ca4419]::placeholder{color:var(--md-text-subtle)}.md-input[data-v-94ca4419]:focus{border-color:var(--md-primary)}.md-input[data-v-94ca4419]:disabled{background:var(--md-surface-hover);color:var(--md-text-subtle);cursor:not-allowed}.md-input--invalid[data-v-94ca4419]{border-color:var(--md-danger)}.md-input--invalid[data-v-94ca4419]:focus{border-color:var(--md-danger);box-shadow:0 0 0 1px var(--md-danger)}.transparent-swatch[data-v-fad96f2e]{background-color:#fff;background-image:linear-gradient(45deg,#ccc 25%,#0000 25%),linear-gradient(-45deg,#ccc 25%,#0000 25%),linear-gradient(45deg,#0000 75%,#ccc 75%),linear-gradient(-45deg,#0000 75%,#ccc 75%);background-position:0 0,0 3px,3px -3px,-3px 0;background-size:6px 6px}.md-sel__anchor{box-sizing:border-box;background:var(--md-surface);border:1px solid var(--md-border);width:100%;min-height:32px;color:var(--md-text);border-radius:.375rem;align-items:center;gap:.25rem;padding:0 .375rem 0 .5rem;font-size:13px;display:flex}.md-sel__anchor:focus-within,.md-sel__anchor--open{border-color:var(--md-primary)}.md-sel__anchor--disabled{background:var(--md-surface-hover);color:var(--md-text-subtle)}.md-sel__input{box-sizing:border-box;width:100%;min-width:0;color:var(--md-text);background:0 0;border:0;outline:none;flex:1;padding:.375rem 0;font-family:inherit;font-size:13px;line-height:1.25rem}.md-sel__input::placeholder{color:var(--md-text-subtle)}.md-sel__triggerText{box-sizing:border-box;cursor:pointer;min-width:0;color:var(--md-text);text-align:left;text-overflow:ellipsis;white-space:nowrap;background:0 0;border:0;outline:none;flex:1;padding:.375rem 0;font-family:inherit;font-size:13px;overflow:hidden}.md-sel__ph{color:var(--md-text-subtle)}.md-sel__chev{cursor:pointer;width:20px;height:20px;color:var(--md-text-muted);background:0 0;border:0;outline:none;flex-shrink:0;justify-content:center;align-items:center;padding:0;transition:transform .15s,color .15s;display:inline-flex}.md-sel__chev--open{color:var(--md-text);transform:rotate(180deg)}.md-sel__content{z-index:999999;width:var(--reka-combobox-trigger-width);box-sizing:border-box;background:var(--md-surface);border:1px solid var(--md-border);border-radius:.5rem;min-width:180px;max-width:320px;position:relative;overflow:hidden;box-shadow:0 10px 15px -3px #0000001f,0 4px 6px -4px #0000001f}.md-sel__viewport{box-sizing:border-box;background:var(--md-surface);width:100%;max-height:240px;padding:4px;overflow:hidden auto}.md-sel__empty{box-sizing:border-box;background:var(--md-surface);width:100%;color:var(--md-text-subtle);text-align:center;padding:8px;font-family:inherit;font-size:12px;display:block}.md-sel__item{box-sizing:border-box;background:var(--md-surface);width:100%;min-height:32px;color:var(--md-text);cursor:pointer;-webkit-user-select:none;user-select:none;border:0;border-radius:6px;outline:none;justify-content:space-between;align-items:center;gap:8px;padding:6px 8px;font-family:inherit;font-size:13px;line-height:18px;display:flex}.md-sel__item:hover,.md-sel__item[data-highlighted]{background:var(--md-surface-muted)}.md-sel__item[data-state=checked]{background:var(--md-success-bg);color:var(--md-success-fg);font-weight:500}.md-sel__item[data-state=checked][data-highlighted]{background:color-mix(in srgb, var(--md-success) 20%, var(--md-success-bg))}.md-sel__itemLabel{text-overflow:ellipsis;white-space:nowrap;flex:1;min-width:0;overflow:hidden}.md-sel__check{color:currentColor;flex-shrink:0;justify-content:center;align-items:center;width:16px;height:16px;font-size:12px;display:inline-flex}.md-btn[data-v-e13a23ac]{cursor:pointer;border:1px solid #0000;border-radius:.375rem;justify-content:center;align-items:center;gap:.375rem;padding:.5rem .875rem;font-size:13px;font-weight:500;transition:background-color .15s,border-color .15s,opacity .15s;display:inline-flex}.md-btn[data-v-e13a23ac]:disabled{opacity:.55;cursor:not-allowed}.md-btn--primary[data-v-e13a23ac]{background:var(--md-button-primary-bg);color:var(--md-button-primary-text)}.md-btn--primary[data-v-e13a23ac]:not(:disabled):hover{background:var(--md-button-primary-hover-bg)}.md-btn--secondary[data-v-e13a23ac]{background:var(--md-button-secondary-bg);color:var(--md-button-secondary-text);border-color:var(--md-border)}.md-btn--secondary[data-v-e13a23ac]:not(:disabled):hover{background:var(--md-button-secondary-hover-bg)}.md-btn--danger[data-v-e13a23ac]{background:var(--md-danger);color:var(--md-on-danger)}.md-btn--danger[data-v-e13a23ac]:not(:disabled):hover{filter:brightness(.94)}.md-btn--success[data-v-e13a23ac]{background:var(--md-success);color:var(--md-surface)}.md-dialog__overlay[data-v-2491daae]{z-index:9998;background:#0006;justify-content:center;align-items:center;padding:1rem;display:flex;position:fixed;inset:0}.md-dialog[data-v-2491daae]{background:var(--md-surface);border-radius:.75rem;outline:none;flex-direction:column;width:420px;max-width:100%;max-height:calc(100vh - 2rem);display:flex;box-shadow:0 20px 60px #00000040}.md-dialog__header[data-v-2491daae]{justify-content:space-between;align-items:center;gap:1rem;padding:1.125rem 1.25rem .5rem;display:flex}.md-dialog__header--noTitle[data-v-2491daae]{justify-content:flex-end}.md-dialog__title[data-v-2491daae]{color:var(--md-text);margin:0;font-size:17px;font-weight:600}.md-dialog__close[data-v-2491daae]{color:var(--md-text-subtle);cursor:pointer;background:0 0;border:0;border-radius:.25rem;padding:.25rem;display:inline-flex}.md-dialog__close[data-v-2491daae]:hover{color:var(--md-text);background:var(--md-surface-muted)}.md-dialog__body[data-v-2491daae]{color:var(--md-text);padding:.5rem 1.25rem 1.25rem;font-size:14px;overflow-y:auto}.md-dialog__footer[data-v-2491daae]{justify-content:flex-end;gap:.5rem;padding:0 1.25rem 1.25rem;display:flex}.md-dialog__srOnly[data-v-2491daae]{clip:rect(0, 0, 0, 0);white-space:nowrap;border:0;width:1px;height:1px;margin:-1px;padding:0;position:absolute;overflow:hidden}.section-fade-enter-active[data-v-bb838abe],.section-fade-leave-active[data-v-bb838abe]{transition:opacity .15s,transform .15s}.section-fade-enter-from[data-v-bb838abe],.section-fade-leave-to[data-v-bb838abe]{opacity:0;transform:translateY(-3px)}.corner-input[data-v-139dfcd1] input[type=range]{display:none}.transparent-swatch[data-v-7373b74d]{background-color:#fff;background-image:linear-gradient(45deg,#ccc 25%,#0000 25%),linear-gradient(-45deg,#ccc 25%,#0000 25%),linear-gradient(45deg,#0000 75%,#ccc 75%),linear-gradient(-45deg,#0000 75%,#ccc 75%);background-position:0 0,0 3px,3px -3px,-3px 0;background-size:6px 6px}.rules-scroll[data-v-3e175668]{-webkit-overflow-scrolling:touch;max-width:100%;overflow-x:auto}.rules-scroll[data-v-3e175668]::-webkit-scrollbar{height:6px}.rules-scroll[data-v-3e175668]::-webkit-scrollbar-track{background:var(--md-surface-muted);border-radius:4px}.rules-scroll[data-v-3e175668]::-webkit-scrollbar-thumb{background:var(--md-border-strong);border-radius:4px}.rules-scroll[data-v-3e175668]::-webkit-scrollbar-thumb:hover{background:var(--md-text-subtle)}.toggle-btn[data-v-26c04ac4]{cursor:pointer;background:0 0;border:.5px solid #0000;border-radius:6px;outline:none;justify-content:center;align-items:center;height:28px;padding:0;transition:background .1s,border-color .1s,color .1s;display:flex}.toggle-btn[data-v-26c04ac4]:focus-visible{box-shadow:0 0 0 2px var(--md-selection)}.toggle-btn--idle[data-v-26c04ac4]{border-color:var(--md-border);color:var(--md-text-subtle)}.toggle-btn--idle[data-v-26c04ac4]:hover{background:var(--md-surface-hover);border-color:var(--md-border-strong)}.toggle-btn--active[data-v-26c04ac4]{background:var(--md-selection-bg);border-color:var(--md-selection);color:var(--md-selection-fg)}.toggle-btn--active[data-v-26c04ac4]:hover{background:color-mix(in srgb, var(--md-selection) 20%, var(--md-selection-bg))}.toggle-btn[data-v-b01eaed8]{cursor:pointer;background:0 0;border:.5px solid #0000;border-radius:6px;outline:none;justify-content:center;align-items:center;height:28px;padding:0;transition:background .1s,border-color .1s,color .1s;display:flex}.toggle-btn--idle[data-v-b01eaed8]{border-color:color-mix(in srgb, var(--md-border) 80%, transparent);color:var(--md-text-subtle)}.toggle-btn--idle[data-v-b01eaed8]:hover{background:var(--md-surface-hover);border-color:var(--md-border-strong);color:var(--md-text-muted)}.toggle-btn--active[data-v-b01eaed8]{background:var(--md-selection-bg);border-color:var(--md-selection);color:var(--md-selection-fg)}.toggle-btn--active[data-v-b01eaed8]:hover{background:color-mix(in srgb, var(--md-selection) 20%, var(--md-selection-bg))}.panel[data-v-f8eef947]{background:var(--md-surface);border:.5px solid color-mix(in srgb, var(--md-border) 80%, transparent);border-radius:10px;padding:10px 12px}.separator[data-v-f8eef947]{background:color-mix(in srgb, var(--md-border) 80%, transparent);height:.5px;margin-left:-12px;margin-right:-12px}.spinner[data-v-8a2d8f31]{border:5px solid #0003;border-top-color:var(--md-selection);border-radius:50%;width:50px;height:50px;margin:0 auto;animation:1s linear infinite spin-8a2d8f31}@keyframes spin-8a2d8f31{to{transform:rotate(360deg)}}.desktop-gate[data-v-ac364a19]{--brand-primary:var(--md-primary,var(--md-primary));--brand-primary-dark:var(--md-primary-hover,var(--md-primary-hover));--brand-primary-light:var(--md-primary-hover,var(--md-primary-hover));--brand-gradient-start:var(--md-primary,var(--md-primary));--brand-gradient-end:var(--md-primary-hover,var(--md-primary-hover));--gate-surface:var(--md-surface,var(--md-surface));--gate-backdrop:var(--md-background,var(--md-surface-hover));--gate-on-primary:var(--md-on-primary,var(--md-surface));--gate-warning:var(--md-warning,var(--md-warning));--gray-50:var(--md-background,var(--md-surface-hover));--gray-100:var(--md-surface-muted,var(--md-surface-muted));--gray-200:var(--md-border,var(--md-border));--gray-300:var(--md-border-strong,var(--md-border-strong));--gray-400:var(--md-text-subtle,var(--md-text-subtle));--gray-500:var(--md-text-subtle,var(--md-text-muted));--gray-600:var(--md-text-muted,var(--md-text-muted));--gray-700:var(--md-text-muted,var(--md-text-muted));--gray-800:var(--md-text,var(--md-text));--gray-900:var(--md-text,var(--md-text));--shadow-sm:0 1px 2px 0 #0000000d;--shadow-md:0 4px 6px -1px #0000001a, 0 2px 4px -2px #0000001a;--shadow-lg:0 10px 15px -3px #0000001a, 0 4px 6px -4px #0000001a;--shadow-xl:0 20px 25px -5px #0000001a, 0 8px 10px -6px #0000001a;--shadow-2xl:0 25px 50px -12px #00000040;z-index:9999;background:color-mix(in srgb, var(--gate-backdrop) 98%, transparent);-webkit-backdrop-filter:blur(2px);backdrop-filter:blur(2px);justify-content:center;align-items:center;padding:1.5rem;display:flex;position:fixed;inset:0}.gate-container[data-v-ac364a19]{background:var(--gate-surface);text-align:center;width:100%;max-width:520px;box-shadow:var(--shadow-2xl);border:1px solid var(--gray-200);border-radius:2rem;padding:2.5rem;animation:.5s cubic-bezier(.16,1,.3,1) fadeInUp-ac364a19}.brand-badge[data-v-ac364a19]{justify-content:center;align-items:center;width:80px;height:80px;margin:0 auto 1.5rem;display:flex;position:relative}.badge-ring[data-v-ac364a19]{background:linear-gradient(135deg, var(--brand-gradient-start), var(--brand-gradient-end));border-radius:50%;animation:2s ease-out infinite pulseRing-ac364a19;position:absolute;inset:0}.badge-icon[data-v-ac364a19]{background:var(--gate-surface);width:56px;height:56px;color:var(--brand-primary);box-shadow:var(--shadow-md);border-radius:50%;justify-content:center;align-items:center;transition:transform .2s;display:flex;position:relative}.gate-container:hover .badge-icon[data-v-ac364a19]{transform:scale(1.02)}.gate-title[data-v-ac364a19]{letter-spacing:-.02em;color:var(--gray-900);margin:0 0 1rem;font-size:1.875rem;font-weight:700}.brand-gradient[data-v-ac364a19]{background:linear-gradient(135deg, var(--brand-gradient-start), var(--brand-gradient-end));color:#0000;-webkit-background-clip:text;background-clip:text}.gate-description[data-v-ac364a19]{color:var(--gray-600);margin:0 0 1.75rem;font-size:1rem;line-height:1.5}.feature-grid[data-v-ac364a19]{border-top:1px solid var(--gray-200);border-bottom:1px solid var(--gray-200);justify-content:center;gap:2rem;margin-bottom:2rem;padding:1rem 0;display:flex}.feature-item[data-v-ac364a19]{color:var(--gray-700);flex-direction:column;align-items:center;gap:.5rem;font-size:.75rem;font-weight:500;display:flex}.feature-icon[data-v-ac364a19]{background:var(--gray-100);width:36px;height:36px;color:var(--brand-primary);border-radius:12px;justify-content:center;align-items:center;transition:all .2s;display:flex}.feature-item:hover .feature-icon[data-v-ac364a19]{background:var(--brand-primary);color:var(--gate-on-primary);transform:translateY(-2px)}.detection-status[data-v-ac364a19]{background:var(--gray-100);color:var(--gray-600);border-radius:100px;align-items:center;gap:.5rem;padding:.5rem 1rem;font-size:.75rem;font-weight:500;display:inline-flex}.status-dot[data-v-ac364a19]{background:var(--gate-warning);border-radius:50%;width:8px;height:8px;animation:1.5s ease-out infinite pulse-ac364a19}.gate-footer[data-v-ac364a19]{color:var(--gray-400);justify-content:center;align-items:center;gap:.5rem;margin-top:2rem;padding-top:1.5rem;font-size:.75rem;display:flex}.brand-text[data-v-ac364a19]{background:linear-gradient(135deg, var(--brand-gradient-start), var(--brand-gradient-end));color:#0000;-webkit-background-clip:text;background-clip:text;font-weight:600}@keyframes fadeInUp-ac364a19{0%{opacity:0;transform:translateY(20px)}to{opacity:1;transform:translateY(0)}}@keyframes pulseRing-ac364a19{0%{opacity:1;transform:scale(.95)}70%{opacity:.4;transform:scale(1.15)}to{opacity:0;transform:scale(1.25)}}@keyframes pulse-ac364a19{0%,to{opacity:1}50%{opacity:.4}}@media (width<=480px){.gate-container[data-v-ac364a19]{padding:2rem 1.5rem}.gate-title[data-v-ac364a19]{font-size:1.5rem}.feature-grid[data-v-ac364a19]{gap:1.25rem}}.row-drop-bar[data-v-0e09bbe4]{background:color-mix(in srgb, var(--drop-color) 5%, transparent);z-index:20;pointer-events:none;border-radius:6px;align-items:center;gap:8px;height:28px;padding:0 16px;display:flex;position:absolute;left:0;right:0}.row-drop-bar--before[data-v-0e09bbe4]{top:-14px}.row-drop-bar--after[data-v-0e09bbe4]{bottom:-14px}.row-drop-bar-line[data-v-0e09bbe4]{background:color-mix(in srgb, var(--drop-color) 50%, transparent);border-radius:2px;flex:1;height:2px}.row-drop-bar-label[data-v-0e09bbe4]{color:var(--drop-color);white-space:nowrap;background:color-mix(in srgb, var(--drop-color) 10%, transparent);border:1px solid color-mix(in srgb, var(--drop-color) 30%, transparent);border-radius:24px;align-items:center;gap:6px;padding:4px 12px;font-size:11px;font-weight:500;display:flex}.row-drop-bar-icon[data-v-0e09bbe4]{flex-shrink:0;width:12px;height:12px}.fade-enter-active[data-v-74ef2f9d],.fade-leave-active[data-v-74ef2f9d]{transition:opacity .1s}.fade-enter-from[data-v-74ef2f9d],.fade-leave-to[data-v-74ef2f9d]{opacity:0}.canvas-column[data-v-74ef2f9d]{z-index:1;position:relative}.canvas-column.has-selected-child[data-v-74ef2f9d]{z-index:auto}.canvas-drop-zone[data-v-fc3601ee]{z-index:9;height:0;margin:0;transition:height .2s cubic-bezier(.34,1.56,.64,1);position:relative;overflow:visible}.canvas-drop-zone--active[data-v-fc3601ee]{height:52px}.canvas-drop-zone--empty[data-v-fc3601ee]{height:100%;min-height:200px}.canvas-drop-zone--full[data-v-fc3601ee]{height:auto;min-height:100%;position:absolute;inset:0}.canvas-drop-zone--empty .cdz-bar[data-v-fc3601ee]{border-radius:12px;justify-content:center;inset:12px}.cdz-empty-state[data-v-fc3601ee]{pointer-events:none;background:linear-gradient(135deg, color-mix(in srgb, var(--md-row-selection) 4%, var(--md-surface)) 0%, color-mix(in srgb, var(--md-row-selection) 8%, var(--md-surface)) 100%);border:2px dashed color-mix(in srgb, var(--md-row-selection) 22%, var(--md-surface));border-radius:6px;justify-content:center;align-items:center;transition:all .2s;display:flex;position:absolute;inset:0}.canvas-drop-zone--full .cdz-empty-state[data-v-fc3601ee]{animation:.3s fade-in-fc3601ee}@keyframes fade-in-fc3601ee{0%{opacity:0;transform:scale(.98)}to{opacity:1;transform:scale(1)}}.cdz-empty-content[data-v-fc3601ee]{text-align:center;padding:2rem}.cdz-empty-icon[data-v-fc3601ee]{width:48px;height:48px;color:var(--md-text-subtle);stroke-width:1.5px;margin:0 auto 12px}.cdz-empty-title[data-v-fc3601ee]{color:var(--md-selection-fg);letter-spacing:-.01em;margin-bottom:8px;font-size:1.125rem;font-weight:500}.cdz-empty-subtitle[data-v-fc3601ee]{color:var(--md-text-subtle);font-size:.875rem;line-height:1.4}.cdz-hit-area[data-v-fc3601ee]{z-index:1;pointer-events:none;position:absolute;inset:-4px 0}.canvas-drop-zone--receptive .cdz-hit-area[data-v-fc3601ee]{pointer-events:all}.canvas-drop-zone--full.canvas-drop-zone--receptive .cdz-empty-state[data-v-fc3601ee],.canvas-drop-zone--full.canvas-drop-zone--active .cdz-empty-state[data-v-fc3601ee]{opacity:.5;background:color-mix(in srgb, var(--md-row-selection) 4%, transparent)}.cdz-ghost-line[data-v-fc3601ee]{background:repeating-linear-gradient(90deg, color-mix(in srgb, var(--md-row-selection) 25%, transparent) 0px, color-mix(in srgb, var(--md-row-selection) 25%, transparent) 6px, transparent 6px, transparent 12px);pointer-events:none;border-radius:2px;height:2px;animation:2s ease-in-out infinite ghost-pulse-fc3601ee;position:absolute;top:50%;left:0;right:0;transform:translateY(-50%)}@keyframes ghost-pulse-fc3601ee{0%,to{opacity:.5}50%{opacity:1}}.cdz-bar[data-v-fc3601ee]{background:color-mix(in srgb, var(--md-row-selection) 6%, transparent);border:1.5px dashed color-mix(in srgb, var(--md-row-selection) 35%, transparent);pointer-events:none;border-radius:8px;align-items:center;gap:10px;padding:0 20px;display:flex;position:absolute;inset:4px 0}.cdz-line[data-v-fc3601ee]{background:linear-gradient(90deg, transparent, color-mix(in srgb, var(--md-row-selection) 60%, transparent), color-mix(in srgb, var(--md-row-selection) 80%, transparent), color-mix(in srgb, var(--md-row-selection) 60%, transparent), transparent);transform-origin:50%;border-radius:2px;flex:1;height:2px;animation:.2s forwards line-expand-fc3601ee}@keyframes line-expand-fc3601ee{0%{opacity:0;transform:scaleX(0)}to{opacity:1;transform:scaleX(1)}}.cdz-pill[data-v-fc3601ee]{color:var(--md-row-selection-fg);letter-spacing:.01em;white-space:nowrap;background:color-mix(in srgb, var(--md-row-selection) 8%, transparent);border:1.5px solid color-mix(in srgb, var(--md-row-selection) 35%, transparent);box-shadow:0 2px 8px color-mix(in srgb, var(--md-row-selection) 15%, transparent);border-radius:100px;align-items:center;gap:5px;padding:5px 14px;font-size:11px;font-weight:600;animation:.22s cubic-bezier(.34,1.56,.64,1) forwards pill-pop-fc3601ee;display:flex}@keyframes pill-pop-fc3601ee{0%{opacity:0;transform:scale(.75)}to{opacity:1;transform:scale(1)}}.cdz-icon[data-v-fc3601ee]{flex-shrink:0;width:13px;height:13px}.cdz-bar-enter-active[data-v-fc3601ee]{animation:.15s forwards cdz-in-fc3601ee}.cdz-bar-leave-active[data-v-fc3601ee]{transition:opacity .1s}.cdz-bar-leave-to[data-v-fc3601ee]{opacity:0}@keyframes cdz-in-fc3601ee{0%{opacity:0;transform:scaleY(.6)}to{opacity:1;transform:scaleY(1)}}.drop-line-enter-active[data-v-d0f88c76]{transition:opacity 80ms,transform 80ms}.drop-line-leave-active[data-v-d0f88c76]{transition:opacity 60ms,transform 60ms}.drop-line-enter-from[data-v-d0f88c76],.drop-line-leave-to[data-v-d0f88c76]{opacity:0;transform-origin:0;transform:scaleX(.6)}.slide-enter-active[data-v-10da3eee],.slide-leave-active[data-v-10da3eee]{max-height:500px;transition:all .2s;overflow:hidden}.slide-enter-from[data-v-10da3eee],.slide-leave-to[data-v-10da3eee]{opacity:0;max-height:0;transform:translateY(-10px)}.md-dropdown[data-v-3ba80029]{background:var(--md-surface);border:1px solid var(--md-border);z-index:10;border-radius:.375rem;max-height:12rem;margin-top:4px;position:absolute;top:100%;left:0;right:0;overflow-y:auto;box-shadow:0 4px 12px #00000014}.md-dropdown-item[data-v-3ba80029]{cursor:pointer;color:var(--md-text);padding:.5rem .75rem;transition:background .1s}.md-dropdown-item[data-v-3ba80029]:hover{background:var(--md-surface-hover)}.md-dropdown-item--active[data-v-3ba80029]{background:var(--md-primary);color:var(--md-on-primary)}.md-tag[data-v-3ba80029]{background:var(--md-primary);color:var(--md-on-primary);border-radius:9999px;align-items:center;padding:.125rem .75rem;font-size:.875rem;font-weight:500;line-height:1.5;display:inline-flex}.md-tag-remove[data-v-3ba80029]{width:1rem;height:1rem;color:color-mix(in srgb, var(--md-on-primary) 80%, transparent);cursor:pointer;background:0 0;border:none;border-radius:9999px;justify-content:center;align-items:center;margin-left:.5rem;padding:0;transition:background .15s,color .15s;display:inline-flex}.md-tag-remove[data-v-3ba80029]:hover{background:color-mix(in srgb, var(--md-on-primary) 20%, transparent);color:var(--md-on-primary)}.md-tag-remove svg[data-v-3ba80029]{width:100%;height:100%}.md-dropdown[data-v-3ba80029]::-webkit-scrollbar{width:4px}.md-dropdown[data-v-3ba80029]::-webkit-scrollbar-track{background:0 0}.md-dropdown[data-v-3ba80029]::-webkit-scrollbar-thumb{background:var(--md-border);border-radius:8px}.md-dropdown[data-v-3ba80029]::-webkit-scrollbar-thumb:hover{background:var(--md-text-subtle)}.overflow-x-auto[data-v-66ee94f1]{-webkit-overflow-scrolling:touch;max-width:100%}.overflow-x-auto[data-v-66ee94f1]::-webkit-scrollbar{height:6px}.overflow-x-auto[data-v-66ee94f1]::-webkit-scrollbar-track{background:var(--md-surface-muted);border-radius:4px}.overflow-x-auto[data-v-66ee94f1]::-webkit-scrollbar-thumb{background:var(--md-border-strong);border-radius:4px}.overflow-x-auto[data-v-66ee94f1]::-webkit-scrollbar-thumb:hover{background:var(--md-text-subtle)}.overflow-x-auto[data-v-60969a60]{-webkit-overflow-scrolling:touch;max-width:100%}.overflow-x-auto[data-v-60969a60]::-webkit-scrollbar{height:6px}.overflow-x-auto[data-v-60969a60]::-webkit-scrollbar-track{background:var(--md-surface-muted);border-radius:4px}.overflow-x-auto[data-v-60969a60]::-webkit-scrollbar-thumb{background:var(--md-border-strong);border-radius:4px}.overflow-x-auto[data-v-60969a60]::-webkit-scrollbar-thumb:hover{background:var(--md-text-subtle)}.panel-slide-enter-active[data-v-90154b02],.panel-slide-leave-active[data-v-90154b02]{transition:opacity .18s,transform .18s}.panel-slide-enter-from[data-v-90154b02],.panel-slide-leave-to[data-v-90154b02]{opacity:0;transform:translate(-10px)}.row-list-enter-active[data-v-90154b02],.row-list-leave-active[data-v-90154b02]{transition:opacity .2s,transform .2s}.row-list-enter-from[data-v-90154b02],.row-list-leave-to[data-v-90154b02]{opacity:0;transform:translateY(6px)}.row-list-move[data-v-90154b02]{transition:transform .2s}.overflow-y-auto[data-v-90154b02]::-webkit-scrollbar{width:6px}.overflow-y-auto[data-v-90154b02]::-webkit-scrollbar-track{background:0 0}.overflow-y-auto[data-v-90154b02]::-webkit-scrollbar-thumb{background:var(--md-border-strong);border-radius:9999px}.overflow-y-auto[data-v-90154b02]::-webkit-scrollbar-thumb:hover{background:var(--md-text-subtle)}.panel-slide-enter-active[data-v-9d31c919],.panel-slide-leave-active[data-v-9d31c919]{transition:opacity .18s,transform .18s}.panel-slide-enter-from[data-v-9d31c919],.panel-slide-leave-to[data-v-9d31c919]{opacity:0;transform:translate(-10px)}.row-list-enter-active[data-v-9d31c919],.row-list-leave-active[data-v-9d31c919]{transition:opacity .2s,transform .2s}.row-list-enter-from[data-v-9d31c919],.row-list-leave-to[data-v-9d31c919]{opacity:0;transform:translateY(6px)}.row-list-move[data-v-9d31c919]{transition:transform .2s}.overflow-y-auto[data-v-9d31c919]::-webkit-scrollbar{width:6px}.overflow-y-auto[data-v-9d31c919]::-webkit-scrollbar-track{background:0 0}.overflow-y-auto[data-v-9d31c919]::-webkit-scrollbar-thumb{background:var(--md-border-strong);border-radius:9999px}.overflow-y-auto[data-v-9d31c919]::-webkit-scrollbar-thumb:hover{background:var(--md-text-subtle)}.md-toast__region[data-v-7df3ae7b]{z-index:9999;pointer-events:none;flex-direction:column;gap:.5rem;display:flex;position:fixed;top:1rem;right:1rem}.md-toast[data-v-7df3ae7b]{pointer-events:auto;border:1px solid;border-radius:.75rem;align-items:flex-start;gap:.625rem;min-width:280px;max-width:380px;padding:.75rem .875rem;font-size:13px;display:flex;box-shadow:0 8px 30px #0000001f}.md-toast__icon[data-v-7df3ae7b]{flex-shrink:0;margin-top:.0625rem;font-size:15px}.md-toast__body[data-v-7df3ae7b]{flex:1;min-width:0}.md-toast__summary[data-v-7df3ae7b]{font-weight:500}.md-toast__detail[data-v-7df3ae7b]{opacity:.8;margin-top:.125rem;font-size:12px}.md-toast__close[data-v-7df3ae7b]{opacity:.5;cursor:pointer;color:inherit;background:0 0;border:0;flex-shrink:0}.md-toast__close[data-v-7df3ae7b]:hover{opacity:1}.md-toast--success[data-v-7df3ae7b]{background:var(--md-success-bg);border-color:var(--md-success-border);color:var(--md-success-fg)}.md-toast--info[data-v-7df3ae7b]{background:var(--md-info-bg);border-color:var(--md-info-border);color:var(--md-info-fg)}.md-toast--warn[data-v-7df3ae7b]{background:var(--md-surface);border-color:var(--md-warning-border);color:var(--md-warning-fg)}.md-toast--error[data-v-7df3ae7b]{background:var(--md-danger-bg);border-color:var(--md-danger-border);color:var(--md-danger-fg)}.md-toast-enter-active[data-v-7df3ae7b],.md-toast-leave-active[data-v-7df3ae7b]{transition:all .2s}.md-toast-enter-from[data-v-7df3ae7b],.md-toast-leave-to[data-v-7df3ae7b]{opacity:0;transform:translate(20px)}.md-confirm__body[data-v-b70facc7]{align-items:flex-start;gap:.75rem;display:flex}.md-confirm__icon[data-v-b70facc7]{color:var(--md-warning);flex-shrink:0;margin-top:.125rem;font-size:22px}.md-confirm__message[data-v-b70facc7]{color:var(--md-text);margin:0;font-size:14px;line-height:1.5}.picker-overlay-enter-active[data-v-769fdd18],.picker-overlay-leave-active[data-v-769fdd18]{transition:opacity .2s}.picker-overlay-enter-from[data-v-769fdd18],.picker-overlay-leave-to[data-v-769fdd18]{opacity:0}.picker-drawer-enter-active[data-v-769fdd18],.picker-drawer-leave-active[data-v-769fdd18]{transition:transform .28s cubic-bezier(.32,.72,0,1)}.picker-drawer-enter-from[data-v-769fdd18],.picker-drawer-leave-to[data-v-769fdd18]{transform:translate(100%)}.note-enter-active[data-v-3767ab19],.note-leave-active[data-v-3767ab19]{max-height:60px;transition:opacity .2s,max-height .25s;overflow:hidden}.note-enter-from[data-v-3767ab19],.note-leave-to[data-v-3767ab19]{opacity:0;max-height:0}.md-msg[data-v-c41482a2]{border:1px solid;border-radius:.5rem;align-items:flex-start;gap:.5rem;padding:.625rem .75rem;font-size:13px;display:flex}.md-msg__icon[data-v-c41482a2]{flex-shrink:0;margin-top:.125rem;font-size:14px}.md-msg__body[data-v-c41482a2]{flex:1;min-width:0}.md-msg__close[data-v-c41482a2]{opacity:.6;cursor:pointer;background:0 0;border:0}.md-msg__close[data-v-c41482a2]:hover{opacity:1}.md-msg--info[data-v-c41482a2]{background:var(--md-info-bg);border-color:var(--md-info-border);color:var(--md-info-fg)}.md-msg--success[data-v-c41482a2]{background:var(--md-success-bg);border-color:var(--md-success-border);color:var(--md-success-fg)}.md-msg--warn[data-v-c41482a2]{background:var(--md-surface) beb;border-color:var(--md-warning-border);color:var(--md-warning-fg)}.md-msg--error[data-v-c41482a2]{background:var(--md-danger-bg);border-color:var(--md-danger-border);color:var(--md-danger-fg)}.autosave-fade-enter-active[data-v-c4082ced],.autosave-fade-leave-active[data-v-c4082ced]{transition:opacity .2s,transform .2s}.autosave-fade-enter-from[data-v-c4082ced]{opacity:0;transform:translateY(4px)}.autosave-fade-leave-to[data-v-c4082ced]{opacity:0;transform:translateY(-4px)}.md-assistant-fab[data-v-e3d36e68]{z-index:120;border:1px solid var(--md-border);background:var(--md-button-primary-bg,var(--md-primary));width:2.75rem;height:2.75rem;color:var(--md-button-primary-text,var(--md-surface));cursor:pointer;border-radius:9999px;justify-content:center;align-items:center;transition:transform .15s,box-shadow .15s;display:flex;position:fixed;bottom:1.25rem;right:1.25rem;box-shadow:0 2px 10px #0000002e}.md-assistant-fab[data-v-e3d36e68]:hover{transform:translateY(-1px);box-shadow:0 4px 14px #00000038}.md-assistant-fab[data-v-e3d36e68]:focus-visible{outline:2px solid var(--md-primary);outline-offset:2px}.md-assistant-drawer[data-v-e3d36e68]{z-index:120;background:var(--md-surface);border-left:1px solid var(--md-border);flex-direction:column;width:22rem;max-width:100vw;display:flex;position:fixed;top:4rem;bottom:0;right:0;box-shadow:-8px 0 24px #0000001a}.md-assistant-head[data-v-e3d36e68]{border-bottom:1px solid color-mix(in srgb, var(--md-border) 80%, transparent);flex-shrink:0;justify-content:space-between;align-items:center;padding:.75rem .875rem;display:flex}.md-assistant-title[data-v-e3d36e68]{letter-spacing:.08em;text-transform:uppercase;color:var(--md-text-subtle);font-size:11px;font-weight:600}.md-assistant-close[data-v-e3d36e68]{width:1.5rem;height:1.5rem;color:var(--md-text-subtle);cursor:pointer;background:0 0;border:0;border-radius:.375rem;justify-content:center;align-items:center;display:flex}.md-assistant-close[data-v-e3d36e68]:hover{color:var(--md-text-muted);background:var(--md-surface-muted)}.md-assistant-body[data-v-e3d36e68]{flex:auto;padding:.75rem;overflow-y:auto}.md-assistant-body[data-v-e3d36e68]::-webkit-scrollbar{width:6px}.md-assistant-body[data-v-e3d36e68]::-webkit-scrollbar-track{background:0 0}.md-assistant-body[data-v-e3d36e68]::-webkit-scrollbar-thumb{background:var(--md-border-strong);border-radius:9999px}.assistant-slide-enter-active[data-v-e3d36e68],.assistant-slide-leave-active[data-v-e3d36e68]{transition:opacity .18s,transform .18s}.assistant-slide-enter-from[data-v-e3d36e68],.assistant-slide-leave-to[data-v-e3d36e68]{opacity:0;transform:translate(12px)}.md-dp__field{box-sizing:border-box;background:var(--md-surface);border:1px solid var(--md-border);width:100%;min-height:32px;color:var(--md-text);border-radius:.375rem;align-items:center;gap:.0625rem;padding:.375rem .375rem .375rem .5rem;font-family:inherit;font-size:13px;display:flex}.md-dp__field:focus-within{border-color:var(--md-primary);box-shadow:0 0 0 1px var(--md-primary)}.md-dp__seg{border-radius:.125rem;outline:none;padding:0 .0625rem;font-family:inherit;font-size:13px}.md-dp__seg:focus{background:var(--md-primary);color:var(--md-surface)}.md-dp__seg[data-placeholder],.md-dp__lit{color:var(--md-text-subtle)}.md-dp__trigger{cursor:pointer;width:20px;height:20px;color:var(--md-text-subtle);background:0 0;border:0;flex-shrink:0;justify-content:center;align-items:center;margin-left:auto;padding:.125rem;font-size:11px;display:inline-flex}.md-dp__trigger:hover{color:var(--md-text-muted)}.md-dp__content{z-index:999999;box-sizing:border-box;background:var(--md-surface);border:1px solid var(--md-border);border-radius:.625rem;padding:.625rem;box-shadow:0 10px 15px -3px #0000001f,0 4px 6px -4px #0000001f}.md-dp__cal{width:max-content}.md-dp__header{justify-content:space-between;align-items:center;margin-bottom:.5rem;display:flex}.md-dp__heading{color:var(--md-text);font-family:inherit;font-size:13px;font-weight:600}.md-dp__nav{cursor:pointer;width:24px;height:24px;color:var(--md-text-muted);background:0 0;border:0;border-radius:.25rem;justify-content:center;align-items:center;padding:.25rem;font-size:12px;display:inline-flex}.md-dp__nav:hover{background:var(--md-surface-muted);color:var(--md-text)}.md-dp__nav:disabled{opacity:.4;cursor:default}.md-dp__grid{border-collapse:collapse;width:100%}.md-dp__row{display:flex}.md-dp__headCell{width:32px;height:28px;color:var(--md-text-subtle);justify-content:center;align-items:center;font-family:inherit;font-size:11px;font-weight:500;display:inline-flex}.md-dp__day{width:32px;height:30px;color:var(--md-text);cursor:pointer;background:0 0;border:0;border-radius:.3125rem;outline:none;justify-content:center;align-items:center;padding:0;font-family:inherit;font-size:12px;transition:background .1s,color .1s;display:inline-flex}.md-dp__day:hover{background:var(--md-surface-muted)}.md-dp__day:focus-visible{outline:2px solid var(--md-primary);outline-offset:-2px}.md-dp__day[data-selected]{background:var(--md-primary);color:var(--md-surface);font-weight:600}.md-dp__day[data-selected]:hover{background:var(--md-primary)}.md-dp__day[data-today]:not([data-selected]){color:var(--md-primary);font-weight:700}.md-dp__day[data-outside-view]{color:var(--md-border-strong)}.md-dp__day[data-disabled]{color:var(--md-border-strong);cursor:default}.md-dp__day[data-disabled]:hover{background:0 0}[data-v-7facc7e8] a{color:#2563eb;cursor:pointer}[data-v-7facc7e8] a:not([style*=text-decoration]){text-decoration:underline}[data-v-7facc7e8] a:hover{opacity:.8}[data-v-7facc7e8] .merge-tag-node{white-space:nowrap;vertical-align:baseline;cursor:default;border-radius:3px;padding:0 2px;display:inline}[data-v-7facc7e8] li:not(:last-child){margin-bottom:var(--list-item-spacing,.25rem)}.toolbar-font-select[data-v-7facc7e8] .p-select{border-color:var(--md-toolbar-border);border-radius:6px;align-items:center;min-width:110px;max-width:130px;height:28px;padding:0 6px;font-size:.75rem;display:flex}.toolbar-font-select[data-v-7facc7e8] .p-select-label{padding:0;font-size:.85rem;line-height:1}.toolbar-font-select[data-v-7facc7e8] .p-select-dropdown{width:20px}[data-v-7facc7e8] .p-select-overlay{min-width:180px!important}.health-orb[data-v-e50d82a8]{cursor:pointer;background:0 0;border:none;border-radius:50%;outline:none;flex-shrink:0;justify-content:center;align-items:center;width:24px;height:24px;padding:0;display:flex;position:relative}.health-orb:focus-visible .orb-core[data-v-e50d82a8]{box-shadow:0 0 0 3px #42389e66}.orb-ring[data-v-e50d82a8]{border-radius:50%;animation:2.4s ease-out infinite orb-pulse-e50d82a8;position:absolute}.orb-ring--outer[data-v-e50d82a8]{width:22px;height:22px;animation-delay:0s}.orb-ring--inner[data-v-e50d82a8]{width:16px;height:16px;animation-delay:.6s}.orb-core[data-v-e50d82a8]{z-index:1;border-radius:50%;width:10px;height:10px;transition:transform .15s,box-shadow .15s;position:relative}.health-orb:hover .orb-core[data-v-e50d82a8],.health-orb--active .orb-core[data-v-e50d82a8]{transform:scale(1.15)}.health-orb--good .orb-ring[data-v-e50d82a8]{background:#22c55e40}.health-orb--good .orb-core[data-v-e50d82a8]{background:#22c55e;box-shadow:0 0 0 2px #22c55e33,0 0 8px #22c55e66}.health-orb--warn .orb-ring[data-v-e50d82a8]{background:#f59e0b47}.health-orb--warn .orb-core[data-v-e50d82a8]{background:#f59e0b;box-shadow:0 0 0 2px #f59e0b33,0 0 8px #f59e0b66}.health-orb--bad .orb-ring[data-v-e50d82a8]{background:#ef444447}.health-orb--bad .orb-core[data-v-e50d82a8]{background:#ef4444;box-shadow:0 0 0 2px #ef444433,0 0 8px #ef444466}@keyframes orb-pulse-e50d82a8{0%{opacity:.7;transform:scale(.6)}60%{opacity:0;transform:scale(1.6)}to{opacity:0;transform:scale(1.6)}}.health-panel[data-v-e50d82a8]{z-index:9999;background:#18181b;border:1px solid #ffffff14;border-radius:14px;flex-direction:column;gap:8px;width:300px;padding:12px;transition:width .25s cubic-bezier(.4,0,.2,1);display:flex;position:absolute;top:calc(100% + 10px);left:50%;transform:translate(-50%);box-shadow:0 20px 60px #00000080,0 4px 12px #0000004d}.health-panel--expanded[data-v-e50d82a8]{width:400px}.health-panel--expanded .detail-stats[data-v-e50d82a8]{grid-template-columns:repeat(3,1fr)}.health-panel--expanded .a11y-list[data-v-e50d82a8]{max-height:320px}.health-panel--expanded .format-note[data-v-e50d82a8]{grid-template-columns:repeat(3,1fr);gap:6px;display:grid}.health-panel--expanded .format-row[data-v-e50d82a8]{flex-direction:column;align-items:flex-start;gap:4px}.panel-header[data-v-e50d82a8]{border-bottom:1px solid #ffffff0f;justify-content:space-between;align-items:center;padding:0 2px 4px;display:flex}.panel-header-right[data-v-e50d82a8]{align-items:center;gap:6px;display:flex}.panel-expand-btn[data-v-e50d82a8]{color:#ffffff59;cursor:pointer;background:#ffffff0a;border:1px solid #ffffff14;border-radius:6px;flex-shrink:0;justify-content:center;align-items:center;width:22px;height:22px;padding:0;transition:background .15s,color .15s,border-color .15s;display:flex}.panel-expand-btn[data-v-e50d82a8]:hover{color:#a5b4fc;background:#42389e2e;border-color:#42389e66}.panel-expand-btn[data-v-e50d82a8]:focus-visible{outline-offset:1px;outline:2px solid #42389e80}.panel-expand-btn--active[data-v-e50d82a8]{color:#a5b4fc;background:#42389e33;border-color:#42389e73}.panel-title[data-v-e50d82a8]{letter-spacing:.06em;text-transform:uppercase;color:#a5b4fc;font-size:11px;font-weight:600}.panel-status-badge[data-v-e50d82a8]{border-radius:99px;padding:2px 8px;font-size:10px;font-weight:600}.status-badge--good[data-v-e50d82a8]{color:#4ade80;background:#22c55e26}.status-badge--warn[data-v-e50d82a8]{color:#fbbf24;background:#f59e0b26}.status-badge--bad[data-v-e50d82a8]{color:#f87171;background:#ef444426}.metric-card[data-v-e50d82a8]{cursor:pointer;-webkit-user-select:none;user-select:none;background:#ffffff0a;border:1px solid #ffffff0f;border-radius:10px;transition:background .15s,border-color .15s;overflow:hidden}.metric-card[data-v-e50d82a8]:hover{background:#42389e1a;border-color:#42389e4d}.metric-card[data-v-e50d82a8]:focus-visible{outline-offset:2px;outline:2px solid #42389e80}.metric-card--good[data-v-e50d82a8]{border-color:#22c55e26}.metric-card--warn[data-v-e50d82a8]{border-color:#f59e0b26}.metric-card--bad[data-v-e50d82a8]{border-color:#ef444433}.metric-card--good.metric-card--expanded[data-v-e50d82a8]{background:#22c55e0d}.metric-card--warn.metric-card--expanded[data-v-e50d82a8]{background:#f59e0b0d}.metric-card--bad.metric-card--expanded[data-v-e50d82a8]{background:#ef44440f}.metric-summary[data-v-e50d82a8]{justify-content:space-between;align-items:center;gap:8px;padding:9px 10px;display:flex}.metric-left[data-v-e50d82a8]{align-items:center;gap:7px;min-width:0;display:flex}.metric-icon[data-v-e50d82a8]{opacity:.8;flex-shrink:0;align-items:center;display:flex}.metric-label[data-v-e50d82a8]{color:#ffffffb3;white-space:nowrap;font-size:11.5px;font-weight:500}.metric-right[data-v-e50d82a8]{flex-shrink:0;align-items:center;gap:6px;display:flex}.mini-bar[data-v-e50d82a8]{background:#ffffff1a;border-radius:99px;width:36px;height:4px;overflow:hidden}.mini-bar-fill[data-v-e50d82a8]{border-radius:99px;height:100%;transition:width .5s}.mini-bar-fill--good[data-v-e50d82a8]{background:#22c55e}.mini-bar-fill--warn[data-v-e50d82a8]{background:#f59e0b}.mini-bar-fill--bad[data-v-e50d82a8]{background:#ef4444}.status-dot[data-v-e50d82a8]{border-radius:50%;flex-shrink:0;width:6px;height:6px}.status-dot--good[data-v-e50d82a8]{background:#22c55e}.status-dot--warn[data-v-e50d82a8]{background:#f59e0b}.status-dot--bad[data-v-e50d82a8]{background:#ef4444}.pulse-dot[data-v-e50d82a8]{flex-shrink:0;width:6px;height:6px;position:relative}.pulse-dot[data-v-e50d82a8]:before,.pulse-dot[data-v-e50d82a8]:after{content:"";border-radius:50%;position:absolute;inset:0}.pulse-dot--bad[data-v-e50d82a8]:before{z-index:1;background:#ef4444}.pulse-dot--bad[data-v-e50d82a8]:after{background:#ef4444;animation:1.5s ease-out infinite dot-ping-e50d82a8}@keyframes dot-ping-e50d82a8{0%{opacity:.75;transform:scale(1)}to{opacity:0;transform:scale(2.5)}}.metric-value[data-v-e50d82a8]{font-variant-numeric:tabular-nums;font-size:11.5px;font-weight:600}.metric-value--good[data-v-e50d82a8]{color:#4ade80}.metric-value--warn[data-v-e50d82a8]{color:#fbbf24}.metric-value--bad[data-v-e50d82a8]{color:#f87171}.chevron[data-v-e50d82a8]{color:#ffffff4d;flex-shrink:0;transition:transform .2s,color .15s}.chevron--open[data-v-e50d82a8]{color:#fff9;transform:rotate(180deg)}.metric-card:hover .chevron[data-v-e50d82a8]{color:#ffffff80}.metric-detail[data-v-e50d82a8]{border-top:1px solid #ffffff0d;flex-direction:column;gap:8px;padding:0 10px 10px;display:flex}.detail-tip[data-v-e50d82a8]{color:#ffffff8c;margin:6px 0 0;font-size:11px;line-height:1.55}.detail-stats[data-v-e50d82a8]{grid-template-columns:1fr 1fr;gap:4px 12px;display:grid}.stat-item[data-v-e50d82a8]{justify-content:space-between;align-items:baseline;gap:6px;display:flex}.stat-label[data-v-e50d82a8]{color:#ffffff59;white-space:nowrap;font-size:10.5px}.stat-value[data-v-e50d82a8]{color:#ffffffbf;font-variant-numeric:tabular-nums;font-size:11px;font-weight:600}.detail-thresholds[data-v-e50d82a8]{border-top:1px solid #ffffff0d;flex-wrap:wrap;gap:4px;padding-top:4px;display:flex}.threshold[data-v-e50d82a8]{border-radius:99px;padding:2px 7px;font-size:10px;font-weight:500}.threshold--good[data-v-e50d82a8]{color:#4ade80;background:#22c55e1f}.threshold--warn[data-v-e50d82a8]{color:#fbbf24;background:#f59e0b1f}.threshold--bad[data-v-e50d82a8]{color:#f87171;background:#ef44441f}.format-note[data-v-e50d82a8]{background:#0003;border-radius:8px;flex-direction:column;gap:5px;padding:8px;display:flex}.format-row[data-v-e50d82a8]{align-items:flex-start;gap:8px;display:flex}.format-badge[data-v-e50d82a8]{letter-spacing:.05em;color:#a5b4fc;background:#42389e4d;border-radius:4px;flex-shrink:0;margin-top:1px;padding:2px 6px;font-size:9.5px;font-weight:700}.format-badge--muted[data-v-e50d82a8]{color:#ffffff59;background:#ffffff12}.format-info[data-v-e50d82a8]{flex-direction:column;gap:2px;min-width:0;display:flex}.format-range[data-v-e50d82a8]{color:#fffc;font-size:11px;font-weight:600}.format-range--muted[data-v-e50d82a8]{color:#ffffff59;font-weight:500}.format-caveat[data-v-e50d82a8]{color:#ffffff59;font-size:10px;line-height:1.4}.a11y-detail[data-v-e50d82a8]{cursor:default;gap:10px;padding:8px 10px 10px}.a11y-tabs[data-v-e50d82a8]{background:#00000040;border-radius:8px;grid-template-columns:repeat(3,1fr);gap:4px;padding:3px;display:grid}.a11y-tab[data-v-e50d82a8]{cursor:pointer;letter-spacing:.02em;color:#ffffff73;background:0 0;border:none;border-radius:6px;justify-content:center;align-items:center;gap:6px;padding:6px 4px;font-family:inherit;font-size:10.5px;font-weight:600;transition:background .15s,color .15s;display:flex}.a11y-tab[data-v-e50d82a8]:hover{color:#ffffffbf;background:#ffffff0a}.a11y-tab[data-v-e50d82a8]:focus-visible{outline-offset:1px;outline:2px solid #42389e80}.a11y-tab--active[data-v-e50d82a8]{color:#ffffffeb;background:#ffffff12}.a11y-tab-label[data-v-e50d82a8]{text-transform:uppercase}.a11y-tab-count[data-v-e50d82a8]{font-variant-numeric:tabular-nums;border-radius:99px;justify-content:center;align-items:center;min-width:18px;height:16px;padding:0 5px;font-size:10px;font-weight:700;line-height:1;display:inline-flex}.a11y-tab-count--failed[data-v-e50d82a8]{color:#f87171;background:#ef44442e}.a11y-tab-count--passed[data-v-e50d82a8]{color:#4ade80;background:#22c55e2e}.a11y-tab-count--ignored[data-v-e50d82a8]{color:#ffffff80;background:#ffffff14}.a11y-list[data-v-e50d82a8]{scrollbar-width:thin;scrollbar-color:#ffffff1f transparent;flex-direction:column;gap:6px;max-height:240px;display:flex;overflow-y:auto}.a11y-list[data-v-e50d82a8]::-webkit-scrollbar{width:6px}.a11y-list[data-v-e50d82a8]::-webkit-scrollbar-track{background:0 0}.a11y-list[data-v-e50d82a8]::-webkit-scrollbar-thumb{background:#ffffff1f;border-radius:99px}.a11y-empty[data-v-e50d82a8]{color:#fff6;text-align:center;margin:0;padding:12px 4px;font-size:11px}.a11y-item[data-v-e50d82a8]{background:#ffffff08;border-left:2px solid #0000;border-radius:8px;flex-direction:column;gap:4px;padding:8px;display:flex}.a11y-item--critical[data-v-e50d82a8]{border-left-color:#ef4444}.a11y-item--serious[data-v-e50d82a8]{border-left-color:#f59e0b}.a11y-item--passed[data-v-e50d82a8]{border-left-color:#22c55e80}.a11y-item--ignored[data-v-e50d82a8]{opacity:.75;border-left-color:#ffffff2e}.a11y-item-header[data-v-e50d82a8]{align-items:center;gap:6px;display:flex}.a11y-severity[data-v-e50d82a8]{text-transform:uppercase;letter-spacing:.05em;border-radius:4px;flex-shrink:0;align-items:center;padding:2px 6px;font-size:9px;font-weight:700;display:inline-flex}.a11y-severity--critical[data-v-e50d82a8]{color:#f87171;background:#ef44442e}.a11y-severity--serious[data-v-e50d82a8]{color:#fbbf24;background:#f59e0b2e}.a11y-severity--passed[data-v-e50d82a8]{color:#4ade80;background:#22c55e2e}.a11y-severity--ignored[data-v-e50d82a8]{color:#ffffff80;background:#ffffff12}.a11y-rule[data-v-e50d82a8]{color:#ffffffd9;white-space:nowrap;text-overflow:ellipsis;flex:1;min-width:0;font-size:11px;font-weight:600;overflow:hidden}.a11y-action[data-v-e50d82a8]{color:#ffffff80;cursor:pointer;background:0 0;border:1px solid #ffffff1a;border-radius:4px;flex-shrink:0;padding:2px 7px;font-family:inherit;font-size:9.5px;font-weight:600;transition:background .15s,color .15s,border-color .15s}.a11y-action[data-v-e50d82a8]:hover{color:#ffffffd9;background:#ffffff0f;border-color:#fff3}.a11y-action[data-v-e50d82a8]:focus-visible{outline-offset:1px;outline:2px solid #42389e80}.a11y-action--restore[data-v-e50d82a8]{color:#a5b4fc;border-color:#a5b4fc40}.a11y-action--restore[data-v-e50d82a8]:hover{color:#c7d2fe;background:#42389e26;border-color:#a5b4fc66}.a11y-message[data-v-e50d82a8]{color:#ffffffa6;margin:0;font-size:10.5px;line-height:1.5}.a11y-info[data-v-e50d82a8]{color:#ffffff61;border-top:1px dashed #ffffff0f;margin:0;padding-top:2px;font-size:10px;line-height:1.5}.panel-footer[data-v-e50d82a8]{color:#ffffff38;text-align:center;margin:0;padding-top:4px;font-size:10px}.click-outside[data-v-e50d82a8]{z-index:9998;position:fixed;inset:0}.popover-enter-active[data-v-e50d82a8]{transition:opacity .18s,transform .18s cubic-bezier(.34,1.56,.64,1)}.popover-leave-active[data-v-e50d82a8]{transition:opacity .12s,transform .12s}.popover-enter-from[data-v-e50d82a8]{opacity:0;transform:translate(-50%)translateY(-6px)scale(.97)}.popover-leave-to[data-v-e50d82a8]{opacity:0;transform:translate(-50%)translateY(-4px)scale(.98)}.expand-enter-active[data-v-e50d82a8]{max-height:300px;transition:opacity .18s,max-height .22s;overflow:hidden}.expand-leave-active[data-v-e50d82a8]{transition:opacity .12s,max-height .18s;overflow:hidden}.expand-enter-from[data-v-e50d82a8],.expand-leave-to[data-v-e50d82a8]{opacity:0;max-height:0}.panel-slide-enter-active[data-v-ef885a8c],.panel-slide-leave-active[data-v-ef885a8c]{transition:opacity .18s,transform .18s}.panel-slide-enter-from[data-v-ef885a8c],.panel-slide-leave-to[data-v-ef885a8c]{opacity:0;transform:translate(-10px)}.fade-enter-active[data-v-ef885a8c],.fade-leave-active[data-v-ef885a8c]{transition:opacity .15s,transform .15s}.fade-enter-from[data-v-ef885a8c],.fade-leave-to[data-v-ef885a8c]{opacity:0;transform:translateY(-4px)}.row-list-enter-active[data-v-ef885a8c],.row-list-leave-active[data-v-ef885a8c]{transition:opacity .2s,transform .2s}.row-list-enter-from[data-v-ef885a8c],.row-list-leave-to[data-v-ef885a8c]{opacity:0;transform:translateY(6px)}.row-list-move[data-v-ef885a8c]{transition:transform .2s}.overflow-y-auto[data-v-ef885a8c]::-webkit-scrollbar{width:6px}.overflow-y-auto[data-v-ef885a8c]::-webkit-scrollbar-track{background:0 0}.overflow-y-auto[data-v-ef885a8c]::-webkit-scrollbar-thumb{background:var(--md-border-strong);border-radius:9999px}.overflow-y-auto[data-v-ef885a8c]::-webkit-scrollbar-thumb:hover{background:var(--md-text-subtle)}
|
|
2
|
+
/*$vite$:1*/
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Confirmed against the real pipeline (mergeTagMapper.ts's transformToken):
|
|
3
|
+
* any tag ID not in the hardcoded SYSTEM_TAG_MAP already falls through to
|
|
4
|
+
* transformCustomTag, which handles arbitrary tag names generically for
|
|
5
|
+
* all known ESP syntaxes — this was already true before this registry
|
|
6
|
+
* existed (see the "Zero Vendor Lock-in" note in mergeTagMapper.ts).
|
|
7
|
+
*
|
|
8
|
+
* So registering a merge tag isn't fixing a correctness gap the way the
|
|
9
|
+
* ESP registry was. It solves a narrower, real problem: getSystemTagIds()
|
|
10
|
+
* only returns SYSTEM_TAG_MAP's hardcoded keys, so a host's own fields
|
|
11
|
+
* (order_total, loyalty_points, ...) never show up in the "Common tags"
|
|
12
|
+
* picker UI — a user would have to already know to type {{ order_total }}
|
|
13
|
+
* by hand. This registry makes registered tags discoverable there.
|
|
14
|
+
*
|
|
15
|
+
* Optional per-ESP token overrides exist for the rare case a custom tag
|
|
16
|
+
* needs something other than the generic transform (e.g. a genuinely
|
|
17
|
+
* ESP-specific system-level token) — most registrations won't need them.
|
|
18
|
+
*/
|
|
19
|
+
export interface MergeTagRegistration {
|
|
20
|
+
key: string;
|
|
21
|
+
/** Optional — omit to use the existing generic transformCustomTag path
|
|
22
|
+
* for every ESP syntax, which is already correct for ordinary data
|
|
23
|
+
* fields. Only provide this for a tag that needs ESP-specific hardcoded
|
|
24
|
+
* tokens, the same category SYSTEM_TAG_MAP covers for built-ins. */
|
|
25
|
+
tokens?: Partial<Record<string, string>>;
|
|
26
|
+
}
|
|
27
|
+
export declare function registerMergeTags(tags: MergeTagRegistration[]): void;
|
|
28
|
+
/** Custom-registered IDs, appended after the built-ins for the picker UI. */
|
|
29
|
+
export declare function getRegisteredMergeTagIds(): string[];
|
|
30
|
+
/** Only returns a value for tags that were registered WITH explicit token
|
|
31
|
+
* overrides — most registered tags return undefined here on purpose, so
|
|
32
|
+
* transformToken's existing transformCustomTag fallback handles them. */
|
|
33
|
+
export declare function getRegisteredMergeTagToken(tagId: string, syntax: string): string | undefined;
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
var r = /\{\{\s*(?:'([^']*)'|"([^"]*)"|(\w+))(?:\s*\|\s*(?:'([^']*)'|"([^"]*)"|([^'"\}\s][^'"\}]*?)))?\s*\}\}/g, c = (e) => ({
|
|
2
|
+
name: (e[1] ?? e[2] ?? e[3] ?? "").trim(),
|
|
3
|
+
fallback: (e[4] ?? e[5] ?? e[6] ?? "").trim()
|
|
4
|
+
}), o = (e) => {
|
|
5
|
+
const a = /* @__PURE__ */ new Set();
|
|
6
|
+
r.lastIndex = 0;
|
|
7
|
+
let t;
|
|
8
|
+
for (; (t = r.exec(e)) !== null; ) a.add(c(t).name);
|
|
9
|
+
return [...a];
|
|
10
|
+
}, d = (e) => {
|
|
11
|
+
const a = /* @__PURE__ */ new Map();
|
|
12
|
+
r.lastIndex = 0;
|
|
13
|
+
let t;
|
|
14
|
+
for (; (t = r.exec(e)) !== null; ) {
|
|
15
|
+
const { name: n, fallback: s } = c(t);
|
|
16
|
+
a.has(n) || a.set(n, s);
|
|
17
|
+
}
|
|
18
|
+
return a;
|
|
19
|
+
}, v = (e, a, t) => !t || !e ? e ?? "" : (r.lastIndex = 0, e.replace(r, (n, ...s) => {
|
|
20
|
+
const i = [n, ...s], { name: u, fallback: f } = c(i), l = a[u];
|
|
21
|
+
return l !== void 0 && l !== "" ? l : f || `{{ ${u} }}`;
|
|
22
|
+
}));
|
|
23
|
+
export {
|
|
24
|
+
d as n,
|
|
25
|
+
v as r,
|
|
26
|
+
o as t
|
|
27
|
+
};
|