@tangle-network/sandbox-ui 0.131.1 → 0.131.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/assets.d.ts +21 -1
- package/dist/assets.js +335 -197
- package/dist/globals.css +8 -11
- package/dist/styles.css +8 -11
- package/package.json +1 -1
package/dist/assets.d.ts
CHANGED
|
@@ -237,6 +237,8 @@ interface CopyPreviewProps {
|
|
|
237
237
|
content: CopyContent;
|
|
238
238
|
className?: string;
|
|
239
239
|
}
|
|
240
|
+
export declare const COPY_PLATFORM_LABEL: Record<CopyPlatform, string>;
|
|
241
|
+
/** Copy as it will read: the channel and its length budget, the headline, the body and its hashtags. */
|
|
240
242
|
export declare function CopyPreview({ content, className }: CopyPreviewProps): import("react").JSX.Element;
|
|
241
243
|
//#endregion
|
|
242
244
|
//#region src/assets/preview/email-preview.d.ts
|
|
@@ -246,7 +248,25 @@ interface EmailPreviewProps {
|
|
|
246
248
|
previewUrl?: string;
|
|
247
249
|
className?: string;
|
|
248
250
|
}
|
|
249
|
-
|
|
251
|
+
/**
|
|
252
|
+
* The colours an email body renders in. A brand whose text colour is light
|
|
253
|
+
* writes on a dark page; any brand colour that would not read on that page
|
|
254
|
+
* falls back to the page's own ink.
|
|
255
|
+
*/
|
|
256
|
+
export declare function emailPalette(brand: BrandTokens): {
|
|
257
|
+
scheme: string;
|
|
258
|
+
paper: "#111218" | "#ffffff";
|
|
259
|
+
ink: string;
|
|
260
|
+
accent: string;
|
|
261
|
+
button: string;
|
|
262
|
+
buttonText: string;
|
|
263
|
+
quote: string;
|
|
264
|
+
};
|
|
265
|
+
/**
|
|
266
|
+
* An email as a reader meets it: who it is from, the subject and the inbox
|
|
267
|
+
* preview line, then the body on the brand's page and in its typeface.
|
|
268
|
+
*/
|
|
269
|
+
export declare function EmailPreview({ content, brand, previewUrl, className }: EmailPreviewProps): import("react").JSX.Element;
|
|
250
270
|
//#endregion
|
|
251
271
|
//#region src/assets/preview/image-preview.d.ts
|
|
252
272
|
type ImageFormat = "feed" | "story" | "carousel";
|
package/dist/assets.js
CHANGED
|
@@ -118,6 +118,283 @@ function ImagePreview({ content, brand, format = "feed", className }) {
|
|
|
118
118
|
});
|
|
119
119
|
}
|
|
120
120
|
//#endregion
|
|
121
|
+
//#region src/assets/preview/email-preview.tsx
|
|
122
|
+
/** sRGB relative luminance of a #rgb or #rrggbb colour; null for anything else. */
|
|
123
|
+
function luminance(color) {
|
|
124
|
+
const hex = /^#([0-9a-f]{3}|[0-9a-f]{6})$/i.exec(color.trim())?.[1];
|
|
125
|
+
if (!hex) return null;
|
|
126
|
+
const full = hex.length === 3 ? hex.split("").map((c) => c + c).join("") : hex;
|
|
127
|
+
const [r, g, b] = [
|
|
128
|
+
0,
|
|
129
|
+
2,
|
|
130
|
+
4
|
|
131
|
+
].map((i) => {
|
|
132
|
+
const channel = parseInt(full.slice(i, i + 2), 16) / 255;
|
|
133
|
+
return channel <= .03928 ? channel / 12.92 : ((channel + .055) / 1.055) ** 2.4;
|
|
134
|
+
});
|
|
135
|
+
return .2126 * r + .7152 * g + .0722 * b;
|
|
136
|
+
}
|
|
137
|
+
function contrast(a, b) {
|
|
138
|
+
return (Math.max(a, b) + .05) / (Math.min(a, b) + .05);
|
|
139
|
+
}
|
|
140
|
+
const PAPER = {
|
|
141
|
+
light: "#ffffff",
|
|
142
|
+
dark: "#111218"
|
|
143
|
+
};
|
|
144
|
+
const INK = {
|
|
145
|
+
light: "#16171d",
|
|
146
|
+
dark: "#f4f4f6"
|
|
147
|
+
};
|
|
148
|
+
/**
|
|
149
|
+
* The colours an email body renders in. A brand whose text colour is light
|
|
150
|
+
* writes on a dark page; any brand colour that would not read on that page
|
|
151
|
+
* falls back to the page's own ink.
|
|
152
|
+
*/
|
|
153
|
+
function emailPalette(brand) {
|
|
154
|
+
const text = luminance(brand.textColor);
|
|
155
|
+
const scheme = text !== null && text > .5 ? "dark" : "light";
|
|
156
|
+
const paper = PAPER[scheme];
|
|
157
|
+
const paperLum = luminance(paper);
|
|
158
|
+
const readable = (color, minimum) => {
|
|
159
|
+
const lum = luminance(color);
|
|
160
|
+
return lum !== null && contrast(lum, paperLum) >= minimum;
|
|
161
|
+
};
|
|
162
|
+
const ink = readable(brand.textColor, 4.5) ? brand.textColor : INK[scheme];
|
|
163
|
+
const accent = readable(brand.primaryColor, 3) ? brand.primaryColor : ink;
|
|
164
|
+
const primary = luminance(brand.primaryColor);
|
|
165
|
+
const buttonText = primary !== null && contrast(primary, 1) < contrast(primary, 0) ? "#111111" : "#ffffff";
|
|
166
|
+
return {
|
|
167
|
+
scheme,
|
|
168
|
+
paper,
|
|
169
|
+
ink,
|
|
170
|
+
accent,
|
|
171
|
+
button: brand.primaryColor,
|
|
172
|
+
buttonText,
|
|
173
|
+
quote: brand.accentColor
|
|
174
|
+
};
|
|
175
|
+
}
|
|
176
|
+
function Button$1({ href, label, palette }) {
|
|
177
|
+
return /* @__PURE__ */ jsx("a", {
|
|
178
|
+
href,
|
|
179
|
+
onClick: (event) => event.preventDefault(),
|
|
180
|
+
className: "inline-block rounded-md px-5 py-2.5 text-sm font-semibold no-underline",
|
|
181
|
+
style: {
|
|
182
|
+
background: palette.button,
|
|
183
|
+
color: palette.buttonText
|
|
184
|
+
},
|
|
185
|
+
children: label
|
|
186
|
+
});
|
|
187
|
+
}
|
|
188
|
+
function Section({ section, palette }) {
|
|
189
|
+
const muted = {
|
|
190
|
+
color: palette.ink,
|
|
191
|
+
opacity: .72
|
|
192
|
+
};
|
|
193
|
+
switch (section.type) {
|
|
194
|
+
case "hero": return /* @__PURE__ */ jsxs("div", {
|
|
195
|
+
className: "flex flex-col items-center gap-3 py-2 text-center",
|
|
196
|
+
children: [
|
|
197
|
+
section.imageUrl && /* @__PURE__ */ jsx("img", {
|
|
198
|
+
src: section.imageUrl,
|
|
199
|
+
alt: "",
|
|
200
|
+
className: "w-full rounded-md object-cover"
|
|
201
|
+
}),
|
|
202
|
+
/* @__PURE__ */ jsx("h2", {
|
|
203
|
+
className: "text-2xl font-bold leading-tight tracking-tight",
|
|
204
|
+
style: { color: palette.accent },
|
|
205
|
+
children: section.headline
|
|
206
|
+
}),
|
|
207
|
+
section.subheadline && /* @__PURE__ */ jsx("p", {
|
|
208
|
+
className: "text-base leading-relaxed",
|
|
209
|
+
style: muted,
|
|
210
|
+
children: section.subheadline
|
|
211
|
+
}),
|
|
212
|
+
section.ctaLabel && /* @__PURE__ */ jsx("div", {
|
|
213
|
+
className: "pt-1",
|
|
214
|
+
children: /* @__PURE__ */ jsx(Button$1, {
|
|
215
|
+
href: section.ctaUrl ?? "#",
|
|
216
|
+
label: section.ctaLabel,
|
|
217
|
+
palette
|
|
218
|
+
})
|
|
219
|
+
})
|
|
220
|
+
]
|
|
221
|
+
});
|
|
222
|
+
case "body": return /* @__PURE__ */ jsx("p", {
|
|
223
|
+
className: "text-base leading-7 whitespace-pre-wrap",
|
|
224
|
+
children: section.text
|
|
225
|
+
});
|
|
226
|
+
case "feature": return /* @__PURE__ */ jsxs("div", {
|
|
227
|
+
className: "flex items-start gap-4",
|
|
228
|
+
children: [section.imageUrl && /* @__PURE__ */ jsx("img", {
|
|
229
|
+
src: section.imageUrl,
|
|
230
|
+
alt: "",
|
|
231
|
+
className: "size-16 shrink-0 rounded-md object-cover"
|
|
232
|
+
}), /* @__PURE__ */ jsxs("div", {
|
|
233
|
+
className: "flex flex-col gap-1",
|
|
234
|
+
children: [/* @__PURE__ */ jsx("div", {
|
|
235
|
+
className: "text-base font-semibold",
|
|
236
|
+
children: section.headline
|
|
237
|
+
}), /* @__PURE__ */ jsx("div", {
|
|
238
|
+
className: "text-sm leading-relaxed",
|
|
239
|
+
style: muted,
|
|
240
|
+
children: section.description
|
|
241
|
+
})]
|
|
242
|
+
})]
|
|
243
|
+
});
|
|
244
|
+
case "testimonial": return /* @__PURE__ */ jsxs("blockquote", {
|
|
245
|
+
className: "border-l-4 pl-4",
|
|
246
|
+
style: { borderColor: palette.quote },
|
|
247
|
+
children: [/* @__PURE__ */ jsxs("p", {
|
|
248
|
+
className: "text-base italic leading-relaxed",
|
|
249
|
+
children: [
|
|
250
|
+
"“",
|
|
251
|
+
section.quote,
|
|
252
|
+
"”"
|
|
253
|
+
]
|
|
254
|
+
}), /* @__PURE__ */ jsxs("footer", {
|
|
255
|
+
className: "mt-2 text-sm font-medium",
|
|
256
|
+
style: muted,
|
|
257
|
+
children: [section.author, section.role ? `, ${section.role}` : ""]
|
|
258
|
+
})]
|
|
259
|
+
});
|
|
260
|
+
case "cta": return /* @__PURE__ */ jsxs("div", {
|
|
261
|
+
className: "flex flex-col items-center gap-2 py-2 text-center",
|
|
262
|
+
children: [/* @__PURE__ */ jsx(Button$1, {
|
|
263
|
+
href: section.url,
|
|
264
|
+
label: section.label,
|
|
265
|
+
palette
|
|
266
|
+
}), section.subtext && /* @__PURE__ */ jsx("p", {
|
|
267
|
+
className: "text-sm",
|
|
268
|
+
style: muted,
|
|
269
|
+
children: section.subtext
|
|
270
|
+
})]
|
|
271
|
+
});
|
|
272
|
+
case "divider": return /* @__PURE__ */ jsx("hr", {
|
|
273
|
+
className: "border-0 border-t",
|
|
274
|
+
style: {
|
|
275
|
+
borderColor: palette.ink,
|
|
276
|
+
opacity: .15
|
|
277
|
+
}
|
|
278
|
+
});
|
|
279
|
+
default: return null;
|
|
280
|
+
}
|
|
281
|
+
}
|
|
282
|
+
/**
|
|
283
|
+
* An email as a reader meets it: who it is from, the subject and the inbox
|
|
284
|
+
* preview line, then the body on the brand's page and in its typeface.
|
|
285
|
+
*/
|
|
286
|
+
function EmailPreview({ content, brand, previewUrl, className }) {
|
|
287
|
+
const palette = emailPalette(brand);
|
|
288
|
+
return /* @__PURE__ */ jsxs("article", {
|
|
289
|
+
className: cn("overflow-hidden rounded-lg border border-border bg-card shadow-sm", className),
|
|
290
|
+
children: [/* @__PURE__ */ jsxs("header", {
|
|
291
|
+
className: "flex flex-col gap-1 border-b border-border px-5 py-4",
|
|
292
|
+
children: [
|
|
293
|
+
/* @__PURE__ */ jsxs("div", {
|
|
294
|
+
className: "flex items-center gap-2 text-sm",
|
|
295
|
+
children: [/* @__PURE__ */ jsx("span", {
|
|
296
|
+
"aria-hidden": true,
|
|
297
|
+
className: "flex size-7 shrink-0 items-center justify-center rounded-full text-xs font-semibold",
|
|
298
|
+
style: {
|
|
299
|
+
background: palette.button,
|
|
300
|
+
color: palette.buttonText
|
|
301
|
+
},
|
|
302
|
+
children: brand.businessName.trim().charAt(0).toUpperCase() || "?"
|
|
303
|
+
}), /* @__PURE__ */ jsx("span", {
|
|
304
|
+
className: "font-medium",
|
|
305
|
+
children: brand.businessName
|
|
306
|
+
})]
|
|
307
|
+
}),
|
|
308
|
+
/* @__PURE__ */ jsx("h3", {
|
|
309
|
+
className: "text-base font-semibold leading-snug",
|
|
310
|
+
children: content.subject
|
|
311
|
+
}),
|
|
312
|
+
content.preheader && /* @__PURE__ */ jsx("p", {
|
|
313
|
+
className: "text-sm text-muted-foreground",
|
|
314
|
+
children: content.preheader
|
|
315
|
+
})
|
|
316
|
+
]
|
|
317
|
+
}), previewUrl ? /* @__PURE__ */ jsx("iframe", {
|
|
318
|
+
src: previewUrl,
|
|
319
|
+
title: "Email preview",
|
|
320
|
+
sandbox: "allow-same-origin",
|
|
321
|
+
className: "block h-[480px] w-full bg-white"
|
|
322
|
+
}) : /* @__PURE__ */ jsx("div", {
|
|
323
|
+
className: "px-5 py-8 sm:px-8",
|
|
324
|
+
style: {
|
|
325
|
+
background: palette.paper,
|
|
326
|
+
color: palette.ink,
|
|
327
|
+
fontFamily: brand.fontFamily
|
|
328
|
+
},
|
|
329
|
+
children: /* @__PURE__ */ jsx("div", {
|
|
330
|
+
className: "mx-auto flex max-w-[560px] flex-col gap-5",
|
|
331
|
+
children: content.sections.map((section, index) => /* @__PURE__ */ jsx(Section, {
|
|
332
|
+
section,
|
|
333
|
+
palette
|
|
334
|
+
}, index))
|
|
335
|
+
})
|
|
336
|
+
})]
|
|
337
|
+
});
|
|
338
|
+
}
|
|
339
|
+
//#endregion
|
|
340
|
+
//#region src/assets/preview/copy-preview.tsx
|
|
341
|
+
const PLATFORM_LIMITS = {
|
|
342
|
+
instagram: 2200,
|
|
343
|
+
tiktok: 2200,
|
|
344
|
+
x: 280,
|
|
345
|
+
linkedin: 3e3,
|
|
346
|
+
sms: 160,
|
|
347
|
+
"email-subject": 60
|
|
348
|
+
};
|
|
349
|
+
const COPY_PLATFORM_LABEL = {
|
|
350
|
+
instagram: "Instagram",
|
|
351
|
+
tiktok: "TikTok",
|
|
352
|
+
x: "X",
|
|
353
|
+
linkedin: "LinkedIn",
|
|
354
|
+
sms: "SMS",
|
|
355
|
+
"email-subject": "Email subject"
|
|
356
|
+
};
|
|
357
|
+
/** Copy as it will read: the channel and its length budget, the headline, the body and its hashtags. */
|
|
358
|
+
function CopyPreview({ content, className }) {
|
|
359
|
+
const limit = PLATFORM_LIMITS[content.platform];
|
|
360
|
+
const length = content.body.length;
|
|
361
|
+
const over = limit !== null && length > limit;
|
|
362
|
+
const near = !over && limit !== null && length >= limit * .9;
|
|
363
|
+
return /* @__PURE__ */ jsxs("article", {
|
|
364
|
+
className: cn("flex flex-col gap-4 rounded-xl border border-border bg-card p-6 shadow-sm", className),
|
|
365
|
+
children: [
|
|
366
|
+
/* @__PURE__ */ jsxs("div", {
|
|
367
|
+
className: "flex items-center justify-between gap-3",
|
|
368
|
+
children: [/* @__PURE__ */ jsx(Badge, {
|
|
369
|
+
variant: "secondary",
|
|
370
|
+
className: "text-xs",
|
|
371
|
+
children: COPY_PLATFORM_LABEL[content.platform] ?? content.platform
|
|
372
|
+
}), limit !== null && /* @__PURE__ */ jsxs("span", {
|
|
373
|
+
className: cn("text-xs tabular-nums", over ? "font-medium text-destructive" : near ? "text-warning" : "text-muted-foreground"),
|
|
374
|
+
children: [
|
|
375
|
+
length,
|
|
376
|
+
" / ",
|
|
377
|
+
limit,
|
|
378
|
+
" characters"
|
|
379
|
+
]
|
|
380
|
+
})]
|
|
381
|
+
}),
|
|
382
|
+
content.headline && /* @__PURE__ */ jsx("h3", {
|
|
383
|
+
className: "text-xl font-semibold leading-snug tracking-tight",
|
|
384
|
+
children: content.headline
|
|
385
|
+
}),
|
|
386
|
+
/* @__PURE__ */ jsx("p", {
|
|
387
|
+
className: "text-base leading-7 whitespace-pre-wrap [overflow-wrap:anywhere]",
|
|
388
|
+
children: content.body
|
|
389
|
+
}),
|
|
390
|
+
content.hashtags && content.hashtags.length > 0 && /* @__PURE__ */ jsx("div", {
|
|
391
|
+
className: "flex flex-wrap gap-x-2 gap-y-1 text-sm text-primary",
|
|
392
|
+
children: content.hashtags.map((tag) => /* @__PURE__ */ jsxs("span", { children: ["#", tag.replace(/^#/, "")] }, tag))
|
|
393
|
+
})
|
|
394
|
+
]
|
|
395
|
+
});
|
|
396
|
+
}
|
|
397
|
+
//#endregion
|
|
121
398
|
//#region src/assets/labels.ts
|
|
122
399
|
/** Reader-facing name for each asset format. */
|
|
123
400
|
const ASSET_FORMAT_LABEL = {
|
|
@@ -177,15 +454,46 @@ function Thumbnail({ spec }) {
|
|
|
177
454
|
const { format, brand, content } = spec;
|
|
178
455
|
if (format === "email") {
|
|
179
456
|
const ec = content;
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
className: "
|
|
187
|
-
children: [
|
|
188
|
-
|
|
457
|
+
const palette = emailPalette(brand);
|
|
458
|
+
const hero = ec.sections.find((section) => section.type === "hero");
|
|
459
|
+
const body = ec.sections.find((section) => section.type === "body");
|
|
460
|
+
return /* @__PURE__ */ jsx("div", {
|
|
461
|
+
className: "flex h-full flex-col p-3",
|
|
462
|
+
children: /* @__PURE__ */ jsxs("div", {
|
|
463
|
+
className: "flex h-full flex-col overflow-hidden rounded-md border border-border bg-card shadow-sm",
|
|
464
|
+
children: [/* @__PURE__ */ jsxs("div", {
|
|
465
|
+
className: "flex flex-col gap-0.5 border-b border-border px-3 py-2",
|
|
466
|
+
children: [
|
|
467
|
+
/* @__PURE__ */ jsx("div", {
|
|
468
|
+
className: "truncate text-xs text-muted-foreground",
|
|
469
|
+
children: brand.businessName
|
|
470
|
+
}),
|
|
471
|
+
/* @__PURE__ */ jsx("div", {
|
|
472
|
+
className: "line-clamp-2 text-sm font-semibold leading-snug",
|
|
473
|
+
children: ec.subject
|
|
474
|
+
}),
|
|
475
|
+
ec.preheader && /* @__PURE__ */ jsx("div", {
|
|
476
|
+
className: "truncate text-xs text-muted-foreground",
|
|
477
|
+
children: ec.preheader
|
|
478
|
+
})
|
|
479
|
+
]
|
|
480
|
+
}), /* @__PURE__ */ jsxs("div", {
|
|
481
|
+
className: "flex flex-1 flex-col gap-1 overflow-hidden px-3 py-2",
|
|
482
|
+
style: {
|
|
483
|
+
background: palette.paper,
|
|
484
|
+
color: palette.ink,
|
|
485
|
+
fontFamily: brand.fontFamily
|
|
486
|
+
},
|
|
487
|
+
children: [hero?.type === "hero" && /* @__PURE__ */ jsx("div", {
|
|
488
|
+
className: "line-clamp-2 text-sm font-bold leading-snug",
|
|
489
|
+
style: { color: palette.accent },
|
|
490
|
+
children: hero.headline
|
|
491
|
+
}), body?.type === "body" && /* @__PURE__ */ jsx("div", {
|
|
492
|
+
className: "line-clamp-4 text-xs leading-relaxed opacity-75",
|
|
493
|
+
children: body.text
|
|
494
|
+
})]
|
|
495
|
+
})]
|
|
496
|
+
})
|
|
189
497
|
});
|
|
190
498
|
}
|
|
191
499
|
if (format.startsWith("image:")) {
|
|
@@ -196,7 +504,7 @@ function Thumbnail({ spec }) {
|
|
|
196
504
|
alt: "",
|
|
197
505
|
loading: "lazy",
|
|
198
506
|
decoding: "async",
|
|
199
|
-
className: "h-full w-full object-contain"
|
|
507
|
+
className: "h-full w-full object-contain p-2"
|
|
200
508
|
});
|
|
201
509
|
return /* @__PURE__ */ jsx("div", {
|
|
202
510
|
className: "h-full overflow-hidden",
|
|
@@ -218,7 +526,7 @@ function Thumbnail({ spec }) {
|
|
|
218
526
|
alt: "",
|
|
219
527
|
loading: "lazy",
|
|
220
528
|
decoding: "async",
|
|
221
|
-
className: "h-full w-full object-contain"
|
|
529
|
+
className: "h-full w-full object-contain p-2"
|
|
222
530
|
}) : /* @__PURE__ */ jsx("div", {
|
|
223
531
|
className: "flex h-full flex-col gap-1 p-3 text-sm",
|
|
224
532
|
children: /* @__PURE__ */ jsxs("div", {
|
|
@@ -244,14 +552,21 @@ function Thumbnail({ spec }) {
|
|
|
244
552
|
if (format.startsWith("copy:")) {
|
|
245
553
|
const cc = content;
|
|
246
554
|
return /* @__PURE__ */ jsxs("div", {
|
|
247
|
-
className: "flex h-full flex-col gap-
|
|
248
|
-
children: [
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
555
|
+
className: "flex h-full flex-col gap-2 overflow-hidden p-4",
|
|
556
|
+
children: [
|
|
557
|
+
/* @__PURE__ */ jsx("span", {
|
|
558
|
+
className: "text-xs font-medium text-muted-foreground",
|
|
559
|
+
children: COPY_PLATFORM_LABEL[cc.platform] ?? cc.platform
|
|
560
|
+
}),
|
|
561
|
+
cc.headline && /* @__PURE__ */ jsx("div", {
|
|
562
|
+
className: "line-clamp-3 text-base font-semibold leading-snug",
|
|
563
|
+
children: cc.headline
|
|
564
|
+
}),
|
|
565
|
+
/* @__PURE__ */ jsx("div", {
|
|
566
|
+
className: "line-clamp-5 text-sm leading-relaxed text-muted-foreground",
|
|
567
|
+
children: cc.body
|
|
568
|
+
})
|
|
569
|
+
]
|
|
255
570
|
});
|
|
256
571
|
}
|
|
257
572
|
return null;
|
|
@@ -325,125 +640,6 @@ function AssetCard({ spec, variantCount, onApprove, onReject, onEdit, onOpen, cl
|
|
|
325
640
|
});
|
|
326
641
|
}
|
|
327
642
|
//#endregion
|
|
328
|
-
//#region src/assets/preview/email-preview.tsx
|
|
329
|
-
function EmailPreview({ content, brand, previewUrl, className }) {
|
|
330
|
-
if (previewUrl) return jsxs("div", {
|
|
331
|
-
className: cn("flex flex-col gap-1", className),
|
|
332
|
-
children: [
|
|
333
|
-
jsx("div", {
|
|
334
|
-
className: "text-xs text-muted-foreground font-medium truncate",
|
|
335
|
-
children: content.subject
|
|
336
|
-
}),
|
|
337
|
-
content.preheader && jsx("div", {
|
|
338
|
-
className: "text-xs text-muted-foreground/60 truncate",
|
|
339
|
-
children: content.preheader
|
|
340
|
-
}),
|
|
341
|
-
jsx("iframe", {
|
|
342
|
-
src: previewUrl,
|
|
343
|
-
className: "w-full rounded border border-border",
|
|
344
|
-
style: {
|
|
345
|
-
height: 480,
|
|
346
|
-
background: "#fff"
|
|
347
|
-
},
|
|
348
|
-
title: "Email preview",
|
|
349
|
-
sandbox: "allow-same-origin"
|
|
350
|
-
})
|
|
351
|
-
]
|
|
352
|
-
});
|
|
353
|
-
return jsxs("div", {
|
|
354
|
-
className: cn("flex flex-col gap-2", className),
|
|
355
|
-
children: [
|
|
356
|
-
jsx("div", {
|
|
357
|
-
className: "text-sm font-semibold truncate",
|
|
358
|
-
children: content.subject
|
|
359
|
-
}),
|
|
360
|
-
content.preheader && jsx("div", {
|
|
361
|
-
className: "text-xs text-muted-foreground truncate",
|
|
362
|
-
children: content.preheader
|
|
363
|
-
}),
|
|
364
|
-
jsx("div", {
|
|
365
|
-
className: "rounded border border-border p-4 space-y-3 overflow-y-auto",
|
|
366
|
-
style: {
|
|
367
|
-
maxHeight: 480,
|
|
368
|
-
fontFamily: brand.fontFamily,
|
|
369
|
-
color: brand.textColor
|
|
370
|
-
},
|
|
371
|
-
children: content.sections.map((section, i) => {
|
|
372
|
-
if (section.type === "hero") return jsxs("div", {
|
|
373
|
-
className: "text-center py-4 space-y-2",
|
|
374
|
-
children: [
|
|
375
|
-
section.imageUrl && jsx("img", {
|
|
376
|
-
src: section.imageUrl,
|
|
377
|
-
alt: "",
|
|
378
|
-
className: "mx-auto max-h-40 object-cover rounded"
|
|
379
|
-
}),
|
|
380
|
-
jsx("div", {
|
|
381
|
-
className: "text-xl font-bold",
|
|
382
|
-
style: { color: brand.primaryColor },
|
|
383
|
-
children: section.headline
|
|
384
|
-
}),
|
|
385
|
-
section.subheadline && jsx("div", {
|
|
386
|
-
className: "text-sm text-muted-foreground",
|
|
387
|
-
children: section.subheadline
|
|
388
|
-
}),
|
|
389
|
-
section.ctaLabel && jsx("a", {
|
|
390
|
-
href: section.ctaUrl ?? "#",
|
|
391
|
-
className: "inline-block px-4 py-2 rounded text-sm font-medium text-white",
|
|
392
|
-
style: { background: brand.primaryColor },
|
|
393
|
-
children: section.ctaLabel
|
|
394
|
-
})
|
|
395
|
-
]
|
|
396
|
-
}, i);
|
|
397
|
-
if (section.type === "body") return jsx("p", {
|
|
398
|
-
className: "text-sm leading-relaxed whitespace-pre-wrap",
|
|
399
|
-
children: section.text
|
|
400
|
-
}, i);
|
|
401
|
-
if (section.type === "feature") return jsxs("div", {
|
|
402
|
-
className: "flex gap-3 items-start",
|
|
403
|
-
children: [section.imageUrl && jsx("img", {
|
|
404
|
-
src: section.imageUrl,
|
|
405
|
-
alt: "",
|
|
406
|
-
className: "w-16 h-16 object-cover rounded shrink-0"
|
|
407
|
-
}), jsxs("div", { children: [jsx("div", {
|
|
408
|
-
className: "text-sm font-semibold",
|
|
409
|
-
children: section.headline
|
|
410
|
-
}), jsx("div", {
|
|
411
|
-
className: "text-xs text-muted-foreground mt-0.5",
|
|
412
|
-
children: section.description
|
|
413
|
-
})] })]
|
|
414
|
-
}, i);
|
|
415
|
-
if (section.type === "testimonial") return jsxs("blockquote", {
|
|
416
|
-
className: "border-l-2 pl-3 italic text-sm text-muted-foreground",
|
|
417
|
-
style: { borderColor: brand.accentColor },
|
|
418
|
-
children: [jsxs("p", { children: [
|
|
419
|
-
"\"",
|
|
420
|
-
section.quote,
|
|
421
|
-
"\""
|
|
422
|
-
] }), jsxs("footer", {
|
|
423
|
-
className: "mt-1 text-xs not-italic font-medium",
|
|
424
|
-
children: [section.author, section.role ? `, ${section.role}` : ""]
|
|
425
|
-
})]
|
|
426
|
-
}, i);
|
|
427
|
-
if (section.type === "cta") return jsxs("div", {
|
|
428
|
-
className: "text-center py-3 space-y-1",
|
|
429
|
-
children: [jsx("a", {
|
|
430
|
-
href: section.url,
|
|
431
|
-
className: "inline-block px-5 py-2.5 rounded font-medium text-white text-sm",
|
|
432
|
-
style: { background: brand.primaryColor },
|
|
433
|
-
children: section.label
|
|
434
|
-
}), section.subtext && jsx("p", {
|
|
435
|
-
className: "text-xs text-muted-foreground",
|
|
436
|
-
children: section.subtext
|
|
437
|
-
})]
|
|
438
|
-
}, i);
|
|
439
|
-
if (section.type === "divider") return jsx("hr", { className: "border-border" }, i);
|
|
440
|
-
return null;
|
|
441
|
-
})
|
|
442
|
-
})
|
|
443
|
-
]
|
|
444
|
-
});
|
|
445
|
-
}
|
|
446
|
-
//#endregion
|
|
447
643
|
//#region src/assets/preview/video-preview.tsx
|
|
448
644
|
function VideoPreview({ content, brand, onRenderRequest, isRendering, className }) {
|
|
449
645
|
if (content.renderedUrl) return /* @__PURE__ */ jsx("div", {
|
|
@@ -534,64 +730,6 @@ function VideoPreview({ content, brand, onRenderRequest, isRendering, className
|
|
|
534
730
|
});
|
|
535
731
|
}
|
|
536
732
|
//#endregion
|
|
537
|
-
//#region src/assets/preview/copy-preview.tsx
|
|
538
|
-
const PLATFORM_LIMITS = {
|
|
539
|
-
instagram: 2200,
|
|
540
|
-
tiktok: 2200,
|
|
541
|
-
x: 280,
|
|
542
|
-
linkedin: 3e3,
|
|
543
|
-
sms: 160,
|
|
544
|
-
"email-subject": 60
|
|
545
|
-
};
|
|
546
|
-
const PLATFORM_LABELS = {
|
|
547
|
-
instagram: "Instagram",
|
|
548
|
-
tiktok: "TikTok",
|
|
549
|
-
x: "X / Twitter",
|
|
550
|
-
linkedin: "LinkedIn",
|
|
551
|
-
sms: "SMS",
|
|
552
|
-
"email-subject": "Email Subject"
|
|
553
|
-
};
|
|
554
|
-
function CopyPreview({ content, className }) {
|
|
555
|
-
const limit = PLATFORM_LIMITS[content.platform];
|
|
556
|
-
const bodyLen = content.body.length;
|
|
557
|
-
const isOverLimit = limit !== null && bodyLen > limit;
|
|
558
|
-
const warningThreshold = limit !== null ? limit * .9 : null;
|
|
559
|
-
const isNearLimit = !isOverLimit && warningThreshold !== null && bodyLen >= warningThreshold;
|
|
560
|
-
return /* @__PURE__ */ jsxs("div", {
|
|
561
|
-
className: cn("flex flex-col gap-2", className),
|
|
562
|
-
children: [/* @__PURE__ */ jsxs("div", {
|
|
563
|
-
className: "flex items-center justify-between",
|
|
564
|
-
children: [/* @__PURE__ */ jsx("span", {
|
|
565
|
-
className: "text-xs font-medium text-muted-foreground",
|
|
566
|
-
children: PLATFORM_LABELS[content.platform]
|
|
567
|
-
}), limit !== null && /* @__PURE__ */ jsxs("span", {
|
|
568
|
-
className: cn("text-xs tabular-nums", isOverLimit ? "text-destructive font-medium" : isNearLimit ? "text-warning" : "text-muted-foreground"),
|
|
569
|
-
children: [
|
|
570
|
-
bodyLen,
|
|
571
|
-
" / ",
|
|
572
|
-
limit
|
|
573
|
-
]
|
|
574
|
-
})]
|
|
575
|
-
}), /* @__PURE__ */ jsxs("div", {
|
|
576
|
-
className: "rounded border border-border p-3 space-y-2 bg-card",
|
|
577
|
-
children: [
|
|
578
|
-
content.headline && /* @__PURE__ */ jsx("div", {
|
|
579
|
-
className: "text-sm font-semibold",
|
|
580
|
-
children: content.headline
|
|
581
|
-
}),
|
|
582
|
-
/* @__PURE__ */ jsx("p", {
|
|
583
|
-
className: "text-sm whitespace-pre-wrap leading-relaxed",
|
|
584
|
-
children: content.body
|
|
585
|
-
}),
|
|
586
|
-
content.hashtags && content.hashtags.length > 0 && /* @__PURE__ */ jsx("div", {
|
|
587
|
-
className: "text-sm text-blue-500 flex flex-wrap gap-1",
|
|
588
|
-
children: content.hashtags.map((tag) => /* @__PURE__ */ jsxs("span", { children: ["#", tag] }, tag))
|
|
589
|
-
})
|
|
590
|
-
]
|
|
591
|
-
})]
|
|
592
|
-
});
|
|
593
|
-
}
|
|
594
|
-
//#endregion
|
|
595
733
|
//#region src/assets/asset-editor.tsx
|
|
596
734
|
function BrandPanel({ brand, onChange }) {
|
|
597
735
|
const [open, setOpen] = React$1.useState(false);
|
|
@@ -1126,4 +1264,4 @@ function ApprovalQueue({ assets, variantCounts = {}, onApprove, onReject, onEdit
|
|
|
1126
1264
|
});
|
|
1127
1265
|
}
|
|
1128
1266
|
//#endregion
|
|
1129
|
-
export { ASSET_FORMAT_LABEL, ASSET_STATUS_LABEL, ApprovalQueue, AssetCard, AssetEditor, CopyPreview, EmailPreview, ImagePreview, VideoPreview, imageOnlyUrl, videoPosterUrl };
|
|
1267
|
+
export { ASSET_FORMAT_LABEL, ASSET_STATUS_LABEL, ApprovalQueue, AssetCard, AssetEditor, COPY_PLATFORM_LABEL, CopyPreview, EmailPreview, ImagePreview, VideoPreview, emailPalette, imageOnlyUrl, videoPosterUrl };
|
package/dist/globals.css
CHANGED
|
@@ -1007,9 +1007,6 @@
|
|
|
1007
1007
|
.h-screen {
|
|
1008
1008
|
height: 100vh;
|
|
1009
1009
|
}
|
|
1010
|
-
.max-h-40 {
|
|
1011
|
-
max-height: calc(var(--spacing) * 40);
|
|
1012
|
-
}
|
|
1013
1010
|
.max-h-64 {
|
|
1014
1011
|
max-height: calc(var(--spacing) * 64);
|
|
1015
1012
|
}
|
|
@@ -2184,9 +2181,9 @@
|
|
|
2184
2181
|
border-left-style: var(--tw-border-style);
|
|
2185
2182
|
border-left-width: 0px;
|
|
2186
2183
|
}
|
|
2187
|
-
.border-l-
|
|
2184
|
+
.border-l-4 {
|
|
2188
2185
|
border-left-style: var(--tw-border-style);
|
|
2189
|
-
border-left-width:
|
|
2186
|
+
border-left-width: 4px;
|
|
2190
2187
|
}
|
|
2191
2188
|
.border-dashed {
|
|
2192
2189
|
--tw-border-style: dashed;
|
|
@@ -3747,9 +3744,6 @@
|
|
|
3747
3744
|
.text-blue-400 {
|
|
3748
3745
|
color: var(--color-blue-400);
|
|
3749
3746
|
}
|
|
3750
|
-
.text-blue-500 {
|
|
3751
|
-
color: var(--color-blue-500);
|
|
3752
|
-
}
|
|
3753
3747
|
.text-border {
|
|
3754
3748
|
color: hsl(var(--border));
|
|
3755
3749
|
}
|
|
@@ -3894,13 +3888,13 @@
|
|
|
3894
3888
|
.italic {
|
|
3895
3889
|
font-style: italic;
|
|
3896
3890
|
}
|
|
3897
|
-
.not-italic {
|
|
3898
|
-
font-style: normal;
|
|
3899
|
-
}
|
|
3900
3891
|
.tabular-nums {
|
|
3901
3892
|
--tw-numeric-spacing: tabular-nums;
|
|
3902
3893
|
font-variant-numeric: var(--tw-ordinal,) var(--tw-slashed-zero,) var(--tw-numeric-figure,) var(--tw-numeric-spacing,) var(--tw-numeric-fraction,);
|
|
3903
3894
|
}
|
|
3895
|
+
.no-underline {
|
|
3896
|
+
text-decoration-line: none;
|
|
3897
|
+
}
|
|
3904
3898
|
.underline {
|
|
3905
3899
|
text-decoration-line: underline;
|
|
3906
3900
|
}
|
|
@@ -5376,6 +5370,9 @@
|
|
|
5376
5370
|
.sm\:px-6 {
|
|
5377
5371
|
padding-inline: calc(var(--spacing) * 6);
|
|
5378
5372
|
}
|
|
5373
|
+
.sm\:px-8 {
|
|
5374
|
+
padding-inline: calc(var(--spacing) * 8);
|
|
5375
|
+
}
|
|
5379
5376
|
.sm\:py-1 {
|
|
5380
5377
|
padding-block: var(--spacing);
|
|
5381
5378
|
}
|
package/dist/styles.css
CHANGED
|
@@ -1007,9 +1007,6 @@
|
|
|
1007
1007
|
.h-screen {
|
|
1008
1008
|
height: 100vh;
|
|
1009
1009
|
}
|
|
1010
|
-
.max-h-40 {
|
|
1011
|
-
max-height: calc(var(--spacing) * 40);
|
|
1012
|
-
}
|
|
1013
1010
|
.max-h-64 {
|
|
1014
1011
|
max-height: calc(var(--spacing) * 64);
|
|
1015
1012
|
}
|
|
@@ -2184,9 +2181,9 @@
|
|
|
2184
2181
|
border-left-style: var(--tw-border-style);
|
|
2185
2182
|
border-left-width: 0px;
|
|
2186
2183
|
}
|
|
2187
|
-
.border-l-
|
|
2184
|
+
.border-l-4 {
|
|
2188
2185
|
border-left-style: var(--tw-border-style);
|
|
2189
|
-
border-left-width:
|
|
2186
|
+
border-left-width: 4px;
|
|
2190
2187
|
}
|
|
2191
2188
|
.border-dashed {
|
|
2192
2189
|
--tw-border-style: dashed;
|
|
@@ -3747,9 +3744,6 @@
|
|
|
3747
3744
|
.text-blue-400 {
|
|
3748
3745
|
color: var(--color-blue-400);
|
|
3749
3746
|
}
|
|
3750
|
-
.text-blue-500 {
|
|
3751
|
-
color: var(--color-blue-500);
|
|
3752
|
-
}
|
|
3753
3747
|
.text-border {
|
|
3754
3748
|
color: hsl(var(--border));
|
|
3755
3749
|
}
|
|
@@ -3894,13 +3888,13 @@
|
|
|
3894
3888
|
.italic {
|
|
3895
3889
|
font-style: italic;
|
|
3896
3890
|
}
|
|
3897
|
-
.not-italic {
|
|
3898
|
-
font-style: normal;
|
|
3899
|
-
}
|
|
3900
3891
|
.tabular-nums {
|
|
3901
3892
|
--tw-numeric-spacing: tabular-nums;
|
|
3902
3893
|
font-variant-numeric: var(--tw-ordinal,) var(--tw-slashed-zero,) var(--tw-numeric-figure,) var(--tw-numeric-spacing,) var(--tw-numeric-fraction,);
|
|
3903
3894
|
}
|
|
3895
|
+
.no-underline {
|
|
3896
|
+
text-decoration-line: none;
|
|
3897
|
+
}
|
|
3904
3898
|
.underline {
|
|
3905
3899
|
text-decoration-line: underline;
|
|
3906
3900
|
}
|
|
@@ -5376,6 +5370,9 @@
|
|
|
5376
5370
|
.sm\:px-6 {
|
|
5377
5371
|
padding-inline: calc(var(--spacing) * 6);
|
|
5378
5372
|
}
|
|
5373
|
+
.sm\:px-8 {
|
|
5374
|
+
padding-inline: calc(var(--spacing) * 8);
|
|
5375
|
+
}
|
|
5379
5376
|
.sm\:py-1 {
|
|
5380
5377
|
padding-block: var(--spacing);
|
|
5381
5378
|
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@tangle-network/sandbox-ui",
|
|
3
|
-
"version": "0.131.
|
|
3
|
+
"version": "0.131.2",
|
|
4
4
|
"license": "MIT",
|
|
5
5
|
"description": "Unified UI component library for Tangle Sandbox — primitives, chat, dashboard, terminal, editor, and workspace components",
|
|
6
6
|
"repository": {
|