@shapesos/clay 0.17.0 → 0.19.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/ai-elements.cjs +3 -1
- package/dist/ai-elements.cjs.map +1 -1
- package/dist/ai-elements.js +4 -4
- package/dist/artifacts.cjs +1010 -60
- package/dist/artifacts.cjs.map +1 -1
- package/dist/artifacts.d.cts +20 -3
- package/dist/artifacts.d.ts +20 -3
- package/dist/artifacts.js +15 -6
- package/dist/badge.cjs +70 -0
- package/dist/badge.cjs.map +1 -0
- package/dist/badge.d.cts +28 -0
- package/dist/badge.d.ts +28 -0
- package/dist/badge.js +9 -0
- package/dist/blocks.cjs +981 -96
- package/dist/blocks.cjs.map +1 -1
- package/dist/blocks.css +1 -1
- package/dist/blocks.d.cts +15 -4
- package/dist/blocks.d.ts +15 -4
- package/dist/blocks.js +20 -8
- package/dist/button.cjs +3 -1
- package/dist/button.cjs.map +1 -1
- package/dist/button.js +2 -2
- package/dist/capture.cjs +3 -1
- package/dist/capture.cjs.map +1 -1
- package/dist/capture.js +2 -2
- package/dist/chart.cjs +3 -1
- package/dist/chart.cjs.map +1 -1
- package/dist/chart.js +2 -2
- package/dist/chat.cjs +986 -151
- package/dist/chat.cjs.map +1 -1
- package/dist/chat.d.cts +2 -2
- package/dist/chat.d.ts +2 -2
- package/dist/chat.js +13 -8
- package/dist/{chunk-JGMN6W72.js → chunk-2X4KUXYP.js} +1 -1
- package/dist/chunk-BHHJOG5X.js +1 -0
- package/dist/{chunk-B4U37WIH.js → chunk-CFCLVJIO.js} +2 -2
- package/dist/chunk-CSTCTO3B.js +161 -0
- package/dist/chunk-CSTCTO3B.js.map +1 -0
- package/dist/{chunk-6YZ65KPW.js → chunk-DC5KYT2G.js} +669 -171
- package/dist/chunk-DC5KYT2G.js.map +1 -0
- package/dist/{chunk-PYDVANWI.js → chunk-E36VI2HA.js} +2 -2
- package/dist/chunk-EIAWZXE4.js +69 -0
- package/dist/chunk-EIAWZXE4.js.map +1 -0
- package/dist/chunk-EXRNGIQ2.js +41 -0
- package/dist/chunk-EXRNGIQ2.js.map +1 -0
- package/dist/{chunk-B6GAPZ2R.js → chunk-FCSYVF4Z.js} +12 -46
- package/dist/chunk-FCSYVF4Z.js.map +1 -0
- package/dist/{chunk-PUVZ2S3F.js → chunk-G4NXVFXU.js} +2 -2
- package/dist/{chunk-JAGNXEWK.js → chunk-GK4XW4BC.js} +2 -2
- package/dist/{chunk-4MZZH3WX.js → chunk-HU5W7CGE.js} +37 -2
- package/dist/chunk-HU5W7CGE.js.map +1 -0
- package/dist/chunk-JMHE3Q5K.js +406 -0
- package/dist/chunk-JMHE3Q5K.js.map +1 -0
- package/dist/{chunk-4VE6ZXXW.js → chunk-MQP57DOP.js} +3 -3
- package/dist/{chunk-JF3P66JF.js → chunk-SN3ORQSJ.js} +4 -2
- package/dist/{chunk-JF3P66JF.js.map → chunk-SN3ORQSJ.js.map} +1 -1
- package/dist/{chunk-PGR2MDDU.js → chunk-W66OJM55.js} +2 -2
- package/dist/{chunk-7OYIDM42.js → chunk-XKURJ72I.js} +2 -2
- package/dist/copy-button.cjs +439 -0
- package/dist/copy-button.cjs.map +1 -0
- package/dist/copy-button.d.cts +20 -0
- package/dist/copy-button.d.ts +20 -0
- package/dist/copy-button.js +12 -0
- package/dist/copy-button.js.map +1 -0
- package/dist/{dom-to-image-NATF3446.js → dom-to-image-QB7KMTAE.js} +3 -3
- package/dist/dom-to-image-QB7KMTAE.js.map +1 -0
- package/dist/icon.cjs +3 -1
- package/dist/icon.cjs.map +1 -1
- package/dist/icon.js +2 -2
- package/dist/index.cjs +1070 -209
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +6 -4
- package/dist/index.d.ts +6 -4
- package/dist/index.js +42 -17
- package/dist/keyboard-shortcut.cjs +3 -1
- package/dist/keyboard-shortcut.cjs.map +1 -1
- package/dist/keyboard-shortcut.js +2 -2
- package/dist/table.cjs +40 -0
- package/dist/table.cjs.map +1 -1
- package/dist/table.d.cts +37 -2
- package/dist/table.d.ts +37 -2
- package/dist/table.js +11 -1
- package/dist/text-area.cjs +3 -1
- package/dist/text-area.cjs.map +1 -1
- package/dist/text-area.js +2 -2
- package/dist/tokens.cjs +3 -1
- package/dist/tokens.cjs.map +1 -1
- package/dist/tokens.d.cts +1 -0
- package/dist/tokens.d.ts +1 -0
- package/dist/tokens.js +1 -1
- package/dist/{types-CW45GBXl.d.cts → types-Bhg0_ES8.d.cts} +75 -3
- package/dist/{types-GCkXbyFm.d.ts → types-C8JtnwNY.d.ts} +200 -4
- package/dist/{types-BzXPBy6s.d.cts → types-DTdDFU3O.d.cts} +200 -4
- package/dist/{types-D1b8v7EY.d.ts → types-orOQcI2z.d.ts} +75 -3
- package/package.json +11 -1
- package/dist/chunk-46ZYTBX5.js +0 -250
- package/dist/chunk-46ZYTBX5.js.map +0 -1
- package/dist/chunk-4MZZH3WX.js.map +0 -1
- package/dist/chunk-6YZ65KPW.js.map +0 -1
- package/dist/chunk-B6GAPZ2R.js.map +0 -1
- package/dist/chunk-RSRNSWJN.js +0 -1
- /package/dist/{chunk-RSRNSWJN.js.map → badge.js.map} +0 -0
- /package/dist/{chunk-JGMN6W72.js.map → chunk-2X4KUXYP.js.map} +0 -0
- /package/dist/{dom-to-image-NATF3446.js.map → chunk-BHHJOG5X.js.map} +0 -0
- /package/dist/{chunk-B4U37WIH.js.map → chunk-CFCLVJIO.js.map} +0 -0
- /package/dist/{chunk-PYDVANWI.js.map → chunk-E36VI2HA.js.map} +0 -0
- /package/dist/{chunk-PUVZ2S3F.js.map → chunk-G4NXVFXU.js.map} +0 -0
- /package/dist/{chunk-JAGNXEWK.js.map → chunk-GK4XW4BC.js.map} +0 -0
- /package/dist/{chunk-4VE6ZXXW.js.map → chunk-MQP57DOP.js.map} +0 -0
- /package/dist/{chunk-PGR2MDDU.js.map → chunk-W66OJM55.js.map} +0 -0
- /package/dist/{chunk-7OYIDM42.js.map → chunk-XKURJ72I.js.map} +0 -0
package/dist/artifacts.cjs
CHANGED
|
@@ -128,7 +128,9 @@ var init_colors = __esm({
|
|
|
128
128
|
"red-200": "#FECACA",
|
|
129
129
|
"red-400": "#F7776C",
|
|
130
130
|
"red-500": "#EF4444",
|
|
131
|
-
"red-600": "#DC2626"
|
|
131
|
+
"red-600": "#DC2626",
|
|
132
|
+
// Deck
|
|
133
|
+
"deck-canvas": "#faf8f5"
|
|
132
134
|
};
|
|
133
135
|
}
|
|
134
136
|
});
|
|
@@ -272,10 +274,14 @@ __export(artifacts_exports, {
|
|
|
272
274
|
ArtifactServices: () => ArtifactServices,
|
|
273
275
|
ChartArtifact: () => ChartArtifact,
|
|
274
276
|
DEFAULT_CHART_ARTIFACT_LABELS: () => DEFAULT_CHART_ARTIFACT_LABELS,
|
|
277
|
+
DEFAULT_DECK_ARTIFACT_LABELS: () => DEFAULT_DECK_ARTIFACT_LABELS,
|
|
275
278
|
DEFAULT_TABLE_ARTIFACT_LABELS: () => DEFAULT_TABLE_ARTIFACT_LABELS,
|
|
279
|
+
DeckArtifact: () => DeckArtifact,
|
|
276
280
|
TableArtifact: () => TableArtifact,
|
|
277
281
|
artifactToClipboardText: () => artifactToClipboardText,
|
|
278
282
|
artifactTypes: () => artifactTypes,
|
|
283
|
+
deckBlockTypes: () => deckBlockTypes,
|
|
284
|
+
deckSlideKinds: () => deckSlideKinds,
|
|
279
285
|
isSafeDownloadUrl: () => isSafeDownloadUrl
|
|
280
286
|
});
|
|
281
287
|
module.exports = __toCommonJS(artifacts_exports);
|
|
@@ -283,7 +289,8 @@ module.exports = __toCommonJS(artifacts_exports);
|
|
|
283
289
|
// src/components/artifacts/artifact-base.ts
|
|
284
290
|
var artifactTypes = {
|
|
285
291
|
TABLE: "TABLE",
|
|
286
|
-
CHART: "CHART"
|
|
292
|
+
CHART: "CHART",
|
|
293
|
+
DECK: "DECK"
|
|
287
294
|
};
|
|
288
295
|
|
|
289
296
|
// src/components/artifacts/chart-artifact/types.ts
|
|
@@ -308,6 +315,34 @@ var DEFAULT_TABLE_ARTIFACT_LABELS = {
|
|
|
308
315
|
empty: "No rows to display."
|
|
309
316
|
};
|
|
310
317
|
|
|
318
|
+
// src/components/artifacts/deck-artifact/types.ts
|
|
319
|
+
var deckBlockTypes = {
|
|
320
|
+
TEXT: "TEXT",
|
|
321
|
+
CHART: "CHART",
|
|
322
|
+
TABLE: "TABLE"
|
|
323
|
+
};
|
|
324
|
+
var deckSlideKinds = {
|
|
325
|
+
TITLE: "TITLE",
|
|
326
|
+
AGENDA: "AGENDA",
|
|
327
|
+
SECTION: "SECTION",
|
|
328
|
+
CONTENT: "CONTENT",
|
|
329
|
+
CLOSING: "CLOSING"
|
|
330
|
+
};
|
|
331
|
+
var DEFAULT_DECK_ARTIFACT_LABELS = {
|
|
332
|
+
previous: "Previous slide",
|
|
333
|
+
next: "Next slide",
|
|
334
|
+
position: "Slide {current} of {total}",
|
|
335
|
+
download: "Download",
|
|
336
|
+
unavailable: "Deck content is unavailable.",
|
|
337
|
+
enterFullscreen: "Fullscreen",
|
|
338
|
+
exitFullscreen: "Exit fullscreen",
|
|
339
|
+
thankYou: "Thank you",
|
|
340
|
+
questions: "Questions?",
|
|
341
|
+
agenda: "Agenda",
|
|
342
|
+
chart: DEFAULT_CHART_ARTIFACT_LABELS,
|
|
343
|
+
table: DEFAULT_TABLE_ARTIFACT_LABELS
|
|
344
|
+
};
|
|
345
|
+
|
|
311
346
|
// src/components/artifacts/chart-artifact/chart-artifact.tsx
|
|
312
347
|
var import_react13 = require("react");
|
|
313
348
|
|
|
@@ -400,29 +435,45 @@ var createReactComponent = (type, iconName, iconNamePascal, iconNode) => {
|
|
|
400
435
|
var __iconNode = [["path", { "d": "M3 12a9 9 0 1 0 18 0a9 9 0 0 0 -18 0", "key": "svg-0" }], ["path", { "d": "M12 8v4", "key": "svg-1" }], ["path", { "d": "M12 16h.01", "key": "svg-2" }]];
|
|
401
436
|
var IconAlertCircle = createReactComponent("outline", "alert-circle", "AlertCircle", __iconNode);
|
|
402
437
|
|
|
438
|
+
// node_modules/@tabler/icons-react/dist/esm/icons/IconArrowsMaximize.mjs
|
|
439
|
+
var __iconNode2 = [["path", { "d": "M16 4l4 0l0 4", "key": "svg-0" }], ["path", { "d": "M14 10l6 -6", "key": "svg-1" }], ["path", { "d": "M8 20l-4 0l0 -4", "key": "svg-2" }], ["path", { "d": "M4 20l6 -6", "key": "svg-3" }], ["path", { "d": "M16 20l4 0l0 -4", "key": "svg-4" }], ["path", { "d": "M14 14l6 6", "key": "svg-5" }], ["path", { "d": "M8 4l-4 0l0 4", "key": "svg-6" }], ["path", { "d": "M4 4l6 6", "key": "svg-7" }]];
|
|
440
|
+
var IconArrowsMaximize = createReactComponent("outline", "arrows-maximize", "ArrowsMaximize", __iconNode2);
|
|
441
|
+
|
|
442
|
+
// node_modules/@tabler/icons-react/dist/esm/icons/IconArrowsMinimize.mjs
|
|
443
|
+
var __iconNode3 = [["path", { "d": "M5 9l4 0l0 -4", "key": "svg-0" }], ["path", { "d": "M3 3l6 6", "key": "svg-1" }], ["path", { "d": "M5 15l4 0l0 4", "key": "svg-2" }], ["path", { "d": "M3 21l6 -6", "key": "svg-3" }], ["path", { "d": "M19 9l-4 0l0 -4", "key": "svg-4" }], ["path", { "d": "M15 9l6 -6", "key": "svg-5" }], ["path", { "d": "M19 15l-4 0l0 4", "key": "svg-6" }], ["path", { "d": "M15 15l6 6", "key": "svg-7" }]];
|
|
444
|
+
var IconArrowsMinimize = createReactComponent("outline", "arrows-minimize", "ArrowsMinimize", __iconNode3);
|
|
445
|
+
|
|
403
446
|
// node_modules/@tabler/icons-react/dist/esm/icons/IconCheck.mjs
|
|
404
|
-
var
|
|
405
|
-
var IconCheck = createReactComponent("outline", "check", "Check",
|
|
447
|
+
var __iconNode4 = [["path", { "d": "M5 12l5 5l10 -10", "key": "svg-0" }]];
|
|
448
|
+
var IconCheck = createReactComponent("outline", "check", "Check", __iconNode4);
|
|
449
|
+
|
|
450
|
+
// node_modules/@tabler/icons-react/dist/esm/icons/IconChevronLeft.mjs
|
|
451
|
+
var __iconNode5 = [["path", { "d": "M15 6l-6 6l6 6", "key": "svg-0" }]];
|
|
452
|
+
var IconChevronLeft = createReactComponent("outline", "chevron-left", "ChevronLeft", __iconNode5);
|
|
453
|
+
|
|
454
|
+
// node_modules/@tabler/icons-react/dist/esm/icons/IconChevronRight.mjs
|
|
455
|
+
var __iconNode6 = [["path", { "d": "M9 6l6 6l-6 6", "key": "svg-0" }]];
|
|
456
|
+
var IconChevronRight = createReactComponent("outline", "chevron-right", "ChevronRight", __iconNode6);
|
|
406
457
|
|
|
407
458
|
// node_modules/@tabler/icons-react/dist/esm/icons/IconCopy.mjs
|
|
408
|
-
var
|
|
409
|
-
var IconCopy = createReactComponent("outline", "copy", "Copy",
|
|
459
|
+
var __iconNode7 = [["path", { "d": "M7 9.667a2.667 2.667 0 0 1 2.667 -2.667h8.666a2.667 2.667 0 0 1 2.667 2.667v8.666a2.667 2.667 0 0 1 -2.667 2.667h-8.666a2.667 2.667 0 0 1 -2.667 -2.667l0 -8.666", "key": "svg-0" }], ["path", { "d": "M4.012 16.737a2.005 2.005 0 0 1 -1.012 -1.737v-10c0 -1.1 .9 -2 2 -2h10c.75 0 1.158 .385 1.5 1", "key": "svg-1" }]];
|
|
460
|
+
var IconCopy = createReactComponent("outline", "copy", "Copy", __iconNode7);
|
|
410
461
|
|
|
411
462
|
// node_modules/@tabler/icons-react/dist/esm/icons/IconDownload.mjs
|
|
412
|
-
var
|
|
413
|
-
var IconDownload = createReactComponent("outline", "download", "Download",
|
|
463
|
+
var __iconNode8 = [["path", { "d": "M4 17v2a2 2 0 0 0 2 2h12a2 2 0 0 0 2 -2v-2", "key": "svg-0" }], ["path", { "d": "M7 11l5 5l5 -5", "key": "svg-1" }], ["path", { "d": "M12 4l0 12", "key": "svg-2" }]];
|
|
464
|
+
var IconDownload = createReactComponent("outline", "download", "Download", __iconNode8);
|
|
414
465
|
|
|
415
466
|
// node_modules/@tabler/icons-react/dist/esm/icons/IconFileSpreadsheet.mjs
|
|
416
|
-
var
|
|
417
|
-
var IconFileSpreadsheet = createReactComponent("outline", "file-spreadsheet", "FileSpreadsheet",
|
|
467
|
+
var __iconNode9 = [["path", { "d": "M14 3v4a1 1 0 0 0 1 1h4", "key": "svg-0" }], ["path", { "d": "M17 21h-10a2 2 0 0 1 -2 -2v-14a2 2 0 0 1 2 -2h7l5 5v11a2 2 0 0 1 -2 2", "key": "svg-1" }], ["path", { "d": "M8 11h8v7h-8l0 -7", "key": "svg-2" }], ["path", { "d": "M8 15h8", "key": "svg-3" }], ["path", { "d": "M11 11v7", "key": "svg-4" }]];
|
|
468
|
+
var IconFileSpreadsheet = createReactComponent("outline", "file-spreadsheet", "FileSpreadsheet", __iconNode9);
|
|
418
469
|
|
|
419
470
|
// node_modules/@tabler/icons-react/dist/esm/icons/IconLoader2.mjs
|
|
420
|
-
var
|
|
421
|
-
var IconLoader2 = createReactComponent("outline", "loader-2", "Loader2",
|
|
471
|
+
var __iconNode10 = [["path", { "d": "M12 3a9 9 0 1 0 9 9", "key": "svg-0" }]];
|
|
472
|
+
var IconLoader2 = createReactComponent("outline", "loader-2", "Loader2", __iconNode10);
|
|
422
473
|
|
|
423
474
|
// node_modules/@tabler/icons-react/dist/esm/icons/IconPhoto.mjs
|
|
424
|
-
var
|
|
425
|
-
var IconPhoto = createReactComponent("outline", "photo", "Photo",
|
|
475
|
+
var __iconNode11 = [["path", { "d": "M15 8h.01", "key": "svg-0" }], ["path", { "d": "M3 6a3 3 0 0 1 3 -3h12a3 3 0 0 1 3 3v12a3 3 0 0 1 -3 3h-12a3 3 0 0 1 -3 -3v-12", "key": "svg-1" }], ["path", { "d": "M3 16l5 -5c.928 -.893 2.072 -.893 3 0l5 5", "key": "svg-2" }], ["path", { "d": "M14 14l1 -1c.928 -.893 2.072 -.893 3 0l3 3", "key": "svg-3" }]];
|
|
476
|
+
var IconPhoto = createReactComponent("outline", "photo", "Photo", __iconNode11);
|
|
426
477
|
|
|
427
478
|
// src/components/artifacts/artifact-copy-as-image-button/artifact-copy-as-image-button.tsx
|
|
428
479
|
var import_react6 = require("react");
|
|
@@ -958,6 +1009,300 @@ function ChartTooltipContent({
|
|
|
958
1009
|
// src/tokens/index.ts
|
|
959
1010
|
init_colors();
|
|
960
1011
|
|
|
1012
|
+
// src/tokens/typography.ts
|
|
1013
|
+
var fontFamilies = {
|
|
1014
|
+
/** Geist — primary UI font for body text, labels, headings, and display. */
|
|
1015
|
+
GEIST: "Geist",
|
|
1016
|
+
/** Crimson Pro — editorial/serif font, mostly italic. Used for decorative headings and pull quotes. */
|
|
1017
|
+
CRIMSON_PRO: "Crimson Pro"
|
|
1018
|
+
};
|
|
1019
|
+
var typographyTypes = {
|
|
1020
|
+
// Geist Label Caption (12px)
|
|
1021
|
+
GEIST_LABEL_CAPTION_REGULAR: "GEIST_LABEL_CAPTION_REGULAR",
|
|
1022
|
+
GEIST_LABEL_CAPTION_MEDIUM: "GEIST_LABEL_CAPTION_MEDIUM",
|
|
1023
|
+
GEIST_LABEL_CAPTION_SEMI_BOLD: "GEIST_LABEL_CAPTION_SEMI_BOLD",
|
|
1024
|
+
// Geist Body Extra Small (14px)
|
|
1025
|
+
GEIST_BODY_XS_REGULAR: "GEIST_BODY_XS_REGULAR",
|
|
1026
|
+
GEIST_BODY_XS_MEDIUM: "GEIST_BODY_XS_MEDIUM",
|
|
1027
|
+
GEIST_BODY_XS_BOLD: "GEIST_BODY_XS_BOLD",
|
|
1028
|
+
// Geist Body Small (16px)
|
|
1029
|
+
GEIST_BODY_S_REGULAR: "GEIST_BODY_S_REGULAR",
|
|
1030
|
+
GEIST_BODY_S_MEDIUM: "GEIST_BODY_S_MEDIUM",
|
|
1031
|
+
GEIST_BODY_S_SEMI_BOLD: "GEIST_BODY_S_SEMI_BOLD",
|
|
1032
|
+
GEIST_BODY_S_BOLD: "GEIST_BODY_S_BOLD",
|
|
1033
|
+
// Geist Body Medium (18px)
|
|
1034
|
+
GEIST_BODY_M_LIGHT: "GEIST_BODY_M_LIGHT",
|
|
1035
|
+
GEIST_BODY_M_REGULAR: "GEIST_BODY_M_REGULAR",
|
|
1036
|
+
GEIST_BODY_M_MEDIUM: "GEIST_BODY_M_MEDIUM",
|
|
1037
|
+
GEIST_BODY_M_SEMI_BOLD: "GEIST_BODY_M_SEMI_BOLD",
|
|
1038
|
+
// Geist Body Large (20px)
|
|
1039
|
+
GEIST_BODY_L_REGULAR: "GEIST_BODY_L_REGULAR",
|
|
1040
|
+
GEIST_BODY_L_MEDIUM: "GEIST_BODY_L_MEDIUM",
|
|
1041
|
+
GEIST_BODY_L_SEMI_BOLD: "GEIST_BODY_L_SEMI_BOLD",
|
|
1042
|
+
GEIST_BODY_L_BOLD: "GEIST_BODY_L_BOLD",
|
|
1043
|
+
// Geist Heading Small (24px)
|
|
1044
|
+
GEIST_HEADING_S_REGULAR: "GEIST_HEADING_S_REGULAR",
|
|
1045
|
+
GEIST_HEADING_S_MEDIUM: "GEIST_HEADING_S_MEDIUM",
|
|
1046
|
+
GEIST_HEADING_S_BOLD: "GEIST_HEADING_S_BOLD",
|
|
1047
|
+
// Geist Heading Medium (28px)
|
|
1048
|
+
GEIST_HEADING_M_BOLD: "GEIST_HEADING_M_BOLD",
|
|
1049
|
+
// Geist Heading Large (32px)
|
|
1050
|
+
GEIST_HEADING_L_REGULAR: "GEIST_HEADING_L_REGULAR",
|
|
1051
|
+
GEIST_HEADING_L_MEDIUM: "GEIST_HEADING_L_MEDIUM",
|
|
1052
|
+
GEIST_HEADING_L_SEMI_BOLD: "GEIST_HEADING_L_SEMI_BOLD",
|
|
1053
|
+
GEIST_HEADING_L_BOLD: "GEIST_HEADING_L_BOLD",
|
|
1054
|
+
// Geist Display Large (36px)
|
|
1055
|
+
GEIST_DISPLAY_L_MEDIUM: "GEIST_DISPLAY_L_MEDIUM",
|
|
1056
|
+
// Crimson Pro Body Small (16px, italic)
|
|
1057
|
+
CRIMSON_PRO_BODY_S_LIGHT_ITALIC: "CRIMSON_PRO_BODY_S_LIGHT_ITALIC",
|
|
1058
|
+
// Crimson Pro Body Medium (18px, italic)
|
|
1059
|
+
CRIMSON_PRO_BODY_M_LIGHT_ITALIC: "CRIMSON_PRO_BODY_M_LIGHT_ITALIC",
|
|
1060
|
+
// Crimson Pro Heading Medium (24px, italic)
|
|
1061
|
+
CRIMSON_PRO_HEADING_M_MEDIUM_ITALIC: "CRIMSON_PRO_HEADING_M_MEDIUM_ITALIC",
|
|
1062
|
+
// Crimson Pro Display Large (40px, upright)
|
|
1063
|
+
CRIMSON_PRO_DISPLAY_L_REGULAR: "CRIMSON_PRO_DISPLAY_L_REGULAR",
|
|
1064
|
+
// Crimson Pro Display Extra Large (46px, italic)
|
|
1065
|
+
CRIMSON_PRO_DISPLAY_XL_REGULAR_ITALIC: "CRIMSON_PRO_DISPLAY_XL_REGULAR_ITALIC"
|
|
1066
|
+
};
|
|
1067
|
+
var typographyStyles = {
|
|
1068
|
+
// Geist Label Caption (12px)
|
|
1069
|
+
[typographyTypes.GEIST_LABEL_CAPTION_REGULAR]: {
|
|
1070
|
+
fontFamily: fontFamilies.GEIST,
|
|
1071
|
+
fontSize: 12,
|
|
1072
|
+
fontWeight: 400,
|
|
1073
|
+
lineHeight: 16
|
|
1074
|
+
},
|
|
1075
|
+
[typographyTypes.GEIST_LABEL_CAPTION_MEDIUM]: {
|
|
1076
|
+
fontFamily: fontFamilies.GEIST,
|
|
1077
|
+
fontSize: 12,
|
|
1078
|
+
fontWeight: 500,
|
|
1079
|
+
lineHeight: 16
|
|
1080
|
+
},
|
|
1081
|
+
[typographyTypes.GEIST_LABEL_CAPTION_SEMI_BOLD]: {
|
|
1082
|
+
fontFamily: fontFamilies.GEIST,
|
|
1083
|
+
fontSize: 12,
|
|
1084
|
+
fontWeight: 600,
|
|
1085
|
+
lineHeight: 16
|
|
1086
|
+
},
|
|
1087
|
+
// Geist Body Extra Small (14px)
|
|
1088
|
+
[typographyTypes.GEIST_BODY_XS_REGULAR]: {
|
|
1089
|
+
fontFamily: fontFamilies.GEIST,
|
|
1090
|
+
fontSize: 14,
|
|
1091
|
+
fontWeight: 400,
|
|
1092
|
+
lineHeight: 20
|
|
1093
|
+
},
|
|
1094
|
+
[typographyTypes.GEIST_BODY_XS_MEDIUM]: {
|
|
1095
|
+
fontFamily: fontFamilies.GEIST,
|
|
1096
|
+
fontSize: 14,
|
|
1097
|
+
fontWeight: 500,
|
|
1098
|
+
lineHeight: 20
|
|
1099
|
+
},
|
|
1100
|
+
[typographyTypes.GEIST_BODY_XS_BOLD]: {
|
|
1101
|
+
fontFamily: fontFamilies.GEIST,
|
|
1102
|
+
fontSize: 14,
|
|
1103
|
+
fontWeight: 600,
|
|
1104
|
+
lineHeight: 20
|
|
1105
|
+
},
|
|
1106
|
+
// Geist Body Small (16px)
|
|
1107
|
+
[typographyTypes.GEIST_BODY_S_REGULAR]: {
|
|
1108
|
+
fontFamily: fontFamilies.GEIST,
|
|
1109
|
+
fontSize: 16,
|
|
1110
|
+
fontWeight: 400,
|
|
1111
|
+
lineHeight: 24,
|
|
1112
|
+
letterSpacing: -0.08
|
|
1113
|
+
},
|
|
1114
|
+
[typographyTypes.GEIST_BODY_S_MEDIUM]: {
|
|
1115
|
+
fontFamily: fontFamilies.GEIST,
|
|
1116
|
+
fontSize: 16,
|
|
1117
|
+
fontWeight: 500,
|
|
1118
|
+
lineHeight: 24,
|
|
1119
|
+
letterSpacing: -0.08
|
|
1120
|
+
},
|
|
1121
|
+
[typographyTypes.GEIST_BODY_S_SEMI_BOLD]: {
|
|
1122
|
+
fontFamily: fontFamilies.GEIST,
|
|
1123
|
+
fontSize: 16,
|
|
1124
|
+
fontWeight: 600,
|
|
1125
|
+
lineHeight: 24,
|
|
1126
|
+
letterSpacing: -0.08
|
|
1127
|
+
},
|
|
1128
|
+
[typographyTypes.GEIST_BODY_S_BOLD]: {
|
|
1129
|
+
fontFamily: fontFamilies.GEIST,
|
|
1130
|
+
fontSize: 16,
|
|
1131
|
+
fontWeight: 700,
|
|
1132
|
+
lineHeight: 24,
|
|
1133
|
+
letterSpacing: -0.08
|
|
1134
|
+
},
|
|
1135
|
+
// Geist Body Medium (18px)
|
|
1136
|
+
[typographyTypes.GEIST_BODY_M_LIGHT]: {
|
|
1137
|
+
fontFamily: fontFamilies.GEIST,
|
|
1138
|
+
fontSize: 18,
|
|
1139
|
+
fontWeight: 300,
|
|
1140
|
+
lineHeight: 28,
|
|
1141
|
+
letterSpacing: -0.09
|
|
1142
|
+
},
|
|
1143
|
+
[typographyTypes.GEIST_BODY_M_REGULAR]: {
|
|
1144
|
+
fontFamily: fontFamilies.GEIST,
|
|
1145
|
+
fontSize: 18,
|
|
1146
|
+
fontWeight: 400,
|
|
1147
|
+
lineHeight: 28,
|
|
1148
|
+
letterSpacing: -0.09
|
|
1149
|
+
},
|
|
1150
|
+
[typographyTypes.GEIST_BODY_M_MEDIUM]: {
|
|
1151
|
+
fontFamily: fontFamilies.GEIST,
|
|
1152
|
+
fontSize: 18,
|
|
1153
|
+
fontWeight: 500,
|
|
1154
|
+
lineHeight: 28,
|
|
1155
|
+
letterSpacing: -0.09
|
|
1156
|
+
},
|
|
1157
|
+
[typographyTypes.GEIST_BODY_M_SEMI_BOLD]: {
|
|
1158
|
+
fontFamily: fontFamilies.GEIST,
|
|
1159
|
+
fontSize: 18,
|
|
1160
|
+
fontWeight: 600,
|
|
1161
|
+
lineHeight: 28,
|
|
1162
|
+
letterSpacing: -0.09
|
|
1163
|
+
},
|
|
1164
|
+
// Geist Body Large (20px)
|
|
1165
|
+
[typographyTypes.GEIST_BODY_L_REGULAR]: {
|
|
1166
|
+
fontFamily: fontFamilies.GEIST,
|
|
1167
|
+
fontSize: 20,
|
|
1168
|
+
fontWeight: 400,
|
|
1169
|
+
lineHeight: 30,
|
|
1170
|
+
letterSpacing: -0.2
|
|
1171
|
+
},
|
|
1172
|
+
[typographyTypes.GEIST_BODY_L_MEDIUM]: {
|
|
1173
|
+
fontFamily: fontFamilies.GEIST,
|
|
1174
|
+
fontSize: 20,
|
|
1175
|
+
fontWeight: 500,
|
|
1176
|
+
lineHeight: 30,
|
|
1177
|
+
letterSpacing: -0.2
|
|
1178
|
+
},
|
|
1179
|
+
[typographyTypes.GEIST_BODY_L_SEMI_BOLD]: {
|
|
1180
|
+
fontFamily: fontFamilies.GEIST,
|
|
1181
|
+
fontSize: 20,
|
|
1182
|
+
fontWeight: 600,
|
|
1183
|
+
lineHeight: 30,
|
|
1184
|
+
letterSpacing: -0.2
|
|
1185
|
+
},
|
|
1186
|
+
[typographyTypes.GEIST_BODY_L_BOLD]: {
|
|
1187
|
+
fontFamily: fontFamilies.GEIST,
|
|
1188
|
+
fontSize: 20,
|
|
1189
|
+
fontWeight: 700,
|
|
1190
|
+
lineHeight: 30,
|
|
1191
|
+
letterSpacing: -0.2
|
|
1192
|
+
},
|
|
1193
|
+
// Geist Heading Small (24px)
|
|
1194
|
+
[typographyTypes.GEIST_HEADING_S_REGULAR]: {
|
|
1195
|
+
fontFamily: fontFamilies.GEIST,
|
|
1196
|
+
fontSize: 24,
|
|
1197
|
+
fontWeight: 400,
|
|
1198
|
+
lineHeight: 32,
|
|
1199
|
+
letterSpacing: -0.48
|
|
1200
|
+
},
|
|
1201
|
+
[typographyTypes.GEIST_HEADING_S_MEDIUM]: {
|
|
1202
|
+
fontFamily: fontFamilies.GEIST,
|
|
1203
|
+
fontSize: 24,
|
|
1204
|
+
fontWeight: 500,
|
|
1205
|
+
lineHeight: 32,
|
|
1206
|
+
letterSpacing: -0.48
|
|
1207
|
+
},
|
|
1208
|
+
[typographyTypes.GEIST_HEADING_S_BOLD]: {
|
|
1209
|
+
fontFamily: fontFamilies.GEIST,
|
|
1210
|
+
fontSize: 24,
|
|
1211
|
+
fontWeight: 700,
|
|
1212
|
+
lineHeight: 32,
|
|
1213
|
+
letterSpacing: -0.48
|
|
1214
|
+
},
|
|
1215
|
+
// Geist Heading Medium (28px)
|
|
1216
|
+
[typographyTypes.GEIST_HEADING_M_BOLD]: {
|
|
1217
|
+
fontFamily: fontFamilies.GEIST,
|
|
1218
|
+
fontSize: 28,
|
|
1219
|
+
fontWeight: 700,
|
|
1220
|
+
lineHeight: 36,
|
|
1221
|
+
letterSpacing: -0.6
|
|
1222
|
+
},
|
|
1223
|
+
// Geist Heading Large (32px)
|
|
1224
|
+
[typographyTypes.GEIST_HEADING_L_REGULAR]: {
|
|
1225
|
+
fontFamily: fontFamilies.GEIST,
|
|
1226
|
+
fontSize: 32,
|
|
1227
|
+
fontWeight: 400,
|
|
1228
|
+
lineHeight: 40,
|
|
1229
|
+
letterSpacing: -0.64
|
|
1230
|
+
},
|
|
1231
|
+
[typographyTypes.GEIST_HEADING_L_MEDIUM]: {
|
|
1232
|
+
fontFamily: fontFamilies.GEIST,
|
|
1233
|
+
fontSize: 32,
|
|
1234
|
+
fontWeight: 500,
|
|
1235
|
+
lineHeight: 40,
|
|
1236
|
+
letterSpacing: -0.64
|
|
1237
|
+
},
|
|
1238
|
+
[typographyTypes.GEIST_HEADING_L_SEMI_BOLD]: {
|
|
1239
|
+
fontFamily: fontFamilies.GEIST,
|
|
1240
|
+
fontSize: 32,
|
|
1241
|
+
fontWeight: 600,
|
|
1242
|
+
lineHeight: 40,
|
|
1243
|
+
letterSpacing: -0.64
|
|
1244
|
+
},
|
|
1245
|
+
[typographyTypes.GEIST_HEADING_L_BOLD]: {
|
|
1246
|
+
fontFamily: fontFamilies.GEIST,
|
|
1247
|
+
fontSize: 32,
|
|
1248
|
+
fontWeight: 700,
|
|
1249
|
+
lineHeight: 40,
|
|
1250
|
+
letterSpacing: -0.64
|
|
1251
|
+
},
|
|
1252
|
+
// Geist Display Large (36px)
|
|
1253
|
+
[typographyTypes.GEIST_DISPLAY_L_MEDIUM]: {
|
|
1254
|
+
fontFamily: fontFamilies.GEIST,
|
|
1255
|
+
fontSize: 36,
|
|
1256
|
+
fontWeight: 500,
|
|
1257
|
+
lineHeight: 44,
|
|
1258
|
+
letterSpacing: -0.72
|
|
1259
|
+
},
|
|
1260
|
+
// Crimson Pro Body Small (16px, italic)
|
|
1261
|
+
[typographyTypes.CRIMSON_PRO_BODY_S_LIGHT_ITALIC]: {
|
|
1262
|
+
fontFamily: fontFamilies.CRIMSON_PRO,
|
|
1263
|
+
fontSize: 16,
|
|
1264
|
+
fontWeight: 300,
|
|
1265
|
+
lineHeight: 20,
|
|
1266
|
+
letterSpacing: -0.32,
|
|
1267
|
+
fontStyle: "italic"
|
|
1268
|
+
},
|
|
1269
|
+
// Crimson Pro Body Medium (18px, italic)
|
|
1270
|
+
[typographyTypes.CRIMSON_PRO_BODY_M_LIGHT_ITALIC]: {
|
|
1271
|
+
fontFamily: fontFamilies.CRIMSON_PRO,
|
|
1272
|
+
fontSize: 18,
|
|
1273
|
+
fontWeight: 300,
|
|
1274
|
+
lineHeight: 28,
|
|
1275
|
+
letterSpacing: 0,
|
|
1276
|
+
fontStyle: "italic"
|
|
1277
|
+
},
|
|
1278
|
+
// Crimson Pro Heading Medium (24px, italic)
|
|
1279
|
+
[typographyTypes.CRIMSON_PRO_HEADING_M_MEDIUM_ITALIC]: {
|
|
1280
|
+
fontFamily: fontFamilies.CRIMSON_PRO,
|
|
1281
|
+
fontSize: 24,
|
|
1282
|
+
fontWeight: 400,
|
|
1283
|
+
lineHeight: 32,
|
|
1284
|
+
letterSpacing: -0.48,
|
|
1285
|
+
fontStyle: "italic"
|
|
1286
|
+
},
|
|
1287
|
+
// Crimson Pro Display Large (40px, upright)
|
|
1288
|
+
[typographyTypes.CRIMSON_PRO_DISPLAY_L_REGULAR]: {
|
|
1289
|
+
fontFamily: fontFamilies.CRIMSON_PRO,
|
|
1290
|
+
fontSize: 40,
|
|
1291
|
+
fontWeight: 300,
|
|
1292
|
+
lineHeight: 48,
|
|
1293
|
+
letterSpacing: -1.6
|
|
1294
|
+
},
|
|
1295
|
+
// Crimson Pro Display Extra Large (46px, italic)
|
|
1296
|
+
[typographyTypes.CRIMSON_PRO_DISPLAY_XL_REGULAR_ITALIC]: {
|
|
1297
|
+
fontFamily: fontFamilies.CRIMSON_PRO,
|
|
1298
|
+
fontSize: 46,
|
|
1299
|
+
fontWeight: 400,
|
|
1300
|
+
lineHeight: 54,
|
|
1301
|
+
letterSpacing: -1.38,
|
|
1302
|
+
fontStyle: "italic"
|
|
1303
|
+
}
|
|
1304
|
+
};
|
|
1305
|
+
|
|
961
1306
|
// src/components/chart/chart-palette.ts
|
|
962
1307
|
var CHART_PALETTE = [
|
|
963
1308
|
colors["blue-600"],
|
|
@@ -1690,8 +2035,13 @@ var ChartArtifactService = {
|
|
|
1690
2035
|
toClipboardText: chartArtifactToClipboardText
|
|
1691
2036
|
};
|
|
1692
2037
|
|
|
1693
|
-
// src/components/artifacts/
|
|
1694
|
-
var
|
|
2038
|
+
// src/components/artifacts/deck-artifact/deck-artifact.tsx
|
|
2039
|
+
var import_react17 = require("react");
|
|
2040
|
+
var import_react_dom = require("react-dom");
|
|
2041
|
+
init_capture_exclude_attribute();
|
|
2042
|
+
|
|
2043
|
+
// src/components/artifacts/deck-artifact/deck-artifact-content.tsx
|
|
2044
|
+
var import_react16 = require("react");
|
|
1695
2045
|
|
|
1696
2046
|
// src/components/ui/table.tsx
|
|
1697
2047
|
var React3 = __toESM(require("react"), 1);
|
|
@@ -1770,6 +2120,36 @@ function useScrollShadow() {
|
|
|
1770
2120
|
return { targetRef, isScrolled };
|
|
1771
2121
|
}
|
|
1772
2122
|
|
|
2123
|
+
// src/components/table/data-table.tsx
|
|
2124
|
+
var import_jsx_runtime21 = require("react/jsx-runtime");
|
|
2125
|
+
var DATA_TABLE_HEAD_CLASS = "h-auto py-2 px-4 text-xs font-medium text-foreground whitespace-nowrap text-left";
|
|
2126
|
+
var DATA_TABLE_CELL_CLASS = "p-4 text-sm font-normal text-foreground align-top min-w-[150px] text-left";
|
|
2127
|
+
var DATA_TABLE_ROW_CLASS = "border-b-brown-30 bg-background/70 hover:bg-secondary";
|
|
2128
|
+
var DATA_TABLE_SCROLL_SHADOW = "0 1px 2px rgb(0 0 0 / 0.01), 0 6px 12px -2px rgb(0 0 0 / 0.03)";
|
|
2129
|
+
function DataTable({ header, children, maxBodyHeight, className }) {
|
|
2130
|
+
const { targetRef, isScrolled } = useScrollShadow();
|
|
2131
|
+
return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
|
|
2132
|
+
"div",
|
|
2133
|
+
{
|
|
2134
|
+
ref: targetRef,
|
|
2135
|
+
className: cn("overscroll-none", className),
|
|
2136
|
+
style: maxBodyHeight !== void 0 ? { maxHeight: maxBodyHeight, overflowY: "auto" } : void 0,
|
|
2137
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(Table, { containerClassName: "overflow-visible", children: [
|
|
2138
|
+
/* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
|
|
2139
|
+
TableHeader,
|
|
2140
|
+
{
|
|
2141
|
+
"data-scrolled": isScrolled ? "true" : void 0,
|
|
2142
|
+
className: "sticky top-0 z-10 bg-background/70 backdrop-blur-lg transition-shadow",
|
|
2143
|
+
style: isScrolled ? { boxShadow: DATA_TABLE_SCROLL_SHADOW } : void 0,
|
|
2144
|
+
children: header
|
|
2145
|
+
}
|
|
2146
|
+
),
|
|
2147
|
+
/* @__PURE__ */ (0, import_jsx_runtime21.jsx)(TableBody, { children })
|
|
2148
|
+
] })
|
|
2149
|
+
}
|
|
2150
|
+
);
|
|
2151
|
+
}
|
|
2152
|
+
|
|
1773
2153
|
// src/components/artifacts/table-artifact/table-artifact-content.constants.ts
|
|
1774
2154
|
var TABLE_STATUS = {
|
|
1775
2155
|
LOADING: "loading",
|
|
@@ -1782,14 +2162,10 @@ var TABLE_STATUS = {
|
|
|
1782
2162
|
function formatCell(row, column) {
|
|
1783
2163
|
return row[column.key] ?? "";
|
|
1784
2164
|
}
|
|
1785
|
-
var
|
|
1786
|
-
var CELL_CLASS = "p-4 text-sm font-normal text-foreground align-top min-w-[150px] text-left";
|
|
1787
|
-
var ROW_CLASSES = "border-b-brown-30 bg-background/70 hover:bg-secondary";
|
|
1788
|
-
var DATA_ROW_CLASSES = `${ROW_CLASSES} animate-in fade-in duration-300`;
|
|
1789
|
-
var SCROLL_SHADOW = "0 1px 2px rgb(0 0 0 / 0.01), 0 6px 12px -2px rgb(0 0 0 / 0.03)";
|
|
2165
|
+
var DATA_ROW_CLASSES = `${DATA_TABLE_ROW_CLASS} animate-in fade-in duration-300`;
|
|
1790
2166
|
|
|
1791
2167
|
// src/components/artifacts/table-artifact/table-artifact-content.tsx
|
|
1792
|
-
var
|
|
2168
|
+
var import_jsx_runtime22 = require("react/jsx-runtime");
|
|
1793
2169
|
function TableArtifactContent({
|
|
1794
2170
|
columns,
|
|
1795
2171
|
data,
|
|
@@ -1799,48 +2175,367 @@ function TableArtifactContent({
|
|
|
1799
2175
|
labels
|
|
1800
2176
|
}) {
|
|
1801
2177
|
if (data.status === TABLE_STATUS.ERROR) {
|
|
1802
|
-
return /* @__PURE__ */ (0,
|
|
2178
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(StatusMessage, { $tone: "error", children: labels.loadError });
|
|
1803
2179
|
}
|
|
1804
2180
|
if (data.status === TABLE_STATUS.UNAVAILABLE) {
|
|
1805
|
-
return /* @__PURE__ */ (0,
|
|
2181
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(StatusMessage, { $tone: "info", children: labels.unavailable });
|
|
1806
2182
|
}
|
|
1807
2183
|
if (data.status === TABLE_STATUS.LOADING) {
|
|
1808
2184
|
if (typeof knownRowCount === "number" && knownRowCount > 0) {
|
|
1809
2185
|
const shimmerCount = Math.min(knownRowCount, maxShimmerRows);
|
|
1810
|
-
return /* @__PURE__ */ (0,
|
|
2186
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(ArtifactTable, { columns, maxBodyHeight, children: renderShimmerRows(columns, shimmerCount) });
|
|
1811
2187
|
}
|
|
1812
|
-
return /* @__PURE__ */ (0,
|
|
2188
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(StatusMessage, { $tone: "info", children: labels.loading });
|
|
1813
2189
|
}
|
|
1814
|
-
return /* @__PURE__ */ (0,
|
|
2190
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(ArtifactTable, { columns, maxBodyHeight, children: data.rows.length === 0 ? renderEmptyRow(columns.length, labels.empty) : renderDataRows(columns, data.rows) });
|
|
1815
2191
|
}
|
|
1816
2192
|
function ArtifactTable({ columns, maxBodyHeight, children }) {
|
|
1817
|
-
|
|
1818
|
-
|
|
1819
|
-
|
|
1820
|
-
|
|
2193
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
2194
|
+
DataTable,
|
|
2195
|
+
{
|
|
2196
|
+
maxBodyHeight,
|
|
2197
|
+
header: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TableRow, { className: "hover:bg-transparent", children: columns.map((column) => /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TableHead, { scope: "col", className: DATA_TABLE_HEAD_CLASS, children: column.label }, column.key)) }),
|
|
2198
|
+
children
|
|
2199
|
+
}
|
|
2200
|
+
);
|
|
2201
|
+
}
|
|
2202
|
+
function renderShimmerRows(columns, count) {
|
|
2203
|
+
return Array.from({ length: count }).map((_, index) => /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TableRow, { className: DATA_TABLE_ROW_CLASS, "aria-hidden": "true", children: columns.map((column) => /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TableCell, { className: DATA_TABLE_CELL_CLASS, children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("span", { className: "block h-3 w-3/4 animate-pulse rounded bg-muted-foreground/20" }) }, column.key)) }, `shimmer-${index}`));
|
|
2204
|
+
}
|
|
2205
|
+
function renderDataRows(columns, rows) {
|
|
2206
|
+
return rows.map((row, index) => /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TableRow, { className: DATA_ROW_CLASSES, children: columns.map((column) => /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TableCell, { className: DATA_TABLE_CELL_CLASS, children: formatCell(row, column) }, column.key)) }, index));
|
|
2207
|
+
}
|
|
2208
|
+
function renderEmptyRow(colSpan, emptyMessage) {
|
|
2209
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TableRow, { className: "hover:bg-transparent", children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TableCell, { colSpan, className: "py-6 text-center text-sm text-muted-foreground", children: emptyMessage }) });
|
|
2210
|
+
}
|
|
2211
|
+
|
|
2212
|
+
// src/components/artifacts/deck-artifact/deck-markdown.tsx
|
|
2213
|
+
var import_react_markdown = __toESM(require("react-markdown"), 1);
|
|
2214
|
+
var import_remark_breaks = __toESM(require("remark-breaks"), 1);
|
|
2215
|
+
var import_remark_gfm = __toESM(require("remark-gfm"), 1);
|
|
2216
|
+
var import_jsx_runtime23 = require("react/jsx-runtime");
|
|
2217
|
+
function sanitize(text) {
|
|
2218
|
+
return text.split("\n").filter((line) => {
|
|
2219
|
+
const t = line.trim();
|
|
2220
|
+
return !(t.startsWith("<!-- table-title:") && t.endsWith("-->"));
|
|
2221
|
+
}).join("\n");
|
|
2222
|
+
}
|
|
2223
|
+
var MARKDOWN_COMPONENTS = {
|
|
2224
|
+
h1: ({ node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("h1", { className: "text-[30px] font-semibold leading-tight text-foreground mb-3", ...props }),
|
|
2225
|
+
h2: ({ node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("h2", { className: "text-[26px] font-semibold leading-tight text-foreground mb-2", ...props }),
|
|
2226
|
+
h3: ({ node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("h3", { className: "text-[24px] font-semibold leading-tight text-foreground mb-2", ...props }),
|
|
2227
|
+
h4: ({ node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("h4", { className: "text-[24px] font-semibold leading-tight text-foreground mb-2", ...props }),
|
|
2228
|
+
h5: ({ node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("h5", { className: "text-[24px] font-semibold leading-tight text-foreground mb-2", ...props }),
|
|
2229
|
+
h6: ({ node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("h6", { className: "text-[24px] font-semibold leading-tight text-foreground mb-2", ...props }),
|
|
2230
|
+
p: ({ node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("p", { className: "text-[22px] leading-relaxed text-foreground my-2", ...props }),
|
|
2231
|
+
ul: ({ node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("ul", { className: "list-disc pl-7 text-[22px] leading-relaxed text-foreground my-2", ...props }),
|
|
2232
|
+
ol: ({ node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("ol", { className: "list-decimal pl-7 text-[22px] leading-relaxed text-foreground my-2", ...props }),
|
|
2233
|
+
// react-markdown injects list metadata (`ordered` / `index` / `checked`) that must not leak to the DOM.
|
|
2234
|
+
li: ({ node: _node, ordered: _ordered, index: _index, checked: _checked, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("li", { className: "my-1", ...props }),
|
|
2235
|
+
strong: ({ node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("strong", { className: "font-semibold", ...props }),
|
|
2236
|
+
em: ({ node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("em", { className: "italic", ...props }),
|
|
2237
|
+
// Gate `<img src>` against an http(s) allowlist. react-markdown v8 percent-encodes the URL but
|
|
2238
|
+
// does NOT protocol-filter image src (unlike link href), so an LLM-authored
|
|
2239
|
+
// `` / `` or a tracking-pixel `` would otherwise render
|
|
2240
|
+
// with the raw URL. Unsafe src → render nothing.
|
|
2241
|
+
img: ({ node: _node, src, ...props }) => typeof src === "string" && isSafeDownloadUrl(src) ? /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("img", { src, className: "max-w-full", ...props }) : null,
|
|
2242
|
+
a: ({ node: _node, ...props }) => (
|
|
2243
|
+
// `rel` is forced AFTER `{...props}` so it can't be overridden — if a consumer ever adds
|
|
2244
|
+
// `linkTarget="_blank"`, LLM-authored links still can't reach `window.opener`.
|
|
2245
|
+
/* @__PURE__ */ (0, import_jsx_runtime23.jsx)("a", { className: "underline underline-offset-2", ...props, rel: "noopener noreferrer" })
|
|
2246
|
+
),
|
|
2247
|
+
// react-markdown passes `inline` to distinguish inline code from fenced blocks — strip it from the DOM.
|
|
2248
|
+
code: ({ node: _node, inline: _inline, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("code", { className: "rounded bg-muted px-1.5 py-0.5 font-mono text-[18px]", ...props }),
|
|
2249
|
+
blockquote: ({ node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("blockquote", { className: "border-l-2 border-brown-alpha-12 pl-4 text-[22px] text-muted-foreground", ...props }),
|
|
2250
|
+
hr: ({ node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("hr", { className: "my-4 border-brown-alpha-12", ...props }),
|
|
2251
|
+
table: ({ node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("div", { className: "overflow-x-auto", children: /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("table", { className: "w-full border-collapse text-[20px]", ...props }) }),
|
|
2252
|
+
// react-markdown passes `isHeader` to cell renderers — strip it so it never reaches the DOM.
|
|
2253
|
+
th: ({ node: _node, isHeader: _isHeader, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("th", { className: "border-b border-brown-alpha-12 px-3 py-1.5 text-left font-medium", ...props }),
|
|
2254
|
+
td: ({ node: _node, isHeader: _isHeader, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("td", { className: "border-b border-brown-alpha-12 px-3 py-1.5", ...props })
|
|
2255
|
+
};
|
|
2256
|
+
function DeckMarkdown({ markdown }) {
|
|
2257
|
+
return /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(import_react_markdown.default, { remarkPlugins: [import_remark_gfm.default, import_remark_breaks.default], components: MARKDOWN_COMPONENTS, children: sanitize(markdown) });
|
|
2258
|
+
}
|
|
2259
|
+
|
|
2260
|
+
// src/components/artifacts/deck-artifact/slide-renderers.tsx
|
|
2261
|
+
var import_react15 = require("react");
|
|
2262
|
+
var import_jsx_runtime24 = require("react/jsx-runtime");
|
|
2263
|
+
function safeLogoUrl(meta) {
|
|
2264
|
+
return meta?.logoUrl && isSafeDownloadUrl(meta.logoUrl) ? meta.logoUrl : null;
|
|
2265
|
+
}
|
|
2266
|
+
var DESIGN_W = 1280;
|
|
2267
|
+
var DESIGN_H = 720;
|
|
2268
|
+
var EYEBROW_H = 84;
|
|
2269
|
+
var CANVAS_LOGO_MAX_H = 48;
|
|
2270
|
+
var ACCENT_FONT = { fontFamily: `"${fontFamilies.CRIMSON_PRO}", serif`, fontStyle: "italic" };
|
|
2271
|
+
function SlideFrame({ meta, children, accent = false, bare = false }) {
|
|
2272
|
+
const frameRef = (0, import_react15.useRef)(null);
|
|
2273
|
+
const [scale, setScale] = (0, import_react15.useState)(null);
|
|
2274
|
+
(0, import_react15.useLayoutEffect)(() => {
|
|
2275
|
+
const el = frameRef.current;
|
|
2276
|
+
if (!el) return;
|
|
2277
|
+
const apply = (width) => {
|
|
2278
|
+
if (width > 0) setScale(width / DESIGN_W);
|
|
2279
|
+
};
|
|
2280
|
+
apply(el.clientWidth);
|
|
2281
|
+
const ro = new ResizeObserver((entries) => apply(entries[0]?.contentRect.width ?? 0));
|
|
2282
|
+
ro.observe(el);
|
|
2283
|
+
return () => ro.disconnect();
|
|
2284
|
+
}, []);
|
|
2285
|
+
const bg = accent ? "bg-indigo-600" : "bg-deck-canvas";
|
|
2286
|
+
const eyebrowColor = accent ? "text-white/70" : "text-brown-60";
|
|
2287
|
+
const borderColor = accent ? "border-white/20" : "border-brown-alpha-12";
|
|
2288
|
+
const logoSrc = safeLogoUrl(meta);
|
|
2289
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { ref: frameRef, className: `relative aspect-[16/9] w-full overflow-hidden rounded-lg ${bg}`, children: /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)(
|
|
2290
|
+
"div",
|
|
2291
|
+
{
|
|
2292
|
+
className: "absolute left-0 top-0 origin-top-left",
|
|
2293
|
+
style: {
|
|
2294
|
+
width: DESIGN_W,
|
|
2295
|
+
height: DESIGN_H,
|
|
2296
|
+
transform: `scale(${scale ?? 0})`,
|
|
2297
|
+
visibility: scale === null ? "hidden" : "visible"
|
|
2298
|
+
},
|
|
2299
|
+
children: [
|
|
2300
|
+
!bare ? /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)(
|
|
2301
|
+
"div",
|
|
2302
|
+
{
|
|
2303
|
+
className: `absolute inset-x-0 top-0 flex items-center justify-between border-b px-16 ${borderColor}`,
|
|
2304
|
+
style: { height: EYEBROW_H },
|
|
2305
|
+
children: [
|
|
2306
|
+
meta?.eyebrow ? /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", { className: eyebrowColor, style: { ...ACCENT_FONT, fontSize: 22 }, children: meta.eyebrow }) : /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", {}),
|
|
2307
|
+
logoSrc ? /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("img", { src: logoSrc, alt: "", className: "object-contain", style: { maxHeight: CANVAS_LOGO_MAX_H } }) : null
|
|
2308
|
+
]
|
|
2309
|
+
}
|
|
2310
|
+
) : null,
|
|
2311
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: "absolute inset-x-0 bottom-0 overflow-hidden", style: { top: bare ? 0 : EYEBROW_H }, children })
|
|
2312
|
+
]
|
|
2313
|
+
}
|
|
2314
|
+
) });
|
|
2315
|
+
}
|
|
2316
|
+
function TitleSlide({ slide, meta }) {
|
|
2317
|
+
const logoSrc = safeLogoUrl(meta);
|
|
2318
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(SlideFrame, { meta, bare: true, children: /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "flex h-full flex-col justify-center px-24 py-16", children: [
|
|
2319
|
+
logoSrc ? /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
2320
|
+
"img",
|
|
2321
|
+
{
|
|
2322
|
+
src: logoSrc,
|
|
2323
|
+
alt: "",
|
|
2324
|
+
className: "mb-16 object-contain object-left",
|
|
2325
|
+
style: { maxHeight: 56, maxWidth: 380 }
|
|
2326
|
+
}
|
|
2327
|
+
) : null,
|
|
2328
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
2329
|
+
"h1",
|
|
1821
2330
|
{
|
|
1822
|
-
"
|
|
1823
|
-
|
|
1824
|
-
|
|
1825
|
-
children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(TableRow, { className: "hover:bg-transparent", children: columns.map((column) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(TableHead, { scope: "col", className: HEAD_CLASS, children: column.label }, column.key)) })
|
|
2331
|
+
className: "font-bold tracking-tight text-brown-100",
|
|
2332
|
+
style: { fontSize: 92, lineHeight: 1.04, maxWidth: 1060 },
|
|
2333
|
+
children: slide.title
|
|
1826
2334
|
}
|
|
1827
2335
|
),
|
|
1828
|
-
/* @__PURE__ */ (0,
|
|
2336
|
+
slide.subtitle ? /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("p", { className: "mt-7 text-brown-70", style: { ...ACCENT_FONT, fontSize: 34 }, children: slide.subtitle }) : null,
|
|
2337
|
+
slide.description ? /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("p", { className: "mt-4 leading-relaxed text-brown-70", style: { fontSize: 24, maxWidth: 880 }, children: slide.description }) : null,
|
|
2338
|
+
meta?.date ? /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("p", { className: "mt-10 text-brown-70", style: { ...ACCENT_FONT, fontSize: 30 }, children: meta.date }) : null
|
|
1829
2339
|
] }) });
|
|
1830
2340
|
}
|
|
1831
|
-
function
|
|
1832
|
-
|
|
2341
|
+
function AgendaSlide({ slide, meta, labels }) {
|
|
2342
|
+
const items = slide.items ?? [];
|
|
2343
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(SlideFrame, { meta, children: /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "h-full px-24 py-14", children: [
|
|
2344
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("h2", { className: "mb-10 font-bold text-brown-90", style: { fontSize: 40 }, children: slide.title || labels.agenda }),
|
|
2345
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: "flex flex-col", children: items.map((item, i) => /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "flex items-baseline gap-6 border-b border-brown-alpha-12 py-5", children: [
|
|
2346
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", { className: "shrink-0 text-indigo-600", style: { ...ACCENT_FONT, fontSize: 28, width: 64 }, children: String(i + 1).padStart(2, "0") }),
|
|
2347
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", { className: "text-brown-90", style: { fontSize: 28 }, children: item })
|
|
2348
|
+
] }, i)) })
|
|
2349
|
+
] }) });
|
|
1833
2350
|
}
|
|
1834
|
-
function
|
|
1835
|
-
return
|
|
2351
|
+
function SectionSlide({ slide, meta }) {
|
|
2352
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(SlideFrame, { meta, accent: true, children: /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "flex h-full flex-col justify-center gap-6 px-24", children: [
|
|
2353
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("h2", { className: "font-bold text-white", style: { fontSize: 72, lineHeight: 1.05, maxWidth: 940 }, children: slide.title }),
|
|
2354
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: "mt-2 bg-white/50", style: { width: 96, height: 5 } })
|
|
2355
|
+
] }) });
|
|
1836
2356
|
}
|
|
1837
|
-
function
|
|
1838
|
-
return /* @__PURE__ */ (0,
|
|
2357
|
+
function ClosingSlide({ meta, labels }) {
|
|
2358
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(SlideFrame, { meta, children: /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "flex h-full flex-col items-center justify-center gap-6 px-24 text-center", children: [
|
|
2359
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("h1", { className: "font-bold text-brown-100", style: { fontSize: 72 }, children: labels.thankYou }),
|
|
2360
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("p", { className: "text-indigo-600", style: { ...ACCENT_FONT, fontSize: 36 }, children: labels.questions })
|
|
2361
|
+
] }) });
|
|
1839
2362
|
}
|
|
1840
2363
|
|
|
1841
|
-
// src/components/artifacts/
|
|
1842
|
-
|
|
1843
|
-
|
|
2364
|
+
// src/components/artifacts/deck-artifact/deck-artifact-content.tsx
|
|
2365
|
+
var import_jsx_runtime25 = require("react/jsx-runtime");
|
|
2366
|
+
var TABLE_BLOCK_MAX_SHIMMER_ROWS = 10;
|
|
2367
|
+
var TABLE_CHROME_RESERVE = 56;
|
|
2368
|
+
var VISUAL_FALLBACK_HEIGHT = 360;
|
|
2369
|
+
function DeckArtifactContent({
|
|
2370
|
+
slides,
|
|
2371
|
+
labels,
|
|
2372
|
+
onNavigate,
|
|
2373
|
+
meta,
|
|
2374
|
+
onDark = false,
|
|
2375
|
+
currentSlide,
|
|
2376
|
+
onSlideChange
|
|
2377
|
+
}) {
|
|
2378
|
+
const navBtnClass = onDark ? "[&_svg]:!text-white hover:!bg-white/20 disabled:opacity-40" : void 0;
|
|
2379
|
+
const navBtnSize = onDark ? "medium" : "small";
|
|
2380
|
+
const isControlled = currentSlide !== void 0;
|
|
2381
|
+
const [internalIndex, setInternalIndex] = (0, import_react16.useState)(0);
|
|
2382
|
+
const index = isControlled ? currentSlide : internalIndex;
|
|
2383
|
+
const current = Math.min(index, slides.length - 1);
|
|
2384
|
+
const slide = slides[current];
|
|
2385
|
+
const goTo = (0, import_react16.useCallback)(
|
|
2386
|
+
(next) => {
|
|
2387
|
+
const clamped = Math.max(0, Math.min(next, slides.length - 1));
|
|
2388
|
+
if (isControlled) onSlideChange?.(clamped);
|
|
2389
|
+
else setInternalIndex(clamped);
|
|
2390
|
+
onNavigate?.(clamped);
|
|
2391
|
+
},
|
|
2392
|
+
[slides.length, onNavigate, isControlled, onSlideChange]
|
|
2393
|
+
);
|
|
2394
|
+
const position = labels.position.replace("{current}", String(current + 1)).replace("{total}", String(slides.length));
|
|
2395
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("div", { className: "flex flex-col gap-3 p-4", children: [
|
|
2396
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(SlideDispatch, { slide, labels, meta }),
|
|
2397
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(
|
|
2398
|
+
"div",
|
|
2399
|
+
{
|
|
2400
|
+
className: `flex items-center justify-between border-t pt-2 ${onDark ? "border-white/20" : "border-brown-alpha-12"}`,
|
|
2401
|
+
children: [
|
|
2402
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
|
|
2403
|
+
IconButton,
|
|
2404
|
+
{
|
|
2405
|
+
icon: IconChevronLeft,
|
|
2406
|
+
size: navBtnSize,
|
|
2407
|
+
className: navBtnClass,
|
|
2408
|
+
"aria-label": labels.previous,
|
|
2409
|
+
disabled: current === 0,
|
|
2410
|
+
onClick: () => goTo(current - 1)
|
|
2411
|
+
}
|
|
2412
|
+
),
|
|
2413
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { className: `text-xs font-medium ${onDark ? "text-white/70" : "text-brown-70"}`, children: position }),
|
|
2414
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
|
|
2415
|
+
IconButton,
|
|
2416
|
+
{
|
|
2417
|
+
icon: IconChevronRight,
|
|
2418
|
+
size: navBtnSize,
|
|
2419
|
+
className: navBtnClass,
|
|
2420
|
+
"aria-label": labels.next,
|
|
2421
|
+
disabled: current === slides.length - 1,
|
|
2422
|
+
onClick: () => goTo(current + 1)
|
|
2423
|
+
}
|
|
2424
|
+
)
|
|
2425
|
+
]
|
|
2426
|
+
}
|
|
2427
|
+
)
|
|
2428
|
+
] });
|
|
2429
|
+
}
|
|
2430
|
+
function SlideDispatch({ slide, labels, meta }) {
|
|
2431
|
+
const kind = slide.kind ?? deckSlideKinds.CONTENT;
|
|
2432
|
+
switch (kind) {
|
|
2433
|
+
case deckSlideKinds.TITLE:
|
|
2434
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(TitleSlide, { slide, meta });
|
|
2435
|
+
case deckSlideKinds.AGENDA:
|
|
2436
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(AgendaSlide, { slide, meta, labels });
|
|
2437
|
+
case deckSlideKinds.SECTION:
|
|
2438
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(SectionSlide, { slide, meta });
|
|
2439
|
+
case deckSlideKinds.CLOSING:
|
|
2440
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(ClosingSlide, { meta, labels });
|
|
2441
|
+
case deckSlideKinds.CONTENT:
|
|
2442
|
+
default:
|
|
2443
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(ContentSlide, { slide, meta, labels });
|
|
2444
|
+
}
|
|
2445
|
+
}
|
|
2446
|
+
function isVisualBlock(block) {
|
|
2447
|
+
return block.type === deckBlockTypes.CHART || block.type === deckBlockTypes.TABLE;
|
|
2448
|
+
}
|
|
2449
|
+
function ContentSlide({ slide, meta, labels }) {
|
|
2450
|
+
const content = slide.content ?? [];
|
|
2451
|
+
const visuals = content.filter(isVisualBlock);
|
|
2452
|
+
const texts = content.filter(
|
|
2453
|
+
(b) => b.type === deckBlockTypes.TEXT
|
|
2454
|
+
);
|
|
2455
|
+
if (visuals.length === 1 && texts.length > 0) {
|
|
2456
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(SlideFrame, { meta, children: /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("div", { className: "flex h-full items-stretch gap-12 px-16 py-12", children: [
|
|
2457
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: "flex w-[42%] shrink-0 flex-col overflow-hidden", children: /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(AutoFit, { children: [
|
|
2458
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)("h3", { className: "mb-5 font-bold leading-tight text-foreground", style: { fontSize: 34 }, children: slide.title }),
|
|
2459
|
+
texts.map((block, i) => /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(DeckMarkdown, { markdown: block.markdown }, i))
|
|
2460
|
+
] }) }),
|
|
2461
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: "min-h-0 min-w-0 flex-1", children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(FillVisual, { block: visuals[0], labels }) })
|
|
2462
|
+
] }) });
|
|
2463
|
+
}
|
|
2464
|
+
if (visuals.length > 0) {
|
|
2465
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(SlideFrame, { meta, children: /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("div", { className: "flex h-full flex-col gap-5 px-16 py-10", children: [
|
|
2466
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)("h3", { className: "shrink-0 font-bold leading-tight text-foreground", style: { fontSize: 32 }, children: slide.title }),
|
|
2467
|
+
content.map(
|
|
2468
|
+
(block, i) => isVisualBlock(block) ? /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: "min-h-0 min-w-0 flex-1", children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(FillVisual, { block, labels }) }, i) : /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: "shrink-0 overflow-hidden", children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(DeckMarkdown, { markdown: block.markdown }) }, i)
|
|
2469
|
+
)
|
|
2470
|
+
] }) });
|
|
2471
|
+
}
|
|
2472
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(SlideFrame, { meta, children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: "h-full px-24 py-12", children: /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(AutoFit, { children: [
|
|
2473
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)("h3", { className: "mb-6 font-bold leading-tight text-foreground", style: { fontSize: 38 }, children: slide.title }),
|
|
2474
|
+
texts.map((block, i) => /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(DeckMarkdown, { markdown: block.markdown }, i))
|
|
2475
|
+
] }) }) });
|
|
2476
|
+
}
|
|
2477
|
+
function AutoFit({ children }) {
|
|
2478
|
+
const boxRef = (0, import_react16.useRef)(null);
|
|
2479
|
+
const contentRef = (0, import_react16.useRef)(null);
|
|
2480
|
+
const [fit, setFit] = (0, import_react16.useState)({ scale: 1, height: 0 });
|
|
2481
|
+
(0, import_react16.useLayoutEffect)(() => {
|
|
2482
|
+
const boxEl = boxRef.current;
|
|
2483
|
+
const contentEl = contentRef.current;
|
|
2484
|
+
if (!boxEl || !contentEl) return;
|
|
2485
|
+
const measure = () => {
|
|
2486
|
+
const avail = boxEl.clientHeight;
|
|
2487
|
+
const natural = contentEl.offsetHeight;
|
|
2488
|
+
const scale = avail > 0 && natural > avail ? avail / natural : 1;
|
|
2489
|
+
setFit({ scale, height: natural * scale });
|
|
2490
|
+
};
|
|
2491
|
+
measure();
|
|
2492
|
+
const ro = new ResizeObserver(measure);
|
|
2493
|
+
ro.observe(boxEl);
|
|
2494
|
+
ro.observe(contentEl);
|
|
2495
|
+
return () => ro.disconnect();
|
|
2496
|
+
}, []);
|
|
2497
|
+
const scaled = fit.scale < 1;
|
|
2498
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { ref: boxRef, className: "flex h-full min-h-0 w-full flex-col justify-center overflow-hidden", children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { style: scaled ? { height: fit.height } : void 0, children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
|
|
2499
|
+
"div",
|
|
2500
|
+
{
|
|
2501
|
+
ref: contentRef,
|
|
2502
|
+
className: "w-full origin-top-left",
|
|
2503
|
+
style: scaled ? { transform: `scale(${fit.scale})` } : void 0,
|
|
2504
|
+
children
|
|
2505
|
+
}
|
|
2506
|
+
) }) });
|
|
2507
|
+
}
|
|
2508
|
+
function FillVisual({ block, labels }) {
|
|
2509
|
+
const ref = (0, import_react16.useRef)(null);
|
|
2510
|
+
const [height, setHeight] = (0, import_react16.useState)(VISUAL_FALLBACK_HEIGHT);
|
|
2511
|
+
(0, import_react16.useLayoutEffect)(() => {
|
|
2512
|
+
const el = ref.current;
|
|
2513
|
+
if (!el) return;
|
|
2514
|
+
const apply = (h) => {
|
|
2515
|
+
if (h > 0) setHeight(h);
|
|
2516
|
+
};
|
|
2517
|
+
apply(el.clientHeight);
|
|
2518
|
+
const ro = new ResizeObserver((entries) => apply(entries[0]?.contentRect.height ?? 0));
|
|
2519
|
+
ro.observe(el);
|
|
2520
|
+
return () => ro.disconnect();
|
|
2521
|
+
}, []);
|
|
2522
|
+
const chartLabels = labels.chart ?? DEFAULT_CHART_ARTIFACT_LABELS;
|
|
2523
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { ref, className: "h-full min-h-0 w-full overflow-hidden", children: block.type === deckBlockTypes.CHART ? (
|
|
2524
|
+
// ChartArtifactContent assumes a non-empty rowset (the standalone ChartArtifact guards
|
|
2525
|
+
// `rows.length > 0` upstream); mirror that guard here so an empty inline chart shows the
|
|
2526
|
+
// localized empty status instead of a blank chart area.
|
|
2527
|
+
block.rows.length === 0 ? /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(StatusMessage, { $tone: "info", children: chartLabels.empty }) : /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { style: { height }, children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(ChartArtifactContent, { config: block.config, rows: block.rows, labels: chartLabels }) })
|
|
2528
|
+
) : /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
|
|
2529
|
+
TableArtifactContent,
|
|
2530
|
+
{
|
|
2531
|
+
columns: block.config.columns,
|
|
2532
|
+
data: { status: "ready", rows: block.rows, error: null },
|
|
2533
|
+
knownRowCount: block.config.stats?.rowCount ?? block.rows.length,
|
|
2534
|
+
maxShimmerRows: TABLE_BLOCK_MAX_SHIMMER_ROWS,
|
|
2535
|
+
maxBodyHeight: Math.max(0, height - TABLE_CHROME_RESERVE),
|
|
2536
|
+
labels: labels.table ?? DEFAULT_TABLE_ARTIFACT_LABELS
|
|
2537
|
+
}
|
|
2538
|
+
) });
|
|
1844
2539
|
}
|
|
1845
2540
|
|
|
1846
2541
|
// src/components/artifacts/table-artifact/validate.ts
|
|
@@ -1859,19 +2554,265 @@ function isValidTableColumn(column) {
|
|
|
1859
2554
|
return true;
|
|
1860
2555
|
}
|
|
1861
2556
|
|
|
1862
|
-
// src/components/artifacts/
|
|
1863
|
-
|
|
2557
|
+
// src/components/artifacts/deck-artifact/validate.ts
|
|
2558
|
+
function isValidDeckConfig(config) {
|
|
2559
|
+
if (!config || typeof config !== "object") return false;
|
|
2560
|
+
const candidate = config;
|
|
2561
|
+
if (!Array.isArray(candidate.slides)) return false;
|
|
2562
|
+
if (candidate.slides.length === 0) return false;
|
|
2563
|
+
return candidate.slides.every(isValidDeckSlide);
|
|
2564
|
+
}
|
|
2565
|
+
function isValidDeckSlide(slide) {
|
|
2566
|
+
if (!slide || typeof slide !== "object") return false;
|
|
2567
|
+
const candidate = slide;
|
|
2568
|
+
if (typeof candidate.title !== "string") return false;
|
|
2569
|
+
const kind = typeof candidate.kind === "string" ? candidate.kind : deckSlideKinds.CONTENT;
|
|
2570
|
+
if (kind === deckSlideKinds.CONTENT && !Array.isArray(candidate.content)) return false;
|
|
2571
|
+
const content = Array.isArray(candidate.content) ? candidate.content : [];
|
|
2572
|
+
if (candidate.items != null) {
|
|
2573
|
+
if (!Array.isArray(candidate.items)) return false;
|
|
2574
|
+
if (!candidate.items.every((item) => typeof item === "string")) return false;
|
|
2575
|
+
}
|
|
2576
|
+
return content.every(isValidDeckBlock);
|
|
2577
|
+
}
|
|
2578
|
+
function isValidDeckBlock(block) {
|
|
2579
|
+
if (!block || typeof block !== "object") return false;
|
|
2580
|
+
const candidate = block;
|
|
2581
|
+
switch (candidate.type) {
|
|
2582
|
+
case deckBlockTypes.TEXT:
|
|
2583
|
+
return typeof candidate.markdown === "string";
|
|
2584
|
+
case deckBlockTypes.CHART:
|
|
2585
|
+
return isValidChartConfig(candidate.config) && Array.isArray(candidate.rows);
|
|
2586
|
+
case deckBlockTypes.TABLE:
|
|
2587
|
+
return isValidTableConfig(candidate.config) && Array.isArray(candidate.rows);
|
|
2588
|
+
default:
|
|
2589
|
+
return false;
|
|
2590
|
+
}
|
|
2591
|
+
}
|
|
2592
|
+
|
|
2593
|
+
// src/components/artifacts/deck-artifact/deck-artifact.tsx
|
|
2594
|
+
var import_jsx_runtime26 = require("react/jsx-runtime");
|
|
1864
2595
|
var TITLE_CLASSES2 = "text-sm font-semibold text-foreground";
|
|
2596
|
+
function DeckArtifact({ artifact, labels, callbacks }) {
|
|
2597
|
+
const validConfig = isValidDeckConfig(artifact.config);
|
|
2598
|
+
const [isFullscreen, setIsFullscreen] = (0, import_react17.useState)(false);
|
|
2599
|
+
const [currentSlide, setCurrentSlide] = (0, import_react17.useState)(0);
|
|
2600
|
+
(0, import_react17.useEffect)(() => {
|
|
2601
|
+
if (validConfig) return;
|
|
2602
|
+
console.warn("[clay] DeckArtifact: malformed `config` \u2014 skipping render.");
|
|
2603
|
+
}, [validConfig]);
|
|
2604
|
+
(0, import_react17.useEffect)(() => {
|
|
2605
|
+
if (!isFullscreen) return;
|
|
2606
|
+
const handleKey = (e) => {
|
|
2607
|
+
if (e.key === "Escape") setIsFullscreen(false);
|
|
2608
|
+
};
|
|
2609
|
+
document.addEventListener("keydown", handleKey);
|
|
2610
|
+
const previousOverflow = document.documentElement.style.overflow;
|
|
2611
|
+
document.documentElement.style.overflow = "hidden";
|
|
2612
|
+
return () => {
|
|
2613
|
+
document.removeEventListener("keydown", handleKey);
|
|
2614
|
+
document.documentElement.style.overflow = previousOverflow;
|
|
2615
|
+
};
|
|
2616
|
+
}, [isFullscreen]);
|
|
2617
|
+
const resolvedLabels = (0, import_react17.useMemo)(
|
|
2618
|
+
() => ({
|
|
2619
|
+
...DEFAULT_DECK_ARTIFACT_LABELS,
|
|
2620
|
+
...labels ?? {},
|
|
2621
|
+
chart: { ...DEFAULT_CHART_ARTIFACT_LABELS, ...labels?.chart ?? {} },
|
|
2622
|
+
table: { ...DEFAULT_TABLE_ARTIFACT_LABELS, ...labels?.table ?? {} }
|
|
2623
|
+
}),
|
|
2624
|
+
[labels]
|
|
2625
|
+
);
|
|
2626
|
+
const onNavigate = callbacks?.onNavigate;
|
|
2627
|
+
const handleNavigate = onNavigate ? (slideIndex) => onNavigate(artifact, slideIndex) : void 0;
|
|
2628
|
+
const onDownload = callbacks?.onDownload;
|
|
2629
|
+
const handleDownload = onDownload ? () => onDownload(artifact) : void 0;
|
|
2630
|
+
const presignedUrl = artifact.protectedAsset?.presignedUrl ?? null;
|
|
2631
|
+
const showDownload = presignedUrl !== null && isSafeDownloadUrl(presignedUrl);
|
|
2632
|
+
const meta = artifact.config?.meta;
|
|
2633
|
+
const handleOpenFullscreen = () => setIsFullscreen(true);
|
|
2634
|
+
const handleCloseFullscreen = () => setIsFullscreen(false);
|
|
2635
|
+
const actions = /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(ArtifactActions, { ...{ [CAPTURE_EXCLUDE_ATTRIBUTE]: "" }, children: [
|
|
2636
|
+
showDownload ? /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(ArtifactDownloadButton, { href: presignedUrl ?? "", label: resolvedLabels.download, onClick: handleDownload }) : null,
|
|
2637
|
+
validConfig ? /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
2638
|
+
IconButton,
|
|
2639
|
+
{
|
|
2640
|
+
icon: IconArrowsMaximize,
|
|
2641
|
+
size: "small",
|
|
2642
|
+
"aria-label": resolvedLabels.enterFullscreen,
|
|
2643
|
+
onClick: handleOpenFullscreen
|
|
2644
|
+
}
|
|
2645
|
+
) : null
|
|
2646
|
+
] });
|
|
2647
|
+
if (!validConfig) {
|
|
2648
|
+
return /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(Artifact, { className: "shadow-none w-full rounded-2xl bg-background/70", children: [
|
|
2649
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(ArtifactHeader, { className: "bg-background/70", children: [
|
|
2650
|
+
artifact.title ? /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(ArtifactTitle, { className: TITLE_CLASSES2, children: artifact.title }) : /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("span", {}),
|
|
2651
|
+
actions
|
|
2652
|
+
] }),
|
|
2653
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)(ArtifactContent, { className: "p-0", children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(StatusMessage, { $tone: "info", children: resolvedLabels.unavailable }) })
|
|
2654
|
+
] });
|
|
2655
|
+
}
|
|
2656
|
+
return /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(import_jsx_runtime26.Fragment, { children: [
|
|
2657
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(Artifact, { className: "shadow-none w-full rounded-2xl bg-background/70", children: [
|
|
2658
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(ArtifactHeader, { className: "bg-background/70", children: [
|
|
2659
|
+
artifact.title ? /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(ArtifactTitle, { className: TITLE_CLASSES2, children: artifact.title }) : /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("span", {}),
|
|
2660
|
+
actions
|
|
2661
|
+
] }),
|
|
2662
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)(ArtifactContent, { className: "p-0", children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
2663
|
+
DeckArtifactContent,
|
|
2664
|
+
{
|
|
2665
|
+
slides: artifact.config.slides,
|
|
2666
|
+
labels: resolvedLabels,
|
|
2667
|
+
onNavigate: handleNavigate,
|
|
2668
|
+
meta,
|
|
2669
|
+
currentSlide,
|
|
2670
|
+
onSlideChange: setCurrentSlide
|
|
2671
|
+
}
|
|
2672
|
+
) })
|
|
2673
|
+
] }),
|
|
2674
|
+
isFullscreen && (0, import_react_dom.createPortal)(
|
|
2675
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
2676
|
+
FullscreenOverlay,
|
|
2677
|
+
{
|
|
2678
|
+
artifact,
|
|
2679
|
+
resolvedLabels,
|
|
2680
|
+
onNavigate: handleNavigate,
|
|
2681
|
+
currentSlide,
|
|
2682
|
+
onSlideChange: setCurrentSlide,
|
|
2683
|
+
onClose: handleCloseFullscreen
|
|
2684
|
+
}
|
|
2685
|
+
),
|
|
2686
|
+
document.body
|
|
2687
|
+
)
|
|
2688
|
+
] });
|
|
2689
|
+
}
|
|
2690
|
+
function FullscreenOverlay({
|
|
2691
|
+
artifact,
|
|
2692
|
+
resolvedLabels,
|
|
2693
|
+
onNavigate,
|
|
2694
|
+
currentSlide,
|
|
2695
|
+
onSlideChange,
|
|
2696
|
+
onClose
|
|
2697
|
+
}) {
|
|
2698
|
+
const meta = artifact.config?.meta;
|
|
2699
|
+
return /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
2700
|
+
"div",
|
|
2701
|
+
{
|
|
2702
|
+
className: "fixed inset-0 z-[2147483647] flex items-center justify-center bg-black/80",
|
|
2703
|
+
role: "dialog",
|
|
2704
|
+
"aria-modal": "true",
|
|
2705
|
+
"aria-label": resolvedLabels.exitFullscreen,
|
|
2706
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)("div", { className: "relative", style: { width: "min(94vw, calc(82vh * 16 / 9))" }, children: [
|
|
2707
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
2708
|
+
DeckArtifactContent,
|
|
2709
|
+
{
|
|
2710
|
+
slides: artifact.config.slides,
|
|
2711
|
+
labels: resolvedLabels,
|
|
2712
|
+
onNavigate,
|
|
2713
|
+
meta,
|
|
2714
|
+
currentSlide,
|
|
2715
|
+
onSlideChange,
|
|
2716
|
+
onDark: true
|
|
2717
|
+
}
|
|
2718
|
+
),
|
|
2719
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(
|
|
2720
|
+
"button",
|
|
2721
|
+
{
|
|
2722
|
+
className: "absolute -top-10 right-6 flex items-center gap-1.5 text-sm text-white/80 hover:text-white",
|
|
2723
|
+
"aria-label": resolvedLabels.exitFullscreen,
|
|
2724
|
+
onClick: onClose,
|
|
2725
|
+
children: [
|
|
2726
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)(IconArrowsMinimize, { size: 16 }),
|
|
2727
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)("span", { children: resolvedLabels.exitFullscreen })
|
|
2728
|
+
]
|
|
2729
|
+
}
|
|
2730
|
+
)
|
|
2731
|
+
] })
|
|
2732
|
+
}
|
|
2733
|
+
);
|
|
2734
|
+
}
|
|
2735
|
+
|
|
2736
|
+
// src/components/artifacts/deck-artifact/to-clipboard-text.ts
|
|
2737
|
+
function deckArtifactToClipboardText(artifact) {
|
|
2738
|
+
const header = artifact.title?.trim() || "Deck";
|
|
2739
|
+
const slides = artifact.config?.slides ?? [];
|
|
2740
|
+
const body = slides.map((slide, i) => slideToText(slide, i)).join("\n\n");
|
|
2741
|
+
return body ? `${header}
|
|
2742
|
+
|
|
2743
|
+
${body}` : header;
|
|
2744
|
+
}
|
|
2745
|
+
function slideToText(slide, index) {
|
|
2746
|
+
const kind = slide.kind ?? deckSlideKinds.CONTENT;
|
|
2747
|
+
const prefix = `Slide ${index + 1}: `;
|
|
2748
|
+
switch (kind) {
|
|
2749
|
+
case deckSlideKinds.TITLE: {
|
|
2750
|
+
const parts = [slide.title];
|
|
2751
|
+
if (slide.subtitle) parts.push(slide.subtitle);
|
|
2752
|
+
if (slide.description) parts.push(slide.description);
|
|
2753
|
+
return `${prefix}${parts.join(" \u2014 ")}`.trim();
|
|
2754
|
+
}
|
|
2755
|
+
case deckSlideKinds.AGENDA: {
|
|
2756
|
+
const items = (slide.items ?? []).map((item, i) => ` ${String(i + 1).padStart(2, "0")}. ${item}`).join("\n");
|
|
2757
|
+
return `${prefix}${slide.title || "Agenda"}${items ? `
|
|
2758
|
+
${items}` : ""}`.trim();
|
|
2759
|
+
}
|
|
2760
|
+
case deckSlideKinds.SECTION:
|
|
2761
|
+
return `${prefix}${slide.title}`.trim();
|
|
2762
|
+
case deckSlideKinds.CLOSING:
|
|
2763
|
+
return `${prefix}Thank you`.trim();
|
|
2764
|
+
case deckSlideKinds.CONTENT:
|
|
2765
|
+
default: {
|
|
2766
|
+
const blocks = (slide.content ?? []).map(blockToText).filter(Boolean).join("\n\n");
|
|
2767
|
+
return `${prefix}${slide.title}${blocks ? `
|
|
2768
|
+
${blocks}` : ""}`.trim();
|
|
2769
|
+
}
|
|
2770
|
+
}
|
|
2771
|
+
}
|
|
2772
|
+
function blockToText(block) {
|
|
2773
|
+
switch (block.type) {
|
|
2774
|
+
case deckBlockTypes.TEXT:
|
|
2775
|
+
return block.markdown.trim();
|
|
2776
|
+
case deckBlockTypes.CHART:
|
|
2777
|
+
return `[Chart: ${block.config.variant}]`;
|
|
2778
|
+
case deckBlockTypes.TABLE: {
|
|
2779
|
+
const columnCount = block.config.columns.length;
|
|
2780
|
+
const rowCount = block.rows.length;
|
|
2781
|
+
return `[Table: ${columnCount} column${columnCount === 1 ? "" : "s"} \xD7 ${rowCount} row${rowCount === 1 ? "" : "s"}]`;
|
|
2782
|
+
}
|
|
2783
|
+
default:
|
|
2784
|
+
return "";
|
|
2785
|
+
}
|
|
2786
|
+
}
|
|
2787
|
+
|
|
2788
|
+
// src/components/artifacts/artifact-services/deck-artifact-service.ts
|
|
2789
|
+
var DeckArtifactService = {
|
|
2790
|
+
type: artifactTypes.DECK,
|
|
2791
|
+
Component: DeckArtifact,
|
|
2792
|
+
toClipboardText: deckArtifactToClipboardText
|
|
2793
|
+
};
|
|
2794
|
+
|
|
2795
|
+
// src/components/artifacts/table-artifact/table-artifact.tsx
|
|
2796
|
+
var import_react18 = require("react");
|
|
2797
|
+
|
|
2798
|
+
// src/components/artifacts/table-artifact/use-table-artifact-data.ts
|
|
2799
|
+
function useTableArtifactData(presignedUrl, columns) {
|
|
2800
|
+
return useRowsArtifactData(presignedUrl, columns, parseCsv);
|
|
2801
|
+
}
|
|
2802
|
+
|
|
2803
|
+
// src/components/artifacts/table-artifact/table-artifact.tsx
|
|
2804
|
+
var import_jsx_runtime27 = require("react/jsx-runtime");
|
|
2805
|
+
var TITLE_CLASSES3 = "text-sm font-semibold text-foreground";
|
|
1865
2806
|
var TABLE_MAX_BODY_HEIGHT = 480;
|
|
1866
2807
|
var MAX_SHIMMER_ROWS = 10;
|
|
1867
2808
|
function TableArtifact({ artifact, labels, callbacks }) {
|
|
1868
2809
|
const validConfig = isValidTableConfig(artifact.config);
|
|
1869
2810
|
const validColumns = validConfig ? artifact.config.columns : null;
|
|
1870
|
-
(0,
|
|
2811
|
+
(0, import_react18.useEffect)(() => {
|
|
1871
2812
|
if (validConfig) return;
|
|
1872
2813
|
console.warn("[clay] TableArtifact: malformed `config` \u2014 skipping render.");
|
|
1873
2814
|
}, [validConfig]);
|
|
1874
|
-
const resolvedLabels = (0,
|
|
2815
|
+
const resolvedLabels = (0, import_react18.useMemo)(
|
|
1875
2816
|
() => ({ ...DEFAULT_TABLE_ARTIFACT_LABELS, ...labels ?? {} }),
|
|
1876
2817
|
[labels]
|
|
1877
2818
|
);
|
|
@@ -1883,10 +2824,10 @@ function TableArtifact({ artifact, labels, callbacks }) {
|
|
|
1883
2824
|
const onDownload = callbacks?.onDownload;
|
|
1884
2825
|
const handleDownloadClick = onDownload ? () => onDownload(artifact) : void 0;
|
|
1885
2826
|
if (!validConfig || !validColumns) {
|
|
1886
|
-
return /* @__PURE__ */ (0,
|
|
1887
|
-
/* @__PURE__ */ (0,
|
|
1888
|
-
artifact.title ? /* @__PURE__ */ (0,
|
|
1889
|
-
presignedUrl ? /* @__PURE__ */ (0,
|
|
2827
|
+
return /* @__PURE__ */ (0, import_jsx_runtime27.jsxs)(Artifact, { className: "shadow-none w-full rounded-2xl bg-background/70", children: [
|
|
2828
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)(ArtifactHeader, { className: "bg-background/70", children: [
|
|
2829
|
+
artifact.title ? /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(ArtifactTitle, { className: TITLE_CLASSES3, children: artifact.title }) : /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("span", {}),
|
|
2830
|
+
presignedUrl ? /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(ArtifactActions, { children: /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(
|
|
1890
2831
|
ArtifactDownloadButton,
|
|
1891
2832
|
{
|
|
1892
2833
|
href: presignedUrl,
|
|
@@ -1895,17 +2836,17 @@ function TableArtifact({ artifact, labels, callbacks }) {
|
|
|
1895
2836
|
}
|
|
1896
2837
|
) }) : null
|
|
1897
2838
|
] }),
|
|
1898
|
-
/* @__PURE__ */ (0,
|
|
2839
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)(ArtifactContent, { className: "p-0 overflow-auto", style: { maxHeight: TABLE_MAX_BODY_HEIGHT }, children: /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(StatusMessage, { $tone: "info", children: resolvedLabels.unavailable }) })
|
|
1899
2840
|
] });
|
|
1900
2841
|
}
|
|
1901
2842
|
return (
|
|
1902
2843
|
// The table body owns its own scroll container (`ArtifactTable` inside `TableArtifactContent`).
|
|
1903
2844
|
// Disable the outer overflow container so only one scroll context exists — this prevents
|
|
1904
2845
|
// double-scroll nesting and lets `useScrollShadow` find the correct scroll ancestor.
|
|
1905
|
-
/* @__PURE__ */ (0,
|
|
1906
|
-
/* @__PURE__ */ (0,
|
|
1907
|
-
artifact.title ? /* @__PURE__ */ (0,
|
|
1908
|
-
/* @__PURE__ */ (0,
|
|
2846
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)(Artifact, { className: "shadow-none w-full rounded-2xl bg-background/70", children: [
|
|
2847
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)(ArtifactHeader, { className: "bg-background/70", children: [
|
|
2848
|
+
artifact.title ? /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(ArtifactTitle, { className: TITLE_CLASSES3, children: artifact.title }) : /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("span", {}),
|
|
2849
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)(ArtifactActions, { children: /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(
|
|
1909
2850
|
ArtifactDownloadButton,
|
|
1910
2851
|
{
|
|
1911
2852
|
href: presignedUrl ?? "",
|
|
@@ -1914,7 +2855,7 @@ function TableArtifact({ artifact, labels, callbacks }) {
|
|
|
1914
2855
|
}
|
|
1915
2856
|
) })
|
|
1916
2857
|
] }),
|
|
1917
|
-
/* @__PURE__ */ (0,
|
|
2858
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)(ArtifactContent, { className: "p-0 overflow-visible", style: { maxHeight: "none" }, children: /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(
|
|
1918
2859
|
TableArtifactContent,
|
|
1919
2860
|
{
|
|
1920
2861
|
columns: validColumns,
|
|
@@ -1945,7 +2886,8 @@ var TableArtifactService = {
|
|
|
1945
2886
|
// src/components/artifacts/artifact-services/index.ts
|
|
1946
2887
|
var ArtifactServices = {
|
|
1947
2888
|
[artifactTypes.TABLE]: TableArtifactService,
|
|
1948
|
-
[artifactTypes.CHART]: ChartArtifactService
|
|
2889
|
+
[artifactTypes.CHART]: ChartArtifactService,
|
|
2890
|
+
[artifactTypes.DECK]: DeckArtifactService
|
|
1949
2891
|
};
|
|
1950
2892
|
function artifactToClipboardText(artifact) {
|
|
1951
2893
|
const entry = ArtifactServices[artifact.type];
|
|
@@ -1962,10 +2904,14 @@ function artifactToClipboardText(artifact) {
|
|
|
1962
2904
|
ArtifactServices,
|
|
1963
2905
|
ChartArtifact,
|
|
1964
2906
|
DEFAULT_CHART_ARTIFACT_LABELS,
|
|
2907
|
+
DEFAULT_DECK_ARTIFACT_LABELS,
|
|
1965
2908
|
DEFAULT_TABLE_ARTIFACT_LABELS,
|
|
2909
|
+
DeckArtifact,
|
|
1966
2910
|
TableArtifact,
|
|
1967
2911
|
artifactToClipboardText,
|
|
1968
2912
|
artifactTypes,
|
|
2913
|
+
deckBlockTypes,
|
|
2914
|
+
deckSlideKinds,
|
|
1969
2915
|
isSafeDownloadUrl
|
|
1970
2916
|
});
|
|
1971
2917
|
/*! Bundled license information:
|
|
@@ -1973,7 +2919,11 @@ function artifactToClipboardText(artifact) {
|
|
|
1973
2919
|
@tabler/icons-react/dist/esm/defaultAttributes.mjs:
|
|
1974
2920
|
@tabler/icons-react/dist/esm/createReactComponent.mjs:
|
|
1975
2921
|
@tabler/icons-react/dist/esm/icons/IconAlertCircle.mjs:
|
|
2922
|
+
@tabler/icons-react/dist/esm/icons/IconArrowsMaximize.mjs:
|
|
2923
|
+
@tabler/icons-react/dist/esm/icons/IconArrowsMinimize.mjs:
|
|
1976
2924
|
@tabler/icons-react/dist/esm/icons/IconCheck.mjs:
|
|
2925
|
+
@tabler/icons-react/dist/esm/icons/IconChevronLeft.mjs:
|
|
2926
|
+
@tabler/icons-react/dist/esm/icons/IconChevronRight.mjs:
|
|
1977
2927
|
@tabler/icons-react/dist/esm/icons/IconCopy.mjs:
|
|
1978
2928
|
@tabler/icons-react/dist/esm/icons/IconDownload.mjs:
|
|
1979
2929
|
@tabler/icons-react/dist/esm/icons/IconFileSpreadsheet.mjs:
|