@popcraft/cli 0.16.0 → 0.17.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/dist/popcraft.mjs +1918 -1947
- package/package.json +2 -2
package/dist/popcraft.mjs
CHANGED
|
@@ -1186,7 +1186,7 @@ function operations(spec = openapi) {
|
|
|
1186
1186
|
}
|
|
1187
1187
|
async function call(target2, method, path, opts = {}) {
|
|
1188
1188
|
const qs = new URLSearchParams(opts.query ?? {}).toString();
|
|
1189
|
-
const headers = { "user-agent": `popcraft-cli/${"0.
|
|
1189
|
+
const headers = { "user-agent": `popcraft-cli/${"0.17.0"}`, ...opts.headers };
|
|
1190
1190
|
if (target2.token) headers.authorization = `Bearer ${target2.token}`;
|
|
1191
1191
|
if (opts.contentType) headers["content-type"] = opts.contentType;
|
|
1192
1192
|
try {
|
|
@@ -32554,14 +32554,12 @@ var init_en2 = __esm({
|
|
|
32554
32554
|
"command:export.storefront": "Export storefront\u2026",
|
|
32555
32555
|
"command:export.storefront#next-commerce": "Export storefront as Next.js Commerce components",
|
|
32556
32556
|
"command:export.storefront#next-commerce-store": "Export storefront as a Next.js Commerce store",
|
|
32557
|
-
"command:export.storefront#shopify-theme": "Export storefront as a Shopify theme",
|
|
32558
32557
|
"command:export.web": "Export as web code\u2026",
|
|
32559
32558
|
"command:export.webm": "Export animation as WebM",
|
|
32560
32559
|
"command:file.duplicate": "Duplicate file",
|
|
32561
32560
|
"command:generate.video": "Generate video",
|
|
32562
32561
|
"command:history.redo": "Redo",
|
|
32563
32562
|
"command:history.undo": "Undo",
|
|
32564
|
-
"command:integration.pullProducts": "Draw with my store's products",
|
|
32565
32563
|
"command:media.download": "Download",
|
|
32566
32564
|
"command:motion.addAudio": "Add audio",
|
|
32567
32565
|
"command:motion.applyPreset": "Animate",
|
|
@@ -32684,6 +32682,7 @@ var init_en2 = __esm({
|
|
|
32684
32682
|
"command:show.setAdvance": "Set how the show advances",
|
|
32685
32683
|
"command:site.setBreakpoints": "Breakpoints",
|
|
32686
32684
|
"command:site.setBreakpoints#defaults": "Reset breakpoints to Desktop, Tablet and Phone",
|
|
32685
|
+
"command:site.setEnvironment": "Site environment",
|
|
32687
32686
|
"command:site.setGpuTransitions": "Draw 3D transitions with WebGPU",
|
|
32688
32687
|
"command:site.setGpuTransitions#off": "Draw 3D transitions in CSS only",
|
|
32689
32688
|
"command:site.setGpuTransitions#on": "Draw 3D transitions with WebGPU",
|
|
@@ -33809,7 +33808,6 @@ var init_en2 = __esm({
|
|
|
33809
33808
|
"integrationsDialog.adminsOnly": "Only owners and admins of this team connect and disconnect accounts.",
|
|
33810
33809
|
"integrationsDialog.cancel": "Cancel",
|
|
33811
33810
|
"integrationsDialog.capabilityAuth": "Sign-in",
|
|
33812
|
-
"integrationsDialog.capabilityCommerce": "Store",
|
|
33813
33811
|
"integrationsDialog.capabilityDatabase": "Database",
|
|
33814
33812
|
"integrationsDialog.capabilityDeploy": "Hosting",
|
|
33815
33813
|
"integrationsDialog.capabilityRepo": "Code",
|
|
@@ -35658,7 +35656,7 @@ var init_en2 = __esm({
|
|
|
35658
35656
|
"stateMachine.wholeFrame": "The whole frame",
|
|
35659
35657
|
"storeSection.about": "Deploy it as a store that sells: a Next.js Commerce store on Vercel, with your Shopify store's products, cart and checkout.",
|
|
35660
35658
|
"storeSection.building": "Building:",
|
|
35661
|
-
"storeSection.connect": "Connect
|
|
35659
|
+
"storeSection.connect": "Connect Vercel\u2026",
|
|
35662
35660
|
"storeSection.deploy": "Deploy store",
|
|
35663
35661
|
"storeSection.deployAgain": "Deploy store again",
|
|
35664
35662
|
"storeSection.deploying": "Deploying store\u2026",
|
|
@@ -35667,6 +35665,7 @@ var init_en2 = __esm({
|
|
|
35667
35665
|
"storeSection.noHost": "Not connected",
|
|
35668
35666
|
"storeSection.noShop": "Not connected",
|
|
35669
35667
|
"storeSection.sellsFrom": "Sells from Shopify",
|
|
35668
|
+
"storeSection.setUpShop": "Choose the Shopify store it sells from in the Ecommerce plugin (Marketplace \u203A Plugins).",
|
|
35670
35669
|
"storeSection.title": "Store",
|
|
35671
35670
|
"strokeEndpointDropdown.circle": "Circle",
|
|
35672
35671
|
"strokeEndpointDropdown.diamond": "Diamond",
|
|
@@ -241678,6 +241677,7 @@ function resyncText(doc2, ids2) {
|
|
|
241678
241677
|
var isVirtualId;
|
|
241679
241678
|
var init_invariants2 = __esm({
|
|
241680
241679
|
"lib/document/invariants.ts"() {
|
|
241680
|
+
"use strict";
|
|
241681
241681
|
init_auto_layout();
|
|
241682
241682
|
init_scene_graph();
|
|
241683
241683
|
init_text_bounds();
|
|
@@ -254786,35 +254786,6 @@ var init_contract = __esm({
|
|
|
254786
254786
|
});
|
|
254787
254787
|
|
|
254788
254788
|
// lib/document/collections.ts
|
|
254789
|
-
var collections_exports = {};
|
|
254790
|
-
__export(collections_exports, {
|
|
254791
|
-
COLLECTION_LIMITS: () => COLLECTION_LIMITS,
|
|
254792
|
-
ITEM_RECORD: () => ITEM_RECORD,
|
|
254793
|
-
copyRecord: () => copyRecord,
|
|
254794
|
-
copySuffix: () => copySuffix,
|
|
254795
|
-
exprData: () => exprData,
|
|
254796
|
-
fieldKey: () => fieldKey,
|
|
254797
|
-
fieldText: () => fieldText,
|
|
254798
|
-
hasItemToken: () => hasItemToken,
|
|
254799
|
-
itemMark: () => itemMark,
|
|
254800
|
-
itemMarks: () => itemMarks,
|
|
254801
|
-
itemNode: () => itemNode,
|
|
254802
|
-
itemScope: () => itemScope,
|
|
254803
|
-
itemText: () => itemText,
|
|
254804
|
-
itemValues: () => itemValues,
|
|
254805
|
-
layerId: () => layerId,
|
|
254806
|
-
recordSlugs: () => recordSlugs,
|
|
254807
|
-
recordsIn: () => recordsIn,
|
|
254808
|
-
removeCollection: () => removeCollection,
|
|
254809
|
-
removeRecords: () => removeRecords,
|
|
254810
|
-
repeatRecords: () => repeatRecords,
|
|
254811
|
-
setCollection: () => setCollection,
|
|
254812
|
-
shownRecordOf: () => shownRecordOf,
|
|
254813
|
-
slugify: () => slugify2,
|
|
254814
|
-
templateRecord: () => templateRecord,
|
|
254815
|
-
upsertRecords: () => upsertRecords,
|
|
254816
|
-
withData: () => withData
|
|
254817
|
-
});
|
|
254818
254789
|
function recordsIn(doc2, collectionId) {
|
|
254819
254790
|
const c2 = doc2.collections?.[collectionId];
|
|
254820
254791
|
if (!c2) return [];
|
|
@@ -264657,7 +264628,7 @@ var init_ydoc = __esm({
|
|
|
264657
264628
|
"use strict";
|
|
264658
264629
|
init_yjs();
|
|
264659
264630
|
LOCAL_ORIGIN = "popcraft-local";
|
|
264660
|
-
RECORD_FIELDS = ["styles", "variables", "variableCollections", "libraries", "compositions", "collections", "records", "codeModules"];
|
|
264631
|
+
RECORD_FIELDS = ["styles", "variables", "variableCollections", "libraries", "compositions", "collections", "records", "codeModules", "pluginData"];
|
|
264661
264632
|
META_FIELDS = ["name", "thumbnailNodeId", "voteResults", "settings", "site"];
|
|
264662
264633
|
yRecordMaps = (ydoc) => RECORD_FIELDS.map((f2) => ydoc.getMap(f2));
|
|
264663
264634
|
TRACK_PREFIX = "motion.tracks/";
|
|
@@ -304658,6 +304629,7 @@ function downloadBlob(blob, filename) {
|
|
|
304658
304629
|
}
|
|
304659
304630
|
var init_download = __esm({
|
|
304660
304631
|
"lib/io/download.ts"() {
|
|
304632
|
+
"use strict";
|
|
304661
304633
|
}
|
|
304662
304634
|
});
|
|
304663
304635
|
|
|
@@ -304875,6 +304847,7 @@ function creditLine(c2) {
|
|
|
304875
304847
|
var MAX_PHOTO_PAGE, MAX_PHOTO_QUERY, UUID, isPhotoId, photoImagePath;
|
|
304876
304848
|
var init_stock = __esm({
|
|
304877
304849
|
"lib/photos/stock.ts"() {
|
|
304850
|
+
"use strict";
|
|
304878
304851
|
MAX_PHOTO_PAGE = 12;
|
|
304879
304852
|
MAX_PHOTO_QUERY = 200;
|
|
304880
304853
|
UUID = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i;
|
|
@@ -305536,6 +305509,7 @@ function applyTextPath(layout2, path, tp, rebase = true) {
|
|
|
305536
305509
|
var defaultCircleRadius, ownsPath, mapPoint;
|
|
305537
305510
|
var init_text_path = __esm({
|
|
305538
305511
|
"lib/engine/text/text-path.ts"() {
|
|
305512
|
+
"use strict";
|
|
305539
305513
|
init_scene_graph();
|
|
305540
305514
|
init_transform();
|
|
305541
305515
|
init_shape_to_path();
|
|
@@ -305653,6 +305627,7 @@ function areaBounds(rings) {
|
|
|
305653
305627
|
}
|
|
305654
305628
|
var init_text_area = __esm({
|
|
305655
305629
|
"lib/engine/text/text-area.ts"() {
|
|
305630
|
+
"use strict";
|
|
305656
305631
|
}
|
|
305657
305632
|
});
|
|
305658
305633
|
|
|
@@ -309977,7 +309952,6 @@ async function selectionReferenceImages(doc2, selection, opts = {}) {
|
|
|
309977
309952
|
var FIT_QUALITIES, FIT_SCALES, blobToDataUrl;
|
|
309978
309953
|
var init_reference_images = __esm({
|
|
309979
309954
|
"lib/ai/reference-images.ts"() {
|
|
309980
|
-
"use strict";
|
|
309981
309955
|
init_export();
|
|
309982
309956
|
init_selection_bounds();
|
|
309983
309957
|
init_renderer_registry();
|
|
@@ -310809,7 +310783,6 @@ function agentToolList() {
|
|
|
310809
310783
|
var AGENT_CAPABILITIES, legacyCommandId, legacyTools, blobToDataUrl3, provided, legacyTool, legacyToolList;
|
|
310810
310784
|
var init_agent = __esm({
|
|
310811
310785
|
"lib/commands/agent.ts"() {
|
|
310812
|
-
"use strict";
|
|
310813
310786
|
init_types5();
|
|
310814
310787
|
init_registry();
|
|
310815
310788
|
init_errors();
|
|
@@ -315221,6 +315194,1674 @@ var init_formats = __esm({
|
|
|
315221
315194
|
}
|
|
315222
315195
|
});
|
|
315223
315196
|
|
|
315197
|
+
// packages/runtime/src/commerce.ts
|
|
315198
|
+
var COMMERCE_SCHEMAS, COMMERCE_FIELDS, COMMERCE_PROP, COMMERCE_ACTIONS, COMMERCE_ACTION_PROP, isCommerceAction;
|
|
315199
|
+
var init_commerce = __esm({
|
|
315200
|
+
"packages/runtime/src/commerce.ts"() {
|
|
315201
|
+
"use strict";
|
|
315202
|
+
COMMERCE_SCHEMAS = ["commerce.product", "commerce.collection", "commerce.cart", "commerce.cartLine", "commerce.menu"];
|
|
315203
|
+
COMMERCE_FIELDS = {
|
|
315204
|
+
"commerce.product": [
|
|
315205
|
+
{ name: "Title", type: "TEXT" },
|
|
315206
|
+
{ name: "Handle", type: "TEXT" },
|
|
315207
|
+
{ name: "URL", type: "URL" },
|
|
315208
|
+
{ name: "Description", type: "TEXT" },
|
|
315209
|
+
{ name: "Price", type: "TEXT" },
|
|
315210
|
+
{ name: "Max price", type: "TEXT" },
|
|
315211
|
+
{ name: "Image", type: "MEDIA" },
|
|
315212
|
+
{ name: "Image alt", type: "TEXT" },
|
|
315213
|
+
{ name: "Available", type: "BOOLEAN" },
|
|
315214
|
+
{ name: "Variant ID", type: "TEXT" },
|
|
315215
|
+
{ name: "Tags", type: "TEXT" }
|
|
315216
|
+
],
|
|
315217
|
+
"commerce.collection": [{ name: "Title", type: "TEXT" }, { name: "Handle", type: "TEXT" }, { name: "URL", type: "URL" }, { name: "Description", type: "TEXT" }],
|
|
315218
|
+
"commerce.cart": [
|
|
315219
|
+
{ name: "Count", type: "NUMBER" },
|
|
315220
|
+
{ name: "Subtotal", type: "TEXT" },
|
|
315221
|
+
{ name: "Taxes", type: "TEXT" },
|
|
315222
|
+
{ name: "Total", type: "TEXT" },
|
|
315223
|
+
{ name: "Checkout URL", type: "URL" }
|
|
315224
|
+
],
|
|
315225
|
+
"commerce.cartLine": [
|
|
315226
|
+
{ name: "Title", type: "TEXT" },
|
|
315227
|
+
{ name: "Variant", type: "TEXT" },
|
|
315228
|
+
{ name: "URL", type: "URL" },
|
|
315229
|
+
{ name: "Image", type: "MEDIA" },
|
|
315230
|
+
{ name: "Quantity", type: "NUMBER" },
|
|
315231
|
+
{ name: "Price", type: "TEXT" },
|
|
315232
|
+
{ name: "Merchandise ID", type: "TEXT" }
|
|
315233
|
+
],
|
|
315234
|
+
"commerce.menu": [{ name: "Title", type: "TEXT" }, { name: "URL", type: "URL" }]
|
|
315235
|
+
};
|
|
315236
|
+
COMMERCE_PROP = {
|
|
315237
|
+
"commerce.product": { name: "products", type: "Product" },
|
|
315238
|
+
"commerce.collection": { name: "collections", type: "Collection" },
|
|
315239
|
+
"commerce.cart": { name: "cart", type: "Cart", one: true },
|
|
315240
|
+
"commerce.cartLine": { name: "lines", type: "CartItem" },
|
|
315241
|
+
"commerce.menu": { name: "menu", type: "Menu" }
|
|
315242
|
+
};
|
|
315243
|
+
COMMERCE_ACTIONS = ["addToCart", "updateCartLine", "removeCartLine", "checkout", "search"];
|
|
315244
|
+
COMMERCE_ACTION_PROP = {
|
|
315245
|
+
addToCart: "onAddToCart",
|
|
315246
|
+
updateCartLine: "onUpdateCartLine",
|
|
315247
|
+
removeCartLine: "onRemoveCartLine",
|
|
315248
|
+
checkout: "onCheckout",
|
|
315249
|
+
search: "onSearch"
|
|
315250
|
+
};
|
|
315251
|
+
isCommerceAction = (a) => typeof a === "string" && COMMERCE_ACTIONS.includes(a);
|
|
315252
|
+
}
|
|
315253
|
+
});
|
|
315254
|
+
|
|
315255
|
+
// lib/code/props.ts
|
|
315256
|
+
function propName(key5) {
|
|
315257
|
+
const words = key5.split("#")[0].trim().split(/[^A-Za-z0-9]+/).filter(Boolean);
|
|
315258
|
+
const name2 = words.map((w, i2) => i2 === 0 ? w.charAt(0).toLowerCase() + w.slice(1) : w.charAt(0).toUpperCase() + w.slice(1)).join("");
|
|
315259
|
+
return /^[A-Za-z_$]/.test(name2) ? name2 : `p${name2}`;
|
|
315260
|
+
}
|
|
315261
|
+
function componentOf(nodes, node2) {
|
|
315262
|
+
const c2 = node2.type === "COMPONENT" ? node2 : node2.type === "INSTANCE" ? nodes[node2.mainComponentId] : void 0;
|
|
315263
|
+
return c2?.type === "COMPONENT" ? c2 : void 0;
|
|
315264
|
+
}
|
|
315265
|
+
function codeOf(nodes, node2) {
|
|
315266
|
+
if (node2.type !== "COMPONENT" && node2.type !== "INSTANCE") return null;
|
|
315267
|
+
return componentOf(nodes, node2)?.code ?? null;
|
|
315268
|
+
}
|
|
315269
|
+
function codeProps(nodes, node2) {
|
|
315270
|
+
const component = componentOf(nodes, node2);
|
|
315271
|
+
const out = {};
|
|
315272
|
+
if (!component) return out;
|
|
315273
|
+
const set4 = component.parentId ? nodes[component.parentId] : void 0;
|
|
315274
|
+
const defs = (set4?.type === "COMPONENT_SET" ? set4.componentPropertyDefinitions : component.componentPropertyDefinitions) ?? {};
|
|
315275
|
+
const given = node2.type === "INSTANCE" ? node2.componentProperties ?? {} : {};
|
|
315276
|
+
for (const key5 of Object.keys(defs).sort()) {
|
|
315277
|
+
const v = value(key5 in given ? given[key5] : defs[key5].defaultValue);
|
|
315278
|
+
if (v !== void 0) out[propName(key5)] = v;
|
|
315279
|
+
}
|
|
315280
|
+
out.width = Math.round(node2.width);
|
|
315281
|
+
out.height = Math.round(node2.height);
|
|
315282
|
+
return out;
|
|
315283
|
+
}
|
|
315284
|
+
var value;
|
|
315285
|
+
var init_props = __esm({
|
|
315286
|
+
"lib/code/props.ts"() {
|
|
315287
|
+
"use strict";
|
|
315288
|
+
init_color();
|
|
315289
|
+
value = (v) => typeof v === "string" || typeof v === "number" || typeof v === "boolean" ? v : v && typeof v === "object" && "r" in v ? colorToHex8(v) : void 0;
|
|
315290
|
+
}
|
|
315291
|
+
});
|
|
315292
|
+
|
|
315293
|
+
// lib/document/controls.ts
|
|
315294
|
+
function fieldPart(nodes, id3) {
|
|
315295
|
+
const n = nodes[id3];
|
|
315296
|
+
if (!n) return null;
|
|
315297
|
+
if (n.type === "TEXT") return id3;
|
|
315298
|
+
for (const c2 of n.childIds ?? []) {
|
|
315299
|
+
const hit = fieldPart(nodes, c2);
|
|
315300
|
+
if (hit) return hit;
|
|
315301
|
+
}
|
|
315302
|
+
return null;
|
|
315303
|
+
}
|
|
315304
|
+
var cleanName;
|
|
315305
|
+
var init_controls = __esm({
|
|
315306
|
+
"lib/document/controls.ts"() {
|
|
315307
|
+
"use strict";
|
|
315308
|
+
cleanName = (raw) => raw.trim().replace(/[^A-Za-z0-9_-]+/g, "-").replace(/^-+|-+$/g, "");
|
|
315309
|
+
}
|
|
315310
|
+
});
|
|
315311
|
+
|
|
315312
|
+
// lib/io/web/paint.ts
|
|
315313
|
+
function toRgba(c2, a) {
|
|
315314
|
+
const alpha2 = a !== void 0 ? a : c2.a;
|
|
315315
|
+
const [r, g, b] = [c2.r, c2.g, c2.b].map((v) => Math.round(v * 255));
|
|
315316
|
+
return alpha2 < 1 ? `rgba(${r}, ${g}, ${b}, ${Math.round(alpha2 * 100) / 100})` : `rgb(${r}, ${g}, ${b})`;
|
|
315317
|
+
}
|
|
315318
|
+
function gradientAngleDeg(paint) {
|
|
315319
|
+
const h = paint.gradientHandlePositions;
|
|
315320
|
+
const p0 = h?.[0] ?? { x: 0, y: 0.5 };
|
|
315321
|
+
const p1 = h?.[1] ?? { x: 1, y: 0.5 };
|
|
315322
|
+
return Math.round(Math.atan2(p1.x - p0.x, -(p1.y - p0.y)) * 180 / Math.PI);
|
|
315323
|
+
}
|
|
315324
|
+
function paintToBackground(paint, opts = {}) {
|
|
315325
|
+
if (paint.type === "SOLID" && paint.color) {
|
|
315326
|
+
const alpha2 = (paint.opacity ?? 1) * paint.color.a;
|
|
315327
|
+
return alpha2 < 1 ? toRgba(paint.color, alpha2) : toHex(paint.color);
|
|
315328
|
+
}
|
|
315329
|
+
if (paint.type === "GRADIENT_LINEAR") return `linear-gradient(${gradientAngleDeg(paint)}deg, ${gradientStopsCSS(paint)})`;
|
|
315330
|
+
if (paint.type === "GRADIENT_RADIAL") return `radial-gradient(circle, ${gradientStopsCSS(paint)})`;
|
|
315331
|
+
if (paint.type === "GRADIENT_ANGULAR") return `conic-gradient(${gradientStopsCSS(paint)})`;
|
|
315332
|
+
if (paint.type === "GRADIENT_DIAMOND") return `radial-gradient(closest-side, ${gradientStopsCSS(paint)})`;
|
|
315333
|
+
if (paint.type === "IMAGE") {
|
|
315334
|
+
const src = paint.imageUrl || paint.imageHash;
|
|
315335
|
+
if (!src) return null;
|
|
315336
|
+
return `url('${opts.fullImageUrl || src.length <= 64 ? src : src.slice(0, 64)}') ${IMAGE_FIT[paint.scaleMode ?? "FILL"]}`;
|
|
315337
|
+
}
|
|
315338
|
+
return null;
|
|
315339
|
+
}
|
|
315340
|
+
function parseCssColor(css) {
|
|
315341
|
+
if (!css) return null;
|
|
315342
|
+
const hex10 = /^#([0-9a-f]{6})$/i.exec(css.trim());
|
|
315343
|
+
if (hex10) {
|
|
315344
|
+
const n = parseInt(hex10[1], 16);
|
|
315345
|
+
return { r: (n >> 16 & 255) / 255, g: (n >> 8 & 255) / 255, b: (n & 255) / 255, a: 1 };
|
|
315346
|
+
}
|
|
315347
|
+
const rgb = /^rgba?\(([^)]+)\)$/i.exec(css.trim());
|
|
315348
|
+
if (!rgb) return null;
|
|
315349
|
+
const parts = rgb[1].split(",").map((v) => Number(v.trim()));
|
|
315350
|
+
if (parts.length < 3 || parts.some((v) => Number.isNaN(v))) return null;
|
|
315351
|
+
return { r: parts[0] / 255, g: parts[1] / 255, b: parts[2] / 255, a: parts[3] ?? 1 };
|
|
315352
|
+
}
|
|
315353
|
+
var hex23, toHex, gradientStopsCSS, IMAGE_FIT, swiftColor, composeColor;
|
|
315354
|
+
var init_paint2 = __esm({
|
|
315355
|
+
"lib/io/web/paint.ts"() {
|
|
315356
|
+
"use strict";
|
|
315357
|
+
hex23 = (v) => Math.round(v * 255).toString(16).padStart(2, "0");
|
|
315358
|
+
toHex = (c2) => `#${hex23(c2.r)}${hex23(c2.g)}${hex23(c2.b)}`.toUpperCase();
|
|
315359
|
+
gradientStopsCSS = (paint) => (paint.gradientStops ?? []).map((s) => `${toRgba(s.color)} ${Math.round((s.position ?? 0) * 100)}%`).join(", ");
|
|
315360
|
+
IMAGE_FIT = {
|
|
315361
|
+
FILL: "center / cover no-repeat",
|
|
315362
|
+
CROP: "center / cover no-repeat",
|
|
315363
|
+
FIT: "center / contain no-repeat",
|
|
315364
|
+
TILE: "top left / auto repeat"
|
|
315365
|
+
};
|
|
315366
|
+
swiftColor = (c2) => {
|
|
315367
|
+
const n = (v) => Math.round(v * 1e3) / 1e3;
|
|
315368
|
+
return `Color(red: ${n(c2.r)}, green: ${n(c2.g)}, blue: ${n(c2.b)}${(c2.a ?? 1) < 1 ? `, opacity: ${Math.round((c2.a ?? 1) * 100) / 100}` : ""})`;
|
|
315369
|
+
};
|
|
315370
|
+
composeColor = (c2) => `Color(0x${[c2.a ?? 1, c2.r, c2.g, c2.b].map((v) => Math.round(v * 255).toString(16).padStart(2, "0")).join("").toUpperCase()})`;
|
|
315371
|
+
}
|
|
315372
|
+
});
|
|
315373
|
+
|
|
315374
|
+
// lib/io/web/css.ts
|
|
315375
|
+
function stylePaints(styleId, styles) {
|
|
315376
|
+
const s = styleId ? styles?.[styleId] : void 0;
|
|
315377
|
+
return s?.type === "PAINT" ? s.paints ?? [] : null;
|
|
315378
|
+
}
|
|
315379
|
+
function transformParts(node2, dx = 0, dy = 0) {
|
|
315380
|
+
return [
|
|
315381
|
+
dx + restValue(node2, "translateX"),
|
|
315382
|
+
dy + restValue(node2, "translateY"),
|
|
315383
|
+
restValue(node2, "z"),
|
|
315384
|
+
node2.rotation || 0,
|
|
315385
|
+
restValue(node2, "rotateY"),
|
|
315386
|
+
restValue(node2, "rotateX"),
|
|
315387
|
+
restValue(node2, "scaleX") * (node2.flipHorizontal ? -1 : 1),
|
|
315388
|
+
restValue(node2, "scaleY") * (node2.flipVertical ? -1 : 1)
|
|
315389
|
+
];
|
|
315390
|
+
}
|
|
315391
|
+
function transformFromParts(p2, orbit) {
|
|
315392
|
+
const [tx2, ty, z2, r, ry0, rx0, sx, sy] = p2;
|
|
315393
|
+
const ry = ry0 + (orbit?.rotateY ?? 0), rx = rx0 + (orbit?.rotateX ?? 0);
|
|
315394
|
+
const parts = [];
|
|
315395
|
+
if (tx2 || ty || z2) parts.push(z2 ? `translate3d(${round(tx2)}px, ${round(ty)}px, ${round(z2)}px)` : `translate(${round(tx2)}px, ${round(ty)}px)`);
|
|
315396
|
+
if (r) parts.push(`rotate(${round(r)}deg)`);
|
|
315397
|
+
if (ry) parts.push(`rotateY(${round(ry)}deg)`);
|
|
315398
|
+
if (rx) parts.push(`rotateX(${round(rx)}deg)`);
|
|
315399
|
+
if (sx !== 1 || sy !== 1) parts.push(`scale(${round(sx)}, ${round(sy)})`);
|
|
315400
|
+
return parts.length ? parts.join(" ") : void 0;
|
|
315401
|
+
}
|
|
315402
|
+
function styleMapFor(node2, styles, opts = {}) {
|
|
315403
|
+
const scene2 = node2;
|
|
315404
|
+
const out = {};
|
|
315405
|
+
out.width = `${Math.round(node2.width)}px`;
|
|
315406
|
+
out.height = `${Math.round(node2.height)}px`;
|
|
315407
|
+
const transform3 = transformCss(node2);
|
|
315408
|
+
if (transform3) out.transform = transform3;
|
|
315409
|
+
const ax = restValue(node2, "anchorX"), ay = restValue(node2, "anchorY");
|
|
315410
|
+
if (transform3 && (ax !== 0.5 || ay !== 0.5)) out["transform-origin"] = `${round(ax * 100)}% ${round(ay * 100)}%`;
|
|
315411
|
+
const scene3d = scene3dOf(node2);
|
|
315412
|
+
if (scene3d) {
|
|
315413
|
+
out.perspective = `${round(zoomPx(scene3d.camera.focalLength, node2.width))}px`;
|
|
315414
|
+
out["perspective-origin"] = `${round((scene3d.originX ?? 0.5) * 100)}% ${round((scene3d.originY ?? 0.5) * 100)}%`;
|
|
315415
|
+
out["transform-style"] = "preserve-3d";
|
|
315416
|
+
} else if (has3DPlacement(node2) && passesThrough(node2)) out["transform-style"] = "preserve-3d";
|
|
315417
|
+
if ((node2.opacity ?? 1) !== 1) out.opacity = String(round(node2.opacity ?? 1));
|
|
315418
|
+
const bm = node2.blendMode;
|
|
315419
|
+
if (bm && bm !== "NORMAL" && bm !== "PASS_THROUGH") out["mix-blend-mode"] = bm.toLowerCase().replace(/_/g, "-");
|
|
315420
|
+
const fills = visibleFills(node2, styles);
|
|
315421
|
+
const own2 = node2.type === "IMAGE" && node2.imageUrl ? [{ type: "IMAGE", imageUrl: node2.imageUrl, scaleMode: node2.scaleMode, visible: true }] : [];
|
|
315422
|
+
const painted = [...fills, ...own2];
|
|
315423
|
+
if (node2.type !== "TEXT" && painted.length) {
|
|
315424
|
+
const layers2 = painted.map((f2) => paintToBackground(f2, opts)).filter((l) => !!l);
|
|
315425
|
+
const over2 = (l) => /^(#|rgb)/.test(l) ? `linear-gradient(${l}, ${l})` : l;
|
|
315426
|
+
if (layers2.length) out.background = layers2.map((l, i2) => i2 === layers2.length - 1 ? l : over2(l)).join(", ");
|
|
315427
|
+
}
|
|
315428
|
+
const cr = scene2.cornerRadius;
|
|
315429
|
+
if (typeof cr === "number" && cr > 0) out["border-radius"] = `${cr}px`;
|
|
315430
|
+
else if (Array.isArray(cr) && cr.some((r) => r > 0)) out["border-radius"] = cr.map((r) => `${r}px`).join(" ");
|
|
315431
|
+
if (node2.type === "ELLIPSE") out["border-radius"] = "50%";
|
|
315432
|
+
const stroke3 = scene2.strokes?.[0];
|
|
315433
|
+
if (stroke3) {
|
|
315434
|
+
const color4 = toHex(stroke3.color);
|
|
315435
|
+
if (Array.isArray(stroke3.width)) {
|
|
315436
|
+
out["border-style"] = "solid";
|
|
315437
|
+
out["border-color"] = color4;
|
|
315438
|
+
out["border-width"] = stroke3.width.map((w) => `${w}px`).join(" ");
|
|
315439
|
+
} else if (stroke3.alignment === "OUTSIDE") {
|
|
315440
|
+
out.outline = `${stroke3.width}px solid ${color4}`;
|
|
315441
|
+
} else {
|
|
315442
|
+
out.border = `${stroke3.width}px ${stroke3.dashPattern?.length ? "dashed" : "solid"} ${color4}`;
|
|
315443
|
+
if (stroke3.alignment === "INSIDE") out["box-sizing"] = "border-box";
|
|
315444
|
+
}
|
|
315445
|
+
}
|
|
315446
|
+
const shadows = shadowsOf(node2, styles).filter((s) => s.visible);
|
|
315447
|
+
if (node2.type === "TEXT") {
|
|
315448
|
+
const drops = shadows.filter((s) => s.type === "DROP_SHADOW");
|
|
315449
|
+
if (drops.length) out["text-shadow"] = drops.map((s) => `${s.offset.x}px ${s.offset.y}px ${s.blur}px ${toRgba(s.color)}`).join(", ");
|
|
315450
|
+
} else if (shadows.length) {
|
|
315451
|
+
out["box-shadow"] = shadows.map((s) => `${s.type === "INNER_SHADOW" ? "inset " : ""}${s.offset.x}px ${s.offset.y}px ${s.blur}px ${s.spread}px ${toRgba(s.color)}`).join(", ");
|
|
315452
|
+
}
|
|
315453
|
+
const blurs = blursOf(node2, styles);
|
|
315454
|
+
const layer2 = blurs.find((b) => b.type === "LAYER");
|
|
315455
|
+
const backdrop = blurs.find((b) => b.type === "BACKGROUND");
|
|
315456
|
+
if (layer2) out.filter = `blur(${layer2.radius}px)`;
|
|
315457
|
+
if (backdrop) out["backdrop-filter"] = `blur(${backdrop.radius}px)`;
|
|
315458
|
+
if (node2.type === "FRAME" || node2.type === "COMPONENT" || node2.type === "INSTANCE") {
|
|
315459
|
+
const f2 = node2;
|
|
315460
|
+
Object.assign(out, flexDeclarations(f2));
|
|
315461
|
+
if (f2.clipsContent) out.overflow = "hidden";
|
|
315462
|
+
}
|
|
315463
|
+
if (node2.type === "TEXT") {
|
|
315464
|
+
const t3 = node2;
|
|
315465
|
+
const tFills = visibleFills(t3, styles);
|
|
315466
|
+
out.margin = "0";
|
|
315467
|
+
if (t3.textAutoResize === "WIDTH_AND_HEIGHT") {
|
|
315468
|
+
out.width = "max-content";
|
|
315469
|
+
out.height = "auto";
|
|
315470
|
+
out["white-space"] = "pre";
|
|
315471
|
+
} else if (t3.textAutoResize === "HEIGHT") out.height = "auto";
|
|
315472
|
+
out["font-family"] = `"${t3.fontFamily}", system-ui, sans-serif`;
|
|
315473
|
+
out["font-size"] = `${t3.fontSize}px`;
|
|
315474
|
+
out["font-weight"] = String(t3.fontWeight);
|
|
315475
|
+
if (t3.fontStyle === "italic") out["font-style"] = "italic";
|
|
315476
|
+
out["line-height"] = t3.lineHeight === "AUTO" ? "normal" : `${t3.lineHeight}px`;
|
|
315477
|
+
if (t3.letterSpacing) out["letter-spacing"] = `${t3.letterSpacing}px`;
|
|
315478
|
+
out["text-align"] = t3.textAlign.toLowerCase();
|
|
315479
|
+
if (t3.textDecoration === "UNDERLINE") out["text-decoration"] = "underline";
|
|
315480
|
+
else if (t3.textDecoration === "STRIKETHROUGH") out["text-decoration"] = "line-through";
|
|
315481
|
+
const tc = t3.textCase;
|
|
315482
|
+
if (tc === "UPPER") out["text-transform"] = "uppercase";
|
|
315483
|
+
else if (tc === "LOWER") out["text-transform"] = "lowercase";
|
|
315484
|
+
else if (tc === "TITLE") out["text-transform"] = "capitalize";
|
|
315485
|
+
const solid5 = tFills.find((f2) => f2.type === "SOLID" && f2.color);
|
|
315486
|
+
if (solid5?.color) out.color = toHex(solid5.color);
|
|
315487
|
+
const grad = tFills.find((f2) => f2.type !== "SOLID");
|
|
315488
|
+
const g = grad ? paintToBackground(grad) : null;
|
|
315489
|
+
if (g) {
|
|
315490
|
+
out.background = g;
|
|
315491
|
+
out["-webkit-background-clip"] = "text";
|
|
315492
|
+
out.color = "transparent";
|
|
315493
|
+
}
|
|
315494
|
+
}
|
|
315495
|
+
return out;
|
|
315496
|
+
}
|
|
315497
|
+
function flexDeclarations(f2) {
|
|
315498
|
+
const out = {};
|
|
315499
|
+
if (f2.layoutMode !== "HORIZONTAL" && f2.layoutMode !== "VERTICAL") return out;
|
|
315500
|
+
out.display = "flex";
|
|
315501
|
+
out["flex-direction"] = f2.layoutMode === "HORIZONTAL" ? "row" : "column";
|
|
315502
|
+
const justify = JUSTIFY[f2.primaryAxisAlignItems ?? "MIN"];
|
|
315503
|
+
const align4 = ALIGN2[f2.counterAxisAlignItems ?? "MIN"];
|
|
315504
|
+
if (justify !== "flex-start") out["justify-content"] = justify;
|
|
315505
|
+
if (align4 !== "flex-start") out["align-items"] = align4;
|
|
315506
|
+
out.gap = `${f2.itemSpacing ?? 0}px`;
|
|
315507
|
+
if (f2.padding) {
|
|
315508
|
+
out.padding = `${f2.padding.top}px ${f2.padding.right}px ${f2.padding.bottom}px ${f2.padding.left}px`;
|
|
315509
|
+
if (f2.padding.top || f2.padding.right || f2.padding.bottom || f2.padding.left) out["box-sizing"] = "border-box";
|
|
315510
|
+
}
|
|
315511
|
+
return out;
|
|
315512
|
+
}
|
|
315513
|
+
var visibleFills, round, transformCss, JUSTIFY, ALIGN2, styleMapToCSSText, styleMapToInline, camel2, styleMapToJSX;
|
|
315514
|
+
var init_css = __esm({
|
|
315515
|
+
"lib/io/web/css.ts"() {
|
|
315516
|
+
"use strict";
|
|
315517
|
+
init_effects();
|
|
315518
|
+
init_paint2();
|
|
315519
|
+
init_scene3d();
|
|
315520
|
+
init_transform3d();
|
|
315521
|
+
init_transform();
|
|
315522
|
+
visibleFills = (node2, styles) => (stylePaints(node2.fillStyleId, styles) ?? node2.fills ?? []).filter((f2) => f2.visible !== false);
|
|
315523
|
+
round = (v) => Math.round(v * 100) / 100;
|
|
315524
|
+
transformCss = (node2) => transformFromParts(transformParts(node2));
|
|
315525
|
+
JUSTIFY = { MIN: "flex-start", MAX: "flex-end", CENTER: "center", SPACE_BETWEEN: "space-between" };
|
|
315526
|
+
ALIGN2 = { MIN: "flex-start", MAX: "flex-end", CENTER: "center", BASELINE: "baseline" };
|
|
315527
|
+
styleMapToCSSText = (m, indent = "") => Object.entries(m).map(([k2, v]) => `${indent}${k2}: ${v};`).join("\n");
|
|
315528
|
+
styleMapToInline = (m) => Object.entries(m).map(([k2, v]) => `${k2}:${v}`).join(";");
|
|
315529
|
+
camel2 = (k2) => k2.startsWith("--") ? k2 : (k2.startsWith("-") ? k2.replace(/^-/, "Webkit").replace(/-webkit-/i, "") : k2).replace(/-([a-z])/g, (_, c2) => c2.toUpperCase());
|
|
315530
|
+
styleMapToJSX = (m) => Object.entries(m).map(([k2, v]) => [camel2(k2), v.replace(/'/g, "\\'")]);
|
|
315531
|
+
}
|
|
315532
|
+
});
|
|
315533
|
+
|
|
315534
|
+
// lib/io/web/expressible.ts
|
|
315535
|
+
function expressibility(node2, styles) {
|
|
315536
|
+
const c2 = capability(node2, "css", styles);
|
|
315537
|
+
return { css: c2.reason === "", reason: c2.reason, needsRaster: c2.verdict === "raster" };
|
|
315538
|
+
}
|
|
315539
|
+
var init_expressible = __esm({
|
|
315540
|
+
"lib/io/web/expressible.ts"() {
|
|
315541
|
+
"use strict";
|
|
315542
|
+
init_capability();
|
|
315543
|
+
}
|
|
315544
|
+
});
|
|
315545
|
+
|
|
315546
|
+
// lib/io/web/keyframes.ts
|
|
315547
|
+
function transformOf(n, rest) {
|
|
315548
|
+
return transformFromParts(transformParts(n, n.x - rest.x, n.y - rest.y)) ?? "none";
|
|
315549
|
+
}
|
|
315550
|
+
function declarationsOf(node2, rest, style) {
|
|
315551
|
+
return { ...style(node2), transform: transformOf(node2, rest), opacity: String(round2(node2.visible === false ? 0 : node2.opacity ?? 1)) };
|
|
315552
|
+
}
|
|
315553
|
+
function vectorOf(style, keys4) {
|
|
315554
|
+
const text = keys4.map((k2) => `${k2}:${style[k2] ?? ""}`).join(";");
|
|
315555
|
+
return { shape: text.replace(NUMBER2, "#"), v: (text.match(NUMBER2) ?? []).map(Number) };
|
|
315556
|
+
}
|
|
315557
|
+
function thinSamples(times2, samples, tol, pinned = []) {
|
|
315558
|
+
const n = samples.length;
|
|
315559
|
+
if (n <= 2) return samples.map((_, i2) => i2);
|
|
315560
|
+
const keep = /* @__PURE__ */ new Set([0, n - 1, ...pinned]);
|
|
315561
|
+
for (let i2 = 1; i2 < n; i2++) if (samples[i2].shape !== samples[i2 - 1].shape) {
|
|
315562
|
+
keep.add(i2 - 1);
|
|
315563
|
+
keep.add(i2);
|
|
315564
|
+
}
|
|
315565
|
+
const sorted = () => [...keep].sort((a, b) => a - b);
|
|
315566
|
+
const stack = [];
|
|
315567
|
+
const kept = sorted();
|
|
315568
|
+
for (let i2 = 1; i2 < kept.length; i2++) stack.push([kept[i2 - 1], kept[i2]]);
|
|
315569
|
+
while (stack.length) {
|
|
315570
|
+
const [a, b] = stack.pop();
|
|
315571
|
+
if (b - a < 2 || samples[a].shape !== samples[b].shape) continue;
|
|
315572
|
+
let worst2 = -1, at3 = -1;
|
|
315573
|
+
for (let i2 = a + 1; i2 < b; i2++) {
|
|
315574
|
+
const k2 = (times2[i2] - times2[a]) / (times2[b] - times2[a] || 1);
|
|
315575
|
+
let err2 = 0;
|
|
315576
|
+
samples[i2].v.forEach((x2, d) => {
|
|
315577
|
+
const want = samples[a].v[d] + (samples[b].v[d] - samples[a].v[d]) * k2;
|
|
315578
|
+
err2 = Math.max(err2, Math.abs(x2 - want) / tol[d]);
|
|
315579
|
+
});
|
|
315580
|
+
if (err2 > worst2) {
|
|
315581
|
+
worst2 = err2;
|
|
315582
|
+
at3 = i2;
|
|
315583
|
+
}
|
|
315584
|
+
}
|
|
315585
|
+
if (worst2 > 1) {
|
|
315586
|
+
keep.add(at3);
|
|
315587
|
+
stack.push([a, at3], [at3, b]);
|
|
315588
|
+
}
|
|
315589
|
+
}
|
|
315590
|
+
return sorted();
|
|
315591
|
+
}
|
|
315592
|
+
function keyframesOf(times2, samples, length2) {
|
|
315593
|
+
const keys4 = [...new Set(samples.flatMap((s) => Object.keys(s)))].filter((k2) => !FIXED.has(k2));
|
|
315594
|
+
const moving = keys4.filter((k2) => samples.some((s) => s[k2] !== samples[0][k2]));
|
|
315595
|
+
if (!moving.length) return null;
|
|
315596
|
+
const vectors = samples.map((s) => vectorOf(s, moving));
|
|
315597
|
+
const dims = Math.max(...vectors.map((v) => v.v.length));
|
|
315598
|
+
const range3 = Array.from({ length: dims }, (_, d) => {
|
|
315599
|
+
let lo = Infinity, hi = -Infinity;
|
|
315600
|
+
for (const v of vectors) if (d < v.v.length) {
|
|
315601
|
+
lo = Math.min(lo, v.v[d]);
|
|
315602
|
+
hi = Math.max(hi, v.v[d]);
|
|
315603
|
+
}
|
|
315604
|
+
return hi > lo ? hi - lo : 0;
|
|
315605
|
+
});
|
|
315606
|
+
const tol = range3.map((r) => Math.max(1e-3, r * 3e-3));
|
|
315607
|
+
const same5 = (a, b) => vectors[a].shape === vectors[b].shape && vectors[a].v.every((x2, d) => Math.abs(x2 - vectors[b].v[d]) <= tol[d]);
|
|
315608
|
+
const jumps = /* @__PURE__ */ new Set();
|
|
315609
|
+
for (let i2 = 1; i2 < samples.length; i2++) {
|
|
315610
|
+
if (same5(i2 - 1, i2)) continue;
|
|
315611
|
+
const stillBefore = i2 >= 2 && same5(i2 - 2, i2 - 1);
|
|
315612
|
+
if (!stillBefore) continue;
|
|
315613
|
+
const words = vectors[i2].shape !== vectors[i2 - 1].shape;
|
|
315614
|
+
const far = !words && vectors[i2].v.some((x2, d) => range3[d] > 0 && Math.abs(x2 - vectors[i2 - 1].v[d]) > range3[d] * 0.2);
|
|
315615
|
+
if (words || far) jumps.add(i2);
|
|
315616
|
+
}
|
|
315617
|
+
const kept = thinSamples(times2, vectors, tol, [...jumps].flatMap((i2) => [i2 - 1, i2]));
|
|
315618
|
+
return kept.map((i2) => {
|
|
315619
|
+
const style = {};
|
|
315620
|
+
for (const k2 of moving) if (samples[i2][k2] !== void 0) style[k2] = samples[i2][k2];
|
|
315621
|
+
return { offset: pct(times2[i2] / (length2 || 1)), style, ...jumps.has(i2 + 1) ? { step: true } : {} };
|
|
315622
|
+
});
|
|
315623
|
+
}
|
|
315624
|
+
var SAMPLE_RATE, round2, pct, FIXED, NUMBER2;
|
|
315625
|
+
var init_keyframes = __esm({
|
|
315626
|
+
"lib/io/web/keyframes.ts"() {
|
|
315627
|
+
"use strict";
|
|
315628
|
+
init_css();
|
|
315629
|
+
SAMPLE_RATE = 30;
|
|
315630
|
+
round2 = (v) => Math.round(v * 1e3) / 1e3;
|
|
315631
|
+
pct = (k2) => Math.round(k2 * 1e5) / 1e3;
|
|
315632
|
+
FIXED = /* @__PURE__ */ new Set(["position", "display", "left", "top", "right", "bottom", "inset", "animation", "animation-play-state", "transform-origin", "transform-style", "box-sizing", "isolation", "z-index"]);
|
|
315633
|
+
NUMBER2 = /-?\d+(?:\.\d+)?(?:e-?\d+)?/g;
|
|
315634
|
+
}
|
|
315635
|
+
});
|
|
315636
|
+
|
|
315637
|
+
// lib/io/web/element.ts
|
|
315638
|
+
function placementStyle(node2, isRoot) {
|
|
315639
|
+
if (node2.place) return { ...node2.place, ...node2.place.position ? {} : node2.layered || node2.children.some((c2) => c2.positioning === "absolute") ? { position: "relative" } : {} };
|
|
315640
|
+
const out = {};
|
|
315641
|
+
if (node2.positioning === "absolute" && !isRoot) {
|
|
315642
|
+
out.position = "absolute";
|
|
315643
|
+
out.left = `${node2.x}px`;
|
|
315644
|
+
out.top = `${node2.y}px`;
|
|
315645
|
+
} else if (node2.layered || node2.children.some((c2) => c2.positioning === "absolute") || isRoot) {
|
|
315646
|
+
out.position = "relative";
|
|
315647
|
+
}
|
|
315648
|
+
return out;
|
|
315649
|
+
}
|
|
315650
|
+
function imageRole(node2) {
|
|
315651
|
+
if (node2.asset || node2.text) return null;
|
|
315652
|
+
if (node2.type !== "IMAGE" && node2.alt === void 0) return null;
|
|
315653
|
+
return roleOf(node2);
|
|
315654
|
+
}
|
|
315655
|
+
function pictureOf(node2) {
|
|
315656
|
+
const a = node2.asset;
|
|
315657
|
+
if (!a) return null;
|
|
315658
|
+
if (a.src) return { kind: "img", src: a.src };
|
|
315659
|
+
if (a.svg) return { kind: "svg", svg: a.svg };
|
|
315660
|
+
if (a.pngDataUrl) return { kind: "img", src: a.pngDataUrl };
|
|
315661
|
+
return { kind: "missing", reason: a.reason, format: a.kind };
|
|
315662
|
+
}
|
|
315663
|
+
function elementOf(node2, ctx2) {
|
|
315664
|
+
const motion = ctx2.still ? void 0 : node2.motion;
|
|
315665
|
+
const spec = ctx2.spec ?? null;
|
|
315666
|
+
const tag = node2.input ? node2.input.tag : node2.link ? "a" : node2.tag ?? (node2.text ? "p" : "div");
|
|
315667
|
+
const attrs = { ...node2.attrs };
|
|
315668
|
+
if (node2.input) Object.assign(attrs, node2.input.attrs);
|
|
315669
|
+
if (node2.link && !node2.input) {
|
|
315670
|
+
attrs.href = node2.link.href;
|
|
315671
|
+
if (node2.link.newTab) {
|
|
315672
|
+
attrs.target = "_blank";
|
|
315673
|
+
attrs.rel = "noopener noreferrer";
|
|
315674
|
+
}
|
|
315675
|
+
}
|
|
315676
|
+
return {
|
|
315677
|
+
tag,
|
|
315678
|
+
attrs,
|
|
315679
|
+
// A tag's own look (a button's border, a link's underline, a list's bullets) is not the layer's: under its declarations.
|
|
315680
|
+
style: { ...node2.link || node2.tag || node2.input ? TAG_RESET[tag] : void 0, ...placementStyle(node2, ctx2.isRoot), ...node2.style, ...motion ? motion.style : {}, ...hiddenAtStart(spec, node2) ? HIDDEN_AT_START : {} },
|
|
315681
|
+
// A field's words are its placeholder (an attribute), not its content.
|
|
315682
|
+
...node2.text && !node2.input ? { text: node2.text.characters } : {},
|
|
315683
|
+
...node2.text && node2.runs && !node2.input ? { runs: node2.runs } : {},
|
|
315684
|
+
...node2.input ? { input: node2.input } : {},
|
|
315685
|
+
...node2.html !== void 0 ? { html: node2.html } : {},
|
|
315686
|
+
...node2.check ? { check: node2.check } : {},
|
|
315687
|
+
picture: pictureOf(node2),
|
|
315688
|
+
role: imageRole(node2),
|
|
315689
|
+
...motion ? { keyframes: motion.keyframes } : {},
|
|
315690
|
+
...node2.motionTrigger ? { motionTrigger: node2.motionTrigger } : {},
|
|
315691
|
+
...spec && node2.uid !== void 0 ? { pc: { uid: node2.uid, layer: node2.name } } : {},
|
|
315692
|
+
...ctx2.listened?.has(node2.id) ? { sm: node2.id } : {}
|
|
315693
|
+
};
|
|
315694
|
+
}
|
|
315695
|
+
var escapeHTML, altFor, roleOf, roleAttrs, labelSVG, imageRoleAttrs, hiddenAtStart, HIDDEN_AT_START, FIELD, HEADING, TAG_RESET, MOTION_PLAY_RULE, CHECK_STYLE;
|
|
315696
|
+
var init_element = __esm({
|
|
315697
|
+
"lib/io/web/element.ts"() {
|
|
315698
|
+
"use strict";
|
|
315699
|
+
escapeHTML = (s) => s.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").replace(/"/g, """);
|
|
315700
|
+
altFor = (node2) => node2.alt ?? node2.name;
|
|
315701
|
+
roleOf = (node2) => {
|
|
315702
|
+
const alt = altFor(node2);
|
|
315703
|
+
return alt === "" ? { hidden: true } : { label: alt };
|
|
315704
|
+
};
|
|
315705
|
+
roleAttrs = (role) => "hidden" in role ? ' aria-hidden="true"' : ` role="img" aria-label="${escapeHTML(role.label)}"`;
|
|
315706
|
+
labelSVG = (svg, node2) => svg.replace(/^<svg\b/, `<svg${roleAttrs(roleOf(node2))}`);
|
|
315707
|
+
imageRoleAttrs = (node2) => {
|
|
315708
|
+
const role = imageRole(node2);
|
|
315709
|
+
return role ? roleAttrs(role) : "";
|
|
315710
|
+
};
|
|
315711
|
+
hiddenAtStart = (spec, node2) => {
|
|
315712
|
+
const e = spec && node2.uid !== void 0 ? spec.e[node2.uid] : void 0;
|
|
315713
|
+
return !!e && e[1][spec.m[e[0]]] === -1;
|
|
315714
|
+
};
|
|
315715
|
+
HIDDEN_AT_START = { opacity: "0", visibility: "hidden", "pointer-events": "none", position: "absolute" };
|
|
315716
|
+
FIELD = { display: "block", border: "0", padding: "0", margin: "0", background: "none", outline: "none", font: "inherit", color: "inherit", "min-width": "0" };
|
|
315717
|
+
HEADING = { margin: "0", "font-size": "inherit", "font-weight": "inherit" };
|
|
315718
|
+
TAG_RESET = {
|
|
315719
|
+
a: { display: "block", color: "inherit", "text-decoration": "none" },
|
|
315720
|
+
button: { display: "block", border: "0", padding: "0", background: "none", font: "inherit", color: "inherit", "text-align": "inherit", cursor: "pointer" },
|
|
315721
|
+
ul: { "list-style": "none", margin: "0", padding: "0" },
|
|
315722
|
+
ol: { "list-style": "none", margin: "0", padding: "0" },
|
|
315723
|
+
h1: HEADING,
|
|
315724
|
+
h2: HEADING,
|
|
315725
|
+
h3: HEADING,
|
|
315726
|
+
h4: HEADING,
|
|
315727
|
+
h5: HEADING,
|
|
315728
|
+
h6: HEADING,
|
|
315729
|
+
p: { margin: "0" },
|
|
315730
|
+
figure: { margin: "0" },
|
|
315731
|
+
span: { display: "block" },
|
|
315732
|
+
label: { display: "block" },
|
|
315733
|
+
form: { margin: "0" },
|
|
315734
|
+
input: FIELD,
|
|
315735
|
+
textarea: { ...FIELD, resize: "none" },
|
|
315736
|
+
select: { ...FIELD, appearance: "none" }
|
|
315737
|
+
};
|
|
315738
|
+
MOTION_PLAY_RULE = "[data-motion-play] [data-motion-child] { animation-play-state: running; }";
|
|
315739
|
+
CHECK_STYLE = "position:absolute;inset:0;width:100%;height:100%;margin:0;opacity:0;cursor:pointer";
|
|
315740
|
+
}
|
|
315741
|
+
});
|
|
315742
|
+
|
|
315743
|
+
// lib/io/web/motion.ts
|
|
315744
|
+
function instanceWebMotion(doc2, instance, style) {
|
|
315745
|
+
const comp = instance.mainComponentId;
|
|
315746
|
+
if (!comp || !isMotionComponent(doc2.nodes, comp)) return null;
|
|
315747
|
+
const m = playbackOf(doc2.nodes, instance, comp);
|
|
315748
|
+
const [a, b] = m.range;
|
|
315749
|
+
const len3 = b - a;
|
|
315750
|
+
if (len3 <= 0) return null;
|
|
315751
|
+
const steps = Math.max(1, Math.ceil(len3 / 1e3 * SAMPLE_RATE));
|
|
315752
|
+
const times2 = Array.from({ length: steps + 1 }, (_, i2) => len3 * i2 / steps);
|
|
315753
|
+
const samples = [];
|
|
315754
|
+
for (let i2 = 0; i2 <= steps; i2++) samples.push(instancePoseAt(doc2.nodes, instance.id, a + len3 * i2 / steps));
|
|
315755
|
+
const ids2 = /* @__PURE__ */ new Set();
|
|
315756
|
+
for (const s of samples) for (const id3 in s) if (id3.includes("::")) ids2.add(id3);
|
|
315757
|
+
const children = /* @__PURE__ */ new Map();
|
|
315758
|
+
const tag = instance.id.replace(/[^a-zA-Z0-9]/g, "").slice(-6);
|
|
315759
|
+
let n = 0;
|
|
315760
|
+
for (const id3 of ids2) {
|
|
315761
|
+
const restNode = resolveVirtualNode2(doc2.nodes, id3);
|
|
315762
|
+
if (!restNode) continue;
|
|
315763
|
+
const frames = keyframesOf(times2, samples.map((s) => declarationsOf(s[id3] ?? restNode, restNode, style)), len3);
|
|
315764
|
+
if (!frames) continue;
|
|
315765
|
+
children.set(id3, {
|
|
315766
|
+
name: `motion-${tag}-${n++}`,
|
|
315767
|
+
frames,
|
|
315768
|
+
durationMs: m.speed > 0 ? Math.round(len3 / m.speed) : 0,
|
|
315769
|
+
delayMs: Math.round(m.start),
|
|
315770
|
+
iterations: m.loop === "none" ? 1 : "infinite",
|
|
315771
|
+
direction: m.loop === "pingpong" ? "alternate" : "normal",
|
|
315772
|
+
fill: m.hold === "first" ? "backwards" : "both"
|
|
315773
|
+
});
|
|
315774
|
+
}
|
|
315775
|
+
return children.size ? { trigger: m.trigger, children } : null;
|
|
315776
|
+
}
|
|
315777
|
+
function animationStyle(mo, trigger) {
|
|
315778
|
+
const out = { animation: `${mo.name} ${mo.durationMs}ms linear ${mo.delayMs}ms ${mo.iterations} ${mo.direction} ${mo.fill}` };
|
|
315779
|
+
if (trigger !== "load") out["animation-play-state"] = "paused";
|
|
315780
|
+
return out;
|
|
315781
|
+
}
|
|
315782
|
+
var keyframesCSS, MOTION_SCRIPT;
|
|
315783
|
+
var init_motion = __esm({
|
|
315784
|
+
"lib/io/web/motion.ts"() {
|
|
315785
|
+
"use strict";
|
|
315786
|
+
init_scene_graph();
|
|
315787
|
+
init_instances2();
|
|
315788
|
+
init_keyframes();
|
|
315789
|
+
init_keyframes();
|
|
315790
|
+
init_element();
|
|
315791
|
+
keyframesCSS = (mo) => `@keyframes ${mo.name} {
|
|
315792
|
+
${mo.frames.map((f2) => ` ${f2.offset}% { ${Object.entries(f2.style).map(([k2, v]) => `${k2}: ${v};`).join(" ")}${f2.step ? " animation-timing-function: step-end;" : ""} }`).join("\n")}
|
|
315793
|
+
}`;
|
|
315794
|
+
MOTION_SCRIPT = `(function () {
|
|
315795
|
+
var play = function (el) { el.setAttribute('data-motion-play', '') };
|
|
315796
|
+
document.querySelectorAll('[data-motion="click"]').forEach(function (el) { el.addEventListener('click', function () { play(el) }) });
|
|
315797
|
+
document.querySelectorAll('[data-motion="hover"]').forEach(function (el) { el.addEventListener('mouseenter', function () { play(el) }) });
|
|
315798
|
+
var seen = document.querySelectorAll('[data-motion="inView"]');
|
|
315799
|
+
if (!('IntersectionObserver' in window)) { seen.forEach(play); return }
|
|
315800
|
+
var io = new IntersectionObserver(function (entries) { entries.forEach(function (e) { if (e.isIntersecting) { play(e.target); io.unobserve(e.target) } }) }, { threshold: 0.25 });
|
|
315801
|
+
seen.forEach(function (el) { io.observe(el) });
|
|
315802
|
+
})();`;
|
|
315803
|
+
}
|
|
315804
|
+
});
|
|
315805
|
+
|
|
315806
|
+
// lib/io/web/responsive.ts
|
|
315807
|
+
function containerStyle(f2) {
|
|
315808
|
+
const out = {};
|
|
315809
|
+
if (isStack(f2) && f2.layoutWrap === "WRAP") {
|
|
315810
|
+
out["flex-wrap"] = "wrap";
|
|
315811
|
+
const cross2 = f2.counterAxisSpacing ?? f2.itemSpacing ?? 0;
|
|
315812
|
+
const main2 = f2.itemSpacing ?? 0;
|
|
315813
|
+
if (cross2 !== main2) out.gap = f2.layoutMode === "HORIZONTAL" ? `${cross2}px ${main2}px` : `${main2}px ${cross2}px`;
|
|
315814
|
+
out["align-content"] = "flex-start";
|
|
315815
|
+
}
|
|
315816
|
+
if (isGrid(f2)) {
|
|
315817
|
+
out.display = "grid";
|
|
315818
|
+
const cols = f2.layoutGridColumns ?? "AUTO";
|
|
315819
|
+
out["grid-template-columns"] = cols === "AUTO" ? `repeat(auto-fill, minmax(${f2.layoutGridMinColumnWidth ?? 100}px, 1fr))` : Array.from({ length: Math.max(1, cols) }, (_, i2) => track(f2.layoutGridColumnSizes?.[i2])).join(" ");
|
|
315820
|
+
const rows = f2.layoutGridRows ?? "AUTO";
|
|
315821
|
+
if (rows === "AUTO") out["grid-auto-rows"] = `minmax(${f2.layoutGridMinRowHeight ?? 100}px, auto)`;
|
|
315822
|
+
else out["grid-template-rows"] = Array.from({ length: Math.max(1, rows) }, (_, i2) => track(f2.layoutGridRowSizes?.[i2])).join(" ");
|
|
315823
|
+
const colGap = f2.itemSpacing ?? 0, rowGap = f2.counterAxisSpacing ?? colGap;
|
|
315824
|
+
out.gap = rowGap === colGap ? `${colGap}px` : `${rowGap}px ${colGap}px`;
|
|
315825
|
+
if (f2.padding) {
|
|
315826
|
+
out.padding = `${f2.padding.top}px ${f2.padding.right}px ${f2.padding.bottom}px ${f2.padding.left}px`;
|
|
315827
|
+
if (f2.padding.top || f2.padding.right || f2.padding.bottom || f2.padding.left) out["box-sizing"] = "border-box";
|
|
315828
|
+
}
|
|
315829
|
+
}
|
|
315830
|
+
const scroll = f2.overflowScrolling;
|
|
315831
|
+
if (scroll && scroll !== "NONE") {
|
|
315832
|
+
out["overflow-x"] = scroll === "HORIZONTAL" || scroll === "BOTH" ? "auto" : "hidden";
|
|
315833
|
+
out["overflow-y"] = scroll === "VERTICAL" || scroll === "BOTH" ? "auto" : "hidden";
|
|
315834
|
+
}
|
|
315835
|
+
return out;
|
|
315836
|
+
}
|
|
315837
|
+
function flowChild(node2, parent) {
|
|
315838
|
+
const style = { ...limits(node2) };
|
|
315839
|
+
const h = node2.layoutSizingHorizontal ?? "FIXED", v = node2.layoutSizingVertical ?? "FIXED";
|
|
315840
|
+
if (isGrid(parent)) {
|
|
315841
|
+
if (h !== "FIXED") style.width = h === "FILL" ? null : "fit-content";
|
|
315842
|
+
if (v !== "FIXED") style.height = null;
|
|
315843
|
+
return { style };
|
|
315844
|
+
}
|
|
315845
|
+
if (h === "FIXED" && style["max-width"] === void 0) style["max-width"] = "100%";
|
|
315846
|
+
const row2 = parent.layoutMode === "HORIZONTAL";
|
|
315847
|
+
const main2 = row2 ? h : v, cross2 = row2 ? v : h;
|
|
315848
|
+
const mainProp = row2 ? "width" : "height", crossProp = row2 ? "height" : "width";
|
|
315849
|
+
if (main2 === "FILL") {
|
|
315850
|
+
style[mainProp] = null;
|
|
315851
|
+
style.flex = "1 1 0";
|
|
315852
|
+
if (style[`min-${mainProp}`] === void 0) style[`min-${mainProp}`] = "0";
|
|
315853
|
+
} else {
|
|
315854
|
+
if (main2 === "HUG") style[mainProp] = null;
|
|
315855
|
+
style["flex-shrink"] = "0";
|
|
315856
|
+
}
|
|
315857
|
+
if (cross2 === "FILL") {
|
|
315858
|
+
style[crossProp] = null;
|
|
315859
|
+
style["align-self"] = "stretch";
|
|
315860
|
+
} else {
|
|
315861
|
+
if (cross2 === "HUG") style[crossProp] = null;
|
|
315862
|
+
if ((parent.counterAxisAlignItems ?? "MIN") === "MIN") style["align-self"] = "flex-start";
|
|
315863
|
+
}
|
|
315864
|
+
return { style };
|
|
315865
|
+
}
|
|
315866
|
+
function constrained(kind, pos, size6, parentSize, start2, end, sizeProp) {
|
|
315867
|
+
const far = parentSize - pos - size6;
|
|
315868
|
+
switch (kind) {
|
|
315869
|
+
case "MAX":
|
|
315870
|
+
return { place: { [end]: px2(far) }, style: {} };
|
|
315871
|
+
case "STRETCH":
|
|
315872
|
+
return { place: { [start2]: px2(pos), [end]: px2(far) }, style: { [sizeProp]: null } };
|
|
315873
|
+
// Its centre keeps its distance from the parent's centre.
|
|
315874
|
+
case "CENTER":
|
|
315875
|
+
return { place: { [start2]: `calc(50% + ${px2(pos - parentSize / 2)})` }, style: {} };
|
|
315876
|
+
case "SCALE":
|
|
315877
|
+
return parentSize > 0 ? { place: { [start2]: pct2(pos / parentSize) }, style: { [sizeProp]: pct2(size6 / parentSize) } } : { place: { [start2]: px2(pos) }, style: {} };
|
|
315878
|
+
default:
|
|
315879
|
+
return { place: { [start2]: px2(pos) }, style: {} };
|
|
315880
|
+
}
|
|
315881
|
+
}
|
|
315882
|
+
function placedChild(node2, parent, frame2 = parent) {
|
|
315883
|
+
const c2 = node2.constraints ?? { horizontal: "MIN", vertical: "MIN" };
|
|
315884
|
+
const x2 = constrained(c2.horizontal, node2.x, node2.width, frame2.width, "left", "right", "width");
|
|
315885
|
+
const y = constrained(c2.vertical, node2.y, node2.height, frame2.height, "top", "bottom", "height");
|
|
315886
|
+
return { style: { ...limits(node2), ...x2.style, ...y.style }, place: { position: "absolute", ...x2.place, ...y.place } };
|
|
315887
|
+
}
|
|
315888
|
+
function siteLayout(node2, parent, layout2) {
|
|
315889
|
+
const own2 = node2.type === "FRAME" || node2.type === "COMPONENT" || node2.type === "INSTANCE" ? node2 : null;
|
|
315890
|
+
if (!parent) {
|
|
315891
|
+
const grows = !own2 || laysOut(own2) || own2.overflowScrolling === "NONE" || !own2.overflowScrolling;
|
|
315892
|
+
return { style: { ...limits(node2), width: "100%", ...grows ? { height: null, "min-height": `max(${px2(node2.height)}, 100dvh)` } : {} }, place: { position: "relative" } };
|
|
315893
|
+
}
|
|
315894
|
+
const s = node2;
|
|
315895
|
+
return layout2 && laysOut(layout2) && s.layoutPositioning !== "ABSOLUTE" ? flowChild(s, layout2) : placedChild(s, parent, parent.type === "INSTANCE" && layout2 ? layout2 : parent);
|
|
315896
|
+
}
|
|
315897
|
+
var px2, pct2, isStack, isGrid, laysOut, track, limits;
|
|
315898
|
+
var init_responsive = __esm({
|
|
315899
|
+
"lib/io/web/responsive.ts"() {
|
|
315900
|
+
"use strict";
|
|
315901
|
+
px2 = (v) => `${Math.round(v * 100) / 100}px`;
|
|
315902
|
+
pct2 = (v) => `${Math.round(v * 1e4) / 100}%`;
|
|
315903
|
+
isStack = (f2) => f2?.layoutMode === "HORIZONTAL" || f2?.layoutMode === "VERTICAL";
|
|
315904
|
+
isGrid = (f2) => f2?.layoutMode === "GRID";
|
|
315905
|
+
laysOut = (f2) => isStack(f2) || isGrid(f2);
|
|
315906
|
+
track = (t3) => {
|
|
315907
|
+
if (!t3 || t3.sizing === "FILL") return t3?.value && /fr$/.test(t3.value) ? t3.value : "1fr";
|
|
315908
|
+
if (t3.sizing === "HUG") return "auto";
|
|
315909
|
+
return /^[\d.]+$/.test(t3.value) ? `${t3.value}px` : t3.value;
|
|
315910
|
+
};
|
|
315911
|
+
limits = (n) => {
|
|
315912
|
+
const out = {};
|
|
315913
|
+
if (n.minWidth !== void 0) out["min-width"] = px2(n.minWidth);
|
|
315914
|
+
if (n.maxWidth !== void 0) out["max-width"] = px2(n.maxWidth);
|
|
315915
|
+
if (n.minHeight !== void 0) out["min-height"] = px2(n.minHeight);
|
|
315916
|
+
if (n.maxHeight !== void 0) out["max-height"] = px2(n.maxHeight);
|
|
315917
|
+
return out;
|
|
315918
|
+
};
|
|
315919
|
+
}
|
|
315920
|
+
});
|
|
315921
|
+
|
|
315922
|
+
// lib/io/web/richtext.ts
|
|
315923
|
+
function runStyle(seg) {
|
|
315924
|
+
const out = {};
|
|
315925
|
+
if (seg.fontFamily) out["font-family"] = `"${seg.fontFamily}", system-ui, sans-serif`;
|
|
315926
|
+
if (seg.fontSize) out["font-size"] = `${seg.fontSize}px`;
|
|
315927
|
+
if (seg.fontWeight) out["font-weight"] = String(seg.fontWeight);
|
|
315928
|
+
if (seg.fontStyle) out["font-style"] = seg.fontStyle;
|
|
315929
|
+
if (seg.lineHeight !== void 0 && seg.lineHeight !== "AUTO") out["line-height"] = `${seg.lineHeight}px`;
|
|
315930
|
+
if (seg.textDecoration === "UNDERLINE") out["text-decoration"] = "underline";
|
|
315931
|
+
else if (seg.textDecoration === "STRIKETHROUGH") out["text-decoration"] = "line-through";
|
|
315932
|
+
else if (seg.textDecoration === "NONE") out["text-decoration"] = "none";
|
|
315933
|
+
if (seg.textCase === "UPPER") out["text-transform"] = "uppercase";
|
|
315934
|
+
else if (seg.textCase === "LOWER") out["text-transform"] = "lowercase";
|
|
315935
|
+
else if (seg.textCase === "TITLE") out["text-transform"] = "capitalize";
|
|
315936
|
+
else if (seg.textCase === "ORIGINAL") out["text-transform"] = "none";
|
|
315937
|
+
const solid5 = seg.fills?.find((f2) => f2.visible !== false && f2.type === "SOLID" && f2.color);
|
|
315938
|
+
if (solid5?.color) out.color = toHex(solid5.color);
|
|
315939
|
+
return out;
|
|
315940
|
+
}
|
|
315941
|
+
function textRuns(t3) {
|
|
315942
|
+
const text = t3.characters ?? "";
|
|
315943
|
+
const segs = [...t3.styledSegments ?? []].filter((s) => s.end > s.start).sort((a, b) => a.start - b.start);
|
|
315944
|
+
if (!segs.length && !t3.link) return void 0;
|
|
315945
|
+
const runs = [];
|
|
315946
|
+
const push2 = (from2, to, seg) => {
|
|
315947
|
+
if (to <= from2) return;
|
|
315948
|
+
const link2 = seg?.link ?? t3.link;
|
|
315949
|
+
runs.push({ text: text.slice(from2, to), style: seg ? runStyle(seg) : {}, ...link2 ? { link: link2 } : {} });
|
|
315950
|
+
};
|
|
315951
|
+
let at3 = 0;
|
|
315952
|
+
for (const s of segs) {
|
|
315953
|
+
const start2 = Math.max(at3, Math.min(text.length, s.start)), end = Math.min(text.length, s.end);
|
|
315954
|
+
push2(at3, start2);
|
|
315955
|
+
push2(start2, end, s);
|
|
315956
|
+
at3 = Math.max(at3, end);
|
|
315957
|
+
}
|
|
315958
|
+
push2(at3, text.length);
|
|
315959
|
+
return runs;
|
|
315960
|
+
}
|
|
315961
|
+
var init_richtext = __esm({
|
|
315962
|
+
"lib/io/web/richtext.ts"() {
|
|
315963
|
+
"use strict";
|
|
315964
|
+
init_paint2();
|
|
315965
|
+
}
|
|
315966
|
+
});
|
|
315967
|
+
|
|
315968
|
+
// lib/document/dev-mode.ts
|
|
315969
|
+
function codeSyntaxFor(v, platform4) {
|
|
315970
|
+
const explicit = v.codeSyntax?.[platform4];
|
|
315971
|
+
if (explicit) return explicit;
|
|
315972
|
+
const parts = v.name.split("/").map((p2) => p2.trim()).filter(Boolean);
|
|
315973
|
+
if (platform4 === "WEB") return `--${parts.join("-").toLowerCase().replace(/[^a-z0-9-]+/g, "-")}`;
|
|
315974
|
+
const camel4 = parts.map((p2, i2) => {
|
|
315975
|
+
const w = p2.replace(/[^A-Za-z0-9]+/g, " ").trim().split(/\s+/);
|
|
315976
|
+
return w.map((x2, j) => i2 === 0 && j === 0 ? x2.toLowerCase() : x2[0].toUpperCase() + x2.slice(1).toLowerCase()).join("");
|
|
315977
|
+
}).join("");
|
|
315978
|
+
return platform4 === "iOS" ? `Tokens.${camel4}` : `Tokens.${camel4}`;
|
|
315979
|
+
}
|
|
315980
|
+
var init_dev_mode = __esm({
|
|
315981
|
+
"lib/document/dev-mode.ts"() {
|
|
315982
|
+
"use strict";
|
|
315983
|
+
}
|
|
315984
|
+
});
|
|
315985
|
+
|
|
315986
|
+
// lib/io/web/tokens.ts
|
|
315987
|
+
function cssValue(v, value3) {
|
|
315988
|
+
if (v.type === "COLOR") return isColor3(value3) ? (value3.a ?? 1) < 1 ? toRgba(value3) : toHex(value3) : null;
|
|
315989
|
+
if (v.type === "FLOAT") return typeof value3 === "number" && Number.isFinite(value3) ? String(Math.round(value3 * 1e3) / 1e3) : null;
|
|
315990
|
+
if (v.type === "STRING") return typeof value3 === "string" ? JSON.stringify(value3) : null;
|
|
315991
|
+
return null;
|
|
315992
|
+
}
|
|
315993
|
+
function siteTokens(doc2) {
|
|
315994
|
+
const collections = Object.values(doc2.variableCollections ?? {}).map((c2) => ({
|
|
315995
|
+
id: c2.id,
|
|
315996
|
+
name: c2.name,
|
|
315997
|
+
defaultMode: c2.defaultModeId,
|
|
315998
|
+
modes: c2.modes.map((m) => ({ id: m.id, name: m.name, className: modeClass(c2, m) }))
|
|
315999
|
+
}));
|
|
316000
|
+
const taken = /* @__PURE__ */ new Set();
|
|
316001
|
+
const vars = [];
|
|
316002
|
+
for (const v of Object.values(doc2.variables ?? {}).sort((a, b) => a.name.localeCompare(b.name) || a.id.localeCompare(b.id))) {
|
|
316003
|
+
const values3 = {};
|
|
316004
|
+
for (const [mode, value3] of Object.entries(v.valuesByMode ?? {})) {
|
|
316005
|
+
const css = cssValue(v, value3);
|
|
316006
|
+
if (css !== null) values3[mode] = css;
|
|
316007
|
+
}
|
|
316008
|
+
if (!Object.keys(values3).length) continue;
|
|
316009
|
+
let name2 = codeSyntaxFor(v, "WEB");
|
|
316010
|
+
if (!name2.startsWith("--")) name2 = `--${slug(name2)}`;
|
|
316011
|
+
if (taken.has(name2)) name2 = `${name2}-${v.id.replace(/[^a-zA-Z0-9]/g, "").slice(-4)}`;
|
|
316012
|
+
taken.add(name2);
|
|
316013
|
+
vars.push({ id: v.id, name: name2, type: v.type, collection: v.variableCollectionId, values: values3 });
|
|
316014
|
+
}
|
|
316015
|
+
const active3 = Object.entries(doc2.activeVariableModes ?? {}).flatMap(([cid, mid]) => {
|
|
316016
|
+
const c2 = collections.find((x2) => x2.id === cid);
|
|
316017
|
+
const m = c2 && mid !== c2.defaultMode ? c2.modes.find((x2) => x2.id === mid) : void 0;
|
|
316018
|
+
return m ? [m.className] : [];
|
|
316019
|
+
});
|
|
316020
|
+
return { collections, vars, active: active3 };
|
|
316021
|
+
}
|
|
316022
|
+
function tokensCSS(tokens) {
|
|
316023
|
+
const rules = [];
|
|
316024
|
+
const defaults3 = [];
|
|
316025
|
+
const byMode = /* @__PURE__ */ new Map();
|
|
316026
|
+
for (const v of tokens.vars) {
|
|
316027
|
+
const c2 = tokens.collections.find((x2) => x2.id === v.collection);
|
|
316028
|
+
const base = v.values[c2?.defaultMode ?? ""] ?? Object.values(v.values)[0];
|
|
316029
|
+
defaults3.push(` ${v.name}: ${base};`);
|
|
316030
|
+
if (v.type === "FLOAT") rules.push(`@property ${v.name} { syntax: '<number>'; inherits: true; initial-value: ${base}; }`);
|
|
316031
|
+
for (const m of c2?.modes ?? []) {
|
|
316032
|
+
if (m.id === c2.defaultMode || v.values[m.id] === void 0 || v.values[m.id] === base) continue;
|
|
316033
|
+
(byMode.get(m.className) ?? byMode.set(m.className, []).get(m.className)).push(` ${v.name}: ${v.values[m.id]};`);
|
|
316034
|
+
}
|
|
316035
|
+
}
|
|
316036
|
+
if (defaults3.length) rules.push(`:root {
|
|
316037
|
+
${defaults3.join("\n")}
|
|
316038
|
+
}`);
|
|
316039
|
+
for (const [cls, lines2] of byMode) rules.push(`.${cls} {
|
|
316040
|
+
${lines2.join("\n")}
|
|
316041
|
+
}`);
|
|
316042
|
+
return rules;
|
|
316043
|
+
}
|
|
316044
|
+
function tokenStyle(raw, style, tokens) {
|
|
316045
|
+
const name2 = (id3) => id3 ? tokens.vars.find((v) => v.id === id3)?.name : void 0;
|
|
316046
|
+
const out = {};
|
|
316047
|
+
const fills = (raw.fills ?? []).filter((f2) => f2.visible !== false);
|
|
316048
|
+
const fill = fills.length === 1 && fills[0].type === "SOLID" && (fills[0].opacity ?? 1) === 1 ? name2(fills[0].boundVariables?.color) : void 0;
|
|
316049
|
+
if (fill) {
|
|
316050
|
+
if (raw.type === "TEXT") {
|
|
316051
|
+
if (style.color) out.color = `var(${fill})`;
|
|
316052
|
+
} else if (style.background) out.background = `var(${fill})`;
|
|
316053
|
+
}
|
|
316054
|
+
const stroke3 = raw.strokes?.[0];
|
|
316055
|
+
const strokeVar = name2(stroke3?.boundVariables?.color);
|
|
316056
|
+
if (strokeVar) {
|
|
316057
|
+
if (style["border-color"]) out["border-color"] = `var(${strokeVar})`;
|
|
316058
|
+
for (const p2 of ["border", "outline"]) if (style[p2]) out[p2] = style[p2].replace(/(#[0-9A-Fa-f]{3,8}|rgba?\([^)]*\))$/, `var(${strokeVar})`);
|
|
316059
|
+
}
|
|
316060
|
+
for (const [prop, id3] of Object.entries(raw.boundVariables ?? {})) {
|
|
316061
|
+
const rule2 = NUMBER_PROPS[prop];
|
|
316062
|
+
const token = tokens.vars.find((v) => v.id === id3);
|
|
316063
|
+
if (!rule2 || !token || token.type !== "FLOAT" || style[rule2[0]] === void 0) continue;
|
|
316064
|
+
out[rule2[0]] = rule2[1](token.name);
|
|
316065
|
+
}
|
|
316066
|
+
return out;
|
|
316067
|
+
}
|
|
316068
|
+
var slug, modeClass, isColor3, px3, NUMBER_PROPS;
|
|
316069
|
+
var init_tokens2 = __esm({
|
|
316070
|
+
"lib/io/web/tokens.ts"() {
|
|
316071
|
+
"use strict";
|
|
316072
|
+
init_dev_mode();
|
|
316073
|
+
init_paint2();
|
|
316074
|
+
slug = (s) => s.toLowerCase().replace(/[^a-z0-9]+/g, "-").replace(/^-|-$/g, "") || "x";
|
|
316075
|
+
modeClass = (collection, mode) => `pc-${slug(collection.name)}-${slug(mode.name)}`;
|
|
316076
|
+
isColor3 = (v) => !!v && typeof v === "object" && "r" in v && "g" in v && "b" in v;
|
|
316077
|
+
px3 = (name2) => `calc(var(${name2}) * 1px)`;
|
|
316078
|
+
NUMBER_PROPS = {
|
|
316079
|
+
width: ["width", px3],
|
|
316080
|
+
height: ["height", px3],
|
|
316081
|
+
opacity: ["opacity", (n) => `var(${n})`],
|
|
316082
|
+
cornerRadius: ["border-radius", px3],
|
|
316083
|
+
itemSpacing: ["gap", px3],
|
|
316084
|
+
fontSize: ["font-size", px3],
|
|
316085
|
+
letterSpacing: ["letter-spacing", px3]
|
|
316086
|
+
};
|
|
316087
|
+
}
|
|
316088
|
+
});
|
|
316089
|
+
|
|
316090
|
+
// lib/io/web/timeline.ts
|
|
316091
|
+
function frameWebMotion(doc2, frameId, style) {
|
|
316092
|
+
const nodes = doc2.nodes;
|
|
316093
|
+
const frame2 = nodes[frameId];
|
|
316094
|
+
if (!frame2 || !hasFrameMotion(nodes, frameId)) return null;
|
|
316095
|
+
const len3 = timelineDuration(nodes, frameId);
|
|
316096
|
+
if (!(len3 > 0)) return null;
|
|
316097
|
+
const steps = Math.max(1, Math.ceil(len3 / 1e3 * SAMPLE_RATE));
|
|
316098
|
+
const times2 = [];
|
|
316099
|
+
const poses = [];
|
|
316100
|
+
for (let i2 = 0; i2 <= steps; i2++) {
|
|
316101
|
+
const t3 = len3 * i2 / steps;
|
|
316102
|
+
times2.push(t3);
|
|
316103
|
+
poses.push(evaluatePose(nodes, { kind: "frame", frameId }, t3).nodes);
|
|
316104
|
+
}
|
|
316105
|
+
const ids2 = /* @__PURE__ */ new Set();
|
|
316106
|
+
for (const p2 of poses) for (const id3 in p2) if (id3 !== frameId && p2[id3] !== nodes[id3]) ids2.add(id3);
|
|
316107
|
+
const loops = frameRunsOn(nodes, frameId);
|
|
316108
|
+
const out = /* @__PURE__ */ new Map();
|
|
316109
|
+
const tag = frameId.replace(/[^a-zA-Z0-9]/g, "").slice(-6);
|
|
316110
|
+
let n = 0;
|
|
316111
|
+
for (const id3 of ids2) {
|
|
316112
|
+
const rest = id3.includes("::") ? resolveVirtualNode2(nodes, id3) : nodes[id3];
|
|
316113
|
+
if (!rest || !underFrame(nodes, id3, frameId)) continue;
|
|
316114
|
+
const frames = keyframesOf(times2, poses.map((p2) => declarationsOf(p2[id3] ?? rest, rest, style)), len3);
|
|
316115
|
+
if (!frames) continue;
|
|
316116
|
+
out.set(id3, {
|
|
316117
|
+
name: `timeline-${tag}-${n++}`,
|
|
316118
|
+
frames,
|
|
316119
|
+
durationMs: Math.round(len3),
|
|
316120
|
+
delayMs: 0,
|
|
316121
|
+
iterations: loops ? "infinite" : 1,
|
|
316122
|
+
direction: "normal",
|
|
316123
|
+
fill: "both"
|
|
316124
|
+
});
|
|
316125
|
+
}
|
|
316126
|
+
return out.size ? out : null;
|
|
316127
|
+
}
|
|
316128
|
+
function underFrame(nodes, id3, frameId) {
|
|
316129
|
+
const real = id3.split("::")[0];
|
|
316130
|
+
for (let n = nodes[real]; n; n = n.parentId ? nodes[n.parentId] : void 0) if (n.id === frameId) return true;
|
|
316131
|
+
return false;
|
|
316132
|
+
}
|
|
316133
|
+
var init_timeline = __esm({
|
|
316134
|
+
"lib/io/web/timeline.ts"() {
|
|
316135
|
+
"use strict";
|
|
316136
|
+
init_scene_graph();
|
|
316137
|
+
init_pose();
|
|
316138
|
+
init_instances2();
|
|
316139
|
+
init_keyframes();
|
|
316140
|
+
}
|
|
316141
|
+
});
|
|
316142
|
+
|
|
316143
|
+
// lib/io/web/generated/runtimes.ts
|
|
316144
|
+
var PROTOTYPE_JS, MACHINE_JS;
|
|
316145
|
+
var init_runtimes = __esm({
|
|
316146
|
+
"lib/io/web/generated/runtimes.ts"() {
|
|
316147
|
+
"use strict";
|
|
316148
|
+
PROTOTYPE_JS = 'function popcraftMount(root, spec) {\n var els = {}, state = {}, owned = {}, orbit = {}, last = {}, holds = {}, hist = [], timers = [];\n var nodes = [root].concat(Array.prototype.slice.call(root.querySelectorAll("[data-pc]")));\n nodes.forEach(function(el) {\n els[el.getAttribute("data-pc")] = el;\n });\n for (var m in spec.m) state[m] = spec.m[m];\n for (var u in spec.e) (owned[spec.e[u][0]] = owned[spec.e[u][0]] || []).push(u);\n var drags = {}, clicks = {};\n spec.on.forEach(function(o) {\n if (o[3] === "drag") drags[o[0]] = 1;\n if (o[3] === "click" || o[3] === "press") clicks[o[0]] = 1;\n });\n function lookIn(u2, st) {\n var e = spec.e[u2];\n if (!e) return -2;\n var i = e[1][st === void 0 ? state[e[0]] : st];\n return i === void 0 ? -1 : i;\n }\n function tf(f, o) {\n var ry = f[4] + (o ? o.ry : 0), rx = f[5] + (o ? o.rx : 0), p = [];\n if (f[0] || f[1] || f[2]) p.push(f[2] ? "translate3d(" + f[0] + "px, " + f[1] + "px, " + f[2] + "px)" : "translate(" + f[0] + "px, " + f[1] + "px)");\n if (f[3]) p.push("rotate(" + f[3] + "deg)");\n if (ry) p.push("rotateY(" + ry + "deg)");\n if (rx) p.push("rotateX(" + rx + "deg)");\n if (f[6] !== 1 || f[7] !== 1) p.push("scale(" + f[6] + ", " + f[7] + ")");\n return p.length ? p.join(" ") : "none";\n }\n function css(u2, i) {\n var L = spec.L[i], c = L[0];\n if (orbit[u2] && L[2]) c += ";transform:" + tf(L[2], orbit[u2]);\n if (drags[u2]) c += ";touch-action:none;user-select:none;-webkit-user-select:none";\n if (clicks[u2]) c += ";cursor:pointer";\n return c;\n }\n var HIDE = ";opacity:0;visibility:hidden;pointer-events:none;position:absolute";\n function set(u2, ms, ez) {\n var el = els[u2], i = lookIn(u2, void 0);\n if (!el || i === -2) return;\n var tr = ms ? ";transition:all " + ms + "ms " + ez : ";transition:none";\n if (i < 0) {\n el.style.cssText = (last[u2] || "") + HIDE + tr;\n return;\n }\n var c = css(u2, i), text = spec.L[i][1];\n if (text !== null && el.textContent !== text) el.textContent = text;\n if (ms && el.style.visibility === "hidden") {\n el.style.cssText = c + ";opacity:0;transition:none";\n void el.offsetWidth;\n }\n el.style.cssText = c + tr;\n last[u2] = c;\n }\n var ANIM = /(?:^|;)animation:[^;]*/;\n function anim(i) {\n var m2 = i >= 0 ? ANIM.exec(spec.L[i][0]) : null;\n return m2 ? m2[0] : "";\n }\n function go(m2, to, ms, ez, fromHistory) {\n if (!(m2 in state) || state[m2] === to) return;\n var list = owned[m2] || [];\n list.forEach(function(u2) {\n var a = lookIn(u2, void 0), b = lookIn(u2, to), el = els[u2];\n if (!el || a < 0 || !anim(a) || anim(a) === anim(b)) return;\n var cs = getComputedStyle(el);\n el.style.cssText = css(u2, a) + ";animation:none;transition:none;transform:" + cs.transform + ";opacity:" + cs.opacity;\n });\n void root.offsetWidth;\n if (m2 === "flow" && !fromHistory) hist.push(state[m2]);\n state[m2] = to;\n list.forEach(function(u2) {\n set(u2, ms, ez);\n });\n arm();\n }\n function active(u2, trig) {\n return spec.on.filter(function(o) {\n return String(o[0]) === String(u2) && o[3] === trig && state[o[1]] === o[2];\n });\n }\n function run(o, u2) {\n var a = o[4];\n if (a.k === "go") {\n if (a.hold) {\n if (!holds[u2]) holds[u2] = { m: a.m, back: state[a.m], ms: a.ms, ez: a.ez };\n }\n go(a.m, a.to, a.ms, a.ez, false);\n } else if (a.k === "back" && hist.length) {\n go(a.m, hist.pop(), 300, "ease-in-out", true);\n }\n }\n function release(u2) {\n var h = holds[u2];\n if (!h) return;\n delete holds[u2];\n go(h.m, h.back, h.ms, h.ez, true);\n }\n function chain(el) {\n var out = [];\n for (var n = el; n && n !== root.parentNode; n = n.parentNode) {\n var id2 = n.getAttribute && n.getAttribute("data-pc");\n if (id2 !== null && id2 !== void 0) out.push(id2);\n if (n === root) break;\n }\n return out;\n }\n function first(ids, trig) {\n for (var i = 0; i < ids.length; i++) {\n var a = active(ids[i], trig);\n if (a.length) return { u: ids[i], list: a };\n }\n return null;\n }\n function arm() {\n timers.forEach(clearTimeout);\n timers = [];\n spec.on.forEach(function(o) {\n if (o[3] === "timeout" && state[o[1]] === o[2]) timers.push(setTimeout(function() {\n if (state[o[1]] === o[2]) run(o, o[0]);\n }, o[5]));\n });\n }\n var over = [];\n function hover(ids) {\n var left = over.filter(function(u2) {\n return ids.indexOf(u2) < 0;\n }), entered = ids.filter(function(u2) {\n return over.indexOf(u2) < 0;\n });\n over = ids;\n left.forEach(function(u2) {\n release(u2);\n active(u2, "leave").forEach(function(o) {\n run(o, u2);\n });\n });\n entered.slice().reverse().forEach(function(u2) {\n active(u2, "hover").concat(active(u2, "enter")).forEach(function(o) {\n run(o, u2);\n });\n });\n }\n var press = null;\n function onMove(e) {\n if (press) {\n var dx = e.clientX - press.x, dy = e.clientY - press.y;\n if (!press.dragged && Math.abs(dx) + Math.abs(dy) > 5) {\n press.dragged = true;\n var d = first(press.ids, "drag");\n if (d) {\n var du = d.u;\n press.drag = d;\n d.list.forEach(function(o) {\n if (o[4].k !== "orbit") run(o, du);\n });\n }\n if (press.held) {\n release(press.held);\n press.held = null;\n }\n }\n if (press.drag) {\n var k = root.getBoundingClientRect().width / (root.offsetWidth || 1) || 1;\n press.drag.list.forEach(function(o) {\n var a = o[4];\n if (a.k !== "orbit") return;\n var cur = orbit[a.t] || { rx: 0, ry: 0 };\n orbit[a.t] = { rx: cur.rx, ry: cur.ry + (e.clientX - press.lx) / k * a.d };\n if (a.tilt) {\n var tc = orbit[a.tt] || { rx: 0, ry: 0 };\n orbit[a.tt] = { ry: tc.ry, rx: Math.max(a.lo, Math.min(a.hi, tc.rx - (e.clientY - press.ly) / k * a.d)) };\n }\n set(a.t, 0, "linear");\n if (a.tt !== a.t) set(a.tt, 0, "linear");\n });\n press.lx = e.clientX;\n press.ly = e.clientY;\n return;\n }\n }\n hover(chain(e.target));\n }\n function onDown(e) {\n var ids = chain(e.target);\n press = { x: e.clientX, y: e.clientY, lx: e.clientX, ly: e.clientY, ids, dragged: false, drag: null, held: null };\n if (first(ids, "drag") && root.setPointerCapture) {\n try {\n root.setPointerCapture(e.pointerId);\n } catch (err) {\n }\n }\n var p = first(ids, "press");\n if (p) {\n var pu = p.u;\n press.held = pu;\n p.list.forEach(function(o) {\n run(o, pu);\n });\n }\n }\n function onUp(e) {\n var p = press;\n press = null;\n if (!p) return;\n if (p.held) release(p.held);\n if (p.dragged) return;\n var c = first(p.ids, "click");\n if (c) {\n var cu = c.u;\n c.list.forEach(function(o) {\n run(o, cu);\n });\n }\n void e;\n }\n function onLeave() {\n if (!press) hover([]);\n }\n function onKey(e) {\n spec.on.forEach(function(o) {\n if (o[3] === "key" && state[o[1]] === o[2] && (!o[6] || o[6].toLowerCase() === String(e.key).toLowerCase())) run(o, o[0]);\n });\n }\n for (var id in els) set(id, 0, "linear");\n root.addEventListener("pointermove", onMove);\n root.addEventListener("pointerdown", onDown);\n root.addEventListener("pointerup", onUp);\n root.addEventListener("pointercancel", onUp);\n root.addEventListener("pointerleave", onLeave);\n window.addEventListener("keydown", onKey);\n arm();\n return function() {\n timers.forEach(clearTimeout);\n root.removeEventListener("pointermove", onMove);\n root.removeEventListener("pointerdown", onDown);\n root.removeEventListener("pointerup", onUp);\n root.removeEventListener("pointercancel", onUp);\n root.removeEventListener("pointerleave", onLeave);\n window.removeEventListener("keydown", onKey);\n };\n}';
|
|
316149
|
+
MACHINE_JS = 'function popcraftMachineCore(spec) {\n function start(id) {\n var t = spec.in[id];\n return !t || t[0] === "event" ? void 0 : t[1];\n }\n function holds(g, values, fired) {\n var t = spec.in[g[0]];\n if (!t) return false;\n if (t[0] === "event") return !!fired[g[0]];\n var v = g[0] in values ? values[g[0]] : start(g[0]), w = g[2];\n switch (g[1]) {\n case "eq":\n return v === w;\n case "neq":\n return v !== w;\n case "gt":\n return typeof v === "number" && typeof w === "number" && v > w;\n case "gte":\n return typeof v === "number" && typeof w === "number" && v >= w;\n case "lt":\n return typeof v === "number" && typeof w === "number" && v < w;\n case "lte":\n return typeof v === "number" && typeof w === "number" && v <= w;\n }\n return false;\n }\n function apply(values, actions) {\n var out = {}, fired = {};\n for (var k in values) out[k] = values[k];\n actions.forEach(function(a) {\n var t = spec.in[a[1]];\n if (!t) return;\n var cur = a[1] in out ? out[a[1]] : start(a[1]), by = typeof a[2] === "number" ? a[2] : 1;\n if (a[0] === "set") {\n if (t[0] === "event") fired[a[1]] = 1;\n else if (a.length > 2 && typeof a[2] === typeof cur) out[a[1]] = a[2];\n } else if (a[0] === "toggle") {\n if (typeof cur === "boolean") out[a[1]] = !cur;\n } else if (a[0] === "increment") {\n if (typeof cur === "number") out[a[1]] = cur + by;\n } else if (a[0] === "decrement") {\n if (typeof cur === "number") out[a[1]] = cur - by;\n } else if (a[0] === "fire") {\n if (t[0] === "event") fired[a[1]] = 1;\n } else if (a[0] === "reset") {\n var s = start(a[1]);\n if (s === void 0) delete out[a[1]];\n else out[a[1]] = s;\n }\n });\n return { values: out, fired };\n }\n function next(r, fired) {\n var own = spec.t.filter(function(t2) {\n return t2[0] === r.state;\n });\n var any = spec.t.filter(function(t2) {\n return t2[0] === "*" && t2[1] !== r.state;\n });\n var all = own.concat(any);\n for (var i = 0; i < all.length; i++) {\n var t = all[i];\n if (spec.s[t[1]] && t[2].every(function(g) {\n return holds(g, r.values, fired);\n })) return t;\n }\n return null;\n }\n function enter(r, id) {\n var res = apply(r.values, spec.s[id] ? spec.s[id][4] : []);\n return { run: { state: id, values: res.values }, fired: res.fired };\n }\n function settle(r, fired) {\n var cur = r, ev = fired || {};\n for (var i = 0; i < 16; i++) {\n var t = next(cur, ev);\n if (!t) break;\n var n = enter(cur, t[1]);\n cur = n.run;\n ev = n.fired;\n }\n return cur;\n }\n function begin() {\n var first = spec.s[spec.i] ? spec.i : Object.keys(spec.s)[0], values = {};\n if (first === void 0) return null;\n for (var k in spec.in) {\n var s = start(k);\n if (s !== void 0) values[k] = s;\n }\n var e = enter({ state: first, values }, first);\n return settle(e.run, e.fired);\n }\n function hears(l, type, chain, key) {\n if (l[0] !== type) return false;\n if (type === "complete") return true;\n if (type === "keyDown" || type === "keyUp") return !l[3] || String(l[3]).toLowerCase() === String(key).toLowerCase();\n return l[1] === null || chain.indexOf(l[1]) >= 0;\n }\n function dispatch(r, type, chain, key) {\n var heard = spec.l.filter(function(l) {\n return hears(l, type, chain, key);\n });\n if (!heard.length) return r;\n var res = apply(r.values, [].concat.apply([], heard.map(function(l) {\n return l[2];\n })));\n return settle({ state: r.state, values: res.values }, res.fired);\n }\n function set(r, id, value) {\n var t = spec.in[id];\n if (!t) return r;\n var res = apply(r.values, [t[0] === "event" ? ["fire", id] : ["set", id, value]]);\n return settle({ state: r.state, values: res.values }, res.fired);\n }\n return { begin, dispatch, set };\n}\nfunction popcraftMachine(root, spec) {\n var core = popcraftMachineCore(spec), run = core.begin(), anims = [], t0 = 0, done = false, raf = 0, over = [];\n if (!run) return function() {\n };\n function chain(el) {\n var out = [];\n for (var n = el; n && n !== root.parentNode; n = n.parentNode) {\n var id = n.getAttribute && n.getAttribute("data-sm");\n if (id) out.push(id);\n if (n === root) break;\n }\n return out;\n }\n function update(r) {\n if (r === run) return;\n var changed = r.state !== run.state;\n run = r;\n if (!changed) return;\n t0 = performance.now();\n done = false;\n root.dispatchEvent(new CustomEvent("popcraft:state", { detail: { state: r.state, name: spec.s[r.state] ? spec.s[r.state][5] : r.state, values: r.values } }));\n }\n function tick(now) {\n var s = spec.s[run.state];\n if (s) {\n var a = s[0], b = s[1], played = Math.max(0, now - t0) * s[3], t;\n if (s[2] && b > a) t = a + played % (b - a);\n else {\n t = Math.min(b, a + played);\n if (!done && a + played >= b) {\n done = true;\n update(core.dispatch(run, "complete", []));\n }\n }\n anims.forEach(function(x) {\n x.currentTime = t;\n });\n }\n raf = requestAnimationFrame(tick);\n }\n function on(type) {\n return function(e) {\n update(core.dispatch(run, type, chain(e.target)));\n };\n }\n function onMove(e) {\n var ids = chain(e.target);\n var left = over.filter(function(u) {\n return ids.indexOf(u) < 0;\n }), entered = ids.filter(function(u) {\n return over.indexOf(u) < 0;\n });\n over = ids;\n if (left.length) update(core.dispatch(run, "pointerExit", left));\n if (entered.length) update(core.dispatch(run, "pointerEnter", entered));\n }\n function onLeave() {\n if (over.length) {\n var left = over;\n over = [];\n update(core.dispatch(run, "pointerExit", left));\n }\n }\n function onKey(type) {\n return function(e) {\n var t = e.target;\n if (e.repeat || e.metaKey || e.ctrlKey || t && (t.tagName === "INPUT" || t.tagName === "TEXTAREA" || t.isContentEditable)) return;\n var r = core.dispatch(run, type, [], e.key);\n if (r !== run) {\n e.preventDefault();\n update(r);\n }\n };\n }\n var down = on("pointerDown"), up = on("pointerUp"), click = on("click"), keyDown = onKey("keyDown"), keyUp = onKey("keyUp");\n anims = root.getAnimations ? root.getAnimations({ subtree: true }) : [];\n anims.forEach(function(x) {\n x.pause();\n });\n t0 = performance.now();\n root.addEventListener("pointerdown", down);\n root.addEventListener("pointerup", up);\n root.addEventListener("click", click);\n root.addEventListener("pointermove", onMove);\n root.addEventListener("pointerleave", onLeave);\n window.addEventListener("keydown", keyDown);\n window.addEventListener("keyup", keyUp);\n raf = requestAnimationFrame(tick);\n function byName(k) {\n if (spec.in[k]) return k;\n for (var id in spec.in) if (spec.in[id][2] === k) return id;\n return k;\n }\n var api = {\n state: function() {\n return run.state;\n },\n values: function() {\n return run.values;\n },\n set: function(input, value) {\n update(core.set(run, byName(input), value));\n },\n fire: function(input) {\n update(core.set(run, byName(input), void 0));\n },\n destroy: function() {\n cancelAnimationFrame(raf);\n root.removeEventListener("pointerdown", down);\n root.removeEventListener("pointerup", up);\n root.removeEventListener("click", click);\n root.removeEventListener("pointermove", onMove);\n root.removeEventListener("pointerleave", onLeave);\n window.removeEventListener("keydown", keyDown);\n window.removeEventListener("keyup", keyUp);\n }\n };\n root.popcraftMachine = api;\n return api.destroy;\n}';
|
|
316150
|
+
}
|
|
316151
|
+
});
|
|
316152
|
+
|
|
316153
|
+
// lib/io/web/machine-runtime.ts
|
|
316154
|
+
var init_machine_runtime = __esm({
|
|
316155
|
+
"lib/io/web/machine-runtime.ts"() {
|
|
316156
|
+
"use strict";
|
|
316157
|
+
init_runtimes();
|
|
316158
|
+
}
|
|
316159
|
+
});
|
|
316160
|
+
|
|
316161
|
+
// lib/io/web/state-machine.ts
|
|
316162
|
+
function webStateMachine(doc2, frameId) {
|
|
316163
|
+
const sm = machineOf(doc2.nodes[frameId]);
|
|
316164
|
+
if (!sm || !doc2.nodes[frameId]?.timeline) return null;
|
|
316165
|
+
const timeline = frameTimeline(doc2.nodes, frameId);
|
|
316166
|
+
const duration3 = timelineDuration(doc2.nodes, frameId);
|
|
316167
|
+
const action3 = (a) => a.value === void 0 ? [a.type, a.input] : [a.type, a.input, a.value];
|
|
316168
|
+
const spec = { i: sm.initial, s: {}, t: [], in: {}, l: [] };
|
|
316169
|
+
for (const i2 of sortedValues(sm.inputs)) spec.in[i2.id] = [i2.type, i2.type === "event" ? null : i2.value ?? defaultOf2(i2.type), i2.name];
|
|
316170
|
+
for (const s of sortedValues(sm.states)) {
|
|
316171
|
+
const [a, b] = stateStretch(s, timeline, duration3);
|
|
316172
|
+
spec.s[s.id] = [a, b, s.loop ? 1 : 0, s.speed ?? 1, (s.entry ?? []).map(action3), s.name];
|
|
316173
|
+
}
|
|
316174
|
+
for (const t3 of sortedValues(sm.transitions)) {
|
|
316175
|
+
spec.t.push([t3.from, t3.to, (t3.guards ?? []).map((g) => {
|
|
316176
|
+
const type = sm.inputs[g.input]?.type;
|
|
316177
|
+
const value3 = type === "event" ? null : g.value ?? (type === "boolean" ? true : type === "number" ? 0 : "");
|
|
316178
|
+
return [g.input, g.op ?? "eq", value3];
|
|
316179
|
+
})]);
|
|
316180
|
+
}
|
|
316181
|
+
for (const l of sortedValues(sm.listeners)) {
|
|
316182
|
+
if (!isKeyListener(l.type)) spec.l.push([l.type, l.layer ?? null, l.actions.map(action3)]);
|
|
316183
|
+
else spec.l.push(l.key ? [l.type, null, l.actions.map(action3), l.key] : [l.type, null, l.actions.map(action3)]);
|
|
316184
|
+
}
|
|
316185
|
+
return spec;
|
|
316186
|
+
}
|
|
316187
|
+
var defaultOf2, machineLayers, machineScript;
|
|
316188
|
+
var init_state_machine2 = __esm({
|
|
316189
|
+
"lib/io/web/state-machine.ts"() {
|
|
316190
|
+
"use strict";
|
|
316191
|
+
init_instances2();
|
|
316192
|
+
init_state_machine();
|
|
316193
|
+
init_machine_runtime();
|
|
316194
|
+
init_machine_runtime();
|
|
316195
|
+
defaultOf2 = (type) => type === "boolean" ? false : type === "number" ? 0 : type === "string" ? "" : null;
|
|
316196
|
+
machineLayers = (spec) => new Set((spec?.l ?? []).map((l) => l[1]).filter((id3) => !!id3));
|
|
316197
|
+
machineScript = (spec) => `${MACHINE_JS}
|
|
316198
|
+
popcraftMachine(document.querySelector('[data-sm-root]'), ${JSON.stringify(spec)});`;
|
|
316199
|
+
}
|
|
316200
|
+
});
|
|
316201
|
+
|
|
316202
|
+
// lib/io/web/interactive.ts
|
|
316203
|
+
function subtreeIds(doc2, id3, out = /* @__PURE__ */ new Set()) {
|
|
316204
|
+
if (out.has(id3)) return out;
|
|
316205
|
+
const n = doc2.nodes[id3];
|
|
316206
|
+
if (!n) return out;
|
|
316207
|
+
out.add(id3);
|
|
316208
|
+
if (n.type === "INSTANCE") subtreeIds(doc2, n.mainComponentId, out);
|
|
316209
|
+
for (const c2 of n.childIds ?? []) subtreeIds(doc2, c2, out);
|
|
316210
|
+
return out;
|
|
316211
|
+
}
|
|
316212
|
+
function flowScreens(doc2, startId) {
|
|
316213
|
+
const start2 = doc2.nodes[startId];
|
|
316214
|
+
if (!start2 || start2.type !== "FRAME" || doc2.nodes[start2.parentId ?? ""]?.type !== "PAGE") return [startId];
|
|
316215
|
+
const out = [startId];
|
|
316216
|
+
for (let i2 = 0; i2 < out.length; i2++) {
|
|
316217
|
+
for (const id3 of subtreeIds(doc2, out[i2])) {
|
|
316218
|
+
for (const ix of interactionsOf(doc2.nodes[id3])) {
|
|
316219
|
+
const to = ix.action.navigationType === "NAVIGATE" ? ix.action.destinationId : null;
|
|
316220
|
+
const dest = to ? doc2.nodes[to] : void 0;
|
|
316221
|
+
if (!dest || out.includes(dest.id) || dest.type !== "FRAME" || doc2.nodes[dest.parentId ?? ""]?.type !== "PAGE") continue;
|
|
316222
|
+
if (Math.round(dest.width) !== Math.round(start2.width) || Math.round(dest.height) !== Math.round(start2.height)) continue;
|
|
316223
|
+
out.push(dest.id);
|
|
316224
|
+
}
|
|
316225
|
+
}
|
|
316226
|
+
}
|
|
316227
|
+
return out;
|
|
316228
|
+
}
|
|
316229
|
+
function variantStates(doc2, mainId) {
|
|
316230
|
+
const out = [mainId];
|
|
316231
|
+
for (let i2 = 0; i2 < out.length; i2++) {
|
|
316232
|
+
for (const id3 of subtreeIds(doc2, out[i2])) {
|
|
316233
|
+
for (const ix of interactionsOf(doc2.nodes[id3])) {
|
|
316234
|
+
const to = ix.action.navigationType === "CHANGE_TO" ? ix.action.destinationId : null;
|
|
316235
|
+
if (to && !out.includes(to) && doc2.nodes[to]?.type === "COMPONENT") out.push(to);
|
|
316236
|
+
}
|
|
316237
|
+
}
|
|
316238
|
+
}
|
|
316239
|
+
return out;
|
|
316240
|
+
}
|
|
316241
|
+
function buildState(ctx2, doc2, id3, machine, state, start2, variantOf2) {
|
|
316242
|
+
const expand = /* @__PURE__ */ new Map();
|
|
316243
|
+
const tree = buildPlainTree(doc2, id3, ctx2.opts, start2, { built: (web, _node, at3) => {
|
|
316244
|
+
if (web.type === "INSTANCE") expand.set(web, at3);
|
|
316245
|
+
} });
|
|
316246
|
+
for (const r of tree.rules ?? []) ctx2.rules.add(r);
|
|
316247
|
+
if (tree.truncated) ctx2.truncated = true;
|
|
316248
|
+
const ids2 = /* @__PURE__ */ new Map();
|
|
316249
|
+
const index2 = (w) => {
|
|
316250
|
+
ids2.set(w.id, w);
|
|
316251
|
+
w.children.forEach(index2);
|
|
316252
|
+
};
|
|
316253
|
+
index2(tree.root);
|
|
316254
|
+
const visit2 = (w, owner, st, isRoot) => {
|
|
316255
|
+
w.owner = owner;
|
|
316256
|
+
w.looks = { [st]: lookOf(w, isRoot) };
|
|
316257
|
+
if (w.motion) ctx2.keyframes.add(w.motion.keyframes);
|
|
316258
|
+
const node2 = nodeOf(doc2, w.id);
|
|
316259
|
+
note(ctx2, w, interactionsOf(doc2.nodes[realId(w.id)]), owner, st, ids2);
|
|
316260
|
+
const at3 = expand.get(w);
|
|
316261
|
+
const inst = node2?.type === "INSTANCE" ? node2 : void 0;
|
|
316262
|
+
const states = inst && at3 && ctx2.depth < 4 ? variantStates(doc2, inst.mainComponentId) : [];
|
|
316263
|
+
if (inst && at3 && states.length > 1 && w.id !== variantOf2) {
|
|
316264
|
+
const m = { id: `m${ctx2.machines.length}`, initial: inst.mainComponentId, states: states.map((s) => ({ id: s, name: stateName(doc2, s) })) };
|
|
316265
|
+
ctx2.machines.push(m);
|
|
316266
|
+
w.machine = m;
|
|
316267
|
+
const perState = [];
|
|
316268
|
+
for (const s of states) {
|
|
316269
|
+
let kids;
|
|
316270
|
+
if (s === inst.mainComponentId) {
|
|
316271
|
+
kids = w.children;
|
|
316272
|
+
kids.forEach((c2) => visit2(c2, m.id, s, false));
|
|
316273
|
+
} else {
|
|
316274
|
+
const shown2 = { ...doc2, nodes: { ...doc2.nodes, [inst.id]: { ...inst, mainComponentId: s } } };
|
|
316275
|
+
ctx2.depth++;
|
|
316276
|
+
try {
|
|
316277
|
+
kids = buildState(ctx2, shown2, inst.id, m.id, s, at3, inst.id).children;
|
|
316278
|
+
} finally {
|
|
316279
|
+
ctx2.depth--;
|
|
316280
|
+
}
|
|
316281
|
+
}
|
|
316282
|
+
note(ctx2, w, interactionsOf(doc2.nodes[s]), m.id, s, ids2, m.id);
|
|
316283
|
+
perState.push([s, kids]);
|
|
316284
|
+
}
|
|
316285
|
+
w.children = mergeChildren(perState, m.id, m.states.map((s) => s.id), ctx2);
|
|
316286
|
+
} else if (w.id === variantOf2) {
|
|
316287
|
+
w.children.forEach((c2) => visit2(c2, owner, st, false));
|
|
316288
|
+
} else {
|
|
316289
|
+
if (inst) note(ctx2, w, interactionsOf(doc2.nodes[inst.mainComponentId]), owner, st, ids2);
|
|
316290
|
+
w.children.forEach((c2) => visit2(c2, owner, st, false));
|
|
316291
|
+
}
|
|
316292
|
+
};
|
|
316293
|
+
visit2(tree.root, machine, state, !start2);
|
|
316294
|
+
return tree.root;
|
|
316295
|
+
}
|
|
316296
|
+
function note(ctx2, w, list2, machine, state, ids2, hostMachine) {
|
|
316297
|
+
if (!list2.length) return;
|
|
316298
|
+
const at3 = ctx2.pending.get(w) ?? [];
|
|
316299
|
+
for (const ix of list2) at3.push({ machine, state, ix, hostMachine: hostMachine ?? (machine !== FLOW ? machine : void 0), ids: ids2 });
|
|
316300
|
+
ctx2.pending.set(w, at3);
|
|
316301
|
+
}
|
|
316302
|
+
function lookOf(w, isRoot) {
|
|
316303
|
+
return {
|
|
316304
|
+
style: { ...placementStyle(w, isRoot), ...w.style, ...w.motion?.style ?? {} },
|
|
316305
|
+
...w.text ? { text: w.text.characters } : {},
|
|
316306
|
+
...w.tf ? { tf: w.tf } : {}
|
|
316307
|
+
};
|
|
316308
|
+
}
|
|
316309
|
+
function keyed(kids) {
|
|
316310
|
+
const seen = /* @__PURE__ */ new Map();
|
|
316311
|
+
return kids.map((k2) => {
|
|
316312
|
+
const base = `${k2.name}\0${k2.type}`;
|
|
316313
|
+
const i2 = seen.get(base) ?? 0;
|
|
316314
|
+
seen.set(base, i2 + 1);
|
|
316315
|
+
return [`${base}\0${i2}`, k2];
|
|
316316
|
+
});
|
|
316317
|
+
}
|
|
316318
|
+
function mergeChildren(perState, machine, states, ctx2) {
|
|
316319
|
+
const order2 = [];
|
|
316320
|
+
const groups = /* @__PURE__ */ new Map();
|
|
316321
|
+
for (const [state, kids] of perState) {
|
|
316322
|
+
let after = -1;
|
|
316323
|
+
for (const [k2, node2] of keyed(kids)) {
|
|
316324
|
+
let at3 = order2.indexOf(k2);
|
|
316325
|
+
if (at3 < 0) {
|
|
316326
|
+
order2.splice(after + 1, 0, k2);
|
|
316327
|
+
at3 = after + 1;
|
|
316328
|
+
}
|
|
316329
|
+
after = at3;
|
|
316330
|
+
(groups.get(k2) ?? groups.set(k2, []).get(k2)).push([state, node2]);
|
|
316331
|
+
}
|
|
316332
|
+
}
|
|
316333
|
+
return order2.map((k2) => mergeNode(groups.get(k2), machine, states, ctx2));
|
|
316334
|
+
}
|
|
316335
|
+
function mergeNode(items, machine, states, ctx2) {
|
|
316336
|
+
const [, first2] = items[0];
|
|
316337
|
+
if (first2.owner !== machine) {
|
|
316338
|
+
for (const [, w] of items.slice(1)) alias(ctx2, w, first2);
|
|
316339
|
+
return first2;
|
|
316340
|
+
}
|
|
316341
|
+
const looks = {};
|
|
316342
|
+
for (const s of states) looks[s] = null;
|
|
316343
|
+
for (const [s, w] of items) looks[s] = w.looks?.[s] ?? null;
|
|
316344
|
+
const merged = { ...first2, looks };
|
|
316345
|
+
const pend = items.flatMap(([, w]) => ctx2.pending.get(w) ?? []);
|
|
316346
|
+
if (pend.length) ctx2.pending.set(merged, pend);
|
|
316347
|
+
for (const [, w] of items) if (w !== merged) alias(ctx2, w, merged);
|
|
316348
|
+
if (first2.machine) {
|
|
316349
|
+
for (const [, w] of items) if (w.machine && w.machine !== first2.machine) ctx2.renamed.set(w.machine.id, first2.machine.id);
|
|
316350
|
+
}
|
|
316351
|
+
merged.children = first2.machine ? first2.children : mergeChildren(items.map(([s, w]) => [s, w.children]), machine, states, ctx2);
|
|
316352
|
+
return merged;
|
|
316353
|
+
}
|
|
316354
|
+
function alias(ctx2, from2, to) {
|
|
316355
|
+
const a = ctx2.alias ??= /* @__PURE__ */ new Map();
|
|
316356
|
+
a.set(from2, to);
|
|
316357
|
+
}
|
|
316358
|
+
function mergedOf(ctx2, w) {
|
|
316359
|
+
const a = ctx2.alias;
|
|
316360
|
+
let cur = w;
|
|
316361
|
+
for (let i2 = 0; i2 < 16 && a?.has(cur); i2++) cur = a.get(cur);
|
|
316362
|
+
return cur;
|
|
316363
|
+
}
|
|
316364
|
+
function actionOf(ctx2, p2) {
|
|
316365
|
+
const a = p2.ix.action;
|
|
316366
|
+
const glide2 = glideOf2(a.transition);
|
|
316367
|
+
const hold = p2.ix.trigger === "ON_HOVER" || p2.ix.trigger === "ON_PRESS";
|
|
316368
|
+
switch (a.navigationType) {
|
|
316369
|
+
case "NAVIGATE":
|
|
316370
|
+
return a.destinationId && ctx2.screens.has(a.destinationId) ? { kind: "go", machine: FLOW, to: a.destinationId, ...glide2, ...hold ? { hold } : {} } : null;
|
|
316371
|
+
case "BACK":
|
|
316372
|
+
return ctx2.screens.size > 1 ? { kind: "back", machine: FLOW } : null;
|
|
316373
|
+
case "CHANGE_TO":
|
|
316374
|
+
return p2.hostMachine && a.destinationId ? { kind: "go", machine: p2.hostMachine, to: a.destinationId, ...glide2, ...hold ? { hold } : {} } : null;
|
|
316375
|
+
case "ORBIT_3D": {
|
|
316376
|
+
const o = a.orbit ?? {};
|
|
316377
|
+
const uidOf = (id3) => {
|
|
316378
|
+
const w = id3 ? p2.ids.get(id3) : void 0;
|
|
316379
|
+
return w ? mergedOf(ctx2, w).uid : void 0;
|
|
316380
|
+
};
|
|
316381
|
+
const uid2 = uidOf(a.destinationId);
|
|
316382
|
+
const tiltUid = uidOf(o.tiltLayerId) ?? uid2;
|
|
316383
|
+
return uid2 === void 0 || tiltUid === void 0 ? null : { kind: "orbit", target: uid2, tiltTarget: tiltUid, degreesPerPx: o.degreesPerPx ?? 0.4, tilt: !!o.tilt, tiltRange: o.tiltRange ?? [-30, 30] };
|
|
316384
|
+
}
|
|
316385
|
+
default:
|
|
316386
|
+
return null;
|
|
316387
|
+
}
|
|
316388
|
+
}
|
|
316389
|
+
function buildWebTree(doc2, nodeId2, opts = {}) {
|
|
316390
|
+
const tree = buildTree(doc2, nodeId2, opts);
|
|
316391
|
+
const machine = opts.static || opts.stateMachine === false ? null : webStateMachine(doc2, nodeId2);
|
|
316392
|
+
return machine ? { ...tree, stateMachine: machine } : tree;
|
|
316393
|
+
}
|
|
316394
|
+
function buildTree(doc2, nodeId2, opts = {}) {
|
|
316395
|
+
if (opts.static || opts.target === "site") return buildPlainTree(doc2, nodeId2, opts);
|
|
316396
|
+
const screens = flowScreens(doc2, nodeId2);
|
|
316397
|
+
const anything = screens.length > 1 || [...subtreeIds(doc2, nodeId2)].some((id3) => interactionsOf(doc2.nodes[id3]).some((ix) => ix.action.navigationType === "CHANGE_TO" || ix.action.navigationType === "ORBIT_3D"));
|
|
316398
|
+
if (!anything) return buildPlainTree(doc2, nodeId2, opts);
|
|
316399
|
+
const flow = { id: FLOW, initial: nodeId2, states: screens.map((s) => ({ id: s, name: doc2.nodes[s]?.name ?? s })) };
|
|
316400
|
+
const ctx2 = { doc: doc2, opts, screens: new Set(screens), machines: [flow], keyframes: /* @__PURE__ */ new Set(), rules: /* @__PURE__ */ new Set(), pending: /* @__PURE__ */ new Map(), depth: 0, renamed: /* @__PURE__ */ new Map() };
|
|
316401
|
+
const roots = screens.map((s) => [s, buildState(ctx2, doc2, s, FLOW, s)]);
|
|
316402
|
+
const truncated = !!ctx2.truncated;
|
|
316403
|
+
const root2 = mergeNode(roots, FLOW, screens, ctx2);
|
|
316404
|
+
let uid2 = 0;
|
|
316405
|
+
const number4 = (w) => {
|
|
316406
|
+
w.uid = uid2++;
|
|
316407
|
+
w.children.forEach(number4);
|
|
316408
|
+
};
|
|
316409
|
+
number4(root2);
|
|
316410
|
+
const place4 = (w) => {
|
|
316411
|
+
const pend = ctx2.pending.get(w);
|
|
316412
|
+
if (pend) {
|
|
316413
|
+
const seen = /* @__PURE__ */ new Set();
|
|
316414
|
+
const on = [];
|
|
316415
|
+
for (const raw of pend) {
|
|
316416
|
+
const p2 = { ...raw, machine: ctx2.renamed.get(raw.machine) ?? raw.machine, ...raw.hostMachine ? { hostMachine: ctx2.renamed.get(raw.hostMachine) ?? raw.hostMachine } : {} };
|
|
316417
|
+
const trigger = TRIGGERS[p2.ix.trigger];
|
|
316418
|
+
const action3 = trigger ? actionOf(ctx2, p2) : null;
|
|
316419
|
+
if (!trigger || !action3) continue;
|
|
316420
|
+
const ix = { machine: p2.machine, state: p2.state, trigger, ...p2.ix.triggerDelay ? { delay: p2.ix.triggerDelay } : {}, ...p2.ix.triggerKey ? { key: p2.ix.triggerKey } : {}, action: action3 };
|
|
316421
|
+
const sig = JSON.stringify(ix);
|
|
316422
|
+
if (!seen.has(sig)) {
|
|
316423
|
+
seen.add(sig);
|
|
316424
|
+
on.push(ix);
|
|
316425
|
+
}
|
|
316426
|
+
}
|
|
316427
|
+
if (on.length) w.on = on;
|
|
316428
|
+
}
|
|
316429
|
+
w.children.forEach(place4);
|
|
316430
|
+
};
|
|
316431
|
+
place4(root2);
|
|
316432
|
+
return { root: root2, truncated, ...ctx2.rules.size ? { rules: [...ctx2.rules].sort() } : {}, interactive: { machines: ctx2.machines.filter((m) => !ctx2.renamed.has(m.id)), keyframes: [...ctx2.keyframes] } };
|
|
316433
|
+
}
|
|
316434
|
+
var FLOW, interactionsOf, realId, nodeOf, stateName, TRIGGERS, EASINGS2, glideOf2;
|
|
316435
|
+
var init_interactive = __esm({
|
|
316436
|
+
"lib/io/web/interactive.ts"() {
|
|
316437
|
+
"use strict";
|
|
316438
|
+
init_scene_graph();
|
|
316439
|
+
init_tree();
|
|
316440
|
+
init_state_machine2();
|
|
316441
|
+
init_element();
|
|
316442
|
+
FLOW = "flow";
|
|
316443
|
+
interactionsOf = (n) => n?.interactions ?? [];
|
|
316444
|
+
realId = (id3) => id3.includes("::") ? id3.slice(id3.lastIndexOf("::") + 2) : id3;
|
|
316445
|
+
nodeOf = (doc2, id3) => doc2.nodes[id3] ?? (id3.includes("::") ? resolveVirtualNode2(doc2.nodes, id3) ?? void 0 : void 0);
|
|
316446
|
+
stateName = (doc2, id3) => {
|
|
316447
|
+
const n = doc2.nodes[id3];
|
|
316448
|
+
const v = n?.variantProperties;
|
|
316449
|
+
return v ? Object.values(v).join(", ") : n?.name ?? id3;
|
|
316450
|
+
};
|
|
316451
|
+
TRIGGERS = {
|
|
316452
|
+
ON_CLICK: "click",
|
|
316453
|
+
ON_HOVER: "hover",
|
|
316454
|
+
ON_PRESS: "press",
|
|
316455
|
+
ON_DRAG: "drag",
|
|
316456
|
+
MOUSE_ENTER: "enter",
|
|
316457
|
+
MOUSE_LEAVE: "leave",
|
|
316458
|
+
AFTER_TIMEOUT: "timeout",
|
|
316459
|
+
KEY_DOWN: "key"
|
|
316460
|
+
};
|
|
316461
|
+
EASINGS2 = { EASE_IN: "ease-in", EASE_OUT: "ease-out", EASE_IN_OUT: "ease-in-out", LINEAR: "linear", SPRING: "cubic-bezier(0.34, 1.56, 0.64, 1)" };
|
|
316462
|
+
glideOf2 = (t3) => !t3 || t3.type === "INSTANT" || t3.type === "CUT" ? { ms: 0, easing: "linear" } : { ms: Math.max(0, Math.round(t3.duration)), easing: EASINGS2[t3.easing] ?? "ease-in-out" };
|
|
316463
|
+
}
|
|
316464
|
+
});
|
|
316465
|
+
|
|
316466
|
+
// lib/io/web/tree.ts
|
|
316467
|
+
var tree_exports = {};
|
|
316468
|
+
__export(tree_exports, {
|
|
316469
|
+
DEFAULT_NODE_CAP: () => DEFAULT_NODE_CAP,
|
|
316470
|
+
EXPORT_NODE_CAP: () => EXPORT_NODE_CAP,
|
|
316471
|
+
buildPlainTree: () => buildPlainTree,
|
|
316472
|
+
buildWebTree: () => buildWebTree,
|
|
316473
|
+
flatten: () => flatten2,
|
|
316474
|
+
foldRules: () => foldRules,
|
|
316475
|
+
foldVar: () => foldVar,
|
|
316476
|
+
prepared: () => prepared
|
|
316477
|
+
});
|
|
316478
|
+
function anchorTargets(doc2) {
|
|
316479
|
+
const hit = anchorMemo.get(doc2.nodes);
|
|
316480
|
+
if (hit) return hit;
|
|
316481
|
+
const out = /* @__PURE__ */ new Set();
|
|
316482
|
+
for (const id3 in doc2.nodes) {
|
|
316483
|
+
const n = doc2.nodes[id3];
|
|
316484
|
+
if (n.semantics?.link?.kind === "anchor") out.add(n.semantics.link.nodeId);
|
|
316485
|
+
for (const ix of n.interactions ?? []) if (ix.action.link?.kind === "anchor" && ix.action.link.nodeId) out.add(ix.action.link.nodeId);
|
|
316486
|
+
}
|
|
316487
|
+
anchorMemo.set(doc2.nodes, out);
|
|
316488
|
+
return out;
|
|
316489
|
+
}
|
|
316490
|
+
function spriteOnly(nodes, id3) {
|
|
316491
|
+
let leaves = 0;
|
|
316492
|
+
const visit2 = (nid, depth2) => {
|
|
316493
|
+
const n = nodes[nid];
|
|
316494
|
+
if (!n || n.visible === false) return true;
|
|
316495
|
+
if (n.type === "PIXEL_GRID") {
|
|
316496
|
+
leaves++;
|
|
316497
|
+
return true;
|
|
316498
|
+
}
|
|
316499
|
+
if (depth2 > 8 || n.type !== "INSTANCE" && n.type !== "COMPONENT" && n.type !== "FRAME" && n.type !== "GROUP") return false;
|
|
316500
|
+
const main2 = n.mainComponentId;
|
|
316501
|
+
const kids = n.childIds?.length ? n.childIds : main2 ? [main2] : [];
|
|
316502
|
+
return kids.every((k2) => visit2(k2, depth2 + 1));
|
|
316503
|
+
};
|
|
316504
|
+
return visit2(id3, 0) && leaves > 0;
|
|
316505
|
+
}
|
|
316506
|
+
function prepared(node2, doc2) {
|
|
316507
|
+
let n = node2;
|
|
316508
|
+
if (n.id.includes("::")) n = withInstanceBox(n, doc2.nodes);
|
|
316509
|
+
n = resolveNodeVariables(n, doc2.variables, doc2.variableCollections, doc2.activeVariableModes, exprData(doc2));
|
|
316510
|
+
n = resolveTextNodeStyles(n, doc2.styles ?? {});
|
|
316511
|
+
return n;
|
|
316512
|
+
}
|
|
316513
|
+
function layoutOf2(node2, nodes) {
|
|
316514
|
+
if (!node2) return null;
|
|
316515
|
+
if (node2.type === "INSTANCE") {
|
|
316516
|
+
const mainId = node2.mainComponentId;
|
|
316517
|
+
const main2 = mainId ? nodes[mainId] : void 0;
|
|
316518
|
+
return main2 ?? null;
|
|
316519
|
+
}
|
|
316520
|
+
if (node2.id.includes("::")) {
|
|
316521
|
+
const real = nodes[node2.id.split("::").pop()];
|
|
316522
|
+
return real ?? node2;
|
|
316523
|
+
}
|
|
316524
|
+
return node2;
|
|
316525
|
+
}
|
|
316526
|
+
function buildPlainTree(doc2, nodeId2, opts = {}, start2, hooks = {}) {
|
|
316527
|
+
const cap2 = opts.nodeCap ?? DEFAULT_NODE_CAP;
|
|
316528
|
+
const first2 = doc2.nodes[nodeId2] ?? (nodeId2.includes("::") ? childLookup(doc2, nodeId2) : void 0);
|
|
316529
|
+
if (!first2) throw new Error(`No node ${nodeId2}`);
|
|
316530
|
+
let emitted = 0;
|
|
316531
|
+
let truncated = false;
|
|
316532
|
+
let folds = 0;
|
|
316533
|
+
const tokens = opts.target === "site" && Object.keys(doc2.variables ?? {}).length ? siteTokens(doc2) : null;
|
|
316534
|
+
const anchored = anchorTargets(doc2);
|
|
316535
|
+
const pageItem = () => {
|
|
316536
|
+
const c2 = opts.item && doc2.collections?.[opts.item.collectionId];
|
|
316537
|
+
if (c2 && opts.item.recordId === ITEM_RECORD) return { collection: c2, record: templateRecord(c2), suffix: `~${ITEM_RECORD}` };
|
|
316538
|
+
const r = opts.item && doc2.records?.[opts.item.recordId];
|
|
316539
|
+
return c2 && r ? { collection: c2, record: r, suffix: "" } : null;
|
|
316540
|
+
};
|
|
316541
|
+
let item = pageItem();
|
|
316542
|
+
const scopeOf2 = (it) => itemScope(it.collection, it.record, withData(variablesScope(doc2.variables, doc2.variableCollections, doc2.activeVariableModes), doc2));
|
|
316543
|
+
const itemised = (node2, raw, it) => itemNode(node2, raw, it.collection, it.record, scopeOf2(it));
|
|
316544
|
+
const itemLink = (link2, it) => {
|
|
316545
|
+
const filled2 = it && link2.kind === "url" ? { ...link2, url: itemText(link2.url, it.collection, it.record) } : it && (link2.kind === "email" || link2.kind === "tel") ? { ...link2, value: itemText(link2.value, it.collection, it.record) } : link2;
|
|
316546
|
+
if (filled2.kind === "screen") {
|
|
316547
|
+
const dest = doc2.nodes[filled2.frameId];
|
|
316548
|
+
const base = opts.routes?.[filled2.frameId];
|
|
316549
|
+
const of = dest?.route?.collectionId;
|
|
316550
|
+
if (of && base !== void 0) {
|
|
316551
|
+
const slugField = it?.record.id === ITEM_RECORD && it.collection.id === of ? it.collection.fields.find((f2) => f2.id === it.collection.slugFieldId) ?? it.collection.fields.find((f2) => f2.type === "SLUG" || f2.type === "TEXT") : void 0;
|
|
316552
|
+
if (slugField) return { link: filled2, href: `${base === "/" ? "" : base}/${itemMark(fieldKey(slugField.name))}`, screen: filled2.frameId };
|
|
316553
|
+
const slugs = recordSlugs(doc2, of);
|
|
316554
|
+
const rec = it?.collection.id === of ? it.record.id : slugs.keys().next().value;
|
|
316555
|
+
const slug3 = rec ? slugs.get(rec) : void 0;
|
|
316556
|
+
return slug3 ? { link: filled2, href: `${base === "/" ? "" : base}/${slug3}`, screen: `${filled2.frameId}~${rec}` } : { link: filled2, href: null };
|
|
316557
|
+
}
|
|
316558
|
+
return { link: filled2, href: base ?? null, screen: filled2.frameId };
|
|
316559
|
+
}
|
|
316560
|
+
if (filled2.kind === "url" && it?.record.id === ITEM_RECORD && itemMarks(filled2.url)) return { link: filled2, href: filled2.url.trim() };
|
|
316561
|
+
return { link: filled2, href: hrefOf(filled2, doc2.nodes, opts.routes) };
|
|
316562
|
+
};
|
|
316563
|
+
const fields = /* @__PURE__ */ new Map();
|
|
316564
|
+
const styleOpts = { fullImageUrl: opts.fullImageUrls ?? opts.target === "site" };
|
|
316565
|
+
const stylesOf = (n) => styleMapFor(n, doc2.styles, styleOpts);
|
|
316566
|
+
let motion = null;
|
|
316567
|
+
const timeline = !opts.static && !start2 && first2.type === "FRAME" ? frameWebMotion(doc2, first2.id, (n) => stylesOf(prepared(n, doc2))) : null;
|
|
316568
|
+
const build3 = (raw, parent, in3D2, fold) => {
|
|
316569
|
+
if (emitted >= cap2) {
|
|
316570
|
+
truncated = true;
|
|
316571
|
+
return null;
|
|
316572
|
+
}
|
|
316573
|
+
emitted++;
|
|
316574
|
+
const node2 = item ? itemised(prepared(raw, doc2), raw, item) : prepared(raw, doc2);
|
|
316575
|
+
const waits = node2.visible === false && parent !== null;
|
|
316576
|
+
if (waits && !(opts.target === "site" && followsVisibility(raw))) return null;
|
|
316577
|
+
const exp = expressibility(node2, doc2.styles);
|
|
316578
|
+
const f2 = layoutOf2(node2, doc2.nodes) ?? node2;
|
|
316579
|
+
const style = stylesOf(node2);
|
|
316580
|
+
if (f2 !== node2 && !style.display) Object.assign(style, flexDeclarations(f2));
|
|
316581
|
+
const through = in3D2 && passesThrough(raw, doc2.nodes);
|
|
316582
|
+
const own2 = typeof node2.opacity === "number" ? node2.opacity : 1;
|
|
316583
|
+
if (through) {
|
|
316584
|
+
style["transform-style"] = "preserve-3d";
|
|
316585
|
+
delete style.opacity;
|
|
316586
|
+
style[foldVar(fold + 1)] = fold ? `calc(var(${foldVar(fold)}) * ${round3(own2)})` : String(round3(own2));
|
|
316587
|
+
folds = Math.max(folds, fold + 1);
|
|
316588
|
+
} else if (fold) style.opacity = own2 === 1 ? `var(${foldVar(fold)})` : `calc(var(${foldVar(fold)}) * ${round3(own2)})`;
|
|
316589
|
+
if (own2 === 0) style["pointer-events"] = "none";
|
|
316590
|
+
if (clickable(raw) && !style.cursor) style.cursor = "pointer";
|
|
316591
|
+
const web = {
|
|
316592
|
+
id: item?.suffix ? `${node2.id}${item.suffix}` : node2.id,
|
|
316593
|
+
name: node2.name || node2.type,
|
|
316594
|
+
type: node2.type,
|
|
316595
|
+
x: Math.round(node2.x),
|
|
316596
|
+
y: Math.round(node2.y),
|
|
316597
|
+
width: Math.round(node2.width),
|
|
316598
|
+
height: Math.round(node2.height),
|
|
316599
|
+
// Absolutely-positioned auto-layout children are taken out of the flow, exactly as the canvas does.
|
|
316600
|
+
// A grid's children are in its flow too: its tracks place them.
|
|
316601
|
+
positioning: (isFlex(layoutOf2(parent, doc2.nodes)) || layoutOf2(parent, doc2.nodes)?.layoutMode === "GRID") && node2.layoutPositioning !== "ABSOLUTE" ? "flow" : "absolute",
|
|
316602
|
+
style,
|
|
316603
|
+
children: []
|
|
316604
|
+
};
|
|
316605
|
+
if (tokens) Object.assign(style, tokenStyle(raw, style, tokens));
|
|
316606
|
+
if (opts.target === "site") {
|
|
316607
|
+
const lay = siteLayout(node2, parent, layoutOf2(parent, doc2.nodes));
|
|
316608
|
+
for (const [k2, v] of Object.entries(lay.style)) {
|
|
316609
|
+
if (v === null) delete style[k2];
|
|
316610
|
+
else style[k2] = v;
|
|
316611
|
+
}
|
|
316612
|
+
if (laysOut(f2) || f2.overflowScrolling) Object.assign(style, containerStyle(f2));
|
|
316613
|
+
if (node2.type === "TEXT") {
|
|
316614
|
+
if (style["white-space"] === "pre") {
|
|
316615
|
+
style["white-space"] = "pre-wrap";
|
|
316616
|
+
style.width = "fit-content";
|
|
316617
|
+
}
|
|
316618
|
+
if (style["max-width"] === void 0) style["max-width"] = "100%";
|
|
316619
|
+
if (style.height && style.height !== "auto") {
|
|
316620
|
+
style["min-height"] = style.height;
|
|
316621
|
+
delete style.height;
|
|
316622
|
+
}
|
|
316623
|
+
}
|
|
316624
|
+
if (lay.place && (parent !== null || !start2?.parent)) web.place = lay.place;
|
|
316625
|
+
}
|
|
316626
|
+
if (waits) web.hidden = true;
|
|
316627
|
+
const sem = node2.semantics;
|
|
316628
|
+
if (sem) {
|
|
316629
|
+
if (sem.tag && sem.tag !== "div") web.tag = sem.tag;
|
|
316630
|
+
const attrs = {};
|
|
316631
|
+
if (sem.label) attrs["aria-label"] = sem.label;
|
|
316632
|
+
if (sem.hidden) attrs["aria-hidden"] = "true";
|
|
316633
|
+
if (Object.keys(attrs).length) web.attrs = attrs;
|
|
316634
|
+
const to = sem.link ? itemLink(sem.link, item) : null;
|
|
316635
|
+
if (to?.href) web.link = { href: to.href, ...opensNewTab(to.link) ? { newTab: true } : {}, ...to.screen ? { screen: to.screen } : {} };
|
|
316636
|
+
}
|
|
316637
|
+
const control = node2.control;
|
|
316638
|
+
if (control) {
|
|
316639
|
+
const named = control.name ? { name: control.name } : {};
|
|
316640
|
+
if (control.kind === "FORM") {
|
|
316641
|
+
web.tag = "form";
|
|
316642
|
+
if (isCommerceAction(control.formAction)) web.action = control.formAction;
|
|
316643
|
+
} else if (control.kind === "BUTTON") {
|
|
316644
|
+
web.tag = "button";
|
|
316645
|
+
web.attrs = { ...web.attrs, type: control.buttonType ?? "submit", ...named, ...control.name && control.value !== void 0 ? { value: item && hasItemToken(control.value) ? itemText(control.value, item.collection, item.record) : control.value } : {} };
|
|
316646
|
+
} else if (control.kind === "CHECKBOX" || control.kind === "RADIO") {
|
|
316647
|
+
web.check = { attrs: { type: control.kind === "RADIO" ? "radio" : "checkbox", ...named, ...control.value !== void 0 ? { value: control.value } : {}, ...control.checked ? { checked: "" } : {}, ...control.required ? { required: "" } : {} }, ...control.variableId ? { variable: control.variableId } : {} };
|
|
316648
|
+
} else fields.set(fieldPart(doc2.nodes, raw.id) ?? raw.id, control);
|
|
316649
|
+
}
|
|
316650
|
+
const control0 = fields.get(raw.id);
|
|
316651
|
+
const field = control0 && item && control0.value !== void 0 && hasItemToken(control0.value) ? { ...control0, value: itemText(control0.value, item.collection, item.record) } : control0;
|
|
316652
|
+
if (field) {
|
|
316653
|
+
const tag = field.kind === "TEXTAREA" ? "textarea" : field.kind === "SELECT" ? "select" : "input";
|
|
316654
|
+
const words = node2.characters;
|
|
316655
|
+
web.input = {
|
|
316656
|
+
tag,
|
|
316657
|
+
attrs: {
|
|
316658
|
+
...tag === "input" ? { type: field.inputType ?? "text" } : {},
|
|
316659
|
+
...field.name ? { name: field.name } : {},
|
|
316660
|
+
...tag !== "select" && (field.placeholder ?? words) ? { placeholder: field.placeholder ?? words } : {},
|
|
316661
|
+
...field.required ? { required: "" } : {},
|
|
316662
|
+
...tag === "input" && field.value !== void 0 ? { value: field.value } : {},
|
|
316663
|
+
"aria-label": node2.semantics?.label ?? field.placeholder ?? field.name ?? web.name
|
|
316664
|
+
},
|
|
316665
|
+
...tag === "select" ? { options: field.options ?? [] } : {},
|
|
316666
|
+
...tag !== "input" && field.value !== void 0 ? { value: field.value } : {},
|
|
316667
|
+
...field.variableId ? { variable: field.variableId } : {}
|
|
316668
|
+
};
|
|
316669
|
+
}
|
|
316670
|
+
if (sem?.anchor || anchored.has(node2.id)) web.attrs = { ...web.attrs, id: anchorOf(node2) };
|
|
316671
|
+
if (through) web.preserve3d = true;
|
|
316672
|
+
web.tf = transformParts(node2);
|
|
316673
|
+
if (typeof node2.altText === "string") web.alt = node2.altText;
|
|
316674
|
+
if (parent === null) web.positioning = start2?.parent ? web.positioning : "flow";
|
|
316675
|
+
if (f2.layoutMode === "HORIZONTAL" || f2.layoutMode === "VERTICAL") {
|
|
316676
|
+
web.layout = {
|
|
316677
|
+
direction: f2.layoutMode === "HORIZONTAL" ? "row" : "column",
|
|
316678
|
+
gap: f2.itemSpacing ?? 0,
|
|
316679
|
+
justify: JUSTIFY[f2.primaryAxisAlignItems ?? "MIN"],
|
|
316680
|
+
align: ALIGN2[f2.counterAxisAlignItems ?? "MIN"],
|
|
316681
|
+
padding: f2.padding ?? { top: 0, right: 0, bottom: 0, left: 0 }
|
|
316682
|
+
};
|
|
316683
|
+
}
|
|
316684
|
+
if (node2.type === "TEXT") {
|
|
316685
|
+
const t3 = node2;
|
|
316686
|
+
const solid5 = (t3.fills ?? []).find((p2) => p2.visible !== false && p2.type === "SOLID" && p2.color);
|
|
316687
|
+
web.text = {
|
|
316688
|
+
characters: t3.characters ?? "",
|
|
316689
|
+
align: t3.textAlign,
|
|
316690
|
+
fontFamily: t3.fontFamily,
|
|
316691
|
+
fontSize: t3.fontSize,
|
|
316692
|
+
fontWeight: t3.fontWeight,
|
|
316693
|
+
italic: t3.fontStyle === "italic",
|
|
316694
|
+
...solid5?.color ? { color: toHex(solid5.color) } : {},
|
|
316695
|
+
...t3.letterSpacing ? { letterSpacing: t3.letterSpacing } : {},
|
|
316696
|
+
...t3.lineHeight !== "AUTO" ? { lineHeight: t3.lineHeight } : {}
|
|
316697
|
+
};
|
|
316698
|
+
const runs = textRuns(t3);
|
|
316699
|
+
if (runs) web.runs = runs;
|
|
316700
|
+
}
|
|
316701
|
+
const tl = timeline?.get(node2.id);
|
|
316702
|
+
const mo = tl ?? motion?.children.get(node2.id);
|
|
316703
|
+
if (mo) web.motion = { style: animationStyle(mo, tl ? "load" : motion.trigger), keyframes: keyframesCSS(mo) };
|
|
316704
|
+
const ext = getNativeExtension(raw.type);
|
|
316705
|
+
if (ext?.toWeb) {
|
|
316706
|
+
const said = ext.toWeb(node2, { escape: escapeHTML, color: (c2) => toRgba({ ...c2, a: c2.a ?? 1 }) });
|
|
316707
|
+
if (said.tag) web.tag = said.tag;
|
|
316708
|
+
Object.assign(style, said.style);
|
|
316709
|
+
web.html = said.html;
|
|
316710
|
+
hooks.built?.(web, node2, { parent, in3D: in3D2, fold });
|
|
316711
|
+
return web;
|
|
316712
|
+
}
|
|
316713
|
+
const code = opts.target === "site" ? codeOf(doc2.nodes, raw) : null;
|
|
316714
|
+
if (code && doc2.codeModules?.[code.moduleId]) {
|
|
316715
|
+
for (const k2 of PAINTED) delete style[k2];
|
|
316716
|
+
web.code = { module: code.moduleId, ...code.exportName ? { export: code.exportName } : {}, props: codeProps(doc2.nodes, node2) };
|
|
316717
|
+
hooks.built?.(web, node2, { parent, in3D: in3D2, fold });
|
|
316718
|
+
return web;
|
|
316719
|
+
}
|
|
316720
|
+
const sprite = opts.target === "site" && raw.type === "INSTANCE" && !raw.id.includes("::") && spriteOnly(doc2.nodes, raw.id) && isLive(doc2.nodes, raw.id);
|
|
316721
|
+
if (!exp.css || sprite) {
|
|
316722
|
+
for (const k2 of PAINTED) delete style[k2];
|
|
316723
|
+
web.asset = { kind: opts.assetKind ?? (exp.needsRaster ? "png" : "svg"), reason: exp.reason || (sprite ? "an animated sprite" : ""), ...item?.suffix ? { of: node2.id } : {} };
|
|
316724
|
+
if (isPixelArt(doc2, raw.id)) style["image-rendering"] = "pixelated";
|
|
316725
|
+
if (sprite || opts.target === "site" && renderMode(node2, { styles: doc2.styles, live: isLive(doc2.nodes, raw.id) }) === "island") web.island = true;
|
|
316726
|
+
hooks.built?.(web, node2, { parent, in3D: in3D2, fold });
|
|
316727
|
+
return web;
|
|
316728
|
+
}
|
|
316729
|
+
const lost = capability(node2, "css", doc2.styles).dropped.find((f3) => f3.startsWith("paint:"));
|
|
316730
|
+
if (lost && !node2.id.includes("::")) {
|
|
316731
|
+
const site = opts.target === "site";
|
|
316732
|
+
style.isolation = "isolate";
|
|
316733
|
+
web.children.push({
|
|
316734
|
+
id: `${node2.id}/backdrop${item?.suffix ?? ""}`,
|
|
316735
|
+
name: `${web.name} fill`,
|
|
316736
|
+
type: "BACKDROP",
|
|
316737
|
+
x: 0,
|
|
316738
|
+
y: 0,
|
|
316739
|
+
width: web.width,
|
|
316740
|
+
height: web.height,
|
|
316741
|
+
positioning: "absolute",
|
|
316742
|
+
...site ? { place: { position: "absolute", inset: "0" } } : {},
|
|
316743
|
+
style: { ...site ? {} : { width: `${web.width}px`, height: `${web.height}px` }, "border-radius": "inherit", overflow: "hidden", "z-index": "-1", "pointer-events": "none" },
|
|
316744
|
+
alt: "",
|
|
316745
|
+
asset: { kind: "png", reason: featureName(lost), of: node2.id, self: true },
|
|
316746
|
+
...site && movesItself(raw) ? { island: true } : {},
|
|
316747
|
+
children: []
|
|
316748
|
+
});
|
|
316749
|
+
}
|
|
316750
|
+
const outer = motion;
|
|
316751
|
+
if (!motion && node2.type === "INSTANCE" && !opts.static) {
|
|
316752
|
+
motion = instanceWebMotion(doc2, node2, (n) => stylesOf(prepared(n, doc2)));
|
|
316753
|
+
if (motion && (motion.trigger !== "load" || opts.target === "site")) web.motionTrigger = motion.trigger;
|
|
316754
|
+
}
|
|
316755
|
+
try {
|
|
316756
|
+
if (opts.includeChildren !== false) {
|
|
316757
|
+
const kids3D = in3D2 ? through : is3DContext(raw) && !raw.id.includes("::");
|
|
316758
|
+
const kidFold = through ? fold + 1 : 0;
|
|
316759
|
+
const repeat = raw.repeat;
|
|
316760
|
+
const collection = repeat && doc2.collections?.[repeat.collectionId];
|
|
316761
|
+
if (repeat && collection && opts.target === "site") {
|
|
316762
|
+
const outerItem = item;
|
|
316763
|
+
const under = outerItem ? scopeOf2(outerItem) : withData(variablesScope(doc2.variables, doc2.variableCollections, doc2.activeVariableModes), doc2);
|
|
316764
|
+
try {
|
|
316765
|
+
for (const record2 of repeatRecords(doc2, repeat, under)) {
|
|
316766
|
+
item = { collection, record: record2, suffix: `${outerItem?.suffix ?? ""}~${record2.id}` };
|
|
316767
|
+
for (const child of childrenOf(node2, doc2.nodes)) {
|
|
316768
|
+
const built = build3(child, node2, kids3D, kidFold);
|
|
316769
|
+
if (built) web.children.push(built);
|
|
316770
|
+
}
|
|
316771
|
+
}
|
|
316772
|
+
if (collection.perVisitor && !outerItem || collection.schema && opts.listTemplates) {
|
|
316773
|
+
item = { collection, record: templateRecord(collection), suffix: `~${ITEM_RECORD}` };
|
|
316774
|
+
const template2 = [];
|
|
316775
|
+
for (const child of childrenOf(node2, doc2.nodes)) {
|
|
316776
|
+
const built = build3(child, node2, kids3D, kidFold);
|
|
316777
|
+
if (built) template2.push(built);
|
|
316778
|
+
}
|
|
316779
|
+
const sortField = repeat.sort && collection.fields.find((f3) => f3.id === repeat.sort.fieldId);
|
|
316780
|
+
web.repeat = {
|
|
316781
|
+
collectionId: collection.id,
|
|
316782
|
+
template: template2,
|
|
316783
|
+
...repeat.filter?.trim() ? { filter: repeat.filter } : {},
|
|
316784
|
+
...sortField ? { sort: { key: fieldKey(sortField.name), dir: repeat.sort.dir } } : {},
|
|
316785
|
+
...repeat.offset ? { offset: repeat.offset } : {},
|
|
316786
|
+
...repeat.limit ? { limit: repeat.limit } : {}
|
|
316787
|
+
};
|
|
316788
|
+
}
|
|
316789
|
+
} finally {
|
|
316790
|
+
item = outerItem;
|
|
316791
|
+
}
|
|
316792
|
+
} else for (const child of childrenOf(node2, doc2.nodes)) {
|
|
316793
|
+
const built = build3(child, node2, kids3D, kidFold);
|
|
316794
|
+
if (built) web.children.push(built);
|
|
316795
|
+
}
|
|
316796
|
+
}
|
|
316797
|
+
} finally {
|
|
316798
|
+
motion = outer;
|
|
316799
|
+
}
|
|
316800
|
+
if (web.children.some((c2) => c2.positioning === "absolute")) {
|
|
316801
|
+
for (const c2 of web.children) if (c2.positioning === "flow") c2.layered = true;
|
|
316802
|
+
}
|
|
316803
|
+
hooks.built?.(web, node2, { parent, in3D: in3D2, fold });
|
|
316804
|
+
return web;
|
|
316805
|
+
};
|
|
316806
|
+
const root2 = build3(first2, start2?.parent ?? null, start2?.in3D ?? false, start2?.fold ?? 0);
|
|
316807
|
+
if (!root2) throw new Error("Node cap of 0");
|
|
316808
|
+
return { root: root2, truncated, ...folds ? { rules: foldRules(folds) } : {}, ...tokens?.vars.length ? { tokens } : {} };
|
|
316809
|
+
}
|
|
316810
|
+
function childLookup(doc2, id3) {
|
|
316811
|
+
const at3 = id3.lastIndexOf("::");
|
|
316812
|
+
const host = at3 > 0 ? id3.slice(0, at3) : "";
|
|
316813
|
+
const hostNode = doc2.nodes[host] ?? (host.includes("::") ? childLookup(doc2, host) : void 0);
|
|
316814
|
+
return hostNode ? childrenOf(hostNode, doc2.nodes).find((c2) => c2.id === id3) : void 0;
|
|
316815
|
+
}
|
|
316816
|
+
function flatten2(node2, out = []) {
|
|
316817
|
+
out.push(node2);
|
|
316818
|
+
for (const c2 of node2.children) flatten2(c2, out);
|
|
316819
|
+
return out;
|
|
316820
|
+
}
|
|
316821
|
+
var DEFAULT_NODE_CAP, EXPORT_NODE_CAP, PAINTED, anchorMemo, followsVisibility, isFlex, round3, foldVar, foldRules, clickable;
|
|
316822
|
+
var init_tree = __esm({
|
|
316823
|
+
"lib/io/web/tree.ts"() {
|
|
316824
|
+
"use strict";
|
|
316825
|
+
init_pixel_art();
|
|
316826
|
+
init_instance_layout();
|
|
316827
|
+
init_text_styles();
|
|
316828
|
+
init_variables();
|
|
316829
|
+
init_scene3d();
|
|
316830
|
+
init_semantics();
|
|
316831
|
+
init_commerce();
|
|
316832
|
+
init_collections();
|
|
316833
|
+
init_props();
|
|
316834
|
+
init_native_registry();
|
|
316835
|
+
init_controls();
|
|
316836
|
+
init_expressions2();
|
|
316837
|
+
init_children();
|
|
316838
|
+
init_css();
|
|
316839
|
+
init_capability();
|
|
316840
|
+
init_expressible();
|
|
316841
|
+
init_motion();
|
|
316842
|
+
init_element();
|
|
316843
|
+
init_paint2();
|
|
316844
|
+
init_responsive();
|
|
316845
|
+
init_richtext();
|
|
316846
|
+
init_tokens2();
|
|
316847
|
+
init_timeline();
|
|
316848
|
+
init_interactive();
|
|
316849
|
+
DEFAULT_NODE_CAP = 120;
|
|
316850
|
+
EXPORT_NODE_CAP = 2e4;
|
|
316851
|
+
PAINTED = ["background", "border", "border-style", "border-color", "border-width", "outline", "border-radius", "box-shadow", "box-sizing", "filter", "backdrop-filter"];
|
|
316852
|
+
anchorMemo = /* @__PURE__ */ new WeakMap();
|
|
316853
|
+
followsVisibility = (n) => !!n.boundVariables?.visible || !!n.boundExpressions?.visible || // Hidden in the design and shown at a breakpoint: on the page, for the media query that shows it.
|
|
316854
|
+
Object.values(n.responsive ?? {}).some((o) => o.visible === true) || // A game's win banner (LayerPhysics role 'win') and a player's run and jump poses: hidden in the design, shown by
|
|
316855
|
+
// the platformer on winning or as the player moves.
|
|
316856
|
+
n.physics?.role === "win" || n.physics?.role === "pose" || n.physics?.role === "reveal";
|
|
316857
|
+
isFlex = (f2) => f2?.layoutMode === "HORIZONTAL" || f2?.layoutMode === "VERTICAL";
|
|
316858
|
+
round3 = (v) => Math.round(v * 1e3) / 1e3;
|
|
316859
|
+
foldVar = (depth2) => `--pc-f${depth2}`;
|
|
316860
|
+
foldRules = (depth2) => Array.from({ length: depth2 }, (_, i2) => `@property ${foldVar(i2 + 1)} { syntax: '<number>'; inherits: true; initial-value: 1; }`);
|
|
316861
|
+
clickable = (n) => !!n.semantics?.link || (n.interactions ?? []).some((ix) => ix.trigger === "ON_CLICK" || ix.trigger === "ON_PRESS");
|
|
316862
|
+
}
|
|
316863
|
+
});
|
|
316864
|
+
|
|
315224
316865
|
// lib/io/zip-export.ts
|
|
315225
316866
|
var zip_export_exports = {};
|
|
315226
316867
|
__export(zip_export_exports, {
|
|
@@ -316232,7 +317873,7 @@ function stateMachineFromDotLottie(input2, id3 = "sm1", name2 = "State machine")
|
|
|
316232
317873
|
};
|
|
316233
317874
|
}
|
|
316234
317875
|
var INPUT_TYPES2, CONDITIONS, INTERACTIONS, invert2, isObj6, isValue2, DOT_INPUT_TYPES, DOT_CONDITIONS, DOT_INTERACTIONS;
|
|
316235
|
-
var
|
|
317876
|
+
var init_state_machine3 = __esm({
|
|
316236
317877
|
"lib/io/lottie/state-machine.ts"() {
|
|
316237
317878
|
"use strict";
|
|
316238
317879
|
init_state_machine();
|
|
@@ -316439,7 +318080,7 @@ var init_build = __esm({
|
|
|
316439
318080
|
init_channels();
|
|
316440
318081
|
init_ease();
|
|
316441
318082
|
init_shapes();
|
|
316442
|
-
|
|
318083
|
+
init_state_machine3();
|
|
316443
318084
|
BLEND2 = {
|
|
316444
318085
|
NORMAL: 0,
|
|
316445
318086
|
MULTIPLY: 1,
|
|
@@ -317313,7 +318954,7 @@ var init_lottie = __esm({
|
|
|
317313
318954
|
init_scene_graph();
|
|
317314
318955
|
init_png();
|
|
317315
318956
|
init_build();
|
|
317316
|
-
|
|
318957
|
+
init_state_machine3();
|
|
317317
318958
|
init_build();
|
|
317318
318959
|
init_support();
|
|
317319
318960
|
RASTER_SCALE = 2;
|
|
@@ -317458,112 +319099,6 @@ var init_data = __esm({
|
|
|
317458
319099
|
}
|
|
317459
319100
|
});
|
|
317460
319101
|
|
|
317461
|
-
// lib/io/web/element.ts
|
|
317462
|
-
function placementStyle(node2, isRoot) {
|
|
317463
|
-
if (node2.place) return { ...node2.place, ...node2.place.position ? {} : node2.layered || node2.children.some((c2) => c2.positioning === "absolute") ? { position: "relative" } : {} };
|
|
317464
|
-
const out = {};
|
|
317465
|
-
if (node2.positioning === "absolute" && !isRoot) {
|
|
317466
|
-
out.position = "absolute";
|
|
317467
|
-
out.left = `${node2.x}px`;
|
|
317468
|
-
out.top = `${node2.y}px`;
|
|
317469
|
-
} else if (node2.layered || node2.children.some((c2) => c2.positioning === "absolute") || isRoot) {
|
|
317470
|
-
out.position = "relative";
|
|
317471
|
-
}
|
|
317472
|
-
return out;
|
|
317473
|
-
}
|
|
317474
|
-
function imageRole(node2) {
|
|
317475
|
-
if (node2.asset || node2.text) return null;
|
|
317476
|
-
if (node2.type !== "IMAGE" && node2.alt === void 0) return null;
|
|
317477
|
-
return roleOf(node2);
|
|
317478
|
-
}
|
|
317479
|
-
function pictureOf(node2) {
|
|
317480
|
-
const a = node2.asset;
|
|
317481
|
-
if (!a) return null;
|
|
317482
|
-
if (a.src) return { kind: "img", src: a.src };
|
|
317483
|
-
if (a.svg) return { kind: "svg", svg: a.svg };
|
|
317484
|
-
if (a.pngDataUrl) return { kind: "img", src: a.pngDataUrl };
|
|
317485
|
-
return { kind: "missing", reason: a.reason, format: a.kind };
|
|
317486
|
-
}
|
|
317487
|
-
function elementOf(node2, ctx2) {
|
|
317488
|
-
const motion = ctx2.still ? void 0 : node2.motion;
|
|
317489
|
-
const spec = ctx2.spec ?? null;
|
|
317490
|
-
const tag = node2.input ? node2.input.tag : node2.link ? "a" : node2.tag ?? (node2.text ? "p" : "div");
|
|
317491
|
-
const attrs = { ...node2.attrs };
|
|
317492
|
-
if (node2.input) Object.assign(attrs, node2.input.attrs);
|
|
317493
|
-
if (node2.link && !node2.input) {
|
|
317494
|
-
attrs.href = node2.link.href;
|
|
317495
|
-
if (node2.link.newTab) {
|
|
317496
|
-
attrs.target = "_blank";
|
|
317497
|
-
attrs.rel = "noopener noreferrer";
|
|
317498
|
-
}
|
|
317499
|
-
}
|
|
317500
|
-
return {
|
|
317501
|
-
tag,
|
|
317502
|
-
attrs,
|
|
317503
|
-
// A tag's own look (a button's border, a link's underline, a list's bullets) is not the layer's: under its declarations.
|
|
317504
|
-
style: { ...node2.link || node2.tag || node2.input ? TAG_RESET[tag] : void 0, ...placementStyle(node2, ctx2.isRoot), ...node2.style, ...motion ? motion.style : {}, ...hiddenAtStart(spec, node2) ? HIDDEN_AT_START : {} },
|
|
317505
|
-
// A field's words are its placeholder (an attribute), not its content.
|
|
317506
|
-
...node2.text && !node2.input ? { text: node2.text.characters } : {},
|
|
317507
|
-
...node2.text && node2.runs && !node2.input ? { runs: node2.runs } : {},
|
|
317508
|
-
...node2.input ? { input: node2.input } : {},
|
|
317509
|
-
...node2.html !== void 0 ? { html: node2.html } : {},
|
|
317510
|
-
...node2.check ? { check: node2.check } : {},
|
|
317511
|
-
picture: pictureOf(node2),
|
|
317512
|
-
role: imageRole(node2),
|
|
317513
|
-
...motion ? { keyframes: motion.keyframes } : {},
|
|
317514
|
-
...node2.motionTrigger ? { motionTrigger: node2.motionTrigger } : {},
|
|
317515
|
-
...spec && node2.uid !== void 0 ? { pc: { uid: node2.uid, layer: node2.name } } : {},
|
|
317516
|
-
...ctx2.listened?.has(node2.id) ? { sm: node2.id } : {}
|
|
317517
|
-
};
|
|
317518
|
-
}
|
|
317519
|
-
var escapeHTML, altFor, roleOf, roleAttrs, labelSVG, imageRoleAttrs, hiddenAtStart, HIDDEN_AT_START, FIELD, HEADING, TAG_RESET, MOTION_PLAY_RULE, CHECK_STYLE;
|
|
317520
|
-
var init_element = __esm({
|
|
317521
|
-
"lib/io/web/element.ts"() {
|
|
317522
|
-
"use strict";
|
|
317523
|
-
escapeHTML = (s) => s.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").replace(/"/g, """);
|
|
317524
|
-
altFor = (node2) => node2.alt ?? node2.name;
|
|
317525
|
-
roleOf = (node2) => {
|
|
317526
|
-
const alt = altFor(node2);
|
|
317527
|
-
return alt === "" ? { hidden: true } : { label: alt };
|
|
317528
|
-
};
|
|
317529
|
-
roleAttrs = (role) => "hidden" in role ? ' aria-hidden="true"' : ` role="img" aria-label="${escapeHTML(role.label)}"`;
|
|
317530
|
-
labelSVG = (svg, node2) => svg.replace(/^<svg\b/, `<svg${roleAttrs(roleOf(node2))}`);
|
|
317531
|
-
imageRoleAttrs = (node2) => {
|
|
317532
|
-
const role = imageRole(node2);
|
|
317533
|
-
return role ? roleAttrs(role) : "";
|
|
317534
|
-
};
|
|
317535
|
-
hiddenAtStart = (spec, node2) => {
|
|
317536
|
-
const e = spec && node2.uid !== void 0 ? spec.e[node2.uid] : void 0;
|
|
317537
|
-
return !!e && e[1][spec.m[e[0]]] === -1;
|
|
317538
|
-
};
|
|
317539
|
-
HIDDEN_AT_START = { opacity: "0", visibility: "hidden", "pointer-events": "none", position: "absolute" };
|
|
317540
|
-
FIELD = { display: "block", border: "0", padding: "0", margin: "0", background: "none", outline: "none", font: "inherit", color: "inherit", "min-width": "0" };
|
|
317541
|
-
HEADING = { margin: "0", "font-size": "inherit", "font-weight": "inherit" };
|
|
317542
|
-
TAG_RESET = {
|
|
317543
|
-
a: { display: "block", color: "inherit", "text-decoration": "none" },
|
|
317544
|
-
button: { display: "block", border: "0", padding: "0", background: "none", font: "inherit", color: "inherit", "text-align": "inherit", cursor: "pointer" },
|
|
317545
|
-
ul: { "list-style": "none", margin: "0", padding: "0" },
|
|
317546
|
-
ol: { "list-style": "none", margin: "0", padding: "0" },
|
|
317547
|
-
h1: HEADING,
|
|
317548
|
-
h2: HEADING,
|
|
317549
|
-
h3: HEADING,
|
|
317550
|
-
h4: HEADING,
|
|
317551
|
-
h5: HEADING,
|
|
317552
|
-
h6: HEADING,
|
|
317553
|
-
p: { margin: "0" },
|
|
317554
|
-
figure: { margin: "0" },
|
|
317555
|
-
span: { display: "block" },
|
|
317556
|
-
label: { display: "block" },
|
|
317557
|
-
form: { margin: "0" },
|
|
317558
|
-
input: FIELD,
|
|
317559
|
-
textarea: { ...FIELD, resize: "none" },
|
|
317560
|
-
select: { ...FIELD, appearance: "none" }
|
|
317561
|
-
};
|
|
317562
|
-
MOTION_PLAY_RULE = "[data-motion-play] [data-motion-child] { animation-play-state: running; }";
|
|
317563
|
-
CHECK_STYLE = "position:absolute;inset:0;width:100%;height:100%;margin:0;opacity:0;cursor:pointer";
|
|
317564
|
-
}
|
|
317565
|
-
});
|
|
317566
|
-
|
|
317567
319102
|
// lib/io/web/fonts.ts
|
|
317568
319103
|
function fontFamilies(tree) {
|
|
317569
319104
|
const families = /* @__PURE__ */ new Map();
|
|
@@ -317586,392 +319121,6 @@ var init_fonts3 = __esm({
|
|
|
317586
319121
|
}
|
|
317587
319122
|
});
|
|
317588
319123
|
|
|
317589
|
-
// lib/io/web/paint.ts
|
|
317590
|
-
function toRgba(c2, a) {
|
|
317591
|
-
const alpha2 = a !== void 0 ? a : c2.a;
|
|
317592
|
-
const [r, g, b] = [c2.r, c2.g, c2.b].map((v) => Math.round(v * 255));
|
|
317593
|
-
return alpha2 < 1 ? `rgba(${r}, ${g}, ${b}, ${Math.round(alpha2 * 100) / 100})` : `rgb(${r}, ${g}, ${b})`;
|
|
317594
|
-
}
|
|
317595
|
-
function gradientAngleDeg(paint) {
|
|
317596
|
-
const h = paint.gradientHandlePositions;
|
|
317597
|
-
const p0 = h?.[0] ?? { x: 0, y: 0.5 };
|
|
317598
|
-
const p1 = h?.[1] ?? { x: 1, y: 0.5 };
|
|
317599
|
-
return Math.round(Math.atan2(p1.x - p0.x, -(p1.y - p0.y)) * 180 / Math.PI);
|
|
317600
|
-
}
|
|
317601
|
-
function paintToBackground(paint, opts = {}) {
|
|
317602
|
-
if (paint.type === "SOLID" && paint.color) {
|
|
317603
|
-
const alpha2 = (paint.opacity ?? 1) * paint.color.a;
|
|
317604
|
-
return alpha2 < 1 ? toRgba(paint.color, alpha2) : toHex(paint.color);
|
|
317605
|
-
}
|
|
317606
|
-
if (paint.type === "GRADIENT_LINEAR") return `linear-gradient(${gradientAngleDeg(paint)}deg, ${gradientStopsCSS(paint)})`;
|
|
317607
|
-
if (paint.type === "GRADIENT_RADIAL") return `radial-gradient(circle, ${gradientStopsCSS(paint)})`;
|
|
317608
|
-
if (paint.type === "GRADIENT_ANGULAR") return `conic-gradient(${gradientStopsCSS(paint)})`;
|
|
317609
|
-
if (paint.type === "GRADIENT_DIAMOND") return `radial-gradient(closest-side, ${gradientStopsCSS(paint)})`;
|
|
317610
|
-
if (paint.type === "IMAGE") {
|
|
317611
|
-
const src = paint.imageUrl || paint.imageHash;
|
|
317612
|
-
if (!src) return null;
|
|
317613
|
-
return `url('${opts.fullImageUrl || src.length <= 64 ? src : src.slice(0, 64)}') ${IMAGE_FIT[paint.scaleMode ?? "FILL"]}`;
|
|
317614
|
-
}
|
|
317615
|
-
return null;
|
|
317616
|
-
}
|
|
317617
|
-
function parseCssColor(css) {
|
|
317618
|
-
if (!css) return null;
|
|
317619
|
-
const hex10 = /^#([0-9a-f]{6})$/i.exec(css.trim());
|
|
317620
|
-
if (hex10) {
|
|
317621
|
-
const n = parseInt(hex10[1], 16);
|
|
317622
|
-
return { r: (n >> 16 & 255) / 255, g: (n >> 8 & 255) / 255, b: (n & 255) / 255, a: 1 };
|
|
317623
|
-
}
|
|
317624
|
-
const rgb = /^rgba?\(([^)]+)\)$/i.exec(css.trim());
|
|
317625
|
-
if (!rgb) return null;
|
|
317626
|
-
const parts = rgb[1].split(",").map((v) => Number(v.trim()));
|
|
317627
|
-
if (parts.length < 3 || parts.some((v) => Number.isNaN(v))) return null;
|
|
317628
|
-
return { r: parts[0] / 255, g: parts[1] / 255, b: parts[2] / 255, a: parts[3] ?? 1 };
|
|
317629
|
-
}
|
|
317630
|
-
var hex23, toHex, gradientStopsCSS, IMAGE_FIT, swiftColor, composeColor;
|
|
317631
|
-
var init_paint2 = __esm({
|
|
317632
|
-
"lib/io/web/paint.ts"() {
|
|
317633
|
-
"use strict";
|
|
317634
|
-
hex23 = (v) => Math.round(v * 255).toString(16).padStart(2, "0");
|
|
317635
|
-
toHex = (c2) => `#${hex23(c2.r)}${hex23(c2.g)}${hex23(c2.b)}`.toUpperCase();
|
|
317636
|
-
gradientStopsCSS = (paint) => (paint.gradientStops ?? []).map((s) => `${toRgba(s.color)} ${Math.round((s.position ?? 0) * 100)}%`).join(", ");
|
|
317637
|
-
IMAGE_FIT = {
|
|
317638
|
-
FILL: "center / cover no-repeat",
|
|
317639
|
-
CROP: "center / cover no-repeat",
|
|
317640
|
-
FIT: "center / contain no-repeat",
|
|
317641
|
-
TILE: "top left / auto repeat"
|
|
317642
|
-
};
|
|
317643
|
-
swiftColor = (c2) => {
|
|
317644
|
-
const n = (v) => Math.round(v * 1e3) / 1e3;
|
|
317645
|
-
return `Color(red: ${n(c2.r)}, green: ${n(c2.g)}, blue: ${n(c2.b)}${(c2.a ?? 1) < 1 ? `, opacity: ${Math.round((c2.a ?? 1) * 100) / 100}` : ""})`;
|
|
317646
|
-
};
|
|
317647
|
-
composeColor = (c2) => `Color(0x${[c2.a ?? 1, c2.r, c2.g, c2.b].map((v) => Math.round(v * 255).toString(16).padStart(2, "0")).join("").toUpperCase()})`;
|
|
317648
|
-
}
|
|
317649
|
-
});
|
|
317650
|
-
|
|
317651
|
-
// lib/io/web/css.ts
|
|
317652
|
-
function stylePaints(styleId, styles) {
|
|
317653
|
-
const s = styleId ? styles?.[styleId] : void 0;
|
|
317654
|
-
return s?.type === "PAINT" ? s.paints ?? [] : null;
|
|
317655
|
-
}
|
|
317656
|
-
function transformParts(node2, dx = 0, dy = 0) {
|
|
317657
|
-
return [
|
|
317658
|
-
dx + restValue(node2, "translateX"),
|
|
317659
|
-
dy + restValue(node2, "translateY"),
|
|
317660
|
-
restValue(node2, "z"),
|
|
317661
|
-
node2.rotation || 0,
|
|
317662
|
-
restValue(node2, "rotateY"),
|
|
317663
|
-
restValue(node2, "rotateX"),
|
|
317664
|
-
restValue(node2, "scaleX") * (node2.flipHorizontal ? -1 : 1),
|
|
317665
|
-
restValue(node2, "scaleY") * (node2.flipVertical ? -1 : 1)
|
|
317666
|
-
];
|
|
317667
|
-
}
|
|
317668
|
-
function transformFromParts(p2, orbit) {
|
|
317669
|
-
const [tx2, ty, z2, r, ry0, rx0, sx, sy] = p2;
|
|
317670
|
-
const ry = ry0 + (orbit?.rotateY ?? 0), rx = rx0 + (orbit?.rotateX ?? 0);
|
|
317671
|
-
const parts = [];
|
|
317672
|
-
if (tx2 || ty || z2) parts.push(z2 ? `translate3d(${round(tx2)}px, ${round(ty)}px, ${round(z2)}px)` : `translate(${round(tx2)}px, ${round(ty)}px)`);
|
|
317673
|
-
if (r) parts.push(`rotate(${round(r)}deg)`);
|
|
317674
|
-
if (ry) parts.push(`rotateY(${round(ry)}deg)`);
|
|
317675
|
-
if (rx) parts.push(`rotateX(${round(rx)}deg)`);
|
|
317676
|
-
if (sx !== 1 || sy !== 1) parts.push(`scale(${round(sx)}, ${round(sy)})`);
|
|
317677
|
-
return parts.length ? parts.join(" ") : void 0;
|
|
317678
|
-
}
|
|
317679
|
-
function styleMapFor(node2, styles, opts = {}) {
|
|
317680
|
-
const scene2 = node2;
|
|
317681
|
-
const out = {};
|
|
317682
|
-
out.width = `${Math.round(node2.width)}px`;
|
|
317683
|
-
out.height = `${Math.round(node2.height)}px`;
|
|
317684
|
-
const transform3 = transformCss(node2);
|
|
317685
|
-
if (transform3) out.transform = transform3;
|
|
317686
|
-
const ax = restValue(node2, "anchorX"), ay = restValue(node2, "anchorY");
|
|
317687
|
-
if (transform3 && (ax !== 0.5 || ay !== 0.5)) out["transform-origin"] = `${round(ax * 100)}% ${round(ay * 100)}%`;
|
|
317688
|
-
const scene3d = scene3dOf(node2);
|
|
317689
|
-
if (scene3d) {
|
|
317690
|
-
out.perspective = `${round(zoomPx(scene3d.camera.focalLength, node2.width))}px`;
|
|
317691
|
-
out["perspective-origin"] = `${round((scene3d.originX ?? 0.5) * 100)}% ${round((scene3d.originY ?? 0.5) * 100)}%`;
|
|
317692
|
-
out["transform-style"] = "preserve-3d";
|
|
317693
|
-
} else if (has3DPlacement(node2) && passesThrough(node2)) out["transform-style"] = "preserve-3d";
|
|
317694
|
-
if ((node2.opacity ?? 1) !== 1) out.opacity = String(round(node2.opacity ?? 1));
|
|
317695
|
-
const bm = node2.blendMode;
|
|
317696
|
-
if (bm && bm !== "NORMAL" && bm !== "PASS_THROUGH") out["mix-blend-mode"] = bm.toLowerCase().replace(/_/g, "-");
|
|
317697
|
-
const fills = visibleFills(node2, styles);
|
|
317698
|
-
const own2 = node2.type === "IMAGE" && node2.imageUrl ? [{ type: "IMAGE", imageUrl: node2.imageUrl, scaleMode: node2.scaleMode, visible: true }] : [];
|
|
317699
|
-
const painted = [...fills, ...own2];
|
|
317700
|
-
if (node2.type !== "TEXT" && painted.length) {
|
|
317701
|
-
const layers2 = painted.map((f2) => paintToBackground(f2, opts)).filter((l) => !!l);
|
|
317702
|
-
const over2 = (l) => /^(#|rgb)/.test(l) ? `linear-gradient(${l}, ${l})` : l;
|
|
317703
|
-
if (layers2.length) out.background = layers2.map((l, i2) => i2 === layers2.length - 1 ? l : over2(l)).join(", ");
|
|
317704
|
-
}
|
|
317705
|
-
const cr = scene2.cornerRadius;
|
|
317706
|
-
if (typeof cr === "number" && cr > 0) out["border-radius"] = `${cr}px`;
|
|
317707
|
-
else if (Array.isArray(cr) && cr.some((r) => r > 0)) out["border-radius"] = cr.map((r) => `${r}px`).join(" ");
|
|
317708
|
-
if (node2.type === "ELLIPSE") out["border-radius"] = "50%";
|
|
317709
|
-
const stroke3 = scene2.strokes?.[0];
|
|
317710
|
-
if (stroke3) {
|
|
317711
|
-
const color4 = toHex(stroke3.color);
|
|
317712
|
-
if (Array.isArray(stroke3.width)) {
|
|
317713
|
-
out["border-style"] = "solid";
|
|
317714
|
-
out["border-color"] = color4;
|
|
317715
|
-
out["border-width"] = stroke3.width.map((w) => `${w}px`).join(" ");
|
|
317716
|
-
} else if (stroke3.alignment === "OUTSIDE") {
|
|
317717
|
-
out.outline = `${stroke3.width}px solid ${color4}`;
|
|
317718
|
-
} else {
|
|
317719
|
-
out.border = `${stroke3.width}px ${stroke3.dashPattern?.length ? "dashed" : "solid"} ${color4}`;
|
|
317720
|
-
if (stroke3.alignment === "INSIDE") out["box-sizing"] = "border-box";
|
|
317721
|
-
}
|
|
317722
|
-
}
|
|
317723
|
-
const shadows = shadowsOf(node2, styles).filter((s) => s.visible);
|
|
317724
|
-
if (node2.type === "TEXT") {
|
|
317725
|
-
const drops = shadows.filter((s) => s.type === "DROP_SHADOW");
|
|
317726
|
-
if (drops.length) out["text-shadow"] = drops.map((s) => `${s.offset.x}px ${s.offset.y}px ${s.blur}px ${toRgba(s.color)}`).join(", ");
|
|
317727
|
-
} else if (shadows.length) {
|
|
317728
|
-
out["box-shadow"] = shadows.map((s) => `${s.type === "INNER_SHADOW" ? "inset " : ""}${s.offset.x}px ${s.offset.y}px ${s.blur}px ${s.spread}px ${toRgba(s.color)}`).join(", ");
|
|
317729
|
-
}
|
|
317730
|
-
const blurs = blursOf(node2, styles);
|
|
317731
|
-
const layer2 = blurs.find((b) => b.type === "LAYER");
|
|
317732
|
-
const backdrop = blurs.find((b) => b.type === "BACKGROUND");
|
|
317733
|
-
if (layer2) out.filter = `blur(${layer2.radius}px)`;
|
|
317734
|
-
if (backdrop) out["backdrop-filter"] = `blur(${backdrop.radius}px)`;
|
|
317735
|
-
if (node2.type === "FRAME" || node2.type === "COMPONENT" || node2.type === "INSTANCE") {
|
|
317736
|
-
const f2 = node2;
|
|
317737
|
-
Object.assign(out, flexDeclarations(f2));
|
|
317738
|
-
if (f2.clipsContent) out.overflow = "hidden";
|
|
317739
|
-
}
|
|
317740
|
-
if (node2.type === "TEXT") {
|
|
317741
|
-
const t3 = node2;
|
|
317742
|
-
const tFills = visibleFills(t3, styles);
|
|
317743
|
-
out.margin = "0";
|
|
317744
|
-
if (t3.textAutoResize === "WIDTH_AND_HEIGHT") {
|
|
317745
|
-
out.width = "max-content";
|
|
317746
|
-
out.height = "auto";
|
|
317747
|
-
out["white-space"] = "pre";
|
|
317748
|
-
} else if (t3.textAutoResize === "HEIGHT") out.height = "auto";
|
|
317749
|
-
out["font-family"] = `"${t3.fontFamily}", system-ui, sans-serif`;
|
|
317750
|
-
out["font-size"] = `${t3.fontSize}px`;
|
|
317751
|
-
out["font-weight"] = String(t3.fontWeight);
|
|
317752
|
-
if (t3.fontStyle === "italic") out["font-style"] = "italic";
|
|
317753
|
-
out["line-height"] = t3.lineHeight === "AUTO" ? "normal" : `${t3.lineHeight}px`;
|
|
317754
|
-
if (t3.letterSpacing) out["letter-spacing"] = `${t3.letterSpacing}px`;
|
|
317755
|
-
out["text-align"] = t3.textAlign.toLowerCase();
|
|
317756
|
-
if (t3.textDecoration === "UNDERLINE") out["text-decoration"] = "underline";
|
|
317757
|
-
else if (t3.textDecoration === "STRIKETHROUGH") out["text-decoration"] = "line-through";
|
|
317758
|
-
const tc = t3.textCase;
|
|
317759
|
-
if (tc === "UPPER") out["text-transform"] = "uppercase";
|
|
317760
|
-
else if (tc === "LOWER") out["text-transform"] = "lowercase";
|
|
317761
|
-
else if (tc === "TITLE") out["text-transform"] = "capitalize";
|
|
317762
|
-
const solid5 = tFills.find((f2) => f2.type === "SOLID" && f2.color);
|
|
317763
|
-
if (solid5?.color) out.color = toHex(solid5.color);
|
|
317764
|
-
const grad = tFills.find((f2) => f2.type !== "SOLID");
|
|
317765
|
-
const g = grad ? paintToBackground(grad) : null;
|
|
317766
|
-
if (g) {
|
|
317767
|
-
out.background = g;
|
|
317768
|
-
out["-webkit-background-clip"] = "text";
|
|
317769
|
-
out.color = "transparent";
|
|
317770
|
-
}
|
|
317771
|
-
}
|
|
317772
|
-
return out;
|
|
317773
|
-
}
|
|
317774
|
-
function flexDeclarations(f2) {
|
|
317775
|
-
const out = {};
|
|
317776
|
-
if (f2.layoutMode !== "HORIZONTAL" && f2.layoutMode !== "VERTICAL") return out;
|
|
317777
|
-
out.display = "flex";
|
|
317778
|
-
out["flex-direction"] = f2.layoutMode === "HORIZONTAL" ? "row" : "column";
|
|
317779
|
-
const justify = JUSTIFY[f2.primaryAxisAlignItems ?? "MIN"];
|
|
317780
|
-
const align4 = ALIGN2[f2.counterAxisAlignItems ?? "MIN"];
|
|
317781
|
-
if (justify !== "flex-start") out["justify-content"] = justify;
|
|
317782
|
-
if (align4 !== "flex-start") out["align-items"] = align4;
|
|
317783
|
-
out.gap = `${f2.itemSpacing ?? 0}px`;
|
|
317784
|
-
if (f2.padding) {
|
|
317785
|
-
out.padding = `${f2.padding.top}px ${f2.padding.right}px ${f2.padding.bottom}px ${f2.padding.left}px`;
|
|
317786
|
-
if (f2.padding.top || f2.padding.right || f2.padding.bottom || f2.padding.left) out["box-sizing"] = "border-box";
|
|
317787
|
-
}
|
|
317788
|
-
return out;
|
|
317789
|
-
}
|
|
317790
|
-
var visibleFills, round, transformCss, JUSTIFY, ALIGN2, styleMapToCSSText, styleMapToInline, camel2, styleMapToJSX;
|
|
317791
|
-
var init_css = __esm({
|
|
317792
|
-
"lib/io/web/css.ts"() {
|
|
317793
|
-
"use strict";
|
|
317794
|
-
init_effects();
|
|
317795
|
-
init_paint2();
|
|
317796
|
-
init_scene3d();
|
|
317797
|
-
init_transform3d();
|
|
317798
|
-
init_transform();
|
|
317799
|
-
visibleFills = (node2, styles) => (stylePaints(node2.fillStyleId, styles) ?? node2.fills ?? []).filter((f2) => f2.visible !== false);
|
|
317800
|
-
round = (v) => Math.round(v * 100) / 100;
|
|
317801
|
-
transformCss = (node2) => transformFromParts(transformParts(node2));
|
|
317802
|
-
JUSTIFY = { MIN: "flex-start", MAX: "flex-end", CENTER: "center", SPACE_BETWEEN: "space-between" };
|
|
317803
|
-
ALIGN2 = { MIN: "flex-start", MAX: "flex-end", CENTER: "center", BASELINE: "baseline" };
|
|
317804
|
-
styleMapToCSSText = (m, indent = "") => Object.entries(m).map(([k2, v]) => `${indent}${k2}: ${v};`).join("\n");
|
|
317805
|
-
styleMapToInline = (m) => Object.entries(m).map(([k2, v]) => `${k2}:${v}`).join(";");
|
|
317806
|
-
camel2 = (k2) => k2.startsWith("--") ? k2 : (k2.startsWith("-") ? k2.replace(/^-/, "Webkit").replace(/-webkit-/i, "") : k2).replace(/-([a-z])/g, (_, c2) => c2.toUpperCase());
|
|
317807
|
-
styleMapToJSX = (m) => Object.entries(m).map(([k2, v]) => [camel2(k2), v.replace(/'/g, "\\'")]);
|
|
317808
|
-
}
|
|
317809
|
-
});
|
|
317810
|
-
|
|
317811
|
-
// lib/io/web/keyframes.ts
|
|
317812
|
-
function transformOf(n, rest) {
|
|
317813
|
-
return transformFromParts(transformParts(n, n.x - rest.x, n.y - rest.y)) ?? "none";
|
|
317814
|
-
}
|
|
317815
|
-
function declarationsOf(node2, rest, style) {
|
|
317816
|
-
return { ...style(node2), transform: transformOf(node2, rest), opacity: String(round2(node2.visible === false ? 0 : node2.opacity ?? 1)) };
|
|
317817
|
-
}
|
|
317818
|
-
function vectorOf(style, keys4) {
|
|
317819
|
-
const text = keys4.map((k2) => `${k2}:${style[k2] ?? ""}`).join(";");
|
|
317820
|
-
return { shape: text.replace(NUMBER2, "#"), v: (text.match(NUMBER2) ?? []).map(Number) };
|
|
317821
|
-
}
|
|
317822
|
-
function thinSamples(times2, samples, tol, pinned = []) {
|
|
317823
|
-
const n = samples.length;
|
|
317824
|
-
if (n <= 2) return samples.map((_, i2) => i2);
|
|
317825
|
-
const keep = /* @__PURE__ */ new Set([0, n - 1, ...pinned]);
|
|
317826
|
-
for (let i2 = 1; i2 < n; i2++) if (samples[i2].shape !== samples[i2 - 1].shape) {
|
|
317827
|
-
keep.add(i2 - 1);
|
|
317828
|
-
keep.add(i2);
|
|
317829
|
-
}
|
|
317830
|
-
const sorted = () => [...keep].sort((a, b) => a - b);
|
|
317831
|
-
const stack = [];
|
|
317832
|
-
const kept = sorted();
|
|
317833
|
-
for (let i2 = 1; i2 < kept.length; i2++) stack.push([kept[i2 - 1], kept[i2]]);
|
|
317834
|
-
while (stack.length) {
|
|
317835
|
-
const [a, b] = stack.pop();
|
|
317836
|
-
if (b - a < 2 || samples[a].shape !== samples[b].shape) continue;
|
|
317837
|
-
let worst2 = -1, at3 = -1;
|
|
317838
|
-
for (let i2 = a + 1; i2 < b; i2++) {
|
|
317839
|
-
const k2 = (times2[i2] - times2[a]) / (times2[b] - times2[a] || 1);
|
|
317840
|
-
let err2 = 0;
|
|
317841
|
-
samples[i2].v.forEach((x2, d) => {
|
|
317842
|
-
const want = samples[a].v[d] + (samples[b].v[d] - samples[a].v[d]) * k2;
|
|
317843
|
-
err2 = Math.max(err2, Math.abs(x2 - want) / tol[d]);
|
|
317844
|
-
});
|
|
317845
|
-
if (err2 > worst2) {
|
|
317846
|
-
worst2 = err2;
|
|
317847
|
-
at3 = i2;
|
|
317848
|
-
}
|
|
317849
|
-
}
|
|
317850
|
-
if (worst2 > 1) {
|
|
317851
|
-
keep.add(at3);
|
|
317852
|
-
stack.push([a, at3], [at3, b]);
|
|
317853
|
-
}
|
|
317854
|
-
}
|
|
317855
|
-
return sorted();
|
|
317856
|
-
}
|
|
317857
|
-
function keyframesOf(times2, samples, length2) {
|
|
317858
|
-
const keys4 = [...new Set(samples.flatMap((s) => Object.keys(s)))].filter((k2) => !FIXED.has(k2));
|
|
317859
|
-
const moving = keys4.filter((k2) => samples.some((s) => s[k2] !== samples[0][k2]));
|
|
317860
|
-
if (!moving.length) return null;
|
|
317861
|
-
const vectors = samples.map((s) => vectorOf(s, moving));
|
|
317862
|
-
const dims = Math.max(...vectors.map((v) => v.v.length));
|
|
317863
|
-
const range3 = Array.from({ length: dims }, (_, d) => {
|
|
317864
|
-
let lo = Infinity, hi = -Infinity;
|
|
317865
|
-
for (const v of vectors) if (d < v.v.length) {
|
|
317866
|
-
lo = Math.min(lo, v.v[d]);
|
|
317867
|
-
hi = Math.max(hi, v.v[d]);
|
|
317868
|
-
}
|
|
317869
|
-
return hi > lo ? hi - lo : 0;
|
|
317870
|
-
});
|
|
317871
|
-
const tol = range3.map((r) => Math.max(1e-3, r * 3e-3));
|
|
317872
|
-
const same5 = (a, b) => vectors[a].shape === vectors[b].shape && vectors[a].v.every((x2, d) => Math.abs(x2 - vectors[b].v[d]) <= tol[d]);
|
|
317873
|
-
const jumps = /* @__PURE__ */ new Set();
|
|
317874
|
-
for (let i2 = 1; i2 < samples.length; i2++) {
|
|
317875
|
-
if (same5(i2 - 1, i2)) continue;
|
|
317876
|
-
const stillBefore = i2 >= 2 && same5(i2 - 2, i2 - 1);
|
|
317877
|
-
if (!stillBefore) continue;
|
|
317878
|
-
const words = vectors[i2].shape !== vectors[i2 - 1].shape;
|
|
317879
|
-
const far = !words && vectors[i2].v.some((x2, d) => range3[d] > 0 && Math.abs(x2 - vectors[i2 - 1].v[d]) > range3[d] * 0.2);
|
|
317880
|
-
if (words || far) jumps.add(i2);
|
|
317881
|
-
}
|
|
317882
|
-
const kept = thinSamples(times2, vectors, tol, [...jumps].flatMap((i2) => [i2 - 1, i2]));
|
|
317883
|
-
return kept.map((i2) => {
|
|
317884
|
-
const style = {};
|
|
317885
|
-
for (const k2 of moving) if (samples[i2][k2] !== void 0) style[k2] = samples[i2][k2];
|
|
317886
|
-
return { offset: pct(times2[i2] / (length2 || 1)), style, ...jumps.has(i2 + 1) ? { step: true } : {} };
|
|
317887
|
-
});
|
|
317888
|
-
}
|
|
317889
|
-
var SAMPLE_RATE, round2, pct, FIXED, NUMBER2;
|
|
317890
|
-
var init_keyframes = __esm({
|
|
317891
|
-
"lib/io/web/keyframes.ts"() {
|
|
317892
|
-
"use strict";
|
|
317893
|
-
init_css();
|
|
317894
|
-
SAMPLE_RATE = 30;
|
|
317895
|
-
round2 = (v) => Math.round(v * 1e3) / 1e3;
|
|
317896
|
-
pct = (k2) => Math.round(k2 * 1e5) / 1e3;
|
|
317897
|
-
FIXED = /* @__PURE__ */ new Set(["position", "display", "left", "top", "right", "bottom", "inset", "animation", "animation-play-state", "transform-origin", "transform-style", "box-sizing", "isolation", "z-index"]);
|
|
317898
|
-
NUMBER2 = /-?\d+(?:\.\d+)?(?:e-?\d+)?/g;
|
|
317899
|
-
}
|
|
317900
|
-
});
|
|
317901
|
-
|
|
317902
|
-
// lib/io/web/motion.ts
|
|
317903
|
-
function instanceWebMotion(doc2, instance, style) {
|
|
317904
|
-
const comp = instance.mainComponentId;
|
|
317905
|
-
if (!comp || !isMotionComponent(doc2.nodes, comp)) return null;
|
|
317906
|
-
const m = playbackOf(doc2.nodes, instance, comp);
|
|
317907
|
-
const [a, b] = m.range;
|
|
317908
|
-
const len3 = b - a;
|
|
317909
|
-
if (len3 <= 0) return null;
|
|
317910
|
-
const steps = Math.max(1, Math.ceil(len3 / 1e3 * SAMPLE_RATE));
|
|
317911
|
-
const times2 = Array.from({ length: steps + 1 }, (_, i2) => len3 * i2 / steps);
|
|
317912
|
-
const samples = [];
|
|
317913
|
-
for (let i2 = 0; i2 <= steps; i2++) samples.push(instancePoseAt(doc2.nodes, instance.id, a + len3 * i2 / steps));
|
|
317914
|
-
const ids2 = /* @__PURE__ */ new Set();
|
|
317915
|
-
for (const s of samples) for (const id3 in s) if (id3.includes("::")) ids2.add(id3);
|
|
317916
|
-
const children = /* @__PURE__ */ new Map();
|
|
317917
|
-
const tag = instance.id.replace(/[^a-zA-Z0-9]/g, "").slice(-6);
|
|
317918
|
-
let n = 0;
|
|
317919
|
-
for (const id3 of ids2) {
|
|
317920
|
-
const restNode = resolveVirtualNode2(doc2.nodes, id3);
|
|
317921
|
-
if (!restNode) continue;
|
|
317922
|
-
const frames = keyframesOf(times2, samples.map((s) => declarationsOf(s[id3] ?? restNode, restNode, style)), len3);
|
|
317923
|
-
if (!frames) continue;
|
|
317924
|
-
children.set(id3, {
|
|
317925
|
-
name: `motion-${tag}-${n++}`,
|
|
317926
|
-
frames,
|
|
317927
|
-
durationMs: m.speed > 0 ? Math.round(len3 / m.speed) : 0,
|
|
317928
|
-
delayMs: Math.round(m.start),
|
|
317929
|
-
iterations: m.loop === "none" ? 1 : "infinite",
|
|
317930
|
-
direction: m.loop === "pingpong" ? "alternate" : "normal",
|
|
317931
|
-
fill: m.hold === "first" ? "backwards" : "both"
|
|
317932
|
-
});
|
|
317933
|
-
}
|
|
317934
|
-
return children.size ? { trigger: m.trigger, children } : null;
|
|
317935
|
-
}
|
|
317936
|
-
function animationStyle(mo, trigger) {
|
|
317937
|
-
const out = { animation: `${mo.name} ${mo.durationMs}ms linear ${mo.delayMs}ms ${mo.iterations} ${mo.direction} ${mo.fill}` };
|
|
317938
|
-
if (trigger !== "load") out["animation-play-state"] = "paused";
|
|
317939
|
-
return out;
|
|
317940
|
-
}
|
|
317941
|
-
var keyframesCSS, MOTION_SCRIPT;
|
|
317942
|
-
var init_motion = __esm({
|
|
317943
|
-
"lib/io/web/motion.ts"() {
|
|
317944
|
-
"use strict";
|
|
317945
|
-
init_scene_graph();
|
|
317946
|
-
init_instances2();
|
|
317947
|
-
init_keyframes();
|
|
317948
|
-
init_keyframes();
|
|
317949
|
-
init_element();
|
|
317950
|
-
keyframesCSS = (mo) => `@keyframes ${mo.name} {
|
|
317951
|
-
${mo.frames.map((f2) => ` ${f2.offset}% { ${Object.entries(f2.style).map(([k2, v]) => `${k2}: ${v};`).join(" ")}${f2.step ? " animation-timing-function: step-end;" : ""} }`).join("\n")}
|
|
317952
|
-
}`;
|
|
317953
|
-
MOTION_SCRIPT = `(function () {
|
|
317954
|
-
var play = function (el) { el.setAttribute('data-motion-play', '') };
|
|
317955
|
-
document.querySelectorAll('[data-motion="click"]').forEach(function (el) { el.addEventListener('click', function () { play(el) }) });
|
|
317956
|
-
document.querySelectorAll('[data-motion="hover"]').forEach(function (el) { el.addEventListener('mouseenter', function () { play(el) }) });
|
|
317957
|
-
var seen = document.querySelectorAll('[data-motion="inView"]');
|
|
317958
|
-
if (!('IntersectionObserver' in window)) { seen.forEach(play); return }
|
|
317959
|
-
var io = new IntersectionObserver(function (entries) { entries.forEach(function (e) { if (e.isIntersecting) { play(e.target); io.unobserve(e.target) } }) }, { threshold: 0.25 });
|
|
317960
|
-
seen.forEach(function (el) { io.observe(el) });
|
|
317961
|
-
})();`;
|
|
317962
|
-
}
|
|
317963
|
-
});
|
|
317964
|
-
|
|
317965
|
-
// lib/io/web/generated/runtimes.ts
|
|
317966
|
-
var PROTOTYPE_JS, MACHINE_JS;
|
|
317967
|
-
var init_runtimes = __esm({
|
|
317968
|
-
"lib/io/web/generated/runtimes.ts"() {
|
|
317969
|
-
"use strict";
|
|
317970
|
-
PROTOTYPE_JS = 'function popcraftMount(root, spec) {\n var els = {}, state = {}, owned = {}, orbit = {}, last = {}, holds = {}, hist = [], timers = [];\n var nodes = [root].concat(Array.prototype.slice.call(root.querySelectorAll("[data-pc]")));\n nodes.forEach(function(el) {\n els[el.getAttribute("data-pc")] = el;\n });\n for (var m in spec.m) state[m] = spec.m[m];\n for (var u in spec.e) (owned[spec.e[u][0]] = owned[spec.e[u][0]] || []).push(u);\n var drags = {}, clicks = {};\n spec.on.forEach(function(o) {\n if (o[3] === "drag") drags[o[0]] = 1;\n if (o[3] === "click" || o[3] === "press") clicks[o[0]] = 1;\n });\n function lookIn(u2, st) {\n var e = spec.e[u2];\n if (!e) return -2;\n var i = e[1][st === void 0 ? state[e[0]] : st];\n return i === void 0 ? -1 : i;\n }\n function tf(f, o) {\n var ry = f[4] + (o ? o.ry : 0), rx = f[5] + (o ? o.rx : 0), p = [];\n if (f[0] || f[1] || f[2]) p.push(f[2] ? "translate3d(" + f[0] + "px, " + f[1] + "px, " + f[2] + "px)" : "translate(" + f[0] + "px, " + f[1] + "px)");\n if (f[3]) p.push("rotate(" + f[3] + "deg)");\n if (ry) p.push("rotateY(" + ry + "deg)");\n if (rx) p.push("rotateX(" + rx + "deg)");\n if (f[6] !== 1 || f[7] !== 1) p.push("scale(" + f[6] + ", " + f[7] + ")");\n return p.length ? p.join(" ") : "none";\n }\n function css(u2, i) {\n var L = spec.L[i], c = L[0];\n if (orbit[u2] && L[2]) c += ";transform:" + tf(L[2], orbit[u2]);\n if (drags[u2]) c += ";touch-action:none;user-select:none;-webkit-user-select:none";\n if (clicks[u2]) c += ";cursor:pointer";\n return c;\n }\n var HIDE = ";opacity:0;visibility:hidden;pointer-events:none;position:absolute";\n function set(u2, ms, ez) {\n var el = els[u2], i = lookIn(u2, void 0);\n if (!el || i === -2) return;\n var tr = ms ? ";transition:all " + ms + "ms " + ez : ";transition:none";\n if (i < 0) {\n el.style.cssText = (last[u2] || "") + HIDE + tr;\n return;\n }\n var c = css(u2, i), text = spec.L[i][1];\n if (text !== null && el.textContent !== text) el.textContent = text;\n if (ms && el.style.visibility === "hidden") {\n el.style.cssText = c + ";opacity:0;transition:none";\n void el.offsetWidth;\n }\n el.style.cssText = c + tr;\n last[u2] = c;\n }\n var ANIM = /(?:^|;)animation:[^;]*/;\n function anim(i) {\n var m2 = i >= 0 ? ANIM.exec(spec.L[i][0]) : null;\n return m2 ? m2[0] : "";\n }\n function go(m2, to, ms, ez, fromHistory) {\n if (!(m2 in state) || state[m2] === to) return;\n var list = owned[m2] || [];\n list.forEach(function(u2) {\n var a = lookIn(u2, void 0), b = lookIn(u2, to), el = els[u2];\n if (!el || a < 0 || !anim(a) || anim(a) === anim(b)) return;\n var cs = getComputedStyle(el);\n el.style.cssText = css(u2, a) + ";animation:none;transition:none;transform:" + cs.transform + ";opacity:" + cs.opacity;\n });\n void root.offsetWidth;\n if (m2 === "flow" && !fromHistory) hist.push(state[m2]);\n state[m2] = to;\n list.forEach(function(u2) {\n set(u2, ms, ez);\n });\n arm();\n }\n function active(u2, trig) {\n return spec.on.filter(function(o) {\n return String(o[0]) === String(u2) && o[3] === trig && state[o[1]] === o[2];\n });\n }\n function run(o, u2) {\n var a = o[4];\n if (a.k === "go") {\n if (a.hold) {\n if (!holds[u2]) holds[u2] = { m: a.m, back: state[a.m], ms: a.ms, ez: a.ez };\n }\n go(a.m, a.to, a.ms, a.ez, false);\n } else if (a.k === "back" && hist.length) {\n go(a.m, hist.pop(), 300, "ease-in-out", true);\n }\n }\n function release(u2) {\n var h = holds[u2];\n if (!h) return;\n delete holds[u2];\n go(h.m, h.back, h.ms, h.ez, true);\n }\n function chain(el) {\n var out = [];\n for (var n = el; n && n !== root.parentNode; n = n.parentNode) {\n var id2 = n.getAttribute && n.getAttribute("data-pc");\n if (id2 !== null && id2 !== void 0) out.push(id2);\n if (n === root) break;\n }\n return out;\n }\n function first(ids, trig) {\n for (var i = 0; i < ids.length; i++) {\n var a = active(ids[i], trig);\n if (a.length) return { u: ids[i], list: a };\n }\n return null;\n }\n function arm() {\n timers.forEach(clearTimeout);\n timers = [];\n spec.on.forEach(function(o) {\n if (o[3] === "timeout" && state[o[1]] === o[2]) timers.push(setTimeout(function() {\n if (state[o[1]] === o[2]) run(o, o[0]);\n }, o[5]));\n });\n }\n var over = [];\n function hover(ids) {\n var left = over.filter(function(u2) {\n return ids.indexOf(u2) < 0;\n }), entered = ids.filter(function(u2) {\n return over.indexOf(u2) < 0;\n });\n over = ids;\n left.forEach(function(u2) {\n release(u2);\n active(u2, "leave").forEach(function(o) {\n run(o, u2);\n });\n });\n entered.slice().reverse().forEach(function(u2) {\n active(u2, "hover").concat(active(u2, "enter")).forEach(function(o) {\n run(o, u2);\n });\n });\n }\n var press = null;\n function onMove(e) {\n if (press) {\n var dx = e.clientX - press.x, dy = e.clientY - press.y;\n if (!press.dragged && Math.abs(dx) + Math.abs(dy) > 5) {\n press.dragged = true;\n var d = first(press.ids, "drag");\n if (d) {\n var du = d.u;\n press.drag = d;\n d.list.forEach(function(o) {\n if (o[4].k !== "orbit") run(o, du);\n });\n }\n if (press.held) {\n release(press.held);\n press.held = null;\n }\n }\n if (press.drag) {\n var k = root.getBoundingClientRect().width / (root.offsetWidth || 1) || 1;\n press.drag.list.forEach(function(o) {\n var a = o[4];\n if (a.k !== "orbit") return;\n var cur = orbit[a.t] || { rx: 0, ry: 0 };\n orbit[a.t] = { rx: cur.rx, ry: cur.ry + (e.clientX - press.lx) / k * a.d };\n if (a.tilt) {\n var tc = orbit[a.tt] || { rx: 0, ry: 0 };\n orbit[a.tt] = { ry: tc.ry, rx: Math.max(a.lo, Math.min(a.hi, tc.rx - (e.clientY - press.ly) / k * a.d)) };\n }\n set(a.t, 0, "linear");\n if (a.tt !== a.t) set(a.tt, 0, "linear");\n });\n press.lx = e.clientX;\n press.ly = e.clientY;\n return;\n }\n }\n hover(chain(e.target));\n }\n function onDown(e) {\n var ids = chain(e.target);\n press = { x: e.clientX, y: e.clientY, lx: e.clientX, ly: e.clientY, ids, dragged: false, drag: null, held: null };\n if (first(ids, "drag") && root.setPointerCapture) {\n try {\n root.setPointerCapture(e.pointerId);\n } catch (err) {\n }\n }\n var p = first(ids, "press");\n if (p) {\n var pu = p.u;\n press.held = pu;\n p.list.forEach(function(o) {\n run(o, pu);\n });\n }\n }\n function onUp(e) {\n var p = press;\n press = null;\n if (!p) return;\n if (p.held) release(p.held);\n if (p.dragged) return;\n var c = first(p.ids, "click");\n if (c) {\n var cu = c.u;\n c.list.forEach(function(o) {\n run(o, cu);\n });\n }\n void e;\n }\n function onLeave() {\n if (!press) hover([]);\n }\n function onKey(e) {\n spec.on.forEach(function(o) {\n if (o[3] === "key" && state[o[1]] === o[2] && (!o[6] || o[6].toLowerCase() === String(e.key).toLowerCase())) run(o, o[0]);\n });\n }\n for (var id in els) set(id, 0, "linear");\n root.addEventListener("pointermove", onMove);\n root.addEventListener("pointerdown", onDown);\n root.addEventListener("pointerup", onUp);\n root.addEventListener("pointercancel", onUp);\n root.addEventListener("pointerleave", onLeave);\n window.addEventListener("keydown", onKey);\n arm();\n return function() {\n timers.forEach(clearTimeout);\n root.removeEventListener("pointermove", onMove);\n root.removeEventListener("pointerdown", onDown);\n root.removeEventListener("pointerup", onUp);\n root.removeEventListener("pointercancel", onUp);\n root.removeEventListener("pointerleave", onLeave);\n window.removeEventListener("keydown", onKey);\n };\n}';
|
|
317971
|
-
MACHINE_JS = 'function popcraftMachineCore(spec) {\n function start(id) {\n var t = spec.in[id];\n return !t || t[0] === "event" ? void 0 : t[1];\n }\n function holds(g, values, fired) {\n var t = spec.in[g[0]];\n if (!t) return false;\n if (t[0] === "event") return !!fired[g[0]];\n var v = g[0] in values ? values[g[0]] : start(g[0]), w = g[2];\n switch (g[1]) {\n case "eq":\n return v === w;\n case "neq":\n return v !== w;\n case "gt":\n return typeof v === "number" && typeof w === "number" && v > w;\n case "gte":\n return typeof v === "number" && typeof w === "number" && v >= w;\n case "lt":\n return typeof v === "number" && typeof w === "number" && v < w;\n case "lte":\n return typeof v === "number" && typeof w === "number" && v <= w;\n }\n return false;\n }\n function apply(values, actions) {\n var out = {}, fired = {};\n for (var k in values) out[k] = values[k];\n actions.forEach(function(a) {\n var t = spec.in[a[1]];\n if (!t) return;\n var cur = a[1] in out ? out[a[1]] : start(a[1]), by = typeof a[2] === "number" ? a[2] : 1;\n if (a[0] === "set") {\n if (t[0] === "event") fired[a[1]] = 1;\n else if (a.length > 2 && typeof a[2] === typeof cur) out[a[1]] = a[2];\n } else if (a[0] === "toggle") {\n if (typeof cur === "boolean") out[a[1]] = !cur;\n } else if (a[0] === "increment") {\n if (typeof cur === "number") out[a[1]] = cur + by;\n } else if (a[0] === "decrement") {\n if (typeof cur === "number") out[a[1]] = cur - by;\n } else if (a[0] === "fire") {\n if (t[0] === "event") fired[a[1]] = 1;\n } else if (a[0] === "reset") {\n var s = start(a[1]);\n if (s === void 0) delete out[a[1]];\n else out[a[1]] = s;\n }\n });\n return { values: out, fired };\n }\n function next(r, fired) {\n var own = spec.t.filter(function(t2) {\n return t2[0] === r.state;\n });\n var any = spec.t.filter(function(t2) {\n return t2[0] === "*" && t2[1] !== r.state;\n });\n var all = own.concat(any);\n for (var i = 0; i < all.length; i++) {\n var t = all[i];\n if (spec.s[t[1]] && t[2].every(function(g) {\n return holds(g, r.values, fired);\n })) return t;\n }\n return null;\n }\n function enter(r, id) {\n var res = apply(r.values, spec.s[id] ? spec.s[id][4] : []);\n return { run: { state: id, values: res.values }, fired: res.fired };\n }\n function settle(r, fired) {\n var cur = r, ev = fired || {};\n for (var i = 0; i < 16; i++) {\n var t = next(cur, ev);\n if (!t) break;\n var n = enter(cur, t[1]);\n cur = n.run;\n ev = n.fired;\n }\n return cur;\n }\n function begin() {\n var first = spec.s[spec.i] ? spec.i : Object.keys(spec.s)[0], values = {};\n if (first === void 0) return null;\n for (var k in spec.in) {\n var s = start(k);\n if (s !== void 0) values[k] = s;\n }\n var e = enter({ state: first, values }, first);\n return settle(e.run, e.fired);\n }\n function hears(l, type, chain, key) {\n if (l[0] !== type) return false;\n if (type === "complete") return true;\n if (type === "keyDown" || type === "keyUp") return !l[3] || String(l[3]).toLowerCase() === String(key).toLowerCase();\n return l[1] === null || chain.indexOf(l[1]) >= 0;\n }\n function dispatch(r, type, chain, key) {\n var heard = spec.l.filter(function(l) {\n return hears(l, type, chain, key);\n });\n if (!heard.length) return r;\n var res = apply(r.values, [].concat.apply([], heard.map(function(l) {\n return l[2];\n })));\n return settle({ state: r.state, values: res.values }, res.fired);\n }\n function set(r, id, value) {\n var t = spec.in[id];\n if (!t) return r;\n var res = apply(r.values, [t[0] === "event" ? ["fire", id] : ["set", id, value]]);\n return settle({ state: r.state, values: res.values }, res.fired);\n }\n return { begin, dispatch, set };\n}\nfunction popcraftMachine(root, spec) {\n var core = popcraftMachineCore(spec), run = core.begin(), anims = [], t0 = 0, done = false, raf = 0, over = [];\n if (!run) return function() {\n };\n function chain(el) {\n var out = [];\n for (var n = el; n && n !== root.parentNode; n = n.parentNode) {\n var id = n.getAttribute && n.getAttribute("data-sm");\n if (id) out.push(id);\n if (n === root) break;\n }\n return out;\n }\n function update(r) {\n if (r === run) return;\n var changed = r.state !== run.state;\n run = r;\n if (!changed) return;\n t0 = performance.now();\n done = false;\n root.dispatchEvent(new CustomEvent("popcraft:state", { detail: { state: r.state, name: spec.s[r.state] ? spec.s[r.state][5] : r.state, values: r.values } }));\n }\n function tick(now) {\n var s = spec.s[run.state];\n if (s) {\n var a = s[0], b = s[1], played = Math.max(0, now - t0) * s[3], t;\n if (s[2] && b > a) t = a + played % (b - a);\n else {\n t = Math.min(b, a + played);\n if (!done && a + played >= b) {\n done = true;\n update(core.dispatch(run, "complete", []));\n }\n }\n anims.forEach(function(x) {\n x.currentTime = t;\n });\n }\n raf = requestAnimationFrame(tick);\n }\n function on(type) {\n return function(e) {\n update(core.dispatch(run, type, chain(e.target)));\n };\n }\n function onMove(e) {\n var ids = chain(e.target);\n var left = over.filter(function(u) {\n return ids.indexOf(u) < 0;\n }), entered = ids.filter(function(u) {\n return over.indexOf(u) < 0;\n });\n over = ids;\n if (left.length) update(core.dispatch(run, "pointerExit", left));\n if (entered.length) update(core.dispatch(run, "pointerEnter", entered));\n }\n function onLeave() {\n if (over.length) {\n var left = over;\n over = [];\n update(core.dispatch(run, "pointerExit", left));\n }\n }\n function onKey(type) {\n return function(e) {\n var t = e.target;\n if (e.repeat || e.metaKey || e.ctrlKey || t && (t.tagName === "INPUT" || t.tagName === "TEXTAREA" || t.isContentEditable)) return;\n var r = core.dispatch(run, type, [], e.key);\n if (r !== run) {\n e.preventDefault();\n update(r);\n }\n };\n }\n var down = on("pointerDown"), up = on("pointerUp"), click = on("click"), keyDown = onKey("keyDown"), keyUp = onKey("keyUp");\n anims = root.getAnimations ? root.getAnimations({ subtree: true }) : [];\n anims.forEach(function(x) {\n x.pause();\n });\n t0 = performance.now();\n root.addEventListener("pointerdown", down);\n root.addEventListener("pointerup", up);\n root.addEventListener("click", click);\n root.addEventListener("pointermove", onMove);\n root.addEventListener("pointerleave", onLeave);\n window.addEventListener("keydown", keyDown);\n window.addEventListener("keyup", keyUp);\n raf = requestAnimationFrame(tick);\n function byName(k) {\n if (spec.in[k]) return k;\n for (var id in spec.in) if (spec.in[id][2] === k) return id;\n return k;\n }\n var api = {\n state: function() {\n return run.state;\n },\n values: function() {\n return run.values;\n },\n set: function(input, value) {\n update(core.set(run, byName(input), value));\n },\n fire: function(input) {\n update(core.set(run, byName(input), void 0));\n },\n destroy: function() {\n cancelAnimationFrame(raf);\n root.removeEventListener("pointerdown", down);\n root.removeEventListener("pointerup", up);\n root.removeEventListener("click", click);\n root.removeEventListener("pointermove", onMove);\n root.removeEventListener("pointerleave", onLeave);\n window.removeEventListener("keydown", keyDown);\n window.removeEventListener("keyup", keyUp);\n }\n };\n root.popcraftMachine = api;\n return api.destroy;\n}';
|
|
317972
|
-
}
|
|
317973
|
-
});
|
|
317974
|
-
|
|
317975
319124
|
// lib/io/web/runtime.ts
|
|
317976
319125
|
function interactiveSpec(tree) {
|
|
317977
319126
|
if (!tree.interactive) return null;
|
|
@@ -318019,55 +319168,6 @@ var init_runtime3 = __esm({
|
|
|
318019
319168
|
}
|
|
318020
319169
|
});
|
|
318021
319170
|
|
|
318022
|
-
// lib/io/web/machine-runtime.ts
|
|
318023
|
-
var init_machine_runtime = __esm({
|
|
318024
|
-
"lib/io/web/machine-runtime.ts"() {
|
|
318025
|
-
"use strict";
|
|
318026
|
-
init_runtimes();
|
|
318027
|
-
}
|
|
318028
|
-
});
|
|
318029
|
-
|
|
318030
|
-
// lib/io/web/state-machine.ts
|
|
318031
|
-
function webStateMachine(doc2, frameId) {
|
|
318032
|
-
const sm = machineOf(doc2.nodes[frameId]);
|
|
318033
|
-
if (!sm || !doc2.nodes[frameId]?.timeline) return null;
|
|
318034
|
-
const timeline = frameTimeline(doc2.nodes, frameId);
|
|
318035
|
-
const duration3 = timelineDuration(doc2.nodes, frameId);
|
|
318036
|
-
const action3 = (a) => a.value === void 0 ? [a.type, a.input] : [a.type, a.input, a.value];
|
|
318037
|
-
const spec = { i: sm.initial, s: {}, t: [], in: {}, l: [] };
|
|
318038
|
-
for (const i2 of sortedValues(sm.inputs)) spec.in[i2.id] = [i2.type, i2.type === "event" ? null : i2.value ?? defaultOf2(i2.type), i2.name];
|
|
318039
|
-
for (const s of sortedValues(sm.states)) {
|
|
318040
|
-
const [a, b] = stateStretch(s, timeline, duration3);
|
|
318041
|
-
spec.s[s.id] = [a, b, s.loop ? 1 : 0, s.speed ?? 1, (s.entry ?? []).map(action3), s.name];
|
|
318042
|
-
}
|
|
318043
|
-
for (const t3 of sortedValues(sm.transitions)) {
|
|
318044
|
-
spec.t.push([t3.from, t3.to, (t3.guards ?? []).map((g) => {
|
|
318045
|
-
const type = sm.inputs[g.input]?.type;
|
|
318046
|
-
const value3 = type === "event" ? null : g.value ?? (type === "boolean" ? true : type === "number" ? 0 : "");
|
|
318047
|
-
return [g.input, g.op ?? "eq", value3];
|
|
318048
|
-
})]);
|
|
318049
|
-
}
|
|
318050
|
-
for (const l of sortedValues(sm.listeners)) {
|
|
318051
|
-
if (!isKeyListener(l.type)) spec.l.push([l.type, l.layer ?? null, l.actions.map(action3)]);
|
|
318052
|
-
else spec.l.push(l.key ? [l.type, null, l.actions.map(action3), l.key] : [l.type, null, l.actions.map(action3)]);
|
|
318053
|
-
}
|
|
318054
|
-
return spec;
|
|
318055
|
-
}
|
|
318056
|
-
var defaultOf2, machineLayers, machineScript;
|
|
318057
|
-
var init_state_machine3 = __esm({
|
|
318058
|
-
"lib/io/web/state-machine.ts"() {
|
|
318059
|
-
"use strict";
|
|
318060
|
-
init_instances2();
|
|
318061
|
-
init_state_machine();
|
|
318062
|
-
init_machine_runtime();
|
|
318063
|
-
init_machine_runtime();
|
|
318064
|
-
defaultOf2 = (type) => type === "boolean" ? false : type === "number" ? 0 : type === "string" ? "" : null;
|
|
318065
|
-
machineLayers = (spec) => new Set((spec?.l ?? []).map((l) => l[1]).filter((id3) => !!id3));
|
|
318066
|
-
machineScript = (spec) => `${MACHINE_JS}
|
|
318067
|
-
popcraftMachine(document.querySelector('[data-sm-root]'), ${JSON.stringify(spec)});`;
|
|
318068
|
-
}
|
|
318069
|
-
});
|
|
318070
|
-
|
|
318071
319171
|
// lib/io/web/naming.ts
|
|
318072
319172
|
var classNameFor, componentName, fileBase;
|
|
318073
319173
|
var init_naming = __esm({
|
|
@@ -318083,128 +319183,6 @@ var init_naming = __esm({
|
|
|
318083
319183
|
}
|
|
318084
319184
|
});
|
|
318085
319185
|
|
|
318086
|
-
// lib/document/dev-mode.ts
|
|
318087
|
-
function codeSyntaxFor(v, platform4) {
|
|
318088
|
-
const explicit = v.codeSyntax?.[platform4];
|
|
318089
|
-
if (explicit) return explicit;
|
|
318090
|
-
const parts = v.name.split("/").map((p2) => p2.trim()).filter(Boolean);
|
|
318091
|
-
if (platform4 === "WEB") return `--${parts.join("-").toLowerCase().replace(/[^a-z0-9-]+/g, "-")}`;
|
|
318092
|
-
const camel4 = parts.map((p2, i2) => {
|
|
318093
|
-
const w = p2.replace(/[^A-Za-z0-9]+/g, " ").trim().split(/\s+/);
|
|
318094
|
-
return w.map((x2, j) => i2 === 0 && j === 0 ? x2.toLowerCase() : x2[0].toUpperCase() + x2.slice(1).toLowerCase()).join("");
|
|
318095
|
-
}).join("");
|
|
318096
|
-
return platform4 === "iOS" ? `Tokens.${camel4}` : `Tokens.${camel4}`;
|
|
318097
|
-
}
|
|
318098
|
-
var init_dev_mode = __esm({
|
|
318099
|
-
"lib/document/dev-mode.ts"() {
|
|
318100
|
-
"use strict";
|
|
318101
|
-
}
|
|
318102
|
-
});
|
|
318103
|
-
|
|
318104
|
-
// lib/io/web/tokens.ts
|
|
318105
|
-
function cssValue(v, value3) {
|
|
318106
|
-
if (v.type === "COLOR") return isColor3(value3) ? (value3.a ?? 1) < 1 ? toRgba(value3) : toHex(value3) : null;
|
|
318107
|
-
if (v.type === "FLOAT") return typeof value3 === "number" && Number.isFinite(value3) ? String(Math.round(value3 * 1e3) / 1e3) : null;
|
|
318108
|
-
if (v.type === "STRING") return typeof value3 === "string" ? JSON.stringify(value3) : null;
|
|
318109
|
-
return null;
|
|
318110
|
-
}
|
|
318111
|
-
function siteTokens(doc2) {
|
|
318112
|
-
const collections = Object.values(doc2.variableCollections ?? {}).map((c2) => ({
|
|
318113
|
-
id: c2.id,
|
|
318114
|
-
name: c2.name,
|
|
318115
|
-
defaultMode: c2.defaultModeId,
|
|
318116
|
-
modes: c2.modes.map((m) => ({ id: m.id, name: m.name, className: modeClass(c2, m) }))
|
|
318117
|
-
}));
|
|
318118
|
-
const taken = /* @__PURE__ */ new Set();
|
|
318119
|
-
const vars = [];
|
|
318120
|
-
for (const v of Object.values(doc2.variables ?? {}).sort((a, b) => a.name.localeCompare(b.name) || a.id.localeCompare(b.id))) {
|
|
318121
|
-
const values3 = {};
|
|
318122
|
-
for (const [mode, value3] of Object.entries(v.valuesByMode ?? {})) {
|
|
318123
|
-
const css = cssValue(v, value3);
|
|
318124
|
-
if (css !== null) values3[mode] = css;
|
|
318125
|
-
}
|
|
318126
|
-
if (!Object.keys(values3).length) continue;
|
|
318127
|
-
let name2 = codeSyntaxFor(v, "WEB");
|
|
318128
|
-
if (!name2.startsWith("--")) name2 = `--${slug(name2)}`;
|
|
318129
|
-
if (taken.has(name2)) name2 = `${name2}-${v.id.replace(/[^a-zA-Z0-9]/g, "").slice(-4)}`;
|
|
318130
|
-
taken.add(name2);
|
|
318131
|
-
vars.push({ id: v.id, name: name2, type: v.type, collection: v.variableCollectionId, values: values3 });
|
|
318132
|
-
}
|
|
318133
|
-
const active3 = Object.entries(doc2.activeVariableModes ?? {}).flatMap(([cid, mid]) => {
|
|
318134
|
-
const c2 = collections.find((x2) => x2.id === cid);
|
|
318135
|
-
const m = c2 && mid !== c2.defaultMode ? c2.modes.find((x2) => x2.id === mid) : void 0;
|
|
318136
|
-
return m ? [m.className] : [];
|
|
318137
|
-
});
|
|
318138
|
-
return { collections, vars, active: active3 };
|
|
318139
|
-
}
|
|
318140
|
-
function tokensCSS(tokens) {
|
|
318141
|
-
const rules = [];
|
|
318142
|
-
const defaults3 = [];
|
|
318143
|
-
const byMode = /* @__PURE__ */ new Map();
|
|
318144
|
-
for (const v of tokens.vars) {
|
|
318145
|
-
const c2 = tokens.collections.find((x2) => x2.id === v.collection);
|
|
318146
|
-
const base = v.values[c2?.defaultMode ?? ""] ?? Object.values(v.values)[0];
|
|
318147
|
-
defaults3.push(` ${v.name}: ${base};`);
|
|
318148
|
-
if (v.type === "FLOAT") rules.push(`@property ${v.name} { syntax: '<number>'; inherits: true; initial-value: ${base}; }`);
|
|
318149
|
-
for (const m of c2?.modes ?? []) {
|
|
318150
|
-
if (m.id === c2.defaultMode || v.values[m.id] === void 0 || v.values[m.id] === base) continue;
|
|
318151
|
-
(byMode.get(m.className) ?? byMode.set(m.className, []).get(m.className)).push(` ${v.name}: ${v.values[m.id]};`);
|
|
318152
|
-
}
|
|
318153
|
-
}
|
|
318154
|
-
if (defaults3.length) rules.push(`:root {
|
|
318155
|
-
${defaults3.join("\n")}
|
|
318156
|
-
}`);
|
|
318157
|
-
for (const [cls, lines2] of byMode) rules.push(`.${cls} {
|
|
318158
|
-
${lines2.join("\n")}
|
|
318159
|
-
}`);
|
|
318160
|
-
return rules;
|
|
318161
|
-
}
|
|
318162
|
-
function tokenStyle(raw, style, tokens) {
|
|
318163
|
-
const name2 = (id3) => id3 ? tokens.vars.find((v) => v.id === id3)?.name : void 0;
|
|
318164
|
-
const out = {};
|
|
318165
|
-
const fills = (raw.fills ?? []).filter((f2) => f2.visible !== false);
|
|
318166
|
-
const fill = fills.length === 1 && fills[0].type === "SOLID" && (fills[0].opacity ?? 1) === 1 ? name2(fills[0].boundVariables?.color) : void 0;
|
|
318167
|
-
if (fill) {
|
|
318168
|
-
if (raw.type === "TEXT") {
|
|
318169
|
-
if (style.color) out.color = `var(${fill})`;
|
|
318170
|
-
} else if (style.background) out.background = `var(${fill})`;
|
|
318171
|
-
}
|
|
318172
|
-
const stroke3 = raw.strokes?.[0];
|
|
318173
|
-
const strokeVar = name2(stroke3?.boundVariables?.color);
|
|
318174
|
-
if (strokeVar) {
|
|
318175
|
-
if (style["border-color"]) out["border-color"] = `var(${strokeVar})`;
|
|
318176
|
-
for (const p2 of ["border", "outline"]) if (style[p2]) out[p2] = style[p2].replace(/(#[0-9A-Fa-f]{3,8}|rgba?\([^)]*\))$/, `var(${strokeVar})`);
|
|
318177
|
-
}
|
|
318178
|
-
for (const [prop, id3] of Object.entries(raw.boundVariables ?? {})) {
|
|
318179
|
-
const rule2 = NUMBER_PROPS[prop];
|
|
318180
|
-
const token = tokens.vars.find((v) => v.id === id3);
|
|
318181
|
-
if (!rule2 || !token || token.type !== "FLOAT" || style[rule2[0]] === void 0) continue;
|
|
318182
|
-
out[rule2[0]] = rule2[1](token.name);
|
|
318183
|
-
}
|
|
318184
|
-
return out;
|
|
318185
|
-
}
|
|
318186
|
-
var slug, modeClass, isColor3, px2, NUMBER_PROPS;
|
|
318187
|
-
var init_tokens2 = __esm({
|
|
318188
|
-
"lib/io/web/tokens.ts"() {
|
|
318189
|
-
"use strict";
|
|
318190
|
-
init_dev_mode();
|
|
318191
|
-
init_paint2();
|
|
318192
|
-
slug = (s) => s.toLowerCase().replace(/[^a-z0-9]+/g, "-").replace(/^-|-$/g, "") || "x";
|
|
318193
|
-
modeClass = (collection, mode) => `pc-${slug(collection.name)}-${slug(mode.name)}`;
|
|
318194
|
-
isColor3 = (v) => !!v && typeof v === "object" && "r" in v && "g" in v && "b" in v;
|
|
318195
|
-
px2 = (name2) => `calc(var(${name2}) * 1px)`;
|
|
318196
|
-
NUMBER_PROPS = {
|
|
318197
|
-
width: ["width", px2],
|
|
318198
|
-
height: ["height", px2],
|
|
318199
|
-
opacity: ["opacity", (n) => `var(${n})`],
|
|
318200
|
-
cornerRadius: ["border-radius", px2],
|
|
318201
|
-
itemSpacing: ["gap", px2],
|
|
318202
|
-
fontSize: ["font-size", px2],
|
|
318203
|
-
letterSpacing: ["letter-spacing", px2]
|
|
318204
|
-
};
|
|
318205
|
-
}
|
|
318206
|
-
});
|
|
318207
|
-
|
|
318208
319186
|
// lib/io/web/html.ts
|
|
318209
319187
|
function serializeHTML(tree, opts = {}) {
|
|
318210
319188
|
const rules = [];
|
|
@@ -318342,7 +319320,7 @@ var init_html = __esm({
|
|
|
318342
319320
|
init_css();
|
|
318343
319321
|
init_motion();
|
|
318344
319322
|
init_runtime3();
|
|
318345
|
-
|
|
319323
|
+
init_state_machine2();
|
|
318346
319324
|
init_element();
|
|
318347
319325
|
init_fonts3();
|
|
318348
319326
|
init_naming();
|
|
@@ -318448,7 +319426,7 @@ function tailwindFor(style) {
|
|
|
318448
319426
|
const out = [];
|
|
318449
319427
|
for (const [k2, v] of Object.entries(style)) {
|
|
318450
319428
|
const util = UTILITIES[k2]?.(v);
|
|
318451
|
-
out.push(util ?? `[${k2}:${
|
|
319429
|
+
out.push(util ?? `[${k2}:${px4(v)}]`);
|
|
318452
319430
|
}
|
|
318453
319431
|
return out.join(" ");
|
|
318454
319432
|
}
|
|
@@ -318468,44 +319446,44 @@ ${indent}</${tag}>` : `${indent}<${tag} class="${cls}"></${tag}>`;
|
|
|
318468
319446
|
};
|
|
318469
319447
|
return emit8(tree.root, 0, true);
|
|
318470
319448
|
}
|
|
318471
|
-
var
|
|
319449
|
+
var px4, UTILITIES;
|
|
318472
319450
|
var init_tailwind = __esm({
|
|
318473
319451
|
"lib/io/web/tailwind.ts"() {
|
|
318474
319452
|
"use strict";
|
|
318475
319453
|
init_element();
|
|
318476
|
-
|
|
319454
|
+
px4 = (v) => v.replace(/"/g, "'").replace(/\s+/g, "_");
|
|
318477
319455
|
UTILITIES = {
|
|
318478
|
-
width: (v) => `w-[${
|
|
318479
|
-
height: (v) => `h-[${
|
|
319456
|
+
width: (v) => `w-[${px4(v)}]`,
|
|
319457
|
+
height: (v) => `h-[${px4(v)}]`,
|
|
318480
319458
|
display: (v) => v === "flex" ? "flex" : v === "block" ? "block" : v === "none" ? "hidden" : null,
|
|
318481
319459
|
"flex-direction": (v) => v === "row" ? "flex-row" : "flex-col",
|
|
318482
|
-
gap: (v) => `gap-[${
|
|
319460
|
+
gap: (v) => `gap-[${px4(v)}]`,
|
|
318483
319461
|
"justify-content": (v) => ({ "flex-start": "justify-start", "flex-end": "justify-end", center: "justify-center", "space-between": "justify-between" })[v] ?? null,
|
|
318484
319462
|
"align-items": (v) => ({ "flex-start": "items-start", "flex-end": "items-end", center: "items-center", baseline: "items-baseline" })[v] ?? null,
|
|
318485
|
-
padding: (v) => `p-[${
|
|
318486
|
-
"border-radius": (v) => `rounded-[${
|
|
319463
|
+
padding: (v) => `p-[${px4(v)}]`,
|
|
319464
|
+
"border-radius": (v) => `rounded-[${px4(v)}]`,
|
|
318487
319465
|
overflow: (v) => v === "hidden" ? "overflow-hidden" : null,
|
|
318488
319466
|
position: (v) => ({ absolute: "absolute", relative: "relative", fixed: "fixed" })[v] ?? null,
|
|
318489
|
-
left: (v) => `left-[${
|
|
318490
|
-
top: (v) => `top-[${
|
|
319467
|
+
left: (v) => `left-[${px4(v)}]`,
|
|
319468
|
+
top: (v) => `top-[${px4(v)}]`,
|
|
318491
319469
|
opacity: (v) => `opacity-[${v}]`,
|
|
318492
|
-
background: (v) => v.startsWith("#") || v.startsWith("rgb") ? `bg-[${
|
|
318493
|
-
color: (v) => `text-[${
|
|
318494
|
-
"font-size": (v) => `text-[${
|
|
319470
|
+
background: (v) => v.startsWith("#") || v.startsWith("rgb") ? `bg-[${px4(v)}]` : `bg-[image:${px4(v)}]`,
|
|
319471
|
+
color: (v) => `text-[${px4(v)}]`,
|
|
319472
|
+
"font-size": (v) => `text-[${px4(v)}]`,
|
|
318495
319473
|
"font-weight": (v) => `font-[${v}]`,
|
|
318496
319474
|
"font-style": (v) => v === "italic" ? "italic" : null,
|
|
318497
|
-
"line-height": (v) => v === "normal" ? "leading-normal" : `leading-[${
|
|
318498
|
-
"letter-spacing": (v) => `tracking-[${
|
|
319475
|
+
"line-height": (v) => v === "normal" ? "leading-normal" : `leading-[${px4(v)}]`,
|
|
319476
|
+
"letter-spacing": (v) => `tracking-[${px4(v)}]`,
|
|
318499
319477
|
"text-align": (v) => `text-${v}`,
|
|
318500
319478
|
"text-decoration": (v) => v === "underline" ? "underline" : v === "line-through" ? "line-through" : null,
|
|
318501
319479
|
"text-transform": (v) => ({ uppercase: "uppercase", lowercase: "lowercase", capitalize: "capitalize" })[v] ?? null,
|
|
318502
319480
|
"mix-blend-mode": (v) => `mix-blend-${v}`,
|
|
318503
|
-
transform: (v) => /^rotate\(/.test(v) ? `rotate-[${
|
|
318504
|
-
filter: (v) => /^blur\(/.test(v) ? `blur-[${
|
|
318505
|
-
"backdrop-filter": (v) => /^blur\(/.test(v) ? `backdrop-blur-[${
|
|
318506
|
-
"box-shadow": (v) => `shadow-[${
|
|
318507
|
-
border: (v) => `border-[${
|
|
318508
|
-
outline: (v) => `outline-[${
|
|
319481
|
+
transform: (v) => /^rotate\(/.test(v) ? `rotate-[${px4(v.slice(7, -1))}]` : null,
|
|
319482
|
+
filter: (v) => /^blur\(/.test(v) ? `blur-[${px4(v.slice(5, -1))}]` : null,
|
|
319483
|
+
"backdrop-filter": (v) => /^blur\(/.test(v) ? `backdrop-blur-[${px4(v.slice(5, -1))}]` : null,
|
|
319484
|
+
"box-shadow": (v) => `shadow-[${px4(v)}]`,
|
|
319485
|
+
border: (v) => `border-[${px4(v)}]`,
|
|
319486
|
+
outline: (v) => `outline-[${px4(v)}]`,
|
|
318509
319487
|
"box-sizing": (v) => v === "border-box" ? "box-border" : "box-content"
|
|
318510
319488
|
};
|
|
318511
319489
|
}
|
|
@@ -318686,7 +319664,7 @@ var init_react2 = __esm({
|
|
|
318686
319664
|
init_naming();
|
|
318687
319665
|
init_motion();
|
|
318688
319666
|
init_runtime3();
|
|
318689
|
-
|
|
319667
|
+
init_state_machine2();
|
|
318690
319668
|
init_tailwind();
|
|
318691
319669
|
jsxText = (s) => `{'${s.replace(/\\/g, "\\\\").replace(/'/g, "\\'").replace(/\n/g, "\\n")}'}`;
|
|
318692
319670
|
template = (s) => "`" + s.replace(/\\/g, "\\\\").replace(/`/g, "\\`").replace(/\$\{/g, "\\${") + "`";
|
|
@@ -318713,140 +319691,6 @@ var init_react2 = __esm({
|
|
|
318713
319691
|
}
|
|
318714
319692
|
});
|
|
318715
319693
|
|
|
318716
|
-
// packages/runtime/src/commerce.ts
|
|
318717
|
-
var commerce_exports = {};
|
|
318718
|
-
__export(commerce_exports, {
|
|
318719
|
-
COMMERCE_ACTIONS: () => COMMERCE_ACTIONS,
|
|
318720
|
-
COMMERCE_ACTION_PROP: () => COMMERCE_ACTION_PROP,
|
|
318721
|
-
COMMERCE_FIELDS: () => COMMERCE_FIELDS,
|
|
318722
|
-
COMMERCE_PROP: () => COMMERCE_PROP,
|
|
318723
|
-
COMMERCE_SCHEMAS: () => COMMERCE_SCHEMAS,
|
|
318724
|
-
commerceItem: () => commerceItem,
|
|
318725
|
-
commerceWords: () => commerceWords,
|
|
318726
|
-
formatMoney: () => formatMoney,
|
|
318727
|
-
isCommerceAction: () => isCommerceAction
|
|
318728
|
-
});
|
|
318729
|
-
function formatMoney(m, locale = "en-US") {
|
|
318730
|
-
if (!m) return "";
|
|
318731
|
-
try {
|
|
318732
|
-
return new Intl.NumberFormat(locale, { style: "currency", currency: m.currencyCode, currencyDisplay: "narrowSymbol" }).format(Number(m.amount));
|
|
318733
|
-
} catch {
|
|
318734
|
-
return `${m.amount} ${m.currencyCode}`;
|
|
318735
|
-
}
|
|
318736
|
-
}
|
|
318737
|
-
function commerceItem(schema, value3) {
|
|
318738
|
-
switch (schema) {
|
|
318739
|
-
case "commerce.product": {
|
|
318740
|
-
const p2 = value3;
|
|
318741
|
-
return { id: p2.id, values: {
|
|
318742
|
-
title: p2.title,
|
|
318743
|
-
handle: p2.handle,
|
|
318744
|
-
url: `/product/${p2.handle}`,
|
|
318745
|
-
description: p2.description,
|
|
318746
|
-
price: formatMoney(p2.priceRange?.minVariantPrice),
|
|
318747
|
-
max_price: formatMoney(p2.priceRange?.maxVariantPrice),
|
|
318748
|
-
image: p2.featuredImage?.url ?? "",
|
|
318749
|
-
image_alt: p2.featuredImage?.altText || p2.title,
|
|
318750
|
-
available: !!p2.availableForSale,
|
|
318751
|
-
variant_id: p2.variants?.find((v) => v.availableForSale)?.id ?? p2.variants?.[0]?.id ?? "",
|
|
318752
|
-
tags: (p2.tags ?? []).join(", ")
|
|
318753
|
-
} };
|
|
318754
|
-
}
|
|
318755
|
-
case "commerce.collection": {
|
|
318756
|
-
const c2 = value3;
|
|
318757
|
-
return { id: c2.handle || "all", values: { title: c2.title, handle: c2.handle, url: c2.path, description: c2.description } };
|
|
318758
|
-
}
|
|
318759
|
-
case "commerce.cart": {
|
|
318760
|
-
const c2 = value3;
|
|
318761
|
-
return { id: c2.id ?? "cart", values: {
|
|
318762
|
-
count: c2.totalQuantity,
|
|
318763
|
-
subtotal: formatMoney(c2.cost?.subtotalAmount),
|
|
318764
|
-
taxes: formatMoney(c2.cost?.totalTaxAmount),
|
|
318765
|
-
total: formatMoney(c2.cost?.totalAmount),
|
|
318766
|
-
checkout_url: c2.checkoutUrl
|
|
318767
|
-
} };
|
|
318768
|
-
}
|
|
318769
|
-
case "commerce.cartLine": {
|
|
318770
|
-
const l = value3;
|
|
318771
|
-
const m = l.merchandise;
|
|
318772
|
-
return { id: l.id ?? m.id, values: {
|
|
318773
|
-
title: m.product.title,
|
|
318774
|
-
variant: m.title === "Default Title" ? "" : m.title,
|
|
318775
|
-
url: `/product/${m.product.handle}`,
|
|
318776
|
-
image: m.product.featuredImage?.url ?? "",
|
|
318777
|
-
quantity: l.quantity,
|
|
318778
|
-
price: formatMoney(l.cost?.totalAmount),
|
|
318779
|
-
merchandise_id: m.id
|
|
318780
|
-
} };
|
|
318781
|
-
}
|
|
318782
|
-
case "commerce.menu": {
|
|
318783
|
-
const m = value3;
|
|
318784
|
-
return { id: m.path, values: { title: m.title, url: m.path } };
|
|
318785
|
-
}
|
|
318786
|
-
}
|
|
318787
|
-
}
|
|
318788
|
-
function commerceWords(item, key5) {
|
|
318789
|
-
if (key5 === "id") return item.id;
|
|
318790
|
-
const v = item.values[key5];
|
|
318791
|
-
return typeof v === "boolean" ? v ? "Yes" : "No" : v === void 0 ? "" : String(v);
|
|
318792
|
-
}
|
|
318793
|
-
var COMMERCE_SCHEMAS, COMMERCE_FIELDS, COMMERCE_PROP, COMMERCE_ACTIONS, COMMERCE_ACTION_PROP, isCommerceAction;
|
|
318794
|
-
var init_commerce = __esm({
|
|
318795
|
-
"packages/runtime/src/commerce.ts"() {
|
|
318796
|
-
"use strict";
|
|
318797
|
-
COMMERCE_SCHEMAS = ["commerce.product", "commerce.collection", "commerce.cart", "commerce.cartLine", "commerce.menu"];
|
|
318798
|
-
COMMERCE_FIELDS = {
|
|
318799
|
-
"commerce.product": [
|
|
318800
|
-
{ name: "Title", type: "TEXT" },
|
|
318801
|
-
{ name: "Handle", type: "TEXT" },
|
|
318802
|
-
{ name: "URL", type: "URL" },
|
|
318803
|
-
{ name: "Description", type: "TEXT" },
|
|
318804
|
-
{ name: "Price", type: "TEXT" },
|
|
318805
|
-
{ name: "Max price", type: "TEXT" },
|
|
318806
|
-
{ name: "Image", type: "MEDIA" },
|
|
318807
|
-
{ name: "Image alt", type: "TEXT" },
|
|
318808
|
-
{ name: "Available", type: "BOOLEAN" },
|
|
318809
|
-
{ name: "Variant ID", type: "TEXT" },
|
|
318810
|
-
{ name: "Tags", type: "TEXT" }
|
|
318811
|
-
],
|
|
318812
|
-
"commerce.collection": [{ name: "Title", type: "TEXT" }, { name: "Handle", type: "TEXT" }, { name: "URL", type: "URL" }, { name: "Description", type: "TEXT" }],
|
|
318813
|
-
"commerce.cart": [
|
|
318814
|
-
{ name: "Count", type: "NUMBER" },
|
|
318815
|
-
{ name: "Subtotal", type: "TEXT" },
|
|
318816
|
-
{ name: "Taxes", type: "TEXT" },
|
|
318817
|
-
{ name: "Total", type: "TEXT" },
|
|
318818
|
-
{ name: "Checkout URL", type: "URL" }
|
|
318819
|
-
],
|
|
318820
|
-
"commerce.cartLine": [
|
|
318821
|
-
{ name: "Title", type: "TEXT" },
|
|
318822
|
-
{ name: "Variant", type: "TEXT" },
|
|
318823
|
-
{ name: "URL", type: "URL" },
|
|
318824
|
-
{ name: "Image", type: "MEDIA" },
|
|
318825
|
-
{ name: "Quantity", type: "NUMBER" },
|
|
318826
|
-
{ name: "Price", type: "TEXT" },
|
|
318827
|
-
{ name: "Merchandise ID", type: "TEXT" }
|
|
318828
|
-
],
|
|
318829
|
-
"commerce.menu": [{ name: "Title", type: "TEXT" }, { name: "URL", type: "URL" }]
|
|
318830
|
-
};
|
|
318831
|
-
COMMERCE_PROP = {
|
|
318832
|
-
"commerce.product": { name: "products", type: "Product" },
|
|
318833
|
-
"commerce.collection": { name: "collections", type: "Collection" },
|
|
318834
|
-
"commerce.cart": { name: "cart", type: "Cart", one: true },
|
|
318835
|
-
"commerce.cartLine": { name: "lines", type: "CartItem" },
|
|
318836
|
-
"commerce.menu": { name: "menu", type: "Menu" }
|
|
318837
|
-
};
|
|
318838
|
-
COMMERCE_ACTIONS = ["addToCart", "updateCartLine", "removeCartLine", "checkout", "search"];
|
|
318839
|
-
COMMERCE_ACTION_PROP = {
|
|
318840
|
-
addToCart: "onAddToCart",
|
|
318841
|
-
updateCartLine: "onUpdateCartLine",
|
|
318842
|
-
removeCartLine: "onRemoveCartLine",
|
|
318843
|
-
checkout: "onCheckout",
|
|
318844
|
-
search: "onSearch"
|
|
318845
|
-
};
|
|
318846
|
-
isCommerceAction = (a) => typeof a === "string" && COMMERCE_ACTIONS.includes(a);
|
|
318847
|
-
}
|
|
318848
|
-
});
|
|
318849
|
-
|
|
318850
319694
|
// lib/sites/auth.ts
|
|
318851
319695
|
function usesSignIn(doc2) {
|
|
318852
319696
|
if (Object.values(doc2.collections ?? {}).some((c2) => c2.perVisitor)) return true;
|
|
@@ -319542,7 +320386,7 @@ var init_package = __esm({
|
|
|
319542
320386
|
"packages/runtime/package.json"() {
|
|
319543
320387
|
package_default = {
|
|
319544
320388
|
name: "@popcraft/runtime",
|
|
319545
|
-
version: "0.
|
|
320389
|
+
version: "0.17.0",
|
|
319546
320390
|
description: "What code exported from PopCraft shares: the meaning of expressions (operators and functions) and, as it grows, the parts of a design's behaviour that are common code rather than generated React.",
|
|
319547
320391
|
license: "MIT",
|
|
319548
320392
|
homepage: "https://popcraft.app/docs/exporting/nextjs",
|
|
@@ -320316,941 +321160,6 @@ var init_physics = __esm({
|
|
|
320316
321160
|
}
|
|
320317
321161
|
});
|
|
320318
321162
|
|
|
320319
|
-
// lib/code/props.ts
|
|
320320
|
-
function propName(key5) {
|
|
320321
|
-
const words = key5.split("#")[0].trim().split(/[^A-Za-z0-9]+/).filter(Boolean);
|
|
320322
|
-
const name2 = words.map((w, i2) => i2 === 0 ? w.charAt(0).toLowerCase() + w.slice(1) : w.charAt(0).toUpperCase() + w.slice(1)).join("");
|
|
320323
|
-
return /^[A-Za-z_$]/.test(name2) ? name2 : `p${name2}`;
|
|
320324
|
-
}
|
|
320325
|
-
function componentOf(nodes, node2) {
|
|
320326
|
-
const c2 = node2.type === "COMPONENT" ? node2 : node2.type === "INSTANCE" ? nodes[node2.mainComponentId] : void 0;
|
|
320327
|
-
return c2?.type === "COMPONENT" ? c2 : void 0;
|
|
320328
|
-
}
|
|
320329
|
-
function codeOf(nodes, node2) {
|
|
320330
|
-
if (node2.type !== "COMPONENT" && node2.type !== "INSTANCE") return null;
|
|
320331
|
-
return componentOf(nodes, node2)?.code ?? null;
|
|
320332
|
-
}
|
|
320333
|
-
function codeProps(nodes, node2) {
|
|
320334
|
-
const component = componentOf(nodes, node2);
|
|
320335
|
-
const out = {};
|
|
320336
|
-
if (!component) return out;
|
|
320337
|
-
const set4 = component.parentId ? nodes[component.parentId] : void 0;
|
|
320338
|
-
const defs = (set4?.type === "COMPONENT_SET" ? set4.componentPropertyDefinitions : component.componentPropertyDefinitions) ?? {};
|
|
320339
|
-
const given = node2.type === "INSTANCE" ? node2.componentProperties ?? {} : {};
|
|
320340
|
-
for (const key5 of Object.keys(defs).sort()) {
|
|
320341
|
-
const v = value(key5 in given ? given[key5] : defs[key5].defaultValue);
|
|
320342
|
-
if (v !== void 0) out[propName(key5)] = v;
|
|
320343
|
-
}
|
|
320344
|
-
out.width = Math.round(node2.width);
|
|
320345
|
-
out.height = Math.round(node2.height);
|
|
320346
|
-
return out;
|
|
320347
|
-
}
|
|
320348
|
-
var value;
|
|
320349
|
-
var init_props = __esm({
|
|
320350
|
-
"lib/code/props.ts"() {
|
|
320351
|
-
"use strict";
|
|
320352
|
-
init_color();
|
|
320353
|
-
value = (v) => typeof v === "string" || typeof v === "number" || typeof v === "boolean" ? v : v && typeof v === "object" && "r" in v ? colorToHex8(v) : void 0;
|
|
320354
|
-
}
|
|
320355
|
-
});
|
|
320356
|
-
|
|
320357
|
-
// lib/document/controls.ts
|
|
320358
|
-
function fieldPart(nodes, id3) {
|
|
320359
|
-
const n = nodes[id3];
|
|
320360
|
-
if (!n) return null;
|
|
320361
|
-
if (n.type === "TEXT") return id3;
|
|
320362
|
-
for (const c2 of n.childIds ?? []) {
|
|
320363
|
-
const hit = fieldPart(nodes, c2);
|
|
320364
|
-
if (hit) return hit;
|
|
320365
|
-
}
|
|
320366
|
-
return null;
|
|
320367
|
-
}
|
|
320368
|
-
var cleanName2;
|
|
320369
|
-
var init_controls = __esm({
|
|
320370
|
-
"lib/document/controls.ts"() {
|
|
320371
|
-
"use strict";
|
|
320372
|
-
cleanName2 = (raw) => raw.trim().replace(/[^A-Za-z0-9_-]+/g, "-").replace(/^-+|-+$/g, "");
|
|
320373
|
-
}
|
|
320374
|
-
});
|
|
320375
|
-
|
|
320376
|
-
// lib/io/web/expressible.ts
|
|
320377
|
-
function expressibility(node2, styles) {
|
|
320378
|
-
const c2 = capability(node2, "css", styles);
|
|
320379
|
-
return { css: c2.reason === "", reason: c2.reason, needsRaster: c2.verdict === "raster" };
|
|
320380
|
-
}
|
|
320381
|
-
var init_expressible = __esm({
|
|
320382
|
-
"lib/io/web/expressible.ts"() {
|
|
320383
|
-
"use strict";
|
|
320384
|
-
init_capability();
|
|
320385
|
-
}
|
|
320386
|
-
});
|
|
320387
|
-
|
|
320388
|
-
// lib/io/web/responsive.ts
|
|
320389
|
-
function containerStyle(f2) {
|
|
320390
|
-
const out = {};
|
|
320391
|
-
if (isStack(f2) && f2.layoutWrap === "WRAP") {
|
|
320392
|
-
out["flex-wrap"] = "wrap";
|
|
320393
|
-
const cross2 = f2.counterAxisSpacing ?? f2.itemSpacing ?? 0;
|
|
320394
|
-
const main2 = f2.itemSpacing ?? 0;
|
|
320395
|
-
if (cross2 !== main2) out.gap = f2.layoutMode === "HORIZONTAL" ? `${cross2}px ${main2}px` : `${main2}px ${cross2}px`;
|
|
320396
|
-
out["align-content"] = "flex-start";
|
|
320397
|
-
}
|
|
320398
|
-
if (isGrid(f2)) {
|
|
320399
|
-
out.display = "grid";
|
|
320400
|
-
const cols = f2.layoutGridColumns ?? "AUTO";
|
|
320401
|
-
out["grid-template-columns"] = cols === "AUTO" ? `repeat(auto-fill, minmax(${f2.layoutGridMinColumnWidth ?? 100}px, 1fr))` : Array.from({ length: Math.max(1, cols) }, (_, i2) => track(f2.layoutGridColumnSizes?.[i2])).join(" ");
|
|
320402
|
-
const rows = f2.layoutGridRows ?? "AUTO";
|
|
320403
|
-
if (rows === "AUTO") out["grid-auto-rows"] = `minmax(${f2.layoutGridMinRowHeight ?? 100}px, auto)`;
|
|
320404
|
-
else out["grid-template-rows"] = Array.from({ length: Math.max(1, rows) }, (_, i2) => track(f2.layoutGridRowSizes?.[i2])).join(" ");
|
|
320405
|
-
const colGap = f2.itemSpacing ?? 0, rowGap = f2.counterAxisSpacing ?? colGap;
|
|
320406
|
-
out.gap = rowGap === colGap ? `${colGap}px` : `${rowGap}px ${colGap}px`;
|
|
320407
|
-
if (f2.padding) {
|
|
320408
|
-
out.padding = `${f2.padding.top}px ${f2.padding.right}px ${f2.padding.bottom}px ${f2.padding.left}px`;
|
|
320409
|
-
if (f2.padding.top || f2.padding.right || f2.padding.bottom || f2.padding.left) out["box-sizing"] = "border-box";
|
|
320410
|
-
}
|
|
320411
|
-
}
|
|
320412
|
-
const scroll = f2.overflowScrolling;
|
|
320413
|
-
if (scroll && scroll !== "NONE") {
|
|
320414
|
-
out["overflow-x"] = scroll === "HORIZONTAL" || scroll === "BOTH" ? "auto" : "hidden";
|
|
320415
|
-
out["overflow-y"] = scroll === "VERTICAL" || scroll === "BOTH" ? "auto" : "hidden";
|
|
320416
|
-
}
|
|
320417
|
-
return out;
|
|
320418
|
-
}
|
|
320419
|
-
function flowChild(node2, parent) {
|
|
320420
|
-
const style = { ...limits(node2) };
|
|
320421
|
-
const h = node2.layoutSizingHorizontal ?? "FIXED", v = node2.layoutSizingVertical ?? "FIXED";
|
|
320422
|
-
if (isGrid(parent)) {
|
|
320423
|
-
if (h !== "FIXED") style.width = h === "FILL" ? null : "fit-content";
|
|
320424
|
-
if (v !== "FIXED") style.height = null;
|
|
320425
|
-
return { style };
|
|
320426
|
-
}
|
|
320427
|
-
if (h === "FIXED" && style["max-width"] === void 0) style["max-width"] = "100%";
|
|
320428
|
-
const row2 = parent.layoutMode === "HORIZONTAL";
|
|
320429
|
-
const main2 = row2 ? h : v, cross2 = row2 ? v : h;
|
|
320430
|
-
const mainProp = row2 ? "width" : "height", crossProp = row2 ? "height" : "width";
|
|
320431
|
-
if (main2 === "FILL") {
|
|
320432
|
-
style[mainProp] = null;
|
|
320433
|
-
style.flex = "1 1 0";
|
|
320434
|
-
if (style[`min-${mainProp}`] === void 0) style[`min-${mainProp}`] = "0";
|
|
320435
|
-
} else {
|
|
320436
|
-
if (main2 === "HUG") style[mainProp] = null;
|
|
320437
|
-
style["flex-shrink"] = "0";
|
|
320438
|
-
}
|
|
320439
|
-
if (cross2 === "FILL") {
|
|
320440
|
-
style[crossProp] = null;
|
|
320441
|
-
style["align-self"] = "stretch";
|
|
320442
|
-
} else {
|
|
320443
|
-
if (cross2 === "HUG") style[crossProp] = null;
|
|
320444
|
-
if ((parent.counterAxisAlignItems ?? "MIN") === "MIN") style["align-self"] = "flex-start";
|
|
320445
|
-
}
|
|
320446
|
-
return { style };
|
|
320447
|
-
}
|
|
320448
|
-
function constrained(kind, pos, size6, parentSize, start2, end, sizeProp) {
|
|
320449
|
-
const far = parentSize - pos - size6;
|
|
320450
|
-
switch (kind) {
|
|
320451
|
-
case "MAX":
|
|
320452
|
-
return { place: { [end]: px4(far) }, style: {} };
|
|
320453
|
-
case "STRETCH":
|
|
320454
|
-
return { place: { [start2]: px4(pos), [end]: px4(far) }, style: { [sizeProp]: null } };
|
|
320455
|
-
// Its centre keeps its distance from the parent's centre.
|
|
320456
|
-
case "CENTER":
|
|
320457
|
-
return { place: { [start2]: `calc(50% + ${px4(pos - parentSize / 2)})` }, style: {} };
|
|
320458
|
-
case "SCALE":
|
|
320459
|
-
return parentSize > 0 ? { place: { [start2]: pct2(pos / parentSize) }, style: { [sizeProp]: pct2(size6 / parentSize) } } : { place: { [start2]: px4(pos) }, style: {} };
|
|
320460
|
-
default:
|
|
320461
|
-
return { place: { [start2]: px4(pos) }, style: {} };
|
|
320462
|
-
}
|
|
320463
|
-
}
|
|
320464
|
-
function placedChild(node2, parent, frame2 = parent) {
|
|
320465
|
-
const c2 = node2.constraints ?? { horizontal: "MIN", vertical: "MIN" };
|
|
320466
|
-
const x2 = constrained(c2.horizontal, node2.x, node2.width, frame2.width, "left", "right", "width");
|
|
320467
|
-
const y = constrained(c2.vertical, node2.y, node2.height, frame2.height, "top", "bottom", "height");
|
|
320468
|
-
return { style: { ...limits(node2), ...x2.style, ...y.style }, place: { position: "absolute", ...x2.place, ...y.place } };
|
|
320469
|
-
}
|
|
320470
|
-
function siteLayout(node2, parent, layout2) {
|
|
320471
|
-
const own2 = node2.type === "FRAME" || node2.type === "COMPONENT" || node2.type === "INSTANCE" ? node2 : null;
|
|
320472
|
-
if (!parent) {
|
|
320473
|
-
const grows = !own2 || laysOut(own2) || own2.overflowScrolling === "NONE" || !own2.overflowScrolling;
|
|
320474
|
-
return { style: { ...limits(node2), width: "100%", ...grows ? { height: null, "min-height": `max(${px4(node2.height)}, 100dvh)` } : {} }, place: { position: "relative" } };
|
|
320475
|
-
}
|
|
320476
|
-
const s = node2;
|
|
320477
|
-
return layout2 && laysOut(layout2) && s.layoutPositioning !== "ABSOLUTE" ? flowChild(s, layout2) : placedChild(s, parent, parent.type === "INSTANCE" && layout2 ? layout2 : parent);
|
|
320478
|
-
}
|
|
320479
|
-
var px4, pct2, isStack, isGrid, laysOut, track, limits;
|
|
320480
|
-
var init_responsive = __esm({
|
|
320481
|
-
"lib/io/web/responsive.ts"() {
|
|
320482
|
-
"use strict";
|
|
320483
|
-
px4 = (v) => `${Math.round(v * 100) / 100}px`;
|
|
320484
|
-
pct2 = (v) => `${Math.round(v * 1e4) / 100}%`;
|
|
320485
|
-
isStack = (f2) => f2?.layoutMode === "HORIZONTAL" || f2?.layoutMode === "VERTICAL";
|
|
320486
|
-
isGrid = (f2) => f2?.layoutMode === "GRID";
|
|
320487
|
-
laysOut = (f2) => isStack(f2) || isGrid(f2);
|
|
320488
|
-
track = (t3) => {
|
|
320489
|
-
if (!t3 || t3.sizing === "FILL") return t3?.value && /fr$/.test(t3.value) ? t3.value : "1fr";
|
|
320490
|
-
if (t3.sizing === "HUG") return "auto";
|
|
320491
|
-
return /^[\d.]+$/.test(t3.value) ? `${t3.value}px` : t3.value;
|
|
320492
|
-
};
|
|
320493
|
-
limits = (n) => {
|
|
320494
|
-
const out = {};
|
|
320495
|
-
if (n.minWidth !== void 0) out["min-width"] = px4(n.minWidth);
|
|
320496
|
-
if (n.maxWidth !== void 0) out["max-width"] = px4(n.maxWidth);
|
|
320497
|
-
if (n.minHeight !== void 0) out["min-height"] = px4(n.minHeight);
|
|
320498
|
-
if (n.maxHeight !== void 0) out["max-height"] = px4(n.maxHeight);
|
|
320499
|
-
return out;
|
|
320500
|
-
};
|
|
320501
|
-
}
|
|
320502
|
-
});
|
|
320503
|
-
|
|
320504
|
-
// lib/io/web/richtext.ts
|
|
320505
|
-
function runStyle(seg) {
|
|
320506
|
-
const out = {};
|
|
320507
|
-
if (seg.fontFamily) out["font-family"] = `"${seg.fontFamily}", system-ui, sans-serif`;
|
|
320508
|
-
if (seg.fontSize) out["font-size"] = `${seg.fontSize}px`;
|
|
320509
|
-
if (seg.fontWeight) out["font-weight"] = String(seg.fontWeight);
|
|
320510
|
-
if (seg.fontStyle) out["font-style"] = seg.fontStyle;
|
|
320511
|
-
if (seg.lineHeight !== void 0 && seg.lineHeight !== "AUTO") out["line-height"] = `${seg.lineHeight}px`;
|
|
320512
|
-
if (seg.textDecoration === "UNDERLINE") out["text-decoration"] = "underline";
|
|
320513
|
-
else if (seg.textDecoration === "STRIKETHROUGH") out["text-decoration"] = "line-through";
|
|
320514
|
-
else if (seg.textDecoration === "NONE") out["text-decoration"] = "none";
|
|
320515
|
-
if (seg.textCase === "UPPER") out["text-transform"] = "uppercase";
|
|
320516
|
-
else if (seg.textCase === "LOWER") out["text-transform"] = "lowercase";
|
|
320517
|
-
else if (seg.textCase === "TITLE") out["text-transform"] = "capitalize";
|
|
320518
|
-
else if (seg.textCase === "ORIGINAL") out["text-transform"] = "none";
|
|
320519
|
-
const solid5 = seg.fills?.find((f2) => f2.visible !== false && f2.type === "SOLID" && f2.color);
|
|
320520
|
-
if (solid5?.color) out.color = toHex(solid5.color);
|
|
320521
|
-
return out;
|
|
320522
|
-
}
|
|
320523
|
-
function textRuns(t3) {
|
|
320524
|
-
const text = t3.characters ?? "";
|
|
320525
|
-
const segs = [...t3.styledSegments ?? []].filter((s) => s.end > s.start).sort((a, b) => a.start - b.start);
|
|
320526
|
-
if (!segs.length && !t3.link) return void 0;
|
|
320527
|
-
const runs = [];
|
|
320528
|
-
const push2 = (from2, to, seg) => {
|
|
320529
|
-
if (to <= from2) return;
|
|
320530
|
-
const link2 = seg?.link ?? t3.link;
|
|
320531
|
-
runs.push({ text: text.slice(from2, to), style: seg ? runStyle(seg) : {}, ...link2 ? { link: link2 } : {} });
|
|
320532
|
-
};
|
|
320533
|
-
let at3 = 0;
|
|
320534
|
-
for (const s of segs) {
|
|
320535
|
-
const start2 = Math.max(at3, Math.min(text.length, s.start)), end = Math.min(text.length, s.end);
|
|
320536
|
-
push2(at3, start2);
|
|
320537
|
-
push2(start2, end, s);
|
|
320538
|
-
at3 = Math.max(at3, end);
|
|
320539
|
-
}
|
|
320540
|
-
push2(at3, text.length);
|
|
320541
|
-
return runs;
|
|
320542
|
-
}
|
|
320543
|
-
var init_richtext = __esm({
|
|
320544
|
-
"lib/io/web/richtext.ts"() {
|
|
320545
|
-
"use strict";
|
|
320546
|
-
init_paint2();
|
|
320547
|
-
}
|
|
320548
|
-
});
|
|
320549
|
-
|
|
320550
|
-
// lib/io/web/timeline.ts
|
|
320551
|
-
function frameWebMotion(doc2, frameId, style) {
|
|
320552
|
-
const nodes = doc2.nodes;
|
|
320553
|
-
const frame2 = nodes[frameId];
|
|
320554
|
-
if (!frame2 || !hasFrameMotion(nodes, frameId)) return null;
|
|
320555
|
-
const len3 = timelineDuration(nodes, frameId);
|
|
320556
|
-
if (!(len3 > 0)) return null;
|
|
320557
|
-
const steps = Math.max(1, Math.ceil(len3 / 1e3 * SAMPLE_RATE));
|
|
320558
|
-
const times2 = [];
|
|
320559
|
-
const poses = [];
|
|
320560
|
-
for (let i2 = 0; i2 <= steps; i2++) {
|
|
320561
|
-
const t3 = len3 * i2 / steps;
|
|
320562
|
-
times2.push(t3);
|
|
320563
|
-
poses.push(evaluatePose(nodes, { kind: "frame", frameId }, t3).nodes);
|
|
320564
|
-
}
|
|
320565
|
-
const ids2 = /* @__PURE__ */ new Set();
|
|
320566
|
-
for (const p2 of poses) for (const id3 in p2) if (id3 !== frameId && p2[id3] !== nodes[id3]) ids2.add(id3);
|
|
320567
|
-
const loops = frameRunsOn(nodes, frameId);
|
|
320568
|
-
const out = /* @__PURE__ */ new Map();
|
|
320569
|
-
const tag = frameId.replace(/[^a-zA-Z0-9]/g, "").slice(-6);
|
|
320570
|
-
let n = 0;
|
|
320571
|
-
for (const id3 of ids2) {
|
|
320572
|
-
const rest = id3.includes("::") ? resolveVirtualNode2(nodes, id3) : nodes[id3];
|
|
320573
|
-
if (!rest || !underFrame(nodes, id3, frameId)) continue;
|
|
320574
|
-
const frames = keyframesOf(times2, poses.map((p2) => declarationsOf(p2[id3] ?? rest, rest, style)), len3);
|
|
320575
|
-
if (!frames) continue;
|
|
320576
|
-
out.set(id3, {
|
|
320577
|
-
name: `timeline-${tag}-${n++}`,
|
|
320578
|
-
frames,
|
|
320579
|
-
durationMs: Math.round(len3),
|
|
320580
|
-
delayMs: 0,
|
|
320581
|
-
iterations: loops ? "infinite" : 1,
|
|
320582
|
-
direction: "normal",
|
|
320583
|
-
fill: "both"
|
|
320584
|
-
});
|
|
320585
|
-
}
|
|
320586
|
-
return out.size ? out : null;
|
|
320587
|
-
}
|
|
320588
|
-
function underFrame(nodes, id3, frameId) {
|
|
320589
|
-
const real = id3.split("::")[0];
|
|
320590
|
-
for (let n = nodes[real]; n; n = n.parentId ? nodes[n.parentId] : void 0) if (n.id === frameId) return true;
|
|
320591
|
-
return false;
|
|
320592
|
-
}
|
|
320593
|
-
var init_timeline = __esm({
|
|
320594
|
-
"lib/io/web/timeline.ts"() {
|
|
320595
|
-
"use strict";
|
|
320596
|
-
init_scene_graph();
|
|
320597
|
-
init_pose();
|
|
320598
|
-
init_instances2();
|
|
320599
|
-
init_keyframes();
|
|
320600
|
-
}
|
|
320601
|
-
});
|
|
320602
|
-
|
|
320603
|
-
// lib/io/web/tree.ts
|
|
320604
|
-
function anchorTargets(doc2) {
|
|
320605
|
-
const hit = anchorMemo.get(doc2.nodes);
|
|
320606
|
-
if (hit) return hit;
|
|
320607
|
-
const out = /* @__PURE__ */ new Set();
|
|
320608
|
-
for (const id3 in doc2.nodes) {
|
|
320609
|
-
const n = doc2.nodes[id3];
|
|
320610
|
-
if (n.semantics?.link?.kind === "anchor") out.add(n.semantics.link.nodeId);
|
|
320611
|
-
for (const ix of n.interactions ?? []) if (ix.action.link?.kind === "anchor" && ix.action.link.nodeId) out.add(ix.action.link.nodeId);
|
|
320612
|
-
}
|
|
320613
|
-
anchorMemo.set(doc2.nodes, out);
|
|
320614
|
-
return out;
|
|
320615
|
-
}
|
|
320616
|
-
function spriteOnly(nodes, id3) {
|
|
320617
|
-
let leaves = 0;
|
|
320618
|
-
const visit2 = (nid, depth2) => {
|
|
320619
|
-
const n = nodes[nid];
|
|
320620
|
-
if (!n || n.visible === false) return true;
|
|
320621
|
-
if (n.type === "PIXEL_GRID") {
|
|
320622
|
-
leaves++;
|
|
320623
|
-
return true;
|
|
320624
|
-
}
|
|
320625
|
-
if (depth2 > 8 || n.type !== "INSTANCE" && n.type !== "COMPONENT" && n.type !== "FRAME" && n.type !== "GROUP") return false;
|
|
320626
|
-
const main2 = n.mainComponentId;
|
|
320627
|
-
const kids = n.childIds?.length ? n.childIds : main2 ? [main2] : [];
|
|
320628
|
-
return kids.every((k2) => visit2(k2, depth2 + 1));
|
|
320629
|
-
};
|
|
320630
|
-
return visit2(id3, 0) && leaves > 0;
|
|
320631
|
-
}
|
|
320632
|
-
function prepared(node2, doc2) {
|
|
320633
|
-
let n = node2;
|
|
320634
|
-
if (n.id.includes("::")) n = withInstanceBox(n, doc2.nodes);
|
|
320635
|
-
n = resolveNodeVariables(n, doc2.variables, doc2.variableCollections, doc2.activeVariableModes, exprData(doc2));
|
|
320636
|
-
n = resolveTextNodeStyles(n, doc2.styles ?? {});
|
|
320637
|
-
return n;
|
|
320638
|
-
}
|
|
320639
|
-
function layoutOf2(node2, nodes) {
|
|
320640
|
-
if (!node2) return null;
|
|
320641
|
-
if (node2.type === "INSTANCE") {
|
|
320642
|
-
const mainId = node2.mainComponentId;
|
|
320643
|
-
const main2 = mainId ? nodes[mainId] : void 0;
|
|
320644
|
-
return main2 ?? null;
|
|
320645
|
-
}
|
|
320646
|
-
if (node2.id.includes("::")) {
|
|
320647
|
-
const real = nodes[node2.id.split("::").pop()];
|
|
320648
|
-
return real ?? node2;
|
|
320649
|
-
}
|
|
320650
|
-
return node2;
|
|
320651
|
-
}
|
|
320652
|
-
function buildPlainTree(doc2, nodeId2, opts = {}, start2, hooks = {}) {
|
|
320653
|
-
const cap2 = opts.nodeCap ?? DEFAULT_NODE_CAP;
|
|
320654
|
-
const first2 = doc2.nodes[nodeId2] ?? (nodeId2.includes("::") ? childLookup(doc2, nodeId2) : void 0);
|
|
320655
|
-
if (!first2) throw new Error(`No node ${nodeId2}`);
|
|
320656
|
-
let emitted = 0;
|
|
320657
|
-
let truncated = false;
|
|
320658
|
-
let folds = 0;
|
|
320659
|
-
const tokens = opts.target === "site" && Object.keys(doc2.variables ?? {}).length ? siteTokens(doc2) : null;
|
|
320660
|
-
const anchored = anchorTargets(doc2);
|
|
320661
|
-
const pageItem = () => {
|
|
320662
|
-
const c2 = opts.item && doc2.collections?.[opts.item.collectionId];
|
|
320663
|
-
if (c2 && opts.item.recordId === ITEM_RECORD) return { collection: c2, record: templateRecord(c2), suffix: `~${ITEM_RECORD}` };
|
|
320664
|
-
const r = opts.item && doc2.records?.[opts.item.recordId];
|
|
320665
|
-
return c2 && r ? { collection: c2, record: r, suffix: "" } : null;
|
|
320666
|
-
};
|
|
320667
|
-
let item = pageItem();
|
|
320668
|
-
const scopeOf2 = (it) => itemScope(it.collection, it.record, withData(variablesScope(doc2.variables, doc2.variableCollections, doc2.activeVariableModes), doc2));
|
|
320669
|
-
const itemised = (node2, raw, it) => itemNode(node2, raw, it.collection, it.record, scopeOf2(it));
|
|
320670
|
-
const itemLink = (link2, it) => {
|
|
320671
|
-
const filled2 = it && link2.kind === "url" ? { ...link2, url: itemText(link2.url, it.collection, it.record) } : it && (link2.kind === "email" || link2.kind === "tel") ? { ...link2, value: itemText(link2.value, it.collection, it.record) } : link2;
|
|
320672
|
-
if (filled2.kind === "screen") {
|
|
320673
|
-
const dest = doc2.nodes[filled2.frameId];
|
|
320674
|
-
const base = opts.routes?.[filled2.frameId];
|
|
320675
|
-
const of = dest?.route?.collectionId;
|
|
320676
|
-
if (of && base !== void 0) {
|
|
320677
|
-
const slugField = it?.record.id === ITEM_RECORD && it.collection.id === of ? it.collection.fields.find((f2) => f2.id === it.collection.slugFieldId) ?? it.collection.fields.find((f2) => f2.type === "SLUG" || f2.type === "TEXT") : void 0;
|
|
320678
|
-
if (slugField) return { link: filled2, href: `${base === "/" ? "" : base}/${itemMark(fieldKey(slugField.name))}`, screen: filled2.frameId };
|
|
320679
|
-
const slugs = recordSlugs(doc2, of);
|
|
320680
|
-
const rec = it?.collection.id === of ? it.record.id : slugs.keys().next().value;
|
|
320681
|
-
const slug3 = rec ? slugs.get(rec) : void 0;
|
|
320682
|
-
return slug3 ? { link: filled2, href: `${base === "/" ? "" : base}/${slug3}`, screen: `${filled2.frameId}~${rec}` } : { link: filled2, href: null };
|
|
320683
|
-
}
|
|
320684
|
-
return { link: filled2, href: base ?? null, screen: filled2.frameId };
|
|
320685
|
-
}
|
|
320686
|
-
if (filled2.kind === "url" && it?.record.id === ITEM_RECORD && itemMarks(filled2.url)) return { link: filled2, href: filled2.url.trim() };
|
|
320687
|
-
return { link: filled2, href: hrefOf(filled2, doc2.nodes, opts.routes) };
|
|
320688
|
-
};
|
|
320689
|
-
const fields = /* @__PURE__ */ new Map();
|
|
320690
|
-
const styleOpts = { fullImageUrl: opts.fullImageUrls ?? opts.target === "site" };
|
|
320691
|
-
const stylesOf = (n) => styleMapFor(n, doc2.styles, styleOpts);
|
|
320692
|
-
let motion = null;
|
|
320693
|
-
const timeline = !opts.static && !start2 && first2.type === "FRAME" ? frameWebMotion(doc2, first2.id, (n) => stylesOf(prepared(n, doc2))) : null;
|
|
320694
|
-
const build3 = (raw, parent, in3D2, fold) => {
|
|
320695
|
-
if (emitted >= cap2) {
|
|
320696
|
-
truncated = true;
|
|
320697
|
-
return null;
|
|
320698
|
-
}
|
|
320699
|
-
emitted++;
|
|
320700
|
-
const node2 = item ? itemised(prepared(raw, doc2), raw, item) : prepared(raw, doc2);
|
|
320701
|
-
const waits = node2.visible === false && parent !== null;
|
|
320702
|
-
if (waits && !(opts.target === "site" && followsVisibility(raw))) return null;
|
|
320703
|
-
const exp = expressibility(node2, doc2.styles);
|
|
320704
|
-
const f2 = layoutOf2(node2, doc2.nodes) ?? node2;
|
|
320705
|
-
const style = stylesOf(node2);
|
|
320706
|
-
if (f2 !== node2 && !style.display) Object.assign(style, flexDeclarations(f2));
|
|
320707
|
-
const through = in3D2 && passesThrough(raw, doc2.nodes);
|
|
320708
|
-
const own2 = typeof node2.opacity === "number" ? node2.opacity : 1;
|
|
320709
|
-
if (through) {
|
|
320710
|
-
style["transform-style"] = "preserve-3d";
|
|
320711
|
-
delete style.opacity;
|
|
320712
|
-
style[foldVar(fold + 1)] = fold ? `calc(var(${foldVar(fold)}) * ${round3(own2)})` : String(round3(own2));
|
|
320713
|
-
folds = Math.max(folds, fold + 1);
|
|
320714
|
-
} else if (fold) style.opacity = own2 === 1 ? `var(${foldVar(fold)})` : `calc(var(${foldVar(fold)}) * ${round3(own2)})`;
|
|
320715
|
-
if (own2 === 0) style["pointer-events"] = "none";
|
|
320716
|
-
if (clickable(raw) && !style.cursor) style.cursor = "pointer";
|
|
320717
|
-
const web = {
|
|
320718
|
-
id: item?.suffix ? `${node2.id}${item.suffix}` : node2.id,
|
|
320719
|
-
name: node2.name || node2.type,
|
|
320720
|
-
type: node2.type,
|
|
320721
|
-
x: Math.round(node2.x),
|
|
320722
|
-
y: Math.round(node2.y),
|
|
320723
|
-
width: Math.round(node2.width),
|
|
320724
|
-
height: Math.round(node2.height),
|
|
320725
|
-
// Absolutely-positioned auto-layout children are taken out of the flow, exactly as the canvas does.
|
|
320726
|
-
// A grid's children are in its flow too: its tracks place them.
|
|
320727
|
-
positioning: (isFlex(layoutOf2(parent, doc2.nodes)) || layoutOf2(parent, doc2.nodes)?.layoutMode === "GRID") && node2.layoutPositioning !== "ABSOLUTE" ? "flow" : "absolute",
|
|
320728
|
-
style,
|
|
320729
|
-
children: []
|
|
320730
|
-
};
|
|
320731
|
-
if (tokens) Object.assign(style, tokenStyle(raw, style, tokens));
|
|
320732
|
-
if (opts.target === "site") {
|
|
320733
|
-
const lay = siteLayout(node2, parent, layoutOf2(parent, doc2.nodes));
|
|
320734
|
-
for (const [k2, v] of Object.entries(lay.style)) {
|
|
320735
|
-
if (v === null) delete style[k2];
|
|
320736
|
-
else style[k2] = v;
|
|
320737
|
-
}
|
|
320738
|
-
if (laysOut(f2) || f2.overflowScrolling) Object.assign(style, containerStyle(f2));
|
|
320739
|
-
if (node2.type === "TEXT") {
|
|
320740
|
-
if (style["white-space"] === "pre") {
|
|
320741
|
-
style["white-space"] = "pre-wrap";
|
|
320742
|
-
style.width = "fit-content";
|
|
320743
|
-
}
|
|
320744
|
-
if (style["max-width"] === void 0) style["max-width"] = "100%";
|
|
320745
|
-
if (style.height && style.height !== "auto") {
|
|
320746
|
-
style["min-height"] = style.height;
|
|
320747
|
-
delete style.height;
|
|
320748
|
-
}
|
|
320749
|
-
}
|
|
320750
|
-
if (lay.place && (parent !== null || !start2?.parent)) web.place = lay.place;
|
|
320751
|
-
}
|
|
320752
|
-
if (waits) web.hidden = true;
|
|
320753
|
-
const sem = node2.semantics;
|
|
320754
|
-
if (sem) {
|
|
320755
|
-
if (sem.tag && sem.tag !== "div") web.tag = sem.tag;
|
|
320756
|
-
const attrs = {};
|
|
320757
|
-
if (sem.label) attrs["aria-label"] = sem.label;
|
|
320758
|
-
if (sem.hidden) attrs["aria-hidden"] = "true";
|
|
320759
|
-
if (Object.keys(attrs).length) web.attrs = attrs;
|
|
320760
|
-
const to = sem.link ? itemLink(sem.link, item) : null;
|
|
320761
|
-
if (to?.href) web.link = { href: to.href, ...opensNewTab(to.link) ? { newTab: true } : {}, ...to.screen ? { screen: to.screen } : {} };
|
|
320762
|
-
}
|
|
320763
|
-
const control = node2.control;
|
|
320764
|
-
if (control) {
|
|
320765
|
-
const named = control.name ? { name: control.name } : {};
|
|
320766
|
-
if (control.kind === "FORM") {
|
|
320767
|
-
web.tag = "form";
|
|
320768
|
-
if (isCommerceAction(control.formAction)) web.action = control.formAction;
|
|
320769
|
-
} else if (control.kind === "BUTTON") {
|
|
320770
|
-
web.tag = "button";
|
|
320771
|
-
web.attrs = { ...web.attrs, type: control.buttonType ?? "submit", ...named, ...control.name && control.value !== void 0 ? { value: item && hasItemToken(control.value) ? itemText(control.value, item.collection, item.record) : control.value } : {} };
|
|
320772
|
-
} else if (control.kind === "CHECKBOX" || control.kind === "RADIO") {
|
|
320773
|
-
web.check = { attrs: { type: control.kind === "RADIO" ? "radio" : "checkbox", ...named, ...control.value !== void 0 ? { value: control.value } : {}, ...control.checked ? { checked: "" } : {}, ...control.required ? { required: "" } : {} }, ...control.variableId ? { variable: control.variableId } : {} };
|
|
320774
|
-
} else fields.set(fieldPart(doc2.nodes, raw.id) ?? raw.id, control);
|
|
320775
|
-
}
|
|
320776
|
-
const control0 = fields.get(raw.id);
|
|
320777
|
-
const field = control0 && item && control0.value !== void 0 && hasItemToken(control0.value) ? { ...control0, value: itemText(control0.value, item.collection, item.record) } : control0;
|
|
320778
|
-
if (field) {
|
|
320779
|
-
const tag = field.kind === "TEXTAREA" ? "textarea" : field.kind === "SELECT" ? "select" : "input";
|
|
320780
|
-
const words = node2.characters;
|
|
320781
|
-
web.input = {
|
|
320782
|
-
tag,
|
|
320783
|
-
attrs: {
|
|
320784
|
-
...tag === "input" ? { type: field.inputType ?? "text" } : {},
|
|
320785
|
-
...field.name ? { name: field.name } : {},
|
|
320786
|
-
...tag !== "select" && (field.placeholder ?? words) ? { placeholder: field.placeholder ?? words } : {},
|
|
320787
|
-
...field.required ? { required: "" } : {},
|
|
320788
|
-
...tag === "input" && field.value !== void 0 ? { value: field.value } : {},
|
|
320789
|
-
"aria-label": node2.semantics?.label ?? field.placeholder ?? field.name ?? web.name
|
|
320790
|
-
},
|
|
320791
|
-
...tag === "select" ? { options: field.options ?? [] } : {},
|
|
320792
|
-
...tag !== "input" && field.value !== void 0 ? { value: field.value } : {},
|
|
320793
|
-
...field.variableId ? { variable: field.variableId } : {}
|
|
320794
|
-
};
|
|
320795
|
-
}
|
|
320796
|
-
if (sem?.anchor || anchored.has(node2.id)) web.attrs = { ...web.attrs, id: anchorOf(node2) };
|
|
320797
|
-
if (through) web.preserve3d = true;
|
|
320798
|
-
web.tf = transformParts(node2);
|
|
320799
|
-
if (typeof node2.altText === "string") web.alt = node2.altText;
|
|
320800
|
-
if (parent === null) web.positioning = start2?.parent ? web.positioning : "flow";
|
|
320801
|
-
if (f2.layoutMode === "HORIZONTAL" || f2.layoutMode === "VERTICAL") {
|
|
320802
|
-
web.layout = {
|
|
320803
|
-
direction: f2.layoutMode === "HORIZONTAL" ? "row" : "column",
|
|
320804
|
-
gap: f2.itemSpacing ?? 0,
|
|
320805
|
-
justify: JUSTIFY[f2.primaryAxisAlignItems ?? "MIN"],
|
|
320806
|
-
align: ALIGN2[f2.counterAxisAlignItems ?? "MIN"],
|
|
320807
|
-
padding: f2.padding ?? { top: 0, right: 0, bottom: 0, left: 0 }
|
|
320808
|
-
};
|
|
320809
|
-
}
|
|
320810
|
-
if (node2.type === "TEXT") {
|
|
320811
|
-
const t3 = node2;
|
|
320812
|
-
const solid5 = (t3.fills ?? []).find((p2) => p2.visible !== false && p2.type === "SOLID" && p2.color);
|
|
320813
|
-
web.text = {
|
|
320814
|
-
characters: t3.characters ?? "",
|
|
320815
|
-
align: t3.textAlign,
|
|
320816
|
-
fontFamily: t3.fontFamily,
|
|
320817
|
-
fontSize: t3.fontSize,
|
|
320818
|
-
fontWeight: t3.fontWeight,
|
|
320819
|
-
italic: t3.fontStyle === "italic",
|
|
320820
|
-
...solid5?.color ? { color: toHex(solid5.color) } : {},
|
|
320821
|
-
...t3.letterSpacing ? { letterSpacing: t3.letterSpacing } : {},
|
|
320822
|
-
...t3.lineHeight !== "AUTO" ? { lineHeight: t3.lineHeight } : {}
|
|
320823
|
-
};
|
|
320824
|
-
const runs = textRuns(t3);
|
|
320825
|
-
if (runs) web.runs = runs;
|
|
320826
|
-
}
|
|
320827
|
-
const tl = timeline?.get(node2.id);
|
|
320828
|
-
const mo = tl ?? motion?.children.get(node2.id);
|
|
320829
|
-
if (mo) web.motion = { style: animationStyle(mo, tl ? "load" : motion.trigger), keyframes: keyframesCSS(mo) };
|
|
320830
|
-
const ext = getNativeExtension(raw.type);
|
|
320831
|
-
if (ext?.toWeb) {
|
|
320832
|
-
const said = ext.toWeb(node2, { escape: escapeHTML, color: (c2) => toRgba({ ...c2, a: c2.a ?? 1 }) });
|
|
320833
|
-
if (said.tag) web.tag = said.tag;
|
|
320834
|
-
Object.assign(style, said.style);
|
|
320835
|
-
web.html = said.html;
|
|
320836
|
-
hooks.built?.(web, node2, { parent, in3D: in3D2, fold });
|
|
320837
|
-
return web;
|
|
320838
|
-
}
|
|
320839
|
-
const code = opts.target === "site" ? codeOf(doc2.nodes, raw) : null;
|
|
320840
|
-
if (code && doc2.codeModules?.[code.moduleId]) {
|
|
320841
|
-
for (const k2 of PAINTED) delete style[k2];
|
|
320842
|
-
web.code = { module: code.moduleId, ...code.exportName ? { export: code.exportName } : {}, props: codeProps(doc2.nodes, node2) };
|
|
320843
|
-
hooks.built?.(web, node2, { parent, in3D: in3D2, fold });
|
|
320844
|
-
return web;
|
|
320845
|
-
}
|
|
320846
|
-
const sprite = opts.target === "site" && raw.type === "INSTANCE" && !raw.id.includes("::") && spriteOnly(doc2.nodes, raw.id) && isLive(doc2.nodes, raw.id);
|
|
320847
|
-
if (!exp.css || sprite) {
|
|
320848
|
-
for (const k2 of PAINTED) delete style[k2];
|
|
320849
|
-
web.asset = { kind: opts.assetKind ?? (exp.needsRaster ? "png" : "svg"), reason: exp.reason || (sprite ? "an animated sprite" : ""), ...item?.suffix ? { of: node2.id } : {} };
|
|
320850
|
-
if (isPixelArt(doc2, raw.id)) style["image-rendering"] = "pixelated";
|
|
320851
|
-
if (sprite || opts.target === "site" && renderMode(node2, { styles: doc2.styles, live: isLive(doc2.nodes, raw.id) }) === "island") web.island = true;
|
|
320852
|
-
hooks.built?.(web, node2, { parent, in3D: in3D2, fold });
|
|
320853
|
-
return web;
|
|
320854
|
-
}
|
|
320855
|
-
const lost = capability(node2, "css", doc2.styles).dropped.find((f3) => f3.startsWith("paint:"));
|
|
320856
|
-
if (lost && !node2.id.includes("::")) {
|
|
320857
|
-
const site = opts.target === "site";
|
|
320858
|
-
style.isolation = "isolate";
|
|
320859
|
-
web.children.push({
|
|
320860
|
-
id: `${node2.id}/backdrop${item?.suffix ?? ""}`,
|
|
320861
|
-
name: `${web.name} fill`,
|
|
320862
|
-
type: "BACKDROP",
|
|
320863
|
-
x: 0,
|
|
320864
|
-
y: 0,
|
|
320865
|
-
width: web.width,
|
|
320866
|
-
height: web.height,
|
|
320867
|
-
positioning: "absolute",
|
|
320868
|
-
...site ? { place: { position: "absolute", inset: "0" } } : {},
|
|
320869
|
-
style: { ...site ? {} : { width: `${web.width}px`, height: `${web.height}px` }, "border-radius": "inherit", overflow: "hidden", "z-index": "-1", "pointer-events": "none" },
|
|
320870
|
-
alt: "",
|
|
320871
|
-
asset: { kind: "png", reason: featureName(lost), of: node2.id, self: true },
|
|
320872
|
-
...site && movesItself(raw) ? { island: true } : {},
|
|
320873
|
-
children: []
|
|
320874
|
-
});
|
|
320875
|
-
}
|
|
320876
|
-
const outer = motion;
|
|
320877
|
-
if (!motion && node2.type === "INSTANCE" && !opts.static) {
|
|
320878
|
-
motion = instanceWebMotion(doc2, node2, (n) => stylesOf(prepared(n, doc2)));
|
|
320879
|
-
if (motion && (motion.trigger !== "load" || opts.target === "site")) web.motionTrigger = motion.trigger;
|
|
320880
|
-
}
|
|
320881
|
-
try {
|
|
320882
|
-
if (opts.includeChildren !== false) {
|
|
320883
|
-
const kids3D = in3D2 ? through : is3DContext(raw) && !raw.id.includes("::");
|
|
320884
|
-
const kidFold = through ? fold + 1 : 0;
|
|
320885
|
-
const repeat = raw.repeat;
|
|
320886
|
-
const collection = repeat && doc2.collections?.[repeat.collectionId];
|
|
320887
|
-
if (repeat && collection && opts.target === "site") {
|
|
320888
|
-
const outerItem = item;
|
|
320889
|
-
const under = outerItem ? scopeOf2(outerItem) : withData(variablesScope(doc2.variables, doc2.variableCollections, doc2.activeVariableModes), doc2);
|
|
320890
|
-
try {
|
|
320891
|
-
for (const record2 of repeatRecords(doc2, repeat, under)) {
|
|
320892
|
-
item = { collection, record: record2, suffix: `${outerItem?.suffix ?? ""}~${record2.id}` };
|
|
320893
|
-
for (const child of childrenOf(node2, doc2.nodes)) {
|
|
320894
|
-
const built = build3(child, node2, kids3D, kidFold);
|
|
320895
|
-
if (built) web.children.push(built);
|
|
320896
|
-
}
|
|
320897
|
-
}
|
|
320898
|
-
if (collection.perVisitor && !outerItem || collection.schema && opts.listTemplates) {
|
|
320899
|
-
item = { collection, record: templateRecord(collection), suffix: `~${ITEM_RECORD}` };
|
|
320900
|
-
const template2 = [];
|
|
320901
|
-
for (const child of childrenOf(node2, doc2.nodes)) {
|
|
320902
|
-
const built = build3(child, node2, kids3D, kidFold);
|
|
320903
|
-
if (built) template2.push(built);
|
|
320904
|
-
}
|
|
320905
|
-
const sortField = repeat.sort && collection.fields.find((f3) => f3.id === repeat.sort.fieldId);
|
|
320906
|
-
web.repeat = {
|
|
320907
|
-
collectionId: collection.id,
|
|
320908
|
-
template: template2,
|
|
320909
|
-
...repeat.filter?.trim() ? { filter: repeat.filter } : {},
|
|
320910
|
-
...sortField ? { sort: { key: fieldKey(sortField.name), dir: repeat.sort.dir } } : {},
|
|
320911
|
-
...repeat.offset ? { offset: repeat.offset } : {},
|
|
320912
|
-
...repeat.limit ? { limit: repeat.limit } : {}
|
|
320913
|
-
};
|
|
320914
|
-
}
|
|
320915
|
-
} finally {
|
|
320916
|
-
item = outerItem;
|
|
320917
|
-
}
|
|
320918
|
-
} else for (const child of childrenOf(node2, doc2.nodes)) {
|
|
320919
|
-
const built = build3(child, node2, kids3D, kidFold);
|
|
320920
|
-
if (built) web.children.push(built);
|
|
320921
|
-
}
|
|
320922
|
-
}
|
|
320923
|
-
} finally {
|
|
320924
|
-
motion = outer;
|
|
320925
|
-
}
|
|
320926
|
-
if (web.children.some((c2) => c2.positioning === "absolute")) {
|
|
320927
|
-
for (const c2 of web.children) if (c2.positioning === "flow") c2.layered = true;
|
|
320928
|
-
}
|
|
320929
|
-
hooks.built?.(web, node2, { parent, in3D: in3D2, fold });
|
|
320930
|
-
return web;
|
|
320931
|
-
};
|
|
320932
|
-
const root2 = build3(first2, start2?.parent ?? null, start2?.in3D ?? false, start2?.fold ?? 0);
|
|
320933
|
-
if (!root2) throw new Error("Node cap of 0");
|
|
320934
|
-
return { root: root2, truncated, ...folds ? { rules: foldRules(folds) } : {}, ...tokens?.vars.length ? { tokens } : {} };
|
|
320935
|
-
}
|
|
320936
|
-
function childLookup(doc2, id3) {
|
|
320937
|
-
const at3 = id3.lastIndexOf("::");
|
|
320938
|
-
const host = at3 > 0 ? id3.slice(0, at3) : "";
|
|
320939
|
-
const hostNode = doc2.nodes[host] ?? (host.includes("::") ? childLookup(doc2, host) : void 0);
|
|
320940
|
-
return hostNode ? childrenOf(hostNode, doc2.nodes).find((c2) => c2.id === id3) : void 0;
|
|
320941
|
-
}
|
|
320942
|
-
function flatten2(node2, out = []) {
|
|
320943
|
-
out.push(node2);
|
|
320944
|
-
for (const c2 of node2.children) flatten2(c2, out);
|
|
320945
|
-
return out;
|
|
320946
|
-
}
|
|
320947
|
-
var DEFAULT_NODE_CAP, PAINTED, anchorMemo, followsVisibility, isFlex, round3, foldVar, foldRules, clickable;
|
|
320948
|
-
var init_tree = __esm({
|
|
320949
|
-
"lib/io/web/tree.ts"() {
|
|
320950
|
-
"use strict";
|
|
320951
|
-
init_pixel_art();
|
|
320952
|
-
init_instance_layout();
|
|
320953
|
-
init_text_styles();
|
|
320954
|
-
init_variables();
|
|
320955
|
-
init_scene3d();
|
|
320956
|
-
init_semantics();
|
|
320957
|
-
init_commerce();
|
|
320958
|
-
init_collections();
|
|
320959
|
-
init_props();
|
|
320960
|
-
init_native_registry();
|
|
320961
|
-
init_controls();
|
|
320962
|
-
init_expressions2();
|
|
320963
|
-
init_children();
|
|
320964
|
-
init_css();
|
|
320965
|
-
init_capability();
|
|
320966
|
-
init_expressible();
|
|
320967
|
-
init_motion();
|
|
320968
|
-
init_element();
|
|
320969
|
-
init_paint2();
|
|
320970
|
-
init_responsive();
|
|
320971
|
-
init_richtext();
|
|
320972
|
-
init_tokens2();
|
|
320973
|
-
init_timeline();
|
|
320974
|
-
init_interactive();
|
|
320975
|
-
DEFAULT_NODE_CAP = 120;
|
|
320976
|
-
PAINTED = ["background", "border", "border-style", "border-color", "border-width", "outline", "border-radius", "box-shadow", "box-sizing", "filter", "backdrop-filter"];
|
|
320977
|
-
anchorMemo = /* @__PURE__ */ new WeakMap();
|
|
320978
|
-
followsVisibility = (n) => !!n.boundVariables?.visible || !!n.boundExpressions?.visible || // Hidden in the design and shown at a breakpoint: on the page, for the media query that shows it.
|
|
320979
|
-
Object.values(n.responsive ?? {}).some((o) => o.visible === true) || // A game's win banner (LayerPhysics role 'win') and a player's run and jump poses: hidden in the design, shown by
|
|
320980
|
-
// the platformer on winning or as the player moves.
|
|
320981
|
-
n.physics?.role === "win" || n.physics?.role === "pose" || n.physics?.role === "reveal";
|
|
320982
|
-
isFlex = (f2) => f2?.layoutMode === "HORIZONTAL" || f2?.layoutMode === "VERTICAL";
|
|
320983
|
-
round3 = (v) => Math.round(v * 1e3) / 1e3;
|
|
320984
|
-
foldVar = (depth2) => `--pc-f${depth2}`;
|
|
320985
|
-
foldRules = (depth2) => Array.from({ length: depth2 }, (_, i2) => `@property ${foldVar(i2 + 1)} { syntax: '<number>'; inherits: true; initial-value: 1; }`);
|
|
320986
|
-
clickable = (n) => !!n.semantics?.link || (n.interactions ?? []).some((ix) => ix.trigger === "ON_CLICK" || ix.trigger === "ON_PRESS");
|
|
320987
|
-
}
|
|
320988
|
-
});
|
|
320989
|
-
|
|
320990
|
-
// lib/io/web/interactive.ts
|
|
320991
|
-
function subtreeIds(doc2, id3, out = /* @__PURE__ */ new Set()) {
|
|
320992
|
-
if (out.has(id3)) return out;
|
|
320993
|
-
const n = doc2.nodes[id3];
|
|
320994
|
-
if (!n) return out;
|
|
320995
|
-
out.add(id3);
|
|
320996
|
-
if (n.type === "INSTANCE") subtreeIds(doc2, n.mainComponentId, out);
|
|
320997
|
-
for (const c2 of n.childIds ?? []) subtreeIds(doc2, c2, out);
|
|
320998
|
-
return out;
|
|
320999
|
-
}
|
|
321000
|
-
function flowScreens(doc2, startId) {
|
|
321001
|
-
const start2 = doc2.nodes[startId];
|
|
321002
|
-
if (!start2 || start2.type !== "FRAME" || doc2.nodes[start2.parentId ?? ""]?.type !== "PAGE") return [startId];
|
|
321003
|
-
const out = [startId];
|
|
321004
|
-
for (let i2 = 0; i2 < out.length; i2++) {
|
|
321005
|
-
for (const id3 of subtreeIds(doc2, out[i2])) {
|
|
321006
|
-
for (const ix of interactionsOf(doc2.nodes[id3])) {
|
|
321007
|
-
const to = ix.action.navigationType === "NAVIGATE" ? ix.action.destinationId : null;
|
|
321008
|
-
const dest = to ? doc2.nodes[to] : void 0;
|
|
321009
|
-
if (!dest || out.includes(dest.id) || dest.type !== "FRAME" || doc2.nodes[dest.parentId ?? ""]?.type !== "PAGE") continue;
|
|
321010
|
-
if (Math.round(dest.width) !== Math.round(start2.width) || Math.round(dest.height) !== Math.round(start2.height)) continue;
|
|
321011
|
-
out.push(dest.id);
|
|
321012
|
-
}
|
|
321013
|
-
}
|
|
321014
|
-
}
|
|
321015
|
-
return out;
|
|
321016
|
-
}
|
|
321017
|
-
function variantStates(doc2, mainId) {
|
|
321018
|
-
const out = [mainId];
|
|
321019
|
-
for (let i2 = 0; i2 < out.length; i2++) {
|
|
321020
|
-
for (const id3 of subtreeIds(doc2, out[i2])) {
|
|
321021
|
-
for (const ix of interactionsOf(doc2.nodes[id3])) {
|
|
321022
|
-
const to = ix.action.navigationType === "CHANGE_TO" ? ix.action.destinationId : null;
|
|
321023
|
-
if (to && !out.includes(to) && doc2.nodes[to]?.type === "COMPONENT") out.push(to);
|
|
321024
|
-
}
|
|
321025
|
-
}
|
|
321026
|
-
}
|
|
321027
|
-
return out;
|
|
321028
|
-
}
|
|
321029
|
-
function buildState(ctx2, doc2, id3, machine, state, start2, variantOf2) {
|
|
321030
|
-
const expand = /* @__PURE__ */ new Map();
|
|
321031
|
-
const tree = buildPlainTree(doc2, id3, ctx2.opts, start2, { built: (web, _node, at3) => {
|
|
321032
|
-
if (web.type === "INSTANCE") expand.set(web, at3);
|
|
321033
|
-
} });
|
|
321034
|
-
for (const r of tree.rules ?? []) ctx2.rules.add(r);
|
|
321035
|
-
if (tree.truncated) ctx2.truncated = true;
|
|
321036
|
-
const ids2 = /* @__PURE__ */ new Map();
|
|
321037
|
-
const index2 = (w) => {
|
|
321038
|
-
ids2.set(w.id, w);
|
|
321039
|
-
w.children.forEach(index2);
|
|
321040
|
-
};
|
|
321041
|
-
index2(tree.root);
|
|
321042
|
-
const visit2 = (w, owner, st, isRoot) => {
|
|
321043
|
-
w.owner = owner;
|
|
321044
|
-
w.looks = { [st]: lookOf(w, isRoot) };
|
|
321045
|
-
if (w.motion) ctx2.keyframes.add(w.motion.keyframes);
|
|
321046
|
-
const node2 = nodeOf(doc2, w.id);
|
|
321047
|
-
note(ctx2, w, interactionsOf(doc2.nodes[realId(w.id)]), owner, st, ids2);
|
|
321048
|
-
const at3 = expand.get(w);
|
|
321049
|
-
const inst = node2?.type === "INSTANCE" ? node2 : void 0;
|
|
321050
|
-
const states = inst && at3 && ctx2.depth < 4 ? variantStates(doc2, inst.mainComponentId) : [];
|
|
321051
|
-
if (inst && at3 && states.length > 1 && w.id !== variantOf2) {
|
|
321052
|
-
const m = { id: `m${ctx2.machines.length}`, initial: inst.mainComponentId, states: states.map((s) => ({ id: s, name: stateName(doc2, s) })) };
|
|
321053
|
-
ctx2.machines.push(m);
|
|
321054
|
-
w.machine = m;
|
|
321055
|
-
const perState = [];
|
|
321056
|
-
for (const s of states) {
|
|
321057
|
-
let kids;
|
|
321058
|
-
if (s === inst.mainComponentId) {
|
|
321059
|
-
kids = w.children;
|
|
321060
|
-
kids.forEach((c2) => visit2(c2, m.id, s, false));
|
|
321061
|
-
} else {
|
|
321062
|
-
const shown2 = { ...doc2, nodes: { ...doc2.nodes, [inst.id]: { ...inst, mainComponentId: s } } };
|
|
321063
|
-
ctx2.depth++;
|
|
321064
|
-
try {
|
|
321065
|
-
kids = buildState(ctx2, shown2, inst.id, m.id, s, at3, inst.id).children;
|
|
321066
|
-
} finally {
|
|
321067
|
-
ctx2.depth--;
|
|
321068
|
-
}
|
|
321069
|
-
}
|
|
321070
|
-
note(ctx2, w, interactionsOf(doc2.nodes[s]), m.id, s, ids2, m.id);
|
|
321071
|
-
perState.push([s, kids]);
|
|
321072
|
-
}
|
|
321073
|
-
w.children = mergeChildren(perState, m.id, m.states.map((s) => s.id), ctx2);
|
|
321074
|
-
} else if (w.id === variantOf2) {
|
|
321075
|
-
w.children.forEach((c2) => visit2(c2, owner, st, false));
|
|
321076
|
-
} else {
|
|
321077
|
-
if (inst) note(ctx2, w, interactionsOf(doc2.nodes[inst.mainComponentId]), owner, st, ids2);
|
|
321078
|
-
w.children.forEach((c2) => visit2(c2, owner, st, false));
|
|
321079
|
-
}
|
|
321080
|
-
};
|
|
321081
|
-
visit2(tree.root, machine, state, !start2);
|
|
321082
|
-
return tree.root;
|
|
321083
|
-
}
|
|
321084
|
-
function note(ctx2, w, list2, machine, state, ids2, hostMachine) {
|
|
321085
|
-
if (!list2.length) return;
|
|
321086
|
-
const at3 = ctx2.pending.get(w) ?? [];
|
|
321087
|
-
for (const ix of list2) at3.push({ machine, state, ix, hostMachine: hostMachine ?? (machine !== FLOW ? machine : void 0), ids: ids2 });
|
|
321088
|
-
ctx2.pending.set(w, at3);
|
|
321089
|
-
}
|
|
321090
|
-
function lookOf(w, isRoot) {
|
|
321091
|
-
return {
|
|
321092
|
-
style: { ...placementStyle(w, isRoot), ...w.style, ...w.motion?.style ?? {} },
|
|
321093
|
-
...w.text ? { text: w.text.characters } : {},
|
|
321094
|
-
...w.tf ? { tf: w.tf } : {}
|
|
321095
|
-
};
|
|
321096
|
-
}
|
|
321097
|
-
function keyed(kids) {
|
|
321098
|
-
const seen = /* @__PURE__ */ new Map();
|
|
321099
|
-
return kids.map((k2) => {
|
|
321100
|
-
const base = `${k2.name}\0${k2.type}`;
|
|
321101
|
-
const i2 = seen.get(base) ?? 0;
|
|
321102
|
-
seen.set(base, i2 + 1);
|
|
321103
|
-
return [`${base}\0${i2}`, k2];
|
|
321104
|
-
});
|
|
321105
|
-
}
|
|
321106
|
-
function mergeChildren(perState, machine, states, ctx2) {
|
|
321107
|
-
const order2 = [];
|
|
321108
|
-
const groups = /* @__PURE__ */ new Map();
|
|
321109
|
-
for (const [state, kids] of perState) {
|
|
321110
|
-
let after = -1;
|
|
321111
|
-
for (const [k2, node2] of keyed(kids)) {
|
|
321112
|
-
let at3 = order2.indexOf(k2);
|
|
321113
|
-
if (at3 < 0) {
|
|
321114
|
-
order2.splice(after + 1, 0, k2);
|
|
321115
|
-
at3 = after + 1;
|
|
321116
|
-
}
|
|
321117
|
-
after = at3;
|
|
321118
|
-
(groups.get(k2) ?? groups.set(k2, []).get(k2)).push([state, node2]);
|
|
321119
|
-
}
|
|
321120
|
-
}
|
|
321121
|
-
return order2.map((k2) => mergeNode(groups.get(k2), machine, states, ctx2));
|
|
321122
|
-
}
|
|
321123
|
-
function mergeNode(items, machine, states, ctx2) {
|
|
321124
|
-
const [, first2] = items[0];
|
|
321125
|
-
if (first2.owner !== machine) {
|
|
321126
|
-
for (const [, w] of items.slice(1)) alias(ctx2, w, first2);
|
|
321127
|
-
return first2;
|
|
321128
|
-
}
|
|
321129
|
-
const looks = {};
|
|
321130
|
-
for (const s of states) looks[s] = null;
|
|
321131
|
-
for (const [s, w] of items) looks[s] = w.looks?.[s] ?? null;
|
|
321132
|
-
const merged = { ...first2, looks };
|
|
321133
|
-
const pend = items.flatMap(([, w]) => ctx2.pending.get(w) ?? []);
|
|
321134
|
-
if (pend.length) ctx2.pending.set(merged, pend);
|
|
321135
|
-
for (const [, w] of items) if (w !== merged) alias(ctx2, w, merged);
|
|
321136
|
-
if (first2.machine) {
|
|
321137
|
-
for (const [, w] of items) if (w.machine && w.machine !== first2.machine) ctx2.renamed.set(w.machine.id, first2.machine.id);
|
|
321138
|
-
}
|
|
321139
|
-
merged.children = first2.machine ? first2.children : mergeChildren(items.map(([s, w]) => [s, w.children]), machine, states, ctx2);
|
|
321140
|
-
return merged;
|
|
321141
|
-
}
|
|
321142
|
-
function alias(ctx2, from2, to) {
|
|
321143
|
-
const a = ctx2.alias ??= /* @__PURE__ */ new Map();
|
|
321144
|
-
a.set(from2, to);
|
|
321145
|
-
}
|
|
321146
|
-
function mergedOf(ctx2, w) {
|
|
321147
|
-
const a = ctx2.alias;
|
|
321148
|
-
let cur = w;
|
|
321149
|
-
for (let i2 = 0; i2 < 16 && a?.has(cur); i2++) cur = a.get(cur);
|
|
321150
|
-
return cur;
|
|
321151
|
-
}
|
|
321152
|
-
function actionOf(ctx2, p2) {
|
|
321153
|
-
const a = p2.ix.action;
|
|
321154
|
-
const glide2 = glideOf2(a.transition);
|
|
321155
|
-
const hold = p2.ix.trigger === "ON_HOVER" || p2.ix.trigger === "ON_PRESS";
|
|
321156
|
-
switch (a.navigationType) {
|
|
321157
|
-
case "NAVIGATE":
|
|
321158
|
-
return a.destinationId && ctx2.screens.has(a.destinationId) ? { kind: "go", machine: FLOW, to: a.destinationId, ...glide2, ...hold ? { hold } : {} } : null;
|
|
321159
|
-
case "BACK":
|
|
321160
|
-
return ctx2.screens.size > 1 ? { kind: "back", machine: FLOW } : null;
|
|
321161
|
-
case "CHANGE_TO":
|
|
321162
|
-
return p2.hostMachine && a.destinationId ? { kind: "go", machine: p2.hostMachine, to: a.destinationId, ...glide2, ...hold ? { hold } : {} } : null;
|
|
321163
|
-
case "ORBIT_3D": {
|
|
321164
|
-
const o = a.orbit ?? {};
|
|
321165
|
-
const uidOf = (id3) => {
|
|
321166
|
-
const w = id3 ? p2.ids.get(id3) : void 0;
|
|
321167
|
-
return w ? mergedOf(ctx2, w).uid : void 0;
|
|
321168
|
-
};
|
|
321169
|
-
const uid2 = uidOf(a.destinationId);
|
|
321170
|
-
const tiltUid = uidOf(o.tiltLayerId) ?? uid2;
|
|
321171
|
-
return uid2 === void 0 || tiltUid === void 0 ? null : { kind: "orbit", target: uid2, tiltTarget: tiltUid, degreesPerPx: o.degreesPerPx ?? 0.4, tilt: !!o.tilt, tiltRange: o.tiltRange ?? [-30, 30] };
|
|
321172
|
-
}
|
|
321173
|
-
default:
|
|
321174
|
-
return null;
|
|
321175
|
-
}
|
|
321176
|
-
}
|
|
321177
|
-
function buildWebTree(doc2, nodeId2, opts = {}) {
|
|
321178
|
-
const tree = buildTree(doc2, nodeId2, opts);
|
|
321179
|
-
const machine = opts.static || opts.stateMachine === false ? null : webStateMachine(doc2, nodeId2);
|
|
321180
|
-
return machine ? { ...tree, stateMachine: machine } : tree;
|
|
321181
|
-
}
|
|
321182
|
-
function buildTree(doc2, nodeId2, opts = {}) {
|
|
321183
|
-
if (opts.static || opts.target === "site") return buildPlainTree(doc2, nodeId2, opts);
|
|
321184
|
-
const screens = flowScreens(doc2, nodeId2);
|
|
321185
|
-
const anything = screens.length > 1 || [...subtreeIds(doc2, nodeId2)].some((id3) => interactionsOf(doc2.nodes[id3]).some((ix) => ix.action.navigationType === "CHANGE_TO" || ix.action.navigationType === "ORBIT_3D"));
|
|
321186
|
-
if (!anything) return buildPlainTree(doc2, nodeId2, opts);
|
|
321187
|
-
const flow = { id: FLOW, initial: nodeId2, states: screens.map((s) => ({ id: s, name: doc2.nodes[s]?.name ?? s })) };
|
|
321188
|
-
const ctx2 = { doc: doc2, opts, screens: new Set(screens), machines: [flow], keyframes: /* @__PURE__ */ new Set(), rules: /* @__PURE__ */ new Set(), pending: /* @__PURE__ */ new Map(), depth: 0, renamed: /* @__PURE__ */ new Map() };
|
|
321189
|
-
const roots = screens.map((s) => [s, buildState(ctx2, doc2, s, FLOW, s)]);
|
|
321190
|
-
const truncated = !!ctx2.truncated;
|
|
321191
|
-
const root2 = mergeNode(roots, FLOW, screens, ctx2);
|
|
321192
|
-
let uid2 = 0;
|
|
321193
|
-
const number4 = (w) => {
|
|
321194
|
-
w.uid = uid2++;
|
|
321195
|
-
w.children.forEach(number4);
|
|
321196
|
-
};
|
|
321197
|
-
number4(root2);
|
|
321198
|
-
const place4 = (w) => {
|
|
321199
|
-
const pend = ctx2.pending.get(w);
|
|
321200
|
-
if (pend) {
|
|
321201
|
-
const seen = /* @__PURE__ */ new Set();
|
|
321202
|
-
const on = [];
|
|
321203
|
-
for (const raw of pend) {
|
|
321204
|
-
const p2 = { ...raw, machine: ctx2.renamed.get(raw.machine) ?? raw.machine, ...raw.hostMachine ? { hostMachine: ctx2.renamed.get(raw.hostMachine) ?? raw.hostMachine } : {} };
|
|
321205
|
-
const trigger = TRIGGERS[p2.ix.trigger];
|
|
321206
|
-
const action3 = trigger ? actionOf(ctx2, p2) : null;
|
|
321207
|
-
if (!trigger || !action3) continue;
|
|
321208
|
-
const ix = { machine: p2.machine, state: p2.state, trigger, ...p2.ix.triggerDelay ? { delay: p2.ix.triggerDelay } : {}, ...p2.ix.triggerKey ? { key: p2.ix.triggerKey } : {}, action: action3 };
|
|
321209
|
-
const sig = JSON.stringify(ix);
|
|
321210
|
-
if (!seen.has(sig)) {
|
|
321211
|
-
seen.add(sig);
|
|
321212
|
-
on.push(ix);
|
|
321213
|
-
}
|
|
321214
|
-
}
|
|
321215
|
-
if (on.length) w.on = on;
|
|
321216
|
-
}
|
|
321217
|
-
w.children.forEach(place4);
|
|
321218
|
-
};
|
|
321219
|
-
place4(root2);
|
|
321220
|
-
return { root: root2, truncated, ...ctx2.rules.size ? { rules: [...ctx2.rules].sort() } : {}, interactive: { machines: ctx2.machines.filter((m) => !ctx2.renamed.has(m.id)), keyframes: [...ctx2.keyframes] } };
|
|
321221
|
-
}
|
|
321222
|
-
var FLOW, interactionsOf, realId, nodeOf, stateName, TRIGGERS, EASINGS2, glideOf2;
|
|
321223
|
-
var init_interactive = __esm({
|
|
321224
|
-
"lib/io/web/interactive.ts"() {
|
|
321225
|
-
"use strict";
|
|
321226
|
-
init_scene_graph();
|
|
321227
|
-
init_tree();
|
|
321228
|
-
init_state_machine3();
|
|
321229
|
-
init_element();
|
|
321230
|
-
FLOW = "flow";
|
|
321231
|
-
interactionsOf = (n) => n?.interactions ?? [];
|
|
321232
|
-
realId = (id3) => id3.includes("::") ? id3.slice(id3.lastIndexOf("::") + 2) : id3;
|
|
321233
|
-
nodeOf = (doc2, id3) => doc2.nodes[id3] ?? (id3.includes("::") ? resolveVirtualNode2(doc2.nodes, id3) ?? void 0 : void 0);
|
|
321234
|
-
stateName = (doc2, id3) => {
|
|
321235
|
-
const n = doc2.nodes[id3];
|
|
321236
|
-
const v = n?.variantProperties;
|
|
321237
|
-
return v ? Object.values(v).join(", ") : n?.name ?? id3;
|
|
321238
|
-
};
|
|
321239
|
-
TRIGGERS = {
|
|
321240
|
-
ON_CLICK: "click",
|
|
321241
|
-
ON_HOVER: "hover",
|
|
321242
|
-
ON_PRESS: "press",
|
|
321243
|
-
ON_DRAG: "drag",
|
|
321244
|
-
MOUSE_ENTER: "enter",
|
|
321245
|
-
MOUSE_LEAVE: "leave",
|
|
321246
|
-
AFTER_TIMEOUT: "timeout",
|
|
321247
|
-
KEY_DOWN: "key"
|
|
321248
|
-
};
|
|
321249
|
-
EASINGS2 = { EASE_IN: "ease-in", EASE_OUT: "ease-out", EASE_IN_OUT: "ease-in-out", LINEAR: "linear", SPRING: "cubic-bezier(0.34, 1.56, 0.64, 1)" };
|
|
321250
|
-
glideOf2 = (t3) => !t3 || t3.type === "INSTANT" || t3.type === "CUT" ? { ms: 0, easing: "linear" } : { ms: Math.max(0, Math.round(t3.duration)), easing: EASINGS2[t3.easing] ?? "ease-in-out" };
|
|
321251
|
-
}
|
|
321252
|
-
});
|
|
321253
|
-
|
|
321254
321163
|
// lib/io/web/site.ts
|
|
321255
321164
|
function light(node2) {
|
|
321256
321165
|
const out = {};
|
|
@@ -321474,7 +321383,7 @@ var init_site = __esm({
|
|
|
321474
321383
|
init_fonts3();
|
|
321475
321384
|
init_slice();
|
|
321476
321385
|
init_render();
|
|
321477
|
-
|
|
321386
|
+
init_state_machine2();
|
|
321478
321387
|
init_physics();
|
|
321479
321388
|
init_interactive();
|
|
321480
321389
|
init_tree();
|
|
@@ -345136,6 +345045,7 @@ function exportsOf(source3) {
|
|
|
345136
345045
|
var CODE_LIMITS, packageOf;
|
|
345137
345046
|
var init_source2 = __esm({
|
|
345138
345047
|
"lib/code/source.ts"() {
|
|
345048
|
+
"use strict";
|
|
345139
345049
|
CODE_LIMITS = { modules: 100, sourceLength: 2e5, packages: 12 };
|
|
345140
345050
|
packageOf = (spec) => spec.split("/").slice(0, spec.startsWith("@") ? 2 : 1).join("/");
|
|
345141
345051
|
}
|
|
@@ -345178,6 +345088,7 @@ function compileModule(module2) {
|
|
|
345178
345088
|
var import_sucrase, BUILT_IN, memo4;
|
|
345179
345089
|
var init_compile2 = __esm({
|
|
345180
345090
|
"lib/code/compile.ts"() {
|
|
345091
|
+
"use strict";
|
|
345181
345092
|
import_sucrase = __toESM(require_dist2());
|
|
345182
345093
|
init_source2();
|
|
345183
345094
|
init_source2();
|
|
@@ -345760,6 +345671,7 @@ __export(web_exports, {
|
|
|
345760
345671
|
CODE_FORMAT_IDS: () => CODE_FORMAT_IDS,
|
|
345761
345672
|
DEFAULT_NODE_CAP: () => DEFAULT_NODE_CAP,
|
|
345762
345673
|
EMAIL_DEFAULT_WIDTH: () => EMAIL_DEFAULT_WIDTH,
|
|
345674
|
+
EXPORT_NODE_CAP: () => EXPORT_NODE_CAP,
|
|
345763
345675
|
WEB_LANGUAGES: () => WEB_LANGUAGES,
|
|
345764
345676
|
assetKindFor: () => assetKindFor,
|
|
345765
345677
|
buildWebSite: () => buildWebSite,
|
|
@@ -347108,24 +347020,6 @@ var init_board_export = __esm({
|
|
|
347108
347020
|
});
|
|
347109
347021
|
|
|
347110
347022
|
// lib/commands/export.ts
|
|
347111
|
-
var export_exports2 = {};
|
|
347112
|
-
__export(export_exports2, {
|
|
347113
|
-
EXPORT_NODE_CAP: () => EXPORT_NODE_CAP,
|
|
347114
|
-
exportBoard: () => exportBoard,
|
|
347115
|
-
exportCopy: () => exportCopy,
|
|
347116
|
-
exportGif: () => exportGif,
|
|
347117
|
-
exportLottie: () => exportLottie2,
|
|
347118
|
-
exportMp4: () => exportMp4,
|
|
347119
|
-
exportNodes: () => exportNodes,
|
|
347120
|
-
exportPages: () => exportPages,
|
|
347121
|
-
exportPdf: () => exportPdf,
|
|
347122
|
-
exportPngSequence: () => exportPngSequence,
|
|
347123
|
-
exportPptx: () => exportPptx,
|
|
347124
|
-
exportStorefront: () => exportStorefront,
|
|
347125
|
-
exportSvg: () => exportSvg,
|
|
347126
|
-
exportWeb: () => exportWeb,
|
|
347127
|
-
exportWebm: () => exportWebm
|
|
347128
|
-
});
|
|
347129
347023
|
function animationTarget(args2, ctx2, doc2) {
|
|
347130
347024
|
if (args2.composition) {
|
|
347131
347025
|
if (!doc2.compositions?.[args2.composition]) throw new ToolError(`There is no composition "${args2.composition}".`);
|
|
@@ -347233,7 +347127,7 @@ async function exportSite(doc2, pageId2, packaging, styling = "css") {
|
|
|
347233
347127
|
downloadBlob2(zipFiles2(files.map((f2) => ({ name: f2.path, bytes: bytesOf2(f2) }))), `${base}.zip`);
|
|
347234
347128
|
return { summary: `Exported ${plural2(site.pages.length, "page")} as ${packaging === "next" ? "a Next.js project" : "a static site"} (${base}.zip)`, data: { filename: `${base}.zip`, packaging, pages: site.pages.map((p2) => p2.route), files: files.length } };
|
|
347235
347129
|
}
|
|
347236
|
-
var MAX_INLINE_BYTES, exportSvg, exportNodes, exportPdf, exportCopy, exportPages, exportPptx, animationParams, videoParams, gifParams, lottieParams, animationCommand, TARGET, exportMp4, exportWebm, exportGif, exportPngSequence, exportLottie2,
|
|
347130
|
+
var MAX_INLINE_BYTES, exportSvg, exportNodes, exportPdf, exportCopy, exportPages, exportPptx, animationParams, videoParams, gifParams, lottieParams, animationCommand, TARGET, exportMp4, exportWebm, exportGif, exportPngSequence, exportLottie2, exportWeb, APP_STOREFRONT_TARGETS, exportStorefront, exportBoard;
|
|
347237
347131
|
var init_export2 = __esm({
|
|
347238
347132
|
"lib/commands/export.ts"() {
|
|
347239
347133
|
"use strict";
|
|
@@ -347246,6 +347140,7 @@ var init_export2 = __esm({
|
|
|
347246
347140
|
init_markers();
|
|
347247
347141
|
init_doc_helpers();
|
|
347248
347142
|
init_formats();
|
|
347143
|
+
init_tree();
|
|
347249
347144
|
MAX_INLINE_BYTES = 15e5;
|
|
347250
347145
|
exportSvg = defineCommand({
|
|
347251
347146
|
id: "export.svg",
|
|
@@ -347594,7 +347489,6 @@ var init_export2 = __esm({
|
|
|
347594
347489
|
name: "export_lottie",
|
|
347595
347490
|
description: `Write ${TARGET.replace(" and \u2014 for video \u2014 its sound", "")} as a Lottie (bodymovin JSON, or a .lottie zip) the user downloads: vector shapes, fills, strokes, masks, text as outlines and images as embedded assets, with our keys and bezier / hold easing where Lottie can say them and every other curve, behaviour and text animator keyed frame by frame. Refuses what Lottie cannot carry (shader fills, blurs, glass, halftone, 3D, video) and lists what it baked. The timeline's markers go in as Lottie markers; a .lottie also carries the frame's state machine. Options: frame rate, range, container, stateMachine.`
|
|
347596
347491
|
});
|
|
347597
|
-
EXPORT_NODE_CAP = 2e4;
|
|
347598
347492
|
exportWeb = defineCommand({
|
|
347599
347493
|
id: "export.web",
|
|
347600
347494
|
title: "Export as web code",
|
|
@@ -347639,6 +347533,7 @@ var init_export2 = __esm({
|
|
|
347639
347533
|
return { summary: `Exported ${node2.name || "layer"} as ${filename}`, data: { filename, format, bytes: markup.length, truncated: tree.truncated } };
|
|
347640
347534
|
}
|
|
347641
347535
|
});
|
|
347536
|
+
APP_STOREFRONT_TARGETS = STOREFRONT_TARGET_IDS.filter((t3) => t3 !== "shopify-theme");
|
|
347642
347537
|
exportStorefront = defineCommand({
|
|
347643
347538
|
id: "export.storefront",
|
|
347644
347539
|
title: "Export storefront",
|
|
@@ -347647,21 +347542,20 @@ var init_export2 = __esm({
|
|
|
347647
347542
|
permission: "export",
|
|
347648
347543
|
needs: ["canvas"],
|
|
347649
347544
|
params: external_exports.object({
|
|
347650
|
-
target: external_exports.enum(
|
|
347545
|
+
target: external_exports.enum(APP_STOREFRONT_TARGETS).default("next-commerce").describe("next-commerce-store: a whole Next.js Commerce store drawn by the design, to deploy with a Shopify store's domain and Storefront token (publish_store deploys it for you). next-commerce: React components a Next.js Commerce store renders with its own data and server actions. A Shopify theme is the Ecommerce plugin's."),
|
|
347651
347546
|
styling: external_exports.enum(["inline", "tailwind"]).optional().describe("next-commerce: style objects (default) or Tailwind CSS v4 classes."),
|
|
347652
347547
|
dir: external_exports.string().max(200).optional().describe("next-commerce: where the components go in the store's project (default components/popcraft).")
|
|
347653
347548
|
}).strict(),
|
|
347654
347549
|
expose: {
|
|
347655
347550
|
ui: {
|
|
347656
347551
|
label: "Export storefront\u2026",
|
|
347657
|
-
keywords: ["commerce", "shopify", "
|
|
347552
|
+
keywords: ["commerce", "shopify", "store", "shop", "next", "react", "components", "export"],
|
|
347658
347553
|
variants: [
|
|
347659
347554
|
{ id: "next-commerce-store", label: "Export storefront as a Next.js Commerce store", params: { target: "next-commerce-store" } },
|
|
347660
|
-
{ id: "next-commerce", label: "Export storefront as Next.js Commerce components", params: { target: "next-commerce" } }
|
|
347661
|
-
{ id: "shopify-theme", label: "Export storefront as a Shopify theme", params: { target: "shopify-theme" } }
|
|
347555
|
+
{ id: "next-commerce", label: "Export storefront as Next.js Commerce components", params: { target: "next-commerce" } }
|
|
347662
347556
|
]
|
|
347663
347557
|
},
|
|
347664
|
-
agent: { name: "export_storefront", readOnly: false, description: "Download a storefront design (a page whose lists and pages read collections with a commerce schema) as a store's project, in a zip. target next-commerce-store: the whole Next.js Commerce app (Shopify client, cart, checkout, a page per screen), ready to deploy. target next-commerce: a React component per screen, each list a typed prop of Next.js Commerce's own types, each storefront form (addToCart, updateCartLine, removeCartLine, checkout, search) an action prop for a server action.
|
|
347558
|
+
agent: { name: "export_storefront", readOnly: false, description: "Download a storefront design (a page whose lists and pages read collections with a commerce schema) as a store's project, in a zip. target next-commerce-store: the whole Next.js Commerce app (Shopify client, cart, checkout, a page per screen), ready to deploy. target next-commerce: a React component per screen, each list a typed prop of Next.js Commerce's own types, each storefront form (addToCart, updateCartLine, removeCartLine, checkout, search) an action prop for a server action. With no store data a Next.js Commerce component draws the design's samples." }
|
|
347665
347559
|
},
|
|
347666
347560
|
run: async (args2, ctx2) => {
|
|
347667
347561
|
const doc2 = ctx2.doc();
|
|
@@ -353593,7 +353487,6 @@ __export(integrations_exports, {
|
|
|
353593
353487
|
attachDatabase: () => attachDatabase,
|
|
353594
353488
|
connectWithOAuth: () => connectWithOAuth,
|
|
353595
353489
|
connectWithToken: () => connectWithToken,
|
|
353596
|
-
connectedStore: () => connectedStore,
|
|
353597
353490
|
createDatabase: () => createDatabase,
|
|
353598
353491
|
createDestination: () => createDestination,
|
|
353599
353492
|
createResource: () => createResource,
|
|
@@ -353609,8 +353502,7 @@ __export(integrations_exports, {
|
|
|
353609
353502
|
listWorkspaceIntegrations: () => listWorkspaceIntegrations,
|
|
353610
353503
|
removeDestination: () => removeDestination,
|
|
353611
353504
|
setSignIn: () => setSignIn,
|
|
353612
|
-
siteBackend: () => siteBackend
|
|
353613
|
-
storeProducts: () => storeProducts
|
|
353505
|
+
siteBackend: () => siteBackend
|
|
353614
353506
|
});
|
|
353615
353507
|
function connectWithOAuth(workspaceId, provider2) {
|
|
353616
353508
|
const popup = window.open("", "popcraft-integration", "popup,width=640,height=760");
|
|
@@ -353647,7 +353539,7 @@ async function sha12(bytes2) {
|
|
|
353647
353539
|
const digest = await crypto.subtle.digest("SHA-1", bytes2);
|
|
353648
353540
|
return [...new Uint8Array(digest)].map((b) => b.toString(16).padStart(2, "0")).join("");
|
|
353649
353541
|
}
|
|
353650
|
-
async function deployStore(key5, id3, files,
|
|
353542
|
+
async function deployStore(key5, id3, files, env, onProgress) {
|
|
353651
353543
|
const listed = await Promise.all(files.map(async (f2) => ({ path: f2.path, sha: await sha12(f2.bytes), size: f2.bytes.length, bytes: f2.bytes })));
|
|
353652
353544
|
const queue2 = [...new Map(listed.map((f2) => [f2.sha, f2])).values()];
|
|
353653
353545
|
const total2 = queue2.length;
|
|
@@ -353658,18 +353550,9 @@ async function deployStore(key5, id3, files, shopifyConnectionId, onProgress) {
|
|
|
353658
353550
|
onProgress?.(++done, total2);
|
|
353659
353551
|
}
|
|
353660
353552
|
}));
|
|
353661
|
-
return (await api(`/api/sites/${key5}/destinations/${id3}/store`, { method: "POST", json: {
|
|
353662
|
-
}
|
|
353663
|
-
|
|
353664
|
-
if (connectionId) return connectionId;
|
|
353665
|
-
const workspaceId = integrationsWorkspaceId();
|
|
353666
|
-
if (!workspaceId) throw new Error("Your workspaces have not loaded yet. Try again in a moment.");
|
|
353667
|
-
const stores2 = (await listWorkspaceIntegrations(workspaceId)).integrations.filter((i2) => i2.manifest.capabilities.includes("commerce")).flatMap((i2) => i2.connections);
|
|
353668
|
-
if (!stores2.length) throw new Error("No store is connected. Connect Shopify in Integrations first.");
|
|
353669
|
-
if (stores2.length > 1) throw new Error(`Name the store: ${stores2.map((c2) => `${c2.account} (${c2.id})`).join(", ")}.`);
|
|
353670
|
-
return stores2[0].id;
|
|
353671
|
-
}
|
|
353672
|
-
var integrationsWorkspaceId, listWorkspaceIntegrations, connectWithToken, disconnect, listResources, createResource, listDestinations, addDestination, removeDestination, deployDestination, siteBackend, attachDatabase, setSignIn, detachDatabase, listSubmissions, listCandidates, createDatabase, createDestination, storeProducts;
|
|
353553
|
+
return (await api(`/api/sites/${key5}/destinations/${id3}/store`, { method: "POST", json: { env, files: listed.map(({ path, sha, size: size6 }) => ({ path, sha, size: size6 })) } })).deploy;
|
|
353554
|
+
}
|
|
353555
|
+
var integrationsWorkspaceId, listWorkspaceIntegrations, connectWithToken, disconnect, listResources, createResource, listDestinations, addDestination, removeDestination, deployDestination, siteBackend, attachDatabase, setSignIn, detachDatabase, listSubmissions, listCandidates, createDatabase, createDestination;
|
|
353673
353556
|
var init_integrations = __esm({
|
|
353674
353557
|
"lib/client/cloud/integrations.ts"() {
|
|
353675
353558
|
init_api4();
|
|
@@ -353692,7 +353575,48 @@ var init_integrations = __esm({
|
|
|
353692
353575
|
listCandidates = async (workspaceId, capability2) => (await api(`/api/workspaces/${encodeURIComponent(workspaceId)}/integrations/candidates?capability=${capability2}`)).candidates;
|
|
353693
353576
|
createDatabase = (key5, provider2, connectionId) => api(`/api/sites/${key5}/backend`, { method: "PUT", json: { create: true, ...provider2 ? { provider: provider2 } : {}, ...connectionId ? { connectionId } : {} } });
|
|
353694
353577
|
createDestination = async (key5, capability2, provider2, connectionId) => (await api(`/api/sites/${key5}/destinations`, { method: "POST", json: { create: true, capability: capability2, ...provider2 ? { provider: provider2 } : {}, ...connectionId ? { connectionId } : {} } })).destination;
|
|
353695
|
-
|
|
353578
|
+
}
|
|
353579
|
+
});
|
|
353580
|
+
|
|
353581
|
+
// lib/client/cloud/publish-store.ts
|
|
353582
|
+
var publish_store_exports = {};
|
|
353583
|
+
__export(publish_store_exports, {
|
|
353584
|
+
deployOpenStore: () => deployOpenStore,
|
|
353585
|
+
isStorefront: () => isStorefront
|
|
353586
|
+
});
|
|
353587
|
+
async function deployOpenStore(doc2, pageId2, o = {}) {
|
|
353588
|
+
const [{ openFileKey: openFileKey2 }, { uploadActiveDocument: uploadActiveDocument2 }, cloud, { storefrontInputs: storefrontInputs2 }, { nextCommerceFiles: nextCommerceFiles2 }, { bytesOf: bytesOf2 }] = await Promise.all([
|
|
353589
|
+
Promise.resolve().then(() => (init_publish_site(), publish_site_exports)),
|
|
353590
|
+
Promise.resolve().then(() => (init_sync2(), sync_exports2)),
|
|
353591
|
+
Promise.resolve().then(() => (init_integrations(), integrations_exports)),
|
|
353592
|
+
Promise.resolve().then(() => (init_storefront_prepare(), storefront_prepare_exports)),
|
|
353593
|
+
Promise.resolve().then(() => (init_next_commerce(), next_commerce_exports)),
|
|
353594
|
+
Promise.resolve().then(() => (init_project(), project_exports))
|
|
353595
|
+
]);
|
|
353596
|
+
if (!isStorefront(doc2)) throw new Error("This file is not a storefront: set a collection to Store products in Collections, or start from a Storefronts template.");
|
|
353597
|
+
const env = doc2.site?.env ?? {};
|
|
353598
|
+
if (!env.SHOPIFY_STORE_DOMAIN || !env.SHOPIFY_STOREFRONT_ACCESS_TOKEN) throw new Error("This store does not say which Shopify store it sells from: connect one in the Ecommerce plugin (it sets SHOPIFY_STORE_DOMAIN and SHOPIFY_STOREFRONT_ACCESS_TOKEN in the site environment).");
|
|
353599
|
+
o.onStep?.("Building the store\u2026");
|
|
353600
|
+
const { screens, media: media2 } = await storefrontInputs2(doc2, pageId2, EXPORT_NODE_CAP);
|
|
353601
|
+
if (!screens.length) throw new Error("This page has no screens: a top-level frame is a page of the store.");
|
|
353602
|
+
const key5 = openFileKey2() ?? await uploadActiveDocument2();
|
|
353603
|
+
const all4 = await cloud.listDestinations(key5);
|
|
353604
|
+
let dest = o.destinationId ? all4.find((d) => d.id === o.destinationId) : all4.find((d) => d.capability === "deploy");
|
|
353605
|
+
if (o.destinationId && !dest) throw new Error(`This file has no destination ${o.destinationId}.`);
|
|
353606
|
+
if (!dest) {
|
|
353607
|
+
o.onStep?.("Making a Vercel project\u2026");
|
|
353608
|
+
dest = await cloud.createDestination(key5, "deploy", "vercel");
|
|
353609
|
+
}
|
|
353610
|
+
const files = nextCommerceFiles2(doc2, screens, { media: media2 }).map((f2) => ({ path: f2.path, bytes: bytesOf2(f2) }));
|
|
353611
|
+
const project = dest.target.map((t3) => t3.name).join(" / ");
|
|
353612
|
+
const done = await cloud.deployStore(key5, dest.id, files, env, (n, total2) => o.onStep?.(`Sending files ${n} of ${total2}\u2026`));
|
|
353613
|
+
return { ...done, destinationId: dest.id, project, files: files.length, pages: screens.map((s) => s.name) };
|
|
353614
|
+
}
|
|
353615
|
+
var isStorefront;
|
|
353616
|
+
var init_publish_store = __esm({
|
|
353617
|
+
"lib/client/cloud/publish-store.ts"() {
|
|
353618
|
+
init_tree();
|
|
353619
|
+
isStorefront = (doc2) => Object.values(doc2.collections ?? {}).some((c2) => c2.schema === "commerce.product");
|
|
353696
353620
|
}
|
|
353697
353621
|
});
|
|
353698
353622
|
|
|
@@ -353821,55 +353745,28 @@ var init_publish = __esm({
|
|
|
353821
353745
|
permission: null,
|
|
353822
353746
|
needs: ["canvas"],
|
|
353823
353747
|
params: external_exports.object({
|
|
353824
|
-
shopifyConnectionId: external_exports.string().optional().describe("The Shopify store it sells from, from list_integrations (capability commerce). Omit when one store is connected."),
|
|
353825
353748
|
destinationId: external_exports.string().optional().describe("The Vercel project to deploy to (a deploy destination, from get_site_status). Omit: the file's deploy destination, or a new project named after the file.")
|
|
353826
353749
|
}),
|
|
353827
353750
|
confirm: {
|
|
353828
353751
|
level: "confirm",
|
|
353829
353752
|
summary: () => "Deploy this page as a store selling your Shopify products",
|
|
353830
|
-
detail: () => "The page becomes a Next.js Commerce store on Vercel, its products, cart and checkout your Shopify store's. A Vercel project is made for it when the file has none, and your store's address and Storefront token
|
|
353753
|
+
detail: () => "The page becomes a Next.js Commerce store on Vercel, its products, cart and checkout your Shopify store's. A Vercel project is made for it when the file has none, and the site environment (your store's address and public Storefront token) is set as that project's. Visitors can buy from it once it is live."
|
|
353831
353754
|
},
|
|
353832
353755
|
expose: {
|
|
353833
353756
|
ui: { label: "Publish as a store\u2026", keywords: ["store", "shop", "shopify", "commerce", "next", "vercel", "deploy", "sell", "ecommerce", "checkout", "cart"] },
|
|
353834
353757
|
agent: {
|
|
353835
353758
|
name: "publish_store",
|
|
353836
|
-
description: "Deploy a storefront design (its lists and pages bound to collections with a commerce schema) as a working store: a Next.js Commerce app on Vercel selling the connected Shopify store's products, with its cart and checkout. Needs
|
|
353759
|
+
description: "Deploy a storefront design (its lists and pages bound to collections with a commerce schema) as a working store: a Next.js Commerce app on Vercel selling the connected Shopify store's products, with its cart and checkout. Needs the site environment to name the Shopify store (SHOPIFY_STORE_DOMAIN, SHOPIFY_STOREFRONT_ACCESS_TOKEN: get_site_environment; the Ecommerce plugin sets them) and a Vercel connection; uses the file's Vercel deploy destination or makes one. Returns the deployment URL (it builds for a minute or two). The user approves every call."
|
|
353837
353760
|
}
|
|
353838
353761
|
},
|
|
353839
353762
|
run: async (p2, ctx2) => {
|
|
353840
353763
|
await signedIn();
|
|
353841
|
-
const
|
|
353842
|
-
|
|
353843
|
-
Promise.resolve().then(() => (init_sync2(), sync_exports2)),
|
|
353844
|
-
Promise.resolve().then(() => (init_integrations(), integrations_exports)),
|
|
353845
|
-
Promise.resolve().then(() => (init_storefront_prepare(), storefront_prepare_exports)),
|
|
353846
|
-
Promise.resolve().then(() => (init_next_commerce(), next_commerce_exports)),
|
|
353847
|
-
Promise.resolve().then(() => (init_project(), project_exports)),
|
|
353848
|
-
Promise.resolve().then(() => (init_export2(), export_exports2))
|
|
353849
|
-
]);
|
|
353850
|
-
const doc2 = ctx2.doc();
|
|
353851
|
-
if (!Object.values(doc2.collections ?? {}).some((c2) => c2.schema === "commerce.product")) throw new CommandError("This file is not a storefront: set a collection to Store products in Collections, or start from a Storefronts template.", "failed");
|
|
353852
|
-
const shop = await cloud.connectedStore(p2.shopifyConnectionId).catch((e) => {
|
|
353764
|
+
const { deployOpenStore: deployOpenStore2 } = await Promise.resolve().then(() => (init_publish_store(), publish_store_exports));
|
|
353765
|
+
const done = await deployOpenStore2(ctx2.doc(), ctx2.pageId(), { destinationId: p2.destinationId }).catch((e) => {
|
|
353853
353766
|
throw new CommandError(e instanceof Error ? e.message : String(e), "failed");
|
|
353854
353767
|
});
|
|
353855
|
-
const { screens, media: media2 } = await storefrontInputs2(doc2, ctx2.pageId(), EXPORT_NODE_CAP2);
|
|
353856
|
-
if (!screens.length) throw new CommandError("This page has no screens: a top-level frame is a page of the store.", "failed");
|
|
353857
|
-
const key5 = openFileKey2() ?? await uploadActiveDocument2();
|
|
353858
|
-
const all4 = await cloud.listDestinations(key5);
|
|
353859
|
-
const deploys = all4.filter((d) => d.capability === "deploy");
|
|
353860
|
-
let dest = p2.destinationId ? all4.find((d) => d.id === p2.destinationId) : deploys[0];
|
|
353861
|
-
if (p2.destinationId && !dest) throw new CommandError(`This file has no destination ${p2.destinationId}.`, "invalid_params");
|
|
353862
|
-
if (!dest) {
|
|
353863
|
-
ctx2.notice("Making a Vercel project for the store\u2026");
|
|
353864
|
-
dest = await cloud.createDestination(key5, "deploy", "vercel");
|
|
353865
|
-
}
|
|
353866
|
-
const files = nextCommerceFiles2(doc2, screens, { media: media2 }).map((f2) => ({ path: f2.path, bytes: bytesOf2(f2) }));
|
|
353867
|
-
const where = dest.target.map((t3) => t3.name).join(" / ");
|
|
353868
|
-
const done = await cloud.deployStore(key5, dest.id, files, shop, (n, total2) => {
|
|
353869
|
-
if (n === total2) ctx2.notice(`Sent ${total2} files to ${where}: building the store`);
|
|
353870
|
-
});
|
|
353871
353768
|
ctx2.notice(done.status === "failed" ? `The store did not deploy: ${done.error ?? "Vercel refused it"}` : `Store deploying: ${done.url}`);
|
|
353872
|
-
return { summary: `Store ${done.status === "ready" ? "is live" : done.status === "building" ? "is building" : "failed"} at ${done.url} (${
|
|
353769
|
+
return { summary: `Store ${done.status === "ready" ? "is live" : done.status === "building" ? "is building" : "failed"} at ${done.url} (${done.project}, ${done.pages.length} ${done.pages.length === 1 ? "page" : "pages"}, ${done.files} files)`, data: { url: done.url, status: done.status, destinationId: done.destinationId, project: done.project, files: done.files, pages: done.pages } };
|
|
353873
353770
|
}
|
|
353874
353771
|
});
|
|
353875
353772
|
publishCommands = [publishSite2, publishSetVersion, publishStore];
|
|
@@ -356276,7 +356173,7 @@ var init_storefront2 = __esm({
|
|
|
356276
356173
|
name: "Design a storefront",
|
|
356277
356174
|
description: "Bind a shop to a store's data and publish or export it for Next.js Commerce or Shopify.",
|
|
356278
356175
|
whenToUse: "the design should sell",
|
|
356279
|
-
tools: ["get_document_outline", "edit_collection", "edit_records", "set_repeat", "set_route", "set_control", "export_storefront", "list_integrations", "open_integrations", "
|
|
356176
|
+
tools: ["get_document_outline", "edit_collection", "edit_records", "set_repeat", "set_route", "set_control", "export_storefront", "list_integrations", "open_integrations", "get_site_environment", "ask_user", "manage_todos"],
|
|
356280
356177
|
instructions: `# Design a storefront
|
|
356281
356178
|
|
|
356282
356179
|
PopCraft draws the shop; a Next.js Commerce store runs it. The store keeps Shopify, the cart, checkout and search;
|
|
@@ -356292,9 +356189,8 @@ are whole stores to begin from.
|
|
|
356292
356189
|
- \`commerce.product\` for products (title, handle, url, description, price, image, variant_id\u2026)
|
|
356293
356190
|
- \`commerce.cartLine\` for the cart's lines, \`commerce.cart\` for its count and totals (one record)
|
|
356294
356191
|
- \`commerce.menu\` for the store's menu, \`commerce.collection\` for its categories
|
|
356295
|
-
Add a few real sample records with \`edit_records\`: the canvas is drawn with them.
|
|
356296
|
-
|
|
356297
|
-
store, then \`pull_store_products\`. You cannot connect a store yourself: say why it helps and \`open_integrations\`.
|
|
356192
|
+
Add a few real sample records with \`edit_records\`: the canvas is drawn with them. A store's real catalogue
|
|
356193
|
+
comes from the Ecommerce plugin (Marketplace \u203A Plugins): it fills these collections from Shopify.
|
|
356298
356194
|
3. **The lists.** \`set_repeat\` on the frame that holds one card, over the collection; the card's texts say
|
|
356299
356195
|
\`{{item.title}}\`, \`{{item.price}}\`, and its picture follows \`item_image\`. The cart's totals are a list of one
|
|
356300
356196
|
(\`limit: 1\`) over the \`commerce.cart\` collection.
|
|
@@ -356306,12 +356202,13 @@ are whole stores to begin from.
|
|
|
356306
356202
|
- \`checkout\`
|
|
356307
356203
|
- \`search\`: a field named \`q\`
|
|
356308
356204
|
6. **Sell.** \`publish_store\` deploys it as a working store: a Next.js Commerce app on Vercel selling the connected
|
|
356309
|
-
Shopify store's products, with its cart and checkout (needs
|
|
356205
|
+
Shopify store's products, with its cart and checkout (needs the site environment to name the Shopify store,
|
|
356206
|
+
\`get_site_environment\`, which the Ecommerce plugin sets, and Vercel connected: \`list_integrations\`).
|
|
356310
356207
|
Or \`export_storefront\` writes the project for a store the user runs:
|
|
356311
356208
|
- \`target: 'next-commerce-store'\`: the whole Next.js Commerce store, to deploy with Shopify's keys.
|
|
356312
356209
|
- \`target: 'next-commerce'\`: components only, for a Next.js Commerce store that exists: a prop per list
|
|
356313
356210
|
(\`products\`, \`cartLines\`, \`cart\`, \`menu\`), \`product\` on a product's page, \`onAddToCart\`, \`onCheckout\`\u2026 for the forms.
|
|
356314
|
-
|
|
356211
|
+
A Shopify theme, the store's catalogue and its setup are the Ecommerce plugin's (Marketplace \u203A Plugins).
|
|
356315
356212
|
Say which, and where it goes (/docs/exporting/commerce).
|
|
356316
356213
|
|
|
356317
356214
|
## Rules
|
|
@@ -358714,16 +358611,16 @@ var init_api5 = __esm({
|
|
|
358714
358611
|
}
|
|
358715
358612
|
});
|
|
358716
358613
|
|
|
358717
|
-
// node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=
|
|
358614
|
+
// node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=e61849e2a6a59df95f0ebad36ab274c37a933fcf798d8b4dd6b3f0ffc625a1da/node_modules/@popcraft/plugins/dist/generated/runtime.js
|
|
358718
358615
|
var MAIN_RUNTIME, UI_RUNTIME;
|
|
358719
358616
|
var init_runtime4 = __esm({
|
|
358720
|
-
"node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=
|
|
358721
|
-
MAIN_RUNTIME = '"use strict";\n(() => {\n // src/runtime/rpc.ts\n function createRpcClient() {\n let port = null;\n const queue = [];\n const pending = {};\n const listeners = {};\n let nextId = 1;\n function send(msg) {\n if (port) port.postMessage(msg);\n else queue.push(msg);\n }\n function call(method, params) {\n return new Promise((resolve, reject) => {\n const id = nextId++;\n pending[id] = { resolve, reject };\n send({ kind: "rpc", id, method, params });\n });\n }\n function emit(event, data) {\n for (const cb of (listeners[event] || []).slice()) {\n try {\n cb(data);\n } catch (e) {\n console.error(e);\n }\n }\n }\n window.addEventListener("message", (e) => {\n const data = e.data;\n if (e.source !== window.parent || !data || data.type !== "popcraft-plugin-port" || port) return;\n port = e.ports[0];\n port.onmessage = (ev) => {\n const m = ev.data || {};\n if (m.kind === "result" && m.id !== void 0 && pending[m.id]) {\n const p = pending[m.id];\n delete pending[m.id];\n if (m.error) p.reject(new Error(m.error));\n else p.resolve(m.result);\n } else if (m.kind === "event" && m.event) {\n emit(m.event, m.data);\n }\n };\n for (const msg of queue.splice(0)) port.postMessage(msg);\n });\n return {\n call,\n send,\n on(event, cb) {\n (listeners[event] = listeners[event] || []).push(cb);\n },\n off(event, cb) {\n listeners[event] = (listeners[event] || []).filter((x) => x !== cb);\n }\n };\n }\n\n // src/runtime/main.ts\n function clone(v) {\n return v === void 0 ? {} : JSON.parse(JSON.stringify(v));\n }\n function createMainApi(rpc = createRpcClient()) {\n const uiHandlers = [];\n let uiOnMessage = null;\n const uiQueue = [];\n function deliverUI(msg) {\n for (const cb of uiHandlers) {\n try {\n cb(msg);\n } catch (e) {\n console.error(e);\n }\n }\n if (typeof uiOnMessage === "function") {\n try {\n uiOnMessage(msg);\n } catch (e) {\n console.error(e);\n }\n }\n }\n function flushUI() {\n if (uiHandlers.length || typeof uiOnMessage === "function") uiQueue.splice(0).forEach(deliverUI);\n }\n rpc.on("uimessage", (msg) => {\n if (!uiHandlers.length && typeof uiOnMessage !== "function") uiQueue.push(msg);\n else deliverUI(msg);\n });\n let widgetDef = null;\n const widgetQueue = [];\n function renderWidget(state) {\n const handlers = {};\n function walk(el, path) {\n if (!el || typeof el !== "object") return el;\n const out = {};\n for (const k of Object.keys(el)) {\n const v = el[k];\n if (k === "children") {\n out.children = (Array.isArray(v) ? v : [v]).filter((c) => c !== null && c !== void 0 && c !== false).map((c, i) => walk(c, path + "." + i));\n } else if (k === "onClick" && typeof v === "function") {\n handlers[path] = v;\n out.onClick = path;\n } else {\n out[k] = v;\n }\n }\n return out;\n }\n return { tree: walk(widgetDef.render(state), "root"), handlers };\n }\n function initialWidgetState() {\n const s = widgetDef && widgetDef.initialState;\n return clone(typeof s === "function" ? s() : s);\n }\n function commitWidget(nodeId, state) {\n return rpc.call("widgetUpdate", { id: nodeId, state, tree: renderWidget(clone(state)).tree });\n }\n function handleWidgetClick(e) {\n Promise.resolve().then(() => {\n const state = clone(e.state);\n const rendered = renderWidget(state);\n const h = rendered.handlers[e.handler] || widgetDef.handlers && widgetDef.handlers[e.handler];\n if (typeof h !== "function") return;\n return Promise.resolve(h(state, { nodeId: e.nodeId })).then((ret) => commitWidget(e.nodeId, ret === void 0 ? state : ret));\n }).catch((err) => rpc.send({ kind: "error", message: String((err == null ? void 0 : err.message) || err) }));\n }\n rpc.on("widgetclick", (e) => {\n if (widgetDef) handleWidgetClick(e);\n else widgetQueue.push(e);\n });\n const popcraft = {\n /** Which menu command the user picked, or null when the plugin ran some other way. */\n command: null,\n /** Host import mode when launched as an importer, else null. */\n importMode: null,\n /** Pending import file when the host handed one over, else null. */\n importFile: null,\n /** Pending export request when the host started this plugin as an exporter, else null. */\n exportRequest: null,\n getSelection: () => rpc.call("getSelection"),\n setSelection: (ids) => rpc.call("setSelection", { ids }),\n getNode: (id) => rpc.call("getNode", { id }),\n findNodes: (query) => rpc.call("findNodes", query || {}),\n getCurrentPage: () => rpc.call("getCurrentPage"),\n createNode: (type, props) => rpc.call("createNode", { type, props: props || {} }),\n updateNode: (id, props) => rpc.call("updateNode", { id, props }),\n deleteNode: (id) => rpc.call("deleteNode", { id }),\n setText: (id, characters) => rpc.call("setText", { id, characters }),\n setTextPath: (opts) => rpc.call("setTextPath", opts || {}),\n flowTextIntoShape: (opts) => rpc.call("flowTextIntoShape", opts || {}),\n detachText: (opts) => rpc.call("detachText", opts || {}),\n setTextFit: (opts) => rpc.call("setTextFit", opts || {}),\n createPage: (name) => rpc.call("createPage", name != null ? { name: String(name) } : {}),\n setCurrentPage: (pageId) => rpc.call("setCurrentPage", { pageId }),\n createImage: (opts) => rpc.call("createImage", opts || {}),\n createDocument: (opts) => rpc.call("createDocument", opts || {}),\n getImportMode: () => rpc.call("getImportMode"),\n getImportFile: () => rpc.call("getImportFile"),\n getStorefront: () => rpc.call("getStorefront"),\n getExportRequest: () => rpc.call("getExportRequest"),\n saveExport: (file) => rpc.call("saveExport", file || {}),\n getPresentationAudio: (opts) => rpc.call("getPresentationAudio", opts || {}),\n setPresentationAudioSettings: (opts) => rpc.call("setPresentationAudioSettings", opts || {}),\n setPresentationAudioClip: (opts) => rpc.call("setPresentationAudioClip", opts || {}),\n removePresentationAudioClip: (opts) => rpc.call("removePresentationAudioClip", opts || {}),\n setPresentationTiming: (opts) => rpc.call("setPresentationTiming", opts || {}),\n getPresentationMix: (opts) => rpc.call("getPresentationMix", opts || {}),\n requestPresentationAudio: (opts) => rpc.call("requestPresentationAudio", opts || {}),\n moveNodes: (opts) => rpc.call("moveNodes", opts || {}),\n resizeNodes: (opts) => rpc.call("resizeNodes", opts || {}),\n renameNodes: (opts) => rpc.call("renameNodes", opts || {}),\n reparentNodes: (opts) => rpc.call("reparentNodes", opts || {}),\n duplicateNodes: (opts) => rpc.call("duplicateNodes", opts || {}),\n groupNodes: (opts) => rpc.call("groupNodes", opts || {}),\n ungroupNodes: (opts) => rpc.call("ungroupNodes", opts || {}),\n alignNodes: (opts) => rpc.call("alignNodes", opts || {}),\n distributeNodes: (opts) => rpc.call("distributeNodes", opts || {}),\n flipNodes: (opts) => rpc.call("flipNodes", opts || {}),\n rotateNodes: (opts) => rpc.call("rotateNodes", opts || {}),\n reorderNodes: (opts) => rpc.call("reorderNodes", opts || {}),\n setLocked: (opts) => rpc.call("setLocked", opts || {}),\n setVisible: (opts) => rpc.call("setVisible", opts || {}),\n setAutoLayout: (opts) => rpc.call("setAutoLayout", opts || {}),\n importSvg: (opts) => rpc.call("importSvg", opts || {}),\n measureNodes: (opts) => rpc.call("measureNodes", opts || {}),\n setFills: (opts) => rpc.call("setFills", opts || {}),\n setStrokes: (opts) => rpc.call("setStrokes", opts || {}),\n setEffects: (opts) => rpc.call("setEffects", opts || {}),\n replaceColor: (opts) => rpc.call("replaceColor", opts || {}),\n setTypography: (opts) => rpc.call("setTypography", opts || {}),\n applyStyle: (opts) => rpc.call("applyStyle", opts || {}),\n createComponent: (opts) => rpc.call("createComponent", opts || {}),\n createInstance: (opts) => rpc.call("createInstance", opts || {}),\n renamePage: (opts) => rpc.call("renamePage", opts || {}),\n getDocumentOutline: (opts) => rpc.call("getDocumentOutline", opts || {}),\n setPageSetup: (opts) => rpc.call("setPageSetup", opts || {}),\n setShowAdvance: (opts) => rpc.call("setShowAdvance", opts || {}),\n booleanOperation: (opts) => rpc.call("booleanOperation", opts || {}),\n flattenNodes: (opts) => rpc.call("flattenNodes", opts || {}),\n outlineStroke: (opts) => rpc.call("outlineStroke", opts || {}),\n setMask: (opts) => rpc.call("setMask", opts || {}),\n setMaskType: (opts) => rpc.call("setMaskType", opts || {}),\n shapeBuilder: (opts) => rpc.call("shapeBuilder", opts || {}),\n setKeyframes: (opts) => rpc.call("setKeyframes", opts || {}),\n getAnimation: (opts) => rpc.call("getAnimation", opts || {}),\n getCompositions: (opts) => rpc.call("getCompositions", opts || {}),\n editBehaviours: (opts) => rpc.call("editBehaviours", opts || {}),\n setTimeline: (opts) => rpc.call("setTimeline", opts || {}),\n setLayerTiming: (opts) => rpc.call("setLayerTiming", opts || {}),\n editTextAnimation: (opts) => rpc.call("editTextAnimation", opts || {}),\n edit3DScene: (opts) => rpc.call("edit3DScene", opts || {}),\n setInstancePlayback: (opts) => rpc.call("setInstancePlayback", opts || {}),\n editComponentProperty: (opts) => rpc.call("editComponentProperty", opts || {}),\n setShaderFill: (opts) => rpc.call("setShaderFill", opts || {}),\n createComposition: (opts) => rpc.call("createComposition", opts || {}),\n editComposition: (opts) => rpc.call("editComposition", opts || {}),\n editStateMachine: (opts) => rpc.call("editStateMachine", opts || {}),\n getStateMachine: (opts) => rpc.call("getStateMachine", opts || {}),\n applyMotionPreset: (opts) => rpc.call("applyMotionPreset", opts || {}),\n staggerMotion: (opts) => rpc.call("staggerMotion", opts || {}),\n createMotionComponent: (opts) => rpc.call("createMotionComponent", opts || {}),\n addAudio: (opts) => rpc.call("addAudio", opts || {}),\n editFrameAudio: (opts) => rpc.call("editFrameAudio", opts || {}),\n editVideoClip: (opts) => rpc.call("editVideoClip", opts || {}),\n detectAudioOnsets: (opts) => rpc.call("detectAudioOnsets", opts || {}),\n cutToBeat: (opts) => rpc.call("cutToBeat", opts || {}),\n editPrototype: (opts) => rpc.call("editPrototype", opts || {}),\n importFile: (opts) => rpc.call("importFile", opts || {}),\n usePresentationFallbackAudio: (opts) => rpc.call("usePresentationFallbackAudio", opts || {}),\n getStyles: () => rpc.call("getStyles"),\n createPaintStyle: (name, paints) => rpc.call("createPaintStyle", { name, paints }),\n getVariables: () => rpc.call("getVariables"),\n setVariableValue: (variableId, modeId, value) => rpc.call("setVariableValue", { variableId, modeId, value }),\n exportNode: (id, options) => rpc.call("exportNode", { id, options: options || {} }),\n openExternal: (url) => rpc.call("openExternal", { url }),\n notify: (message, options) => rpc.call("notify", { message: String(message), error: !!(options && options.error) }),\n showUI: (options) => rpc.call("showUI", options || {}),\n hideUI: () => rpc.call("hideUI"),\n /** Ends the run. The optional message is shown as a notification. */\n closePlugin: (message) => rpc.call("closePlugin", { message }),\n storage: {\n get: (key) => rpc.call("storageGet", { key }),\n set: (key, value) => rpc.call("storageSet", { key, value })\n },\n ui: {\n get onmessage() {\n return uiOnMessage;\n },\n set onmessage(cb) {\n uiOnMessage = cb;\n flushUI();\n },\n postMessage: (msg) => rpc.send({ kind: "toUI", data: msg }),\n on: (cb) => {\n uiHandlers.push(cb);\n flushUI();\n }\n },\n widget: {\n register(def) {\n if (!def || typeof def.render !== "function") throw new Error("popcraft.widget.register needs a render(state) function");\n widgetDef = def;\n widgetQueue.splice(0).forEach(handleWidgetClick);\n },\n insert(options) {\n if (!widgetDef) return Promise.reject(new Error("Call popcraft.widget.register first"));\n const o = options || {};\n const state = o.state !== void 0 ? clone(o.state) : initialWidgetState();\n return rpc.call("widgetInsert", { state, tree: renderWidget(state).tree, x: o.x, y: o.y });\n },\n getState: (nodeId) => rpc.call("widgetGet", { id: nodeId }),\n setState(nodeId, state) {\n if (!widgetDef) return Promise.reject(new Error("Call popcraft.widget.register first"));\n return commitWidget(nodeId, clone(state));\n }\n },\n on: (event, cb) => rpc.on(event, cb),\n off: (event, cb) => rpc.off(event, cb)\n };\n rpc.on("init", (data) => {\n var _a, _b, _c;\n popcraft.command = data.command;\n popcraft.exportRequest = (_c = data.exportRequest) != null ? _c : null;\n popcraft.importMode = (_a = data.importMode) != null ? _a : null;\n popcraft.importFile = (_b = data.importFile) != null ? _b : null;\n });\n return popcraft;\n }\n function installMainApi() {\n const rpc = createRpcClient();\n const api = createMainApi(rpc);\n const w = window;\n w.__popcraftRpc = rpc;\n w.popcraft = api;\n w.vizpops = api;\n window.addEventListener("error", (e) => rpc.send({ kind: "error", message: String(e.message || e) }));\n window.addEventListener("unhandledrejection", (e) => rpc.send({ kind: "error", message: String(e.reason && e.reason.message || e.reason) }));\n return api;\n }\n\n // src/runtime/main.entry.ts\n installMainApi();\n})();';
|
|
358617
|
+
"node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=e61849e2a6a59df95f0ebad36ab274c37a933fcf798d8b4dd6b3f0ffc625a1da/node_modules/@popcraft/plugins/dist/generated/runtime.js"() {
|
|
358618
|
+
MAIN_RUNTIME = '"use strict";\n(() => {\n // src/runtime/rpc.ts\n function createRpcClient() {\n let port = null;\n const queue = [];\n const pending = {};\n const listeners = {};\n let nextId = 1;\n function send(msg) {\n if (port) port.postMessage(msg);\n else queue.push(msg);\n }\n function call(method, params) {\n return new Promise((resolve, reject) => {\n const id = nextId++;\n pending[id] = { resolve, reject };\n send({ kind: "rpc", id, method, params });\n });\n }\n function emit(event, data) {\n for (const cb of (listeners[event] || []).slice()) {\n try {\n cb(data);\n } catch (e) {\n console.error(e);\n }\n }\n }\n window.addEventListener("message", (e) => {\n const data = e.data;\n if (e.source !== window.parent || !data || data.type !== "popcraft-plugin-port" || port) return;\n port = e.ports[0];\n port.onmessage = (ev) => {\n const m = ev.data || {};\n if (m.kind === "result" && m.id !== void 0 && pending[m.id]) {\n const p = pending[m.id];\n delete pending[m.id];\n if (m.error) p.reject(new Error(m.error));\n else p.resolve(m.result);\n } else if (m.kind === "event" && m.event) {\n emit(m.event, m.data);\n }\n };\n for (const msg of queue.splice(0)) port.postMessage(msg);\n });\n return {\n call,\n send,\n on(event, cb) {\n (listeners[event] = listeners[event] || []).push(cb);\n },\n off(event, cb) {\n listeners[event] = (listeners[event] || []).filter((x) => x !== cb);\n }\n };\n }\n\n // src/runtime/main.ts\n function clone(v) {\n return v === void 0 ? {} : JSON.parse(JSON.stringify(v));\n }\n function createMainApi(rpc = createRpcClient()) {\n const uiHandlers = [];\n let uiOnMessage = null;\n const uiQueue = [];\n function deliverUI(msg) {\n for (const cb of uiHandlers) {\n try {\n cb(msg);\n } catch (e) {\n console.error(e);\n }\n }\n if (typeof uiOnMessage === "function") {\n try {\n uiOnMessage(msg);\n } catch (e) {\n console.error(e);\n }\n }\n }\n function flushUI() {\n if (uiHandlers.length || typeof uiOnMessage === "function") uiQueue.splice(0).forEach(deliverUI);\n }\n rpc.on("uimessage", (msg) => {\n if (!uiHandlers.length && typeof uiOnMessage !== "function") uiQueue.push(msg);\n else deliverUI(msg);\n });\n let widgetDef = null;\n const widgetQueue = [];\n function renderWidget(state) {\n const handlers = {};\n function walk(el, path) {\n if (!el || typeof el !== "object") return el;\n const out = {};\n for (const k of Object.keys(el)) {\n const v = el[k];\n if (k === "children") {\n out.children = (Array.isArray(v) ? v : [v]).filter((c) => c !== null && c !== void 0 && c !== false).map((c, i) => walk(c, path + "." + i));\n } else if (k === "onClick" && typeof v === "function") {\n handlers[path] = v;\n out.onClick = path;\n } else {\n out[k] = v;\n }\n }\n return out;\n }\n return { tree: walk(widgetDef.render(state), "root"), handlers };\n }\n function initialWidgetState() {\n const s = widgetDef && widgetDef.initialState;\n return clone(typeof s === "function" ? s() : s);\n }\n function commitWidget(nodeId, state) {\n return rpc.call("widgetUpdate", { id: nodeId, state, tree: renderWidget(clone(state)).tree });\n }\n function handleWidgetClick(e) {\n Promise.resolve().then(() => {\n const state = clone(e.state);\n const rendered = renderWidget(state);\n const h = rendered.handlers[e.handler] || widgetDef.handlers && widgetDef.handlers[e.handler];\n if (typeof h !== "function") return;\n return Promise.resolve(h(state, { nodeId: e.nodeId })).then((ret) => commitWidget(e.nodeId, ret === void 0 ? state : ret));\n }).catch((err) => rpc.send({ kind: "error", message: String((err == null ? void 0 : err.message) || err) }));\n }\n rpc.on("widgetclick", (e) => {\n if (widgetDef) handleWidgetClick(e);\n else widgetQueue.push(e);\n });\n const popcraft = {\n /** Which menu command the user picked, or null when the plugin ran some other way. */\n command: null,\n /** Host import mode when launched as an importer, else null. */\n importMode: null,\n /** Pending import file when the host handed one over, else null. */\n importFile: null,\n /** Pending export request (File \u2192 Export \u2192 this plugin\'s format), else null. */\n exportRequest: null,\n getSelection: () => rpc.call("getSelection"),\n setSelection: (ids) => rpc.call("setSelection", { ids }),\n getNode: (id) => rpc.call("getNode", { id }),\n findNodes: (query) => rpc.call("findNodes", query || {}),\n getCurrentPage: () => rpc.call("getCurrentPage"),\n createNode: (type, props) => rpc.call("createNode", { type, props: props || {} }),\n updateNode: (id, props) => rpc.call("updateNode", { id, props }),\n deleteNode: (id) => rpc.call("deleteNode", { id }),\n setText: (id, characters) => rpc.call("setText", { id, characters }),\n /** Put TEXT layers on a path (another layer\'s outline, or their own arc, circle or wave), or tune one: brackets, alignment, placement, effect, overflow. */\n setTextPath: (opts) => rpc.call("setTextPath", opts || {}),\n /** Area type: flow a TEXT layer inside a closed shape, kept `inset` px in. */\n flowTextIntoShape: (opts) => rpc.call("flowTextIntoShape", opts || {}),\n /** Take TEXT layers off their path or out of their shape (or free every text linked to a path / shape). */\n detachText: (opts) => rpc.call("detachText", opts || {}),\n /** Auto-size TEXT layers\' type to their box, shape or path. */\n setTextFit: (opts) => rpc.call("setTextFit", opts || {}),\n createPage: (name) => rpc.call("createPage", name != null ? { name: String(name) } : {}),\n setCurrentPage: (pageId) => rpc.call("setCurrentPage", { pageId }),\n createImage: (opts) => rpc.call("createImage", opts || {}),\n createDocument: (opts) => rpc.call("createDocument", opts || {}),\n getImportMode: () => rpc.call("getImportMode"),\n getImportFile: () => rpc.call("getImportFile"),\n /**\n * The open page as a storefront design in a neutral form, for an exporter that writes its own store\'s templates:\n * each page\'s HTML with the store\'s data marked (`{{page.title}}`, `{{item.price}}`, `<!-- pc:each \u2026 -->` lists,\n * `data-pc-action` forms), and its collections with their commerce schema and sample records.\n */\n getStorefront: () => rpc.call("getStorefront"),\n /**\n * A design\'s data (docs: Collections): a collection and its fields (`schema`: what it stands for, e.g.\n * `commerce.product`, whose fields are made for it), its records, and reading them.\n */\n editCollection: (opts) => rpc.call("editCollection", opts || {}),\n editRecords: (opts) => rpc.call("editRecords", opts || {}),\n getRecords: (opts) => rpc.call("getRecords", opts || {}),\n /** A layer as a web page\'s form control (a FORM\'s `formAction`, an INPUT\'s name and value), repeated per record, a page\'s address, its semantics. */\n setControl: (opts) => rpc.call("setControl", opts || {}),\n setRepeat: (opts) => rpc.call("setRepeat", opts || {}),\n setRoute: (opts) => rpc.call("setRoute", opts || {}),\n setSemantics: (opts) => rpc.call("setSemantics", opts || {}),\n /** The site\'s environment: public settings its host reads by name when it is deployed (never a secret: the file keeps them). */\n getSiteEnvironment: () => rpc.call("getSiteEnvironment"),\n setSiteEnvironment: (set) => rpc.call("setSiteEnvironment", { set }),\n /** What this plugin keeps with the open file (its settings for this design), under its own id; JSON only. */\n getFileData: (key) => rpc.call("getFileData", { key }),\n setFileData: (key, value) => rpc.call("setFileData", { key, value }),\n /** A store\'s project built from the open page, zipped (needs `export`): what an exporter saves with `saveExport`. */\n getStorefrontFiles: (target) => rpc.call("getStorefrontFiles", { target }),\n getExportRequest: () => rpc.call("getExportRequest"),\n /** Save the exporter\'s file (once per export request); the host enforces the contributed extension. */\n saveExport: (file) => rpc.call("saveExport", file || {}),\n /**\n * Presentation audio (docs/plugins/presentation-audio.md): the deck\'s slides, notes, narration and timing; the\n * soundtrack\'s settings, bed and stinger.\n */\n getPresentationAudio: (opts) => rpc.call("getPresentationAudio", opts || {}),\n /** Change the soundtrack\'s settings (voice, style, mood, loudness, beat alignment, levels) and re-time it. */\n setPresentationAudioSettings: (opts) => rpc.call("setPresentationAudioSettings", opts || {}),\n /** Put a sound in (a slide\'s narration, the bed or the stinger): bytes are normalised to the soundtrack\'s target and stored. */\n setPresentationAudioClip: (opts) => rpc.call("setPresentationAudioClip", opts || {}),\n removePresentationAudioClip: (opts) => rpc.call("removePresentationAudioClip", opts || {}),\n /** Re-time: fixed slide lengths (ms, null clears) and beat-aligned changes. */\n setPresentationTiming: (opts) => rpc.call("setPresentationTiming", opts || {}),\n /** The mix as the export carries it: loudness, true peak, and (wav: true) the 48 kHz stereo WAV. */\n getPresentationMix: (opts) => rpc.call("getPresentationMix", opts || {}),\n /** Ask the user to generate with AI (the panel opens with the request filled in; the user decides). */\n requestPresentationAudio: (opts) => rpc.call("requestPresentationAudio", opts || {}),\n /** Editor commands: each takes the arguments documented in docs/plugins/methods.md (the agent tool of the same purpose). */\n moveNodes: (opts) => rpc.call("moveNodes", opts || {}),\n resizeNodes: (opts) => rpc.call("resizeNodes", opts || {}),\n renameNodes: (opts) => rpc.call("renameNodes", opts || {}),\n reparentNodes: (opts) => rpc.call("reparentNodes", opts || {}),\n duplicateNodes: (opts) => rpc.call("duplicateNodes", opts || {}),\n groupNodes: (opts) => rpc.call("groupNodes", opts || {}),\n ungroupNodes: (opts) => rpc.call("ungroupNodes", opts || {}),\n alignNodes: (opts) => rpc.call("alignNodes", opts || {}),\n distributeNodes: (opts) => rpc.call("distributeNodes", opts || {}),\n flipNodes: (opts) => rpc.call("flipNodes", opts || {}),\n rotateNodes: (opts) => rpc.call("rotateNodes", opts || {}),\n reorderNodes: (opts) => rpc.call("reorderNodes", opts || {}),\n setLocked: (opts) => rpc.call("setLocked", opts || {}),\n setVisible: (opts) => rpc.call("setVisible", opts || {}),\n setAutoLayout: (opts) => rpc.call("setAutoLayout", opts || {}),\n importSvg: (opts) => rpc.call("importSvg", opts || {}),\n measureNodes: (opts) => rpc.call("measureNodes", opts || {}),\n setFills: (opts) => rpc.call("setFills", opts || {}),\n setStrokes: (opts) => rpc.call("setStrokes", opts || {}),\n setEffects: (opts) => rpc.call("setEffects", opts || {}),\n replaceColor: (opts) => rpc.call("replaceColor", opts || {}),\n setTypography: (opts) => rpc.call("setTypography", opts || {}),\n applyStyle: (opts) => rpc.call("applyStyle", opts || {}),\n createComponent: (opts) => rpc.call("createComponent", opts || {}),\n createInstance: (opts) => rpc.call("createInstance", opts || {}),\n renamePage: (opts) => rpc.call("renamePage", opts || {}),\n getDocumentOutline: (opts) => rpc.call("getDocumentOutline", opts || {}),\n setPageSetup: (opts) => rpc.call("setPageSetup", opts || {}),\n setShowAdvance: (opts) => rpc.call("setShowAdvance", opts || {}),\n booleanOperation: (opts) => rpc.call("booleanOperation", opts || {}),\n flattenNodes: (opts) => rpc.call("flattenNodes", opts || {}),\n outlineStroke: (opts) => rpc.call("outlineStroke", opts || {}),\n setMask: (opts) => rpc.call("setMask", opts || {}),\n setMaskType: (opts) => rpc.call("setMaskType", opts || {}),\n shapeBuilder: (opts) => rpc.call("shapeBuilder", opts || {}),\n setKeyframes: (opts) => rpc.call("setKeyframes", opts || {}),\n getAnimation: (opts) => rpc.call("getAnimation", opts || {}),\n getCompositions: (opts) => rpc.call("getCompositions", opts || {}),\n editBehaviours: (opts) => rpc.call("editBehaviours", opts || {}),\n setTimeline: (opts) => rpc.call("setTimeline", opts || {}),\n setLayerTiming: (opts) => rpc.call("setLayerTiming", opts || {}),\n editTextAnimation: (opts) => rpc.call("editTextAnimation", opts || {}),\n edit3DScene: (opts) => rpc.call("edit3DScene", opts || {}),\n setInstancePlayback: (opts) => rpc.call("setInstancePlayback", opts || {}),\n editComponentProperty: (opts) => rpc.call("editComponentProperty", opts || {}),\n setShaderFill: (opts) => rpc.call("setShaderFill", opts || {}),\n createComposition: (opts) => rpc.call("createComposition", opts || {}),\n editComposition: (opts) => rpc.call("editComposition", opts || {}),\n editStateMachine: (opts) => rpc.call("editStateMachine", opts || {}),\n getStateMachine: (opts) => rpc.call("getStateMachine", opts || {}),\n applyMotionPreset: (opts) => rpc.call("applyMotionPreset", opts || {}),\n staggerMotion: (opts) => rpc.call("staggerMotion", opts || {}),\n createMotionComponent: (opts) => rpc.call("createMotionComponent", opts || {}),\n addAudio: (opts) => rpc.call("addAudio", opts || {}),\n editFrameAudio: (opts) => rpc.call("editFrameAudio", opts || {}),\n editVideoClip: (opts) => rpc.call("editVideoClip", opts || {}),\n detectAudioOnsets: (opts) => rpc.call("detectAudioOnsets", opts || {}),\n cutToBeat: (opts) => rpc.call("cutToBeat", opts || {}),\n editPrototype: (opts) => rpc.call("editPrototype", opts || {}),\n usePresentationFallbackAudio: (opts) => rpc.call("usePresentationFallbackAudio", opts || {}),\n /** Bring a Lottie, PDF or PopCraft file into the open document (the `importFile` field is the file an importer was handed). */\n importDocumentFile: (opts) => rpc.call("importDocumentFile", opts || {}),\n getStyles: () => rpc.call("getStyles"),\n createPaintStyle: (name, paints) => rpc.call("createPaintStyle", { name, paints }),\n getVariables: () => rpc.call("getVariables"),\n setVariableValue: (variableId, modeId, value) => rpc.call("setVariableValue", { variableId, modeId, value }),\n exportNode: (id, options) => rpc.call("exportNode", { id, options: options || {} }),\n openExternal: (url) => rpc.call("openExternal", { url }),\n notify: (message, options) => rpc.call("notify", { message: String(message), error: !!(options && options.error) }),\n showUI: (options) => rpc.call("showUI", options || {}),\n hideUI: () => rpc.call("hideUI"),\n /** Ends the run. The optional message is shown as a notification. */\n closePlugin: (message) => rpc.call("closePlugin", { message }),\n storage: {\n get: (key) => rpc.call("storageGet", { key }),\n set: (key, value) => rpc.call("storageSet", { key, value })\n },\n ui: {\n get onmessage() {\n return uiOnMessage;\n },\n set onmessage(cb) {\n uiOnMessage = cb;\n flushUI();\n },\n postMessage: (msg) => rpc.send({ kind: "toUI", data: msg }),\n on: (cb) => {\n uiHandlers.push(cb);\n flushUI();\n }\n },\n widget: {\n register(def) {\n if (!def || typeof def.render !== "function") throw new Error("popcraft.widget.register needs a render(state) function");\n widgetDef = def;\n widgetQueue.splice(0).forEach(handleWidgetClick);\n },\n insert(options) {\n if (!widgetDef) return Promise.reject(new Error("Call popcraft.widget.register first"));\n const o = options || {};\n const state = o.state !== void 0 ? clone(o.state) : initialWidgetState();\n return rpc.call("widgetInsert", { state, tree: renderWidget(state).tree, x: o.x, y: o.y });\n },\n getState: (nodeId) => rpc.call("widgetGet", { id: nodeId }),\n setState(nodeId, state) {\n if (!widgetDef) return Promise.reject(new Error("Call popcraft.widget.register first"));\n return commitWidget(nodeId, clone(state));\n }\n },\n on: (event, cb) => rpc.on(event, cb),\n off: (event, cb) => rpc.off(event, cb)\n };\n rpc.on("init", (data) => {\n var _a, _b, _c;\n popcraft.command = data.command;\n popcraft.importMode = (_a = data.importMode) != null ? _a : null;\n popcraft.importFile = (_b = data.importFile) != null ? _b : null;\n popcraft.exportRequest = (_c = data.exportRequest) != null ? _c : null;\n });\n return popcraft;\n }\n function installMainApi() {\n const rpc = createRpcClient();\n const api = createMainApi(rpc);\n const w = window;\n w.__popcraftRpc = rpc;\n w.popcraft = api;\n w.vizpops = api;\n window.addEventListener("error", (e) => rpc.send({ kind: "error", message: String(e.message || e) }));\n window.addEventListener("unhandledrejection", (e) => rpc.send({ kind: "error", message: String(e.reason && e.reason.message || e.reason) }));\n return api;\n }\n\n // src/runtime/main.entry.ts\n installMainApi();\n})();';
|
|
358722
358619
|
UI_RUNTIME = '"use strict";\n(() => {\n // src/runtime/rpc.ts\n function createRpcClient() {\n let port = null;\n const queue = [];\n const pending = {};\n const listeners = {};\n let nextId = 1;\n function send(msg) {\n if (port) port.postMessage(msg);\n else queue.push(msg);\n }\n function call(method, params) {\n return new Promise((resolve, reject) => {\n const id = nextId++;\n pending[id] = { resolve, reject };\n send({ kind: "rpc", id, method, params });\n });\n }\n function emit(event, data) {\n for (const cb of (listeners[event] || []).slice()) {\n try {\n cb(data);\n } catch (e) {\n console.error(e);\n }\n }\n }\n window.addEventListener("message", (e) => {\n const data = e.data;\n if (e.source !== window.parent || !data || data.type !== "popcraft-plugin-port" || port) return;\n port = e.ports[0];\n port.onmessage = (ev) => {\n const m = ev.data || {};\n if (m.kind === "result" && m.id !== void 0 && pending[m.id]) {\n const p = pending[m.id];\n delete pending[m.id];\n if (m.error) p.reject(new Error(m.error));\n else p.resolve(m.result);\n } else if (m.kind === "event" && m.event) {\n emit(m.event, m.data);\n }\n };\n for (const msg of queue.splice(0)) port.postMessage(msg);\n });\n return {\n call,\n send,\n on(event, cb) {\n (listeners[event] = listeners[event] || []).push(cb);\n },\n off(event, cb) {\n listeners[event] = (listeners[event] || []).filter((x) => x !== cb);\n }\n };\n }\n\n // src/runtime/ui.ts\n function createUiApi(rpc = createRpcClient()) {\n const popcraft = {\n onmessage: null,\n postMessage: (msg) => rpc.send({ kind: "fromUI", data: msg }),\n close: () => rpc.send({ kind: "closeUI" })\n };\n rpc.on("message", (msg) => {\n if (typeof popcraft.onmessage === "function") popcraft.onmessage(msg);\n window.dispatchEvent(new MessageEvent("message", { data: { pluginMessage: msg } }));\n });\n return popcraft;\n }\n function installUiApi() {\n const rpc = createRpcClient();\n const api = createUiApi(rpc);\n const w = window;\n w.__popcraftRpc = rpc;\n w.popcraft = api;\n w.vizpops = api;\n return api;\n }\n\n // src/runtime/ui.entry.ts\n installUiApi();\n})();';
|
|
358723
358620
|
}
|
|
358724
358621
|
});
|
|
358725
358622
|
|
|
358726
|
-
// node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=
|
|
358623
|
+
// node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=e61849e2a6a59df95f0ebad36ab274c37a933fcf798d8b4dd6b3f0ffc625a1da/node_modules/@popcraft/plugins/dist/host.js
|
|
358727
358624
|
function csp(network) {
|
|
358728
358625
|
const connect2 = network ? "connect-src * data: blob:;" : "connect-src 'none';";
|
|
358729
358626
|
const img = network ? "img-src * data: blob:;" : "img-src data: blob:;";
|
|
@@ -358751,40 +358648,40 @@ function buildUIDocument(uiHtml, network) {
|
|
|
358751
358648
|
}
|
|
358752
358649
|
var escapeScript;
|
|
358753
358650
|
var init_host2 = __esm({
|
|
358754
|
-
"node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=
|
|
358651
|
+
"node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=e61849e2a6a59df95f0ebad36ab274c37a933fcf798d8b4dd6b3f0ffc625a1da/node_modules/@popcraft/plugins/dist/host.js"() {
|
|
358755
358652
|
init_runtime4();
|
|
358756
358653
|
escapeScript = (code) => code.replace(/<\/script/gi, "<\\/script");
|
|
358757
358654
|
}
|
|
358758
358655
|
});
|
|
358759
358656
|
|
|
358760
|
-
// node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=
|
|
358657
|
+
// node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=e61849e2a6a59df95f0ebad36ab274c37a933fcf798d8b4dd6b3f0ffc625a1da/node_modules/@popcraft/plugins/dist/runtime/rpc.js
|
|
358761
358658
|
var init_rpc = __esm({
|
|
358762
|
-
"node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=
|
|
358659
|
+
"node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=e61849e2a6a59df95f0ebad36ab274c37a933fcf798d8b4dd6b3f0ffc625a1da/node_modules/@popcraft/plugins/dist/runtime/rpc.js"() {
|
|
358763
358660
|
}
|
|
358764
358661
|
});
|
|
358765
358662
|
|
|
358766
|
-
// node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=
|
|
358663
|
+
// node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=e61849e2a6a59df95f0ebad36ab274c37a933fcf798d8b4dd6b3f0ffc625a1da/node_modules/@popcraft/plugins/dist/runtime/main.js
|
|
358767
358664
|
var init_main = __esm({
|
|
358768
|
-
"node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=
|
|
358665
|
+
"node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=e61849e2a6a59df95f0ebad36ab274c37a933fcf798d8b4dd6b3f0ffc625a1da/node_modules/@popcraft/plugins/dist/runtime/main.js"() {
|
|
358769
358666
|
init_rpc();
|
|
358770
358667
|
}
|
|
358771
358668
|
});
|
|
358772
358669
|
|
|
358773
|
-
// node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=
|
|
358670
|
+
// node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=e61849e2a6a59df95f0ebad36ab274c37a933fcf798d8b4dd6b3f0ffc625a1da/node_modules/@popcraft/plugins/dist/types.js
|
|
358774
358671
|
var init_types9 = __esm({
|
|
358775
|
-
"node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=
|
|
358672
|
+
"node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=e61849e2a6a59df95f0ebad36ab274c37a933fcf798d8b4dd6b3f0ffc625a1da/node_modules/@popcraft/plugins/dist/types.js"() {
|
|
358776
358673
|
}
|
|
358777
358674
|
});
|
|
358778
358675
|
|
|
358779
|
-
// node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=
|
|
358676
|
+
// node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=e61849e2a6a59df95f0ebad36ab274c37a933fcf798d8b4dd6b3f0ffc625a1da/node_modules/@popcraft/plugins/dist/widget.js
|
|
358780
358677
|
var init_widget = __esm({
|
|
358781
|
-
"node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=
|
|
358678
|
+
"node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=e61849e2a6a59df95f0ebad36ab274c37a933fcf798d8b4dd6b3f0ffc625a1da/node_modules/@popcraft/plugins/dist/widget.js"() {
|
|
358782
358679
|
}
|
|
358783
358680
|
});
|
|
358784
358681
|
|
|
358785
|
-
// node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=
|
|
358682
|
+
// node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=e61849e2a6a59df95f0ebad36ab274c37a933fcf798d8b4dd6b3f0ffc625a1da/node_modules/@popcraft/plugins/dist/index.js
|
|
358786
358683
|
var init_dist = __esm({
|
|
358787
|
-
"node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=
|
|
358684
|
+
"node_modules/.pnpm/@popcraft+plugins@1.0.0_patch_hash=e61849e2a6a59df95f0ebad36ab274c37a933fcf798d8b4dd6b3f0ffc625a1da/node_modules/@popcraft/plugins/dist/index.js"() {
|
|
358788
358685
|
init_host2();
|
|
358789
358686
|
init_main();
|
|
358790
358687
|
init_runtime4();
|
|
@@ -359532,7 +359429,7 @@ var init_import = __esm({
|
|
|
359532
359429
|
init_esm2();
|
|
359533
359430
|
init_scene_graph();
|
|
359534
359431
|
init_types();
|
|
359535
|
-
|
|
359432
|
+
init_state_machine3();
|
|
359536
359433
|
GEOMETRY = /* @__PURE__ */ new Set(["gr", "rc", "el", "sh", "sr"]);
|
|
359537
359434
|
BLENDS = ["NORMAL", "MULTIPLY", "SCREEN", "OVERLAY", "DARKEN", "LIGHTEN", "COLOR_DODGE", "COLOR_BURN", "HARD_LIGHT", "SOFT_LIGHT", "DIFFERENCE", "EXCLUSION", "HUE", "SATURATION", "COLOR", "LUMINOSITY"];
|
|
359538
359435
|
nearestFps = (fr) => TIMELINE_FPS_VALUES.reduce((a, b) => Math.abs(b - fr) < Math.abs(a - fr) ? b : a, TIMELINE_FPS_VALUES[0]);
|
|
@@ -388978,6 +388875,10 @@ function isOpenableUrl(v) {
|
|
|
388978
388875
|
return false;
|
|
388979
388876
|
}
|
|
388980
388877
|
}
|
|
388878
|
+
function pluginOf(ctx2) {
|
|
388879
|
+
if (ctx2.actor.kind !== "plugin" || !ctx2.actor.id) throw new PluginApiError("Only a plugin keeps file data");
|
|
388880
|
+
return ctx2.actor.id;
|
|
388881
|
+
}
|
|
388981
388882
|
function pluginMethods() {
|
|
388982
388883
|
registerPluginCommands();
|
|
388983
388884
|
return listCommandsForSurface("plugin").map((c2) => c2.expose.plugin.method);
|
|
@@ -389241,7 +389142,7 @@ var init_plugin = __esm({
|
|
|
389241
389142
|
permission: "read",
|
|
389242
389143
|
expose: { plugin: { method: "getStorefront", shape: (r) => r.data } },
|
|
389243
389144
|
// A storefront design in a neutral form (lib/io/web/project/storefront.ts `storefrontDesign`): what an exporter
|
|
389244
|
-
// plugin turns into its own store's templates, as PopCraft turns it into a Next.js Commerce store
|
|
389145
|
+
// plugin turns into its own store's templates, as PopCraft turns it into a Next.js Commerce store (the Ecommerce plugin makes a Shopify theme of it).
|
|
389245
389146
|
run: async (_p, ctx2) => {
|
|
389246
389147
|
const [{ componentScreens: componentScreens2 }, { storefrontDesign: storefrontDesign2 }] = await Promise.all([Promise.resolve().then(() => (init_components(), components_exports)), Promise.resolve().then(() => (init_storefront(), storefront_exports))]);
|
|
389247
389148
|
const doc2 = ctx2.doc();
|
|
@@ -389249,6 +389150,32 @@ var init_plugin = __esm({
|
|
|
389249
389150
|
return { summary: `Storefront: ${design.pages.length} pages`, data: design };
|
|
389250
389151
|
}
|
|
389251
389152
|
}),
|
|
389153
|
+
defineCommand({
|
|
389154
|
+
id: pluginCommandId("getStorefrontFiles"),
|
|
389155
|
+
title: "Build a storefront target",
|
|
389156
|
+
domain: "export",
|
|
389157
|
+
params: external_exports.object({ target: external_exports.enum(["shopify-theme", "next-commerce", "next-commerce-store"]) }),
|
|
389158
|
+
effect: "none",
|
|
389159
|
+
permission: "export",
|
|
389160
|
+
expose: { plugin: { method: "getStorefrontFiles", shape: (r) => r.data } },
|
|
389161
|
+
// A store's project, built from the open page as Export storefront builds it, zipped: what an exporter plugin
|
|
389162
|
+
// saves (the Ecommerce plugin's Shopify theme), so a target is written once, here, and never again in a plugin.
|
|
389163
|
+
run: async (p2, ctx2) => {
|
|
389164
|
+
const [{ storefrontInputs: storefrontInputs2 }, { STOREFRONT_TARGETS: STOREFRONT_TARGETS2 }, { bytesOf: bytesOf2 }, { zipFiles: zipFiles2 }, { EXPORT_NODE_CAP: EXPORT_NODE_CAP2 }] = await Promise.all([
|
|
389165
|
+
Promise.resolve().then(() => (init_storefront_prepare(), storefront_prepare_exports)),
|
|
389166
|
+
Promise.resolve().then(() => (init_storefront(), storefront_exports)),
|
|
389167
|
+
Promise.resolve().then(() => (init_project(), project_exports)),
|
|
389168
|
+
Promise.resolve().then(() => (init_zip_export(), zip_export_exports)),
|
|
389169
|
+
Promise.resolve().then(() => (init_tree(), tree_exports))
|
|
389170
|
+
]);
|
|
389171
|
+
const doc2 = ctx2.doc();
|
|
389172
|
+
const { screens, media: media2 } = await storefrontInputs2(doc2, ctx2.pageId(), EXPORT_NODE_CAP2);
|
|
389173
|
+
if (!screens.length) throw new PluginApiError("This page has no screens: a top-level frame is a page of the store.");
|
|
389174
|
+
const files = STOREFRONT_TARGETS2[p2.target].files(doc2, screens, { media: media2 });
|
|
389175
|
+
const zip = zipFiles2(files.map((f2) => ({ name: f2.path, bytes: bytesOf2(f2) })));
|
|
389176
|
+
return { summary: `${STOREFRONT_TARGETS2[p2.target].label}: ${files.length} files`, data: { name: `${doc2.name || "store"}-${p2.target}.zip`, files: files.length, bytes: new Uint8Array(await zip.arrayBuffer()) } };
|
|
389177
|
+
}
|
|
389178
|
+
}),
|
|
389252
389179
|
defineCommand({
|
|
389253
389180
|
id: pluginCommandId("getExportRequest"),
|
|
389254
389181
|
title: "Get export request",
|
|
@@ -389378,6 +389305,36 @@ var init_plugin = __esm({
|
|
|
389378
389305
|
return { summary: `Wrote ${p2.key}` };
|
|
389379
389306
|
}
|
|
389380
389307
|
}),
|
|
389308
|
+
// What the plugin keeps with the open file (Document.pluginData), under its own id: its settings for this design.
|
|
389309
|
+
defineCommand({
|
|
389310
|
+
id: pluginCommandId("getFileData"),
|
|
389311
|
+
title: "Read plugin file data",
|
|
389312
|
+
domain: "storage",
|
|
389313
|
+
params: external_exports.object({ key: external_exports.unknown().transform((v) => String(v)) }),
|
|
389314
|
+
effect: "none",
|
|
389315
|
+
permission: "read",
|
|
389316
|
+
expose: { plugin: { method: "getFileData", shape: (r) => r.data } },
|
|
389317
|
+
run: (p2, ctx2) => ({ summary: `Read ${p2.key}`, data: ctx2.doc().pluginData?.[pluginOf(ctx2)]?.[p2.key] })
|
|
389318
|
+
}),
|
|
389319
|
+
defineCommand({
|
|
389320
|
+
id: pluginCommandId("setFileData"),
|
|
389321
|
+
title: "Write plugin file data",
|
|
389322
|
+
domain: "storage",
|
|
389323
|
+
params: external_exports.object({ key: external_exports.unknown().transform((v) => String(v)), value: external_exports.unknown() }),
|
|
389324
|
+
effect: "document",
|
|
389325
|
+
permission: "write",
|
|
389326
|
+
expose: { plugin: { method: "setFileData" } },
|
|
389327
|
+
run: (p2, ctx2) => {
|
|
389328
|
+
const doc2 = ctx2.doc();
|
|
389329
|
+
const id3 = pluginOf(ctx2);
|
|
389330
|
+
const mine = { ...doc2.pluginData?.[id3] ?? {} };
|
|
389331
|
+
if (p2.value === void 0 || p2.value === null) delete mine[p2.key];
|
|
389332
|
+
else mine[p2.key] = plain(p2.value);
|
|
389333
|
+
const { [id3]: _, ...others } = doc2.pluginData ?? {};
|
|
389334
|
+
ctx2.commit({ ...doc2, pluginData: Object.keys(mine).length ? { ...others, [id3]: mine } : others });
|
|
389335
|
+
return { summary: `Wrote ${p2.key}` };
|
|
389336
|
+
}
|
|
389337
|
+
}),
|
|
389381
389338
|
...widgetCommands(pluginCommandId)
|
|
389382
389339
|
];
|
|
389383
389340
|
pluginRun = defineCommand({
|
|
@@ -389435,7 +389392,7 @@ function attached(done, ctx2) {
|
|
|
389435
389392
|
ctx2.notice(`Database attached: ${where}`);
|
|
389436
389393
|
return { summary: `Attached ${where} (${db3.connection.provider}, ${db3.connection.account}): the site's forms are saved there once it is published`, data: { provider: db3.connection.provider, account: db3.connection.account, target: db3.target } };
|
|
389437
389394
|
}
|
|
389438
|
-
var integrationList, integrationOpen, asPath2, integrationListResources, place3, integrationAddDestination, integrationDeploy, integrationAttachDatabase, integrationSubmissions, integrationSetSignIn, integrationConfirmCommands
|
|
389395
|
+
var integrationList, integrationOpen, asPath2, integrationListResources, place3, integrationAddDestination, integrationDeploy, integrationAttachDatabase, integrationSubmissions, integrationSetSignIn, integrationConfirmCommands;
|
|
389439
389396
|
var init_integration = __esm({
|
|
389440
389397
|
"lib/commands/integration.ts"() {
|
|
389441
389398
|
"use strict";
|
|
@@ -389449,13 +389406,13 @@ var init_integration = __esm({
|
|
|
389449
389406
|
effect: "none",
|
|
389450
389407
|
permission: null,
|
|
389451
389408
|
params: external_exports.object({
|
|
389452
|
-
capability: external_exports.enum(["repo", "deploy", "database", "auth"
|
|
389409
|
+
capability: external_exports.enum(["repo", "deploy", "database", "auth"]).optional().describe("Only the integrations that can do this: repo (push code to a repository), deploy (host the site), database (store what forms send and what collections hold), auth (sign-in for the site's visitors).")
|
|
389453
389410
|
}),
|
|
389454
389411
|
expose: {
|
|
389455
389412
|
agent: {
|
|
389456
389413
|
name: "list_integrations",
|
|
389457
389414
|
readOnly: true,
|
|
389458
|
-
description: "The services this workspace can connect its own accounts to (GitHub, Vercel, Neon, Supabase
|
|
389415
|
+
description: "The services this workspace can connect its own accounts to (GitHub, Vercel, Neon, Supabase), what each can do (repo, deploy, database, auth), which accounts are connected, and whether the user can connect more. `notYet` lists what an integration is meant to do and cannot yet: never promise those. Call it before recommending one, and before any step that needs a connection. You cannot connect an account yourself: when one is missing, say which integration fits and why, then call open_integrations so the user can connect it."
|
|
389459
389416
|
}
|
|
389460
389417
|
},
|
|
389461
389418
|
run: async ({ capability: capability2 }) => {
|
|
@@ -389690,50 +389647,6 @@ var init_integration = __esm({
|
|
|
389690
389647
|
}
|
|
389691
389648
|
});
|
|
389692
389649
|
integrationConfirmCommands = [integrationAddDestination, integrationDeploy, integrationAttachDatabase, integrationSetSignIn];
|
|
389693
|
-
integrationPullProducts = defineCommand({
|
|
389694
|
-
id: "integration.pullProducts",
|
|
389695
|
-
title: "Draw the design with a store's products",
|
|
389696
|
-
domain: "integration",
|
|
389697
|
-
effect: "document",
|
|
389698
|
-
permission: "write",
|
|
389699
|
-
undoLabel: "Store products",
|
|
389700
|
-
params: external_exports.object({
|
|
389701
|
-
connectionId: external_exports.string().optional().describe("The connected store, from list_integrations (capability commerce). Omit when one store is connected."),
|
|
389702
|
-
collection: external_exports.string().optional().describe("The collection to fill, by id or name; it must stand for store products (schema commerce.product). Omit when the file has one."),
|
|
389703
|
-
limit: external_exports.number().int().min(1).max(100).default(24).describe("How many of the store's newest products.")
|
|
389704
|
-
}).strict(),
|
|
389705
|
-
expose: {
|
|
389706
|
-
ui: { label: "Draw with my store's products", keywords: ["shopify", "store", "products", "commerce", "shop", "catalogue", "import"] },
|
|
389707
|
-
agent: {
|
|
389708
|
-
name: "pull_store_products",
|
|
389709
|
-
description: "Replace the records of a storefront design's product collection (schema commerce.product) with a connected store's real products (Shopify): titles, prices, pictures, handles and variant ids, newest first. The design's lists and product pages then show them. It reads the store; it never changes it. Needs a Shopify connection (list_integrations, capability commerce); you cannot connect one yourself."
|
|
389710
|
-
}
|
|
389711
|
-
},
|
|
389712
|
-
run: async (args2, ctx2) => {
|
|
389713
|
-
const [{ cloudUser: cloudUser2 }, { connectedStore: connectedStore2, storeProducts: storeProducts2 }, { commerceItem: commerceItem2, COMMERCE_FIELDS: COMMERCE_FIELDS2 }, { fieldKey: fieldKey2, removeRecords: removeRecords2, upsertRecords: upsertRecords2 }] = await Promise.all([
|
|
389714
|
-
Promise.resolve().then(() => (init_session(), session_exports)),
|
|
389715
|
-
Promise.resolve().then(() => (init_integrations(), integrations_exports)),
|
|
389716
|
-
Promise.resolve().then(() => (init_commerce(), commerce_exports)),
|
|
389717
|
-
Promise.resolve().then(() => (init_collections(), collections_exports))
|
|
389718
|
-
]);
|
|
389719
|
-
if (!cloudUser2()) throw new CommandError("You are not signed in: a store is connected to your account's workspace.", "denied");
|
|
389720
|
-
const doc2 = ctx2.doc();
|
|
389721
|
-
const pick5 = Object.values(doc2.collections ?? {}).filter((c2) => c2.schema === "commerce.product" && (!args2.collection || c2.id === args2.collection || c2.name.toLowerCase() === args2.collection.toLowerCase()));
|
|
389722
|
-
if (!pick5.length) throw new CommandError(args2.collection ? `No store products collection "${args2.collection}".` : "This file has no collection that stands for store products: set one to Store products in Collections first.", "invalid_params");
|
|
389723
|
-
if (pick5.length > 1) throw new CommandError(`Name the collection: ${pick5.map((c2) => c2.name).join(", ")}.`, "invalid_params");
|
|
389724
|
-
const collection = pick5[0];
|
|
389725
|
-
const connectionId = await connectedStore2(args2.connectionId).catch((e) => {
|
|
389726
|
-
throw new CommandError(e instanceof Error ? e.message : String(e), "failed");
|
|
389727
|
-
});
|
|
389728
|
-
const products = await storeProducts2(connectionId, args2.limit);
|
|
389729
|
-
if (!products.length) throw new CommandError("The store has no products to show.", "failed");
|
|
389730
|
-
const keys4 = new Map(COMMERCE_FIELDS2["commerce.product"].map((f2) => [fieldKey2(f2.name), f2.name]));
|
|
389731
|
-
const rows = products.map((p2) => ({ values: Object.fromEntries(Object.entries(commerceItem2("commerce.product", p2).values).filter(([k2]) => keys4.has(k2)).map(([k2, v]) => [keys4.get(k2), v])) }));
|
|
389732
|
-
const cleared = removeRecords2(doc2, collection.order);
|
|
389733
|
-
ctx2.commit(upsertRecords2(cleared, collection.id, rows).document);
|
|
389734
|
-
return { summary: `Drew ${collection.name} with ${products.length} of the store's products`, data: { collection: collection.id, products: products.length } };
|
|
389735
|
-
}
|
|
389736
|
-
});
|
|
389737
389650
|
}
|
|
389738
389651
|
});
|
|
389739
389652
|
|
|
@@ -390356,6 +390269,7 @@ function record(source, namespaces, globals, limits) {
|
|
|
390356
390269
|
var HELPER_NAMES;
|
|
390357
390270
|
var init_helper_names = __esm({
|
|
390358
390271
|
"lib/agent/design-script/helper-names.ts"() {
|
|
390272
|
+
"use strict";
|
|
390359
390273
|
HELPER_NAMES = ["draw", "marks", "fit", "motion", "captions", "overlays", "texture", "pointer", "windows", "devices", "type", "beat", "web", "social", "video", "site", "effects"];
|
|
390360
390274
|
}
|
|
390361
390275
|
});
|
|
@@ -393873,7 +393787,7 @@ function collectionOf(doc2, ref3) {
|
|
|
393873
393787
|
if (!c2) throw new ToolError(`No collection "${ref3}". ${Object.values(doc2.collections ?? {}).length ? `There is: ${Object.values(doc2.collections).map((x2) => x2.name).join(", ")}.` : "Make one with edit_collection."}`);
|
|
393874
393788
|
return c2;
|
|
393875
393789
|
}
|
|
393876
|
-
var sizing2, padding2, overrides, nodeSetResponsive, link, nodeSetSemantics, nodeSetControl, siteSetRoute, breakpoint, siteSetBreakpoints, siteSetGpuTransitions, siteGetBreakpoints, described2, dataEditCollection, dataEditRecords, dataGetRecords, nodeSetRepeat;
|
|
393790
|
+
var sizing2, padding2, overrides, nodeSetResponsive, link, nodeSetSemantics, nodeSetControl, siteSetRoute, breakpoint, siteSetBreakpoints, siteSetGpuTransitions, ENV_NAME, RESERVED_ENV, siteSetEnvironment, siteGetEnvironment, siteGetBreakpoints, described2, dataEditCollection, dataEditRecords, dataGetRecords, nodeSetRepeat;
|
|
393877
393791
|
var init_site3 = __esm({
|
|
393878
393792
|
"lib/commands/site.ts"() {
|
|
393879
393793
|
"use strict";
|
|
@@ -393983,6 +393897,7 @@ var init_site3 = __esm({
|
|
|
393983
393897
|
link: link.nullable().optional().describe('Make the whole layer a link: {kind:"url", url, newTab?}, {kind:"screen", frameId} (another top-level frame), {kind:"anchor", nodeId} (a layer on the page), {kind:"email", value} or {kind:"tel", value}; null removes it.')
|
|
393984
393898
|
}).strict(),
|
|
393985
393899
|
expose: {
|
|
393900
|
+
plugin: { method: "setSemantics" },
|
|
393986
393901
|
ui: { label: "Web semantics", keywords: ["semantic", "html", "tag", "heading", "link", "anchor", "accessibility", "aria"], enabled: needsSelection(1), palette: false },
|
|
393987
393902
|
agent: {
|
|
393988
393903
|
name: "set_semantics",
|
|
@@ -394045,6 +393960,7 @@ var init_site3 = __esm({
|
|
|
394045
393960
|
onSubmit: external_exports.record(external_exports.string(), external_exports.unknown()).nullable().optional().describe('FORM: a prototype action run once it is sent, as edit_prototype takes them ({navigationType: "NAVIGATE", destinationId: <thank-you frame>}).')
|
|
394046
393961
|
}).strict(),
|
|
394047
393962
|
expose: {
|
|
393963
|
+
plugin: { method: "setControl" },
|
|
394048
393964
|
ui: { label: "Form control", keywords: ["form", "input", "field", "textarea", "select", "checkbox", "radio", "button", "submit"], enabled: needsSelection(1), palette: false },
|
|
394049
393965
|
agent: {
|
|
394050
393966
|
name: "set_control",
|
|
@@ -394056,7 +393972,7 @@ var init_site3 = __esm({
|
|
|
394056
393972
|
const { ids: _ids, kind, ...rest } = args2;
|
|
394057
393973
|
void _ids;
|
|
394058
393974
|
if (rest.variableId && !doc2.variables?.[rest.variableId]) throw new ToolError(`No variable ${rest.variableId}.`);
|
|
394059
|
-
const name2 = rest.name !== void 0 ?
|
|
393975
|
+
const name2 = rest.name !== void 0 ? cleanName(rest.name) : void 0;
|
|
394060
393976
|
if (rest.name && !name2) throw new ToolError(`"${rest.name}" has nothing a form can send a value under: use letters, digits, dashes and underscores.`);
|
|
394061
393977
|
const patches = /* @__PURE__ */ new Map();
|
|
394062
393978
|
for (const id3 of ids2) {
|
|
@@ -394093,6 +394009,7 @@ var init_site3 = __esm({
|
|
|
394093
394009
|
collectionId: external_exports.string().nullable().optional().describe("Make the screen one page per record of this collection (its address, then the record's: /blog/first-post); texts on it say fields with {{item.title}}. null: an ordinary page again.")
|
|
394094
394010
|
}).strict(),
|
|
394095
394011
|
expose: {
|
|
394012
|
+
plugin: { method: "setRoute" },
|
|
394096
394013
|
ui: { label: "Page address", keywords: ["route", "url", "path", "slug", "page title", "seo", "404"], enabled: needsSelection(1), palette: false },
|
|
394097
394014
|
agent: {
|
|
394098
394015
|
name: "set_route",
|
|
@@ -394184,6 +394101,56 @@ var init_site3 = __esm({
|
|
|
394184
394101
|
return { summary: args2.on ? "3D transitions draw with WebGPU where the browser has it" : "3D transitions draw in CSS 3D only", data: { on: args2.on } };
|
|
394185
394102
|
}
|
|
394186
394103
|
});
|
|
394104
|
+
ENV_NAME = /^[A-Z][A-Z0-9_]{0,63}$/;
|
|
394105
|
+
RESERVED_ENV = /^(VERCEL|NEXT_RUNTIME|NODE_ENV|PORT|DATABASE_URL|SITE_AUTH_)/;
|
|
394106
|
+
siteSetEnvironment = defineCommand({
|
|
394107
|
+
id: "site.setEnvironment",
|
|
394108
|
+
title: "Set site environment",
|
|
394109
|
+
domain: "site",
|
|
394110
|
+
effect: "document",
|
|
394111
|
+
permission: "write",
|
|
394112
|
+
undoLabel: "Change the site environment",
|
|
394113
|
+
params: external_exports.object({
|
|
394114
|
+
set: external_exports.record(external_exports.string().regex(ENV_NAME, "Names are upper case, digits and underscores (SHOPIFY_STORE_DOMAIN)"), external_exports.string().max(4096).nullable()).describe("Each name to its value; null removes it. Public values only: everyone who can open the file sees them.")
|
|
394115
|
+
}).strict(),
|
|
394116
|
+
expose: {
|
|
394117
|
+
plugin: { method: "setSiteEnvironment" },
|
|
394118
|
+
ui: { label: "Site environment", keywords: ["environment", "env", "variables", "settings", "deploy", "store"], palette: false },
|
|
394119
|
+
agent: {
|
|
394120
|
+
name: "set_site_environment",
|
|
394121
|
+
description: "Set or remove the site's environment variables: public settings its host reads by name when it is deployed (a store's SHOPIFY_STORE_DOMAIN and public SHOPIFY_STOREFRONT_ACCESS_TOKEN). Kept in the file, seen by everyone who can open it: never put a secret here. null removes a name."
|
|
394122
|
+
}
|
|
394123
|
+
},
|
|
394124
|
+
run: (args2, ctx2) => {
|
|
394125
|
+
const doc2 = ctx2.doc();
|
|
394126
|
+
const bad = Object.keys(args2.set).find((k2) => RESERVED_ENV.test(k2));
|
|
394127
|
+
if (bad) throw new ToolError(`${bad} is set by the host or kept on the server: a file cannot set it.`);
|
|
394128
|
+
const env = { ...doc2.site?.env ?? {} };
|
|
394129
|
+
for (const [k2, v] of Object.entries(args2.set)) {
|
|
394130
|
+
if (v === null) delete env[k2];
|
|
394131
|
+
else env[k2] = v;
|
|
394132
|
+
}
|
|
394133
|
+
const { env: _, ...rest } = doc2.site ?? {};
|
|
394134
|
+
ctx2.commit({ ...doc2, site: Object.keys(env).length ? { ...rest, env } : rest });
|
|
394135
|
+
return { summary: `Site environment: ${Object.keys(env).sort().join(", ") || "none"}`, data: { names: Object.keys(env).sort() } };
|
|
394136
|
+
}
|
|
394137
|
+
});
|
|
394138
|
+
siteGetEnvironment = defineCommand({
|
|
394139
|
+
id: "site.getEnvironment",
|
|
394140
|
+
title: "Get site environment",
|
|
394141
|
+
domain: "site",
|
|
394142
|
+
effect: "none",
|
|
394143
|
+
permission: "read",
|
|
394144
|
+
params: external_exports.object({}).strict(),
|
|
394145
|
+
expose: {
|
|
394146
|
+
plugin: { method: "getSiteEnvironment", shape: (r) => r.data },
|
|
394147
|
+
agent: { name: "get_site_environment", readOnly: true, description: "The site's environment variables (public settings its host reads by name when it is deployed), by name." }
|
|
394148
|
+
},
|
|
394149
|
+
run: (_args, ctx2) => {
|
|
394150
|
+
const env = ctx2.doc().site?.env ?? {};
|
|
394151
|
+
return { summary: `${Object.keys(env).length} environment variable(s)`, data: env };
|
|
394152
|
+
}
|
|
394153
|
+
});
|
|
394187
394154
|
siteGetBreakpoints = defineCommand({
|
|
394188
394155
|
id: "site.getBreakpoints",
|
|
394189
394156
|
title: "Get breakpoints",
|
|
@@ -394238,6 +394205,7 @@ var init_site3 = __esm({
|
|
|
394238
394205
|
remove: external_exports.boolean().optional().describe("Delete the collection, its records, and the repeaters and collection pages that used it.")
|
|
394239
394206
|
}).strict(),
|
|
394240
394207
|
expose: {
|
|
394208
|
+
plugin: { method: "editCollection" },
|
|
394241
394209
|
ui: { label: "Collections", keywords: ["cms", "collection", "data", "records", "content", "blog", "products"], palette: false },
|
|
394242
394210
|
agent: {
|
|
394243
394211
|
name: "edit_collection",
|
|
@@ -394306,6 +394274,7 @@ var init_site3 = __esm({
|
|
|
394306
394274
|
order: external_exports.array(external_exports.string()).max(COLLECTION_LIMITS.records).optional().describe("Record ids in the order the collection should list them; ones left out keep their order after these.")
|
|
394307
394275
|
}).strict(),
|
|
394308
394276
|
expose: {
|
|
394277
|
+
plugin: { method: "editRecords" },
|
|
394309
394278
|
ui: { label: "Edit records", keywords: ["cms", "record", "row", "content"], palette: false },
|
|
394310
394279
|
agent: {
|
|
394311
394280
|
name: "edit_records",
|
|
@@ -394349,6 +394318,7 @@ var init_site3 = __esm({
|
|
|
394349
394318
|
offset: external_exports.number().int().min(0).optional()
|
|
394350
394319
|
}).strict(),
|
|
394351
394320
|
expose: {
|
|
394321
|
+
plugin: { method: "getRecords" },
|
|
394352
394322
|
agent: {
|
|
394353
394323
|
name: "get_records",
|
|
394354
394324
|
readOnly: true,
|
|
@@ -394385,6 +394355,7 @@ var init_site3 = __esm({
|
|
|
394385
394355
|
filter: external_exports.string().max(500).nullable().optional().describe('An expression over the record, only records it holds for are shown: "item_price > 100", "item_featured".')
|
|
394386
394356
|
}).strict(),
|
|
394387
394357
|
expose: {
|
|
394358
|
+
plugin: { method: "setRepeat" },
|
|
394388
394359
|
ui: { label: "Repeat for each record", keywords: ["repeat", "repeater", "list", "cms", "collection", "loop"], enabled: needsSelection(1), palette: false },
|
|
394389
394360
|
agent: {
|
|
394390
394361
|
name: "set_repeat",
|
|
@@ -394450,7 +394421,7 @@ var init_import2 = __esm({
|
|
|
394450
394421
|
url: external_exports.string().url().max(2e3).optional().describe("Or fetch it from an https URL.")
|
|
394451
394422
|
}).strict(),
|
|
394452
394423
|
expose: {
|
|
394453
|
-
plugin: { method: "
|
|
394424
|
+
plugin: { method: "importDocumentFile" },
|
|
394454
394425
|
agent: {
|
|
394455
394426
|
name: "import_file",
|
|
394456
394427
|
description: "Import a Lottie animation (.json or .lottie: a frame with its timeline, precomps as components), a PDF or a PopCraft file into the open file, onto the current page; later pages are appended. Pass the content as text, base64 or an https url. Returns the added layer ids and anything that did not map."
|
|
@@ -395340,7 +395311,6 @@ function registerBuiltinCommands() {
|
|
|
395340
395311
|
var builtinCommands, uiOnlyCommands;
|
|
395341
395312
|
var init_builtin4 = __esm({
|
|
395342
395313
|
"lib/commands/builtin.ts"() {
|
|
395343
|
-
"use strict";
|
|
395344
395314
|
init_registry();
|
|
395345
395315
|
init_node();
|
|
395346
395316
|
init_node();
|
|
@@ -395521,6 +395491,8 @@ var init_builtin4 = __esm({
|
|
|
395521
395491
|
siteSetRoute,
|
|
395522
395492
|
nodeSetControl,
|
|
395523
395493
|
nodeSetRepeat,
|
|
395494
|
+
siteSetEnvironment,
|
|
395495
|
+
siteGetEnvironment,
|
|
395524
395496
|
codeEditModule,
|
|
395525
395497
|
codeGetModules,
|
|
395526
395498
|
componentSetCode,
|
|
@@ -395541,7 +395513,6 @@ var init_builtin4 = __esm({
|
|
|
395541
395513
|
integrationOpen,
|
|
395542
395514
|
integrationListResources,
|
|
395543
395515
|
integrationSubmissions,
|
|
395544
|
-
integrationPullProducts,
|
|
395545
395516
|
// a copy of the open file as a new file (lib/commands/file.ts) (appended, as above)
|
|
395546
395517
|
fileDuplicate,
|
|
395547
395518
|
// a whiteboard as one picture, or its stickies as Markdown / CSV (lib/popcorn/board-export.ts) (appended, as above)
|
|
@@ -402825,7 +402796,7 @@ init_resources();
|
|
|
402825
402796
|
init_desktop();
|
|
402826
402797
|
init_hypery();
|
|
402827
402798
|
import { createInterface } from "node:readline";
|
|
402828
|
-
var VERSION2 = "0.
|
|
402799
|
+
var VERSION2 = "0.17.0";
|
|
402829
402800
|
var HELP = `popcraft ${VERSION2} \u2014 the PopCraft command line
|
|
402830
402801
|
|
|
402831
402802
|
Files (headless, on .popcraft files):
|