@bendyline/squisq-react 2.11.15 → 2.11.17
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/README.md +12 -0
- package/dist/{chunk-6PUMLLJH.js → chunk-2FZUFQO3.js} +2 -2
- package/dist/{chunk-P3FJ3YKS.js → chunk-2VSD55NT.js} +123 -415
- package/dist/chunk-5FJZDX7H.js +298 -0
- package/dist/{chunk-VUMNXXK4.js → chunk-622IA3KB.js} +12 -9
- package/dist/chunk-63G5OJWY.js +123 -0
- package/dist/{chunk-KDTKUE53.js → chunk-L4LIIOU2.js} +1 -1
- package/dist/{chunk-7T26IKW2.js → chunk-PSAO2CTF.js} +1 -1
- package/dist/{chunk-WHVSQ42V.js → chunk-PZCWGBRQ.js} +2 -2
- package/dist/{chunk-WLUZTUNZ.js → chunk-QXZXQPL3.js} +6 -50
- package/dist/{chunk-U2FIZWAL.js → chunk-SVVPYDV3.js} +160 -16
- package/dist/diagram-pictures/index.d.ts +61 -0
- package/dist/diagram-pictures/index.js +213 -0
- package/dist/hooks/index.d.ts +2 -0
- package/dist/hooks/index.js +2 -2
- package/dist/index.js +24 -22
- package/dist/json-view/index.js +4 -4
- package/dist/layers/index.js +3 -3
- package/dist/markdown/index.js +3 -3
- package/dist/page/index.js +7 -6
- package/dist/player/index.js +10 -9
- package/dist/squisq-player.full.global.js +379 -378
- package/dist/squisq-player.global.js +71 -70
- package/dist/standalone-player-full.d.ts +1 -0
- package/dist/standalone-player-full.js +4 -0
- package/dist/standalone-source.js +1 -1
- package/package.json +10 -2
- package/dist/chunk-LR3AIGDD.js +0 -58
|
@@ -0,0 +1,298 @@
|
|
|
1
|
+
import {
|
|
2
|
+
ImageLayer,
|
|
3
|
+
MapLayer,
|
|
4
|
+
MermaidLayer,
|
|
5
|
+
PathLayer,
|
|
6
|
+
ShapeLayer,
|
|
7
|
+
TableLayer,
|
|
8
|
+
TextLayer,
|
|
9
|
+
TreeLayer,
|
|
10
|
+
VideoLayer,
|
|
11
|
+
getTransitionClass
|
|
12
|
+
} from "./chunk-PZCWGBRQ.js";
|
|
13
|
+
|
|
14
|
+
// src/BlockRenderer.tsx
|
|
15
|
+
import { useId, useLayoutEffect, useRef, useState } from "react";
|
|
16
|
+
import { resolveTransitionDuration } from "@bendyline/squisq/schemas";
|
|
17
|
+
import { isGeometryBoundTemplate } from "@bendyline/squisq/doc";
|
|
18
|
+
|
|
19
|
+
// src/utils/textFit.ts
|
|
20
|
+
function largestFittingTextScale(fits, maximum = 2) {
|
|
21
|
+
if (maximum <= 1 || !fits(1)) return 1;
|
|
22
|
+
if (fits(maximum)) return maximum;
|
|
23
|
+
let low = 1;
|
|
24
|
+
let high = maximum;
|
|
25
|
+
for (let attempt = 0; attempt < 10; attempt += 1) {
|
|
26
|
+
const candidate = (low + high) / 2;
|
|
27
|
+
if (fits(candidate)) low = candidate;
|
|
28
|
+
else high = candidate;
|
|
29
|
+
}
|
|
30
|
+
return Math.max(1, Math.floor(low * 100) / 100);
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
// src/BlockRenderer.tsx
|
|
34
|
+
import { jsx, jsxs } from "react/jsx-runtime";
|
|
35
|
+
var DEFAULT_VIEWPORT = {
|
|
36
|
+
width: 1920,
|
|
37
|
+
height: 1080
|
|
38
|
+
};
|
|
39
|
+
var FIT_TOLERANCE_PX = 1;
|
|
40
|
+
function applyTextScale(targets, scale) {
|
|
41
|
+
for (const target of targets) {
|
|
42
|
+
if (target.dataset.squisqTextFit === "html") {
|
|
43
|
+
const baseFontSize = Number(target.dataset.squisqBaseFontSize);
|
|
44
|
+
if (Number.isFinite(baseFontSize)) target.style.fontSize = `${baseFontSize * scale}px`;
|
|
45
|
+
} else {
|
|
46
|
+
target.style.transform = `scale(${scale})`;
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
function cssPixels(value) {
|
|
51
|
+
const parsed = parseFloat(value);
|
|
52
|
+
return Number.isFinite(parsed) ? parsed : 0;
|
|
53
|
+
}
|
|
54
|
+
function htmlTargetFits(target) {
|
|
55
|
+
const content = target.querySelector('[data-squisq-text-content="true"]');
|
|
56
|
+
if (!content || content.scrollWidth <= 0 || content.scrollHeight <= 0) return false;
|
|
57
|
+
const view = target.ownerDocument.defaultView;
|
|
58
|
+
const computed = view?.getComputedStyle(target);
|
|
59
|
+
const horizontalInset = computed ? cssPixels(computed.paddingLeft) + cssPixels(computed.paddingRight) + cssPixels(computed.borderLeftWidth) + cssPixels(computed.borderRightWidth) : 0;
|
|
60
|
+
const verticalInset = computed ? cssPixels(computed.paddingTop) + cssPixels(computed.paddingBottom) + cssPixels(computed.borderTopWidth) + cssPixels(computed.borderBottomWidth) : 0;
|
|
61
|
+
const availableWidth = Math.max(0, target.clientWidth - horizontalInset);
|
|
62
|
+
const availableHeight = Math.max(0, target.clientHeight - verticalInset);
|
|
63
|
+
if (content.scrollWidth > availableWidth + FIT_TOLERANCE_PX || content.scrollHeight > availableHeight + FIT_TOLERANCE_PX) {
|
|
64
|
+
return false;
|
|
65
|
+
}
|
|
66
|
+
for (const scrollRegion of content.querySelectorAll("[data-squisq-table-scroll]")) {
|
|
67
|
+
if (scrollRegion.clientWidth > 0 && scrollRegion.scrollWidth > scrollRegion.clientWidth + FIT_TOLERANCE_PX || scrollRegion.clientHeight > 0 && scrollRegion.scrollHeight > scrollRegion.clientHeight + FIT_TOLERANCE_PX) {
|
|
68
|
+
return false;
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
return true;
|
|
72
|
+
}
|
|
73
|
+
function svgTargetFits(target, scale) {
|
|
74
|
+
const content = target.querySelector('[data-squisq-text-content="true"]');
|
|
75
|
+
if (!content || typeof content.getBBox !== "function") return false;
|
|
76
|
+
try {
|
|
77
|
+
const box = content.getBBox();
|
|
78
|
+
const availableWidth = Number(target.dataset.squisqFitWidth);
|
|
79
|
+
const availableHeight = Number(target.dataset.squisqFitHeight);
|
|
80
|
+
return box.width > 0 && box.height > 0 && box.width * scale <= availableWidth + FIT_TOLERANCE_PX && box.height * scale <= availableHeight + FIT_TOLERANCE_PX;
|
|
81
|
+
} catch {
|
|
82
|
+
return false;
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
function renderedTextRects(targets) {
|
|
86
|
+
return targets.map(
|
|
87
|
+
(target) => target.querySelector('[data-squisq-text-content="true"]')?.getBoundingClientRect()
|
|
88
|
+
).filter((rect) => !!rect && rect.width > 0 && rect.height > 0);
|
|
89
|
+
}
|
|
90
|
+
function overlapPairs(rects) {
|
|
91
|
+
const pairs = /* @__PURE__ */ new Set();
|
|
92
|
+
for (let left = 0; left < rects.length; left += 1) {
|
|
93
|
+
for (let right = left + 1; right < rects.length; right += 1) {
|
|
94
|
+
const a = rects[left];
|
|
95
|
+
const b = rects[right];
|
|
96
|
+
if (a.left < b.right - FIT_TOLERANCE_PX && a.right > b.left + FIT_TOLERANCE_PX && a.top < b.bottom - FIT_TOLERANCE_PX && a.bottom > b.top + FIT_TOLERANCE_PX) {
|
|
97
|
+
pairs.add(`${left}:${right}`);
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
}
|
|
101
|
+
return pairs;
|
|
102
|
+
}
|
|
103
|
+
function BlockRenderer({
|
|
104
|
+
block,
|
|
105
|
+
blockTime,
|
|
106
|
+
basePath,
|
|
107
|
+
isEntering = false,
|
|
108
|
+
isExiting = false,
|
|
109
|
+
transition,
|
|
110
|
+
viewport = DEFAULT_VIEWPORT,
|
|
111
|
+
isPlaying,
|
|
112
|
+
muted = false,
|
|
113
|
+
animationsEnabled = true,
|
|
114
|
+
theme,
|
|
115
|
+
tableContentRenderer,
|
|
116
|
+
growTextToFit = false
|
|
117
|
+
}) {
|
|
118
|
+
let transitionClass = "";
|
|
119
|
+
const transitionStyle = {};
|
|
120
|
+
const activeTransition = animationsEnabled ? transition ?? block.transition : void 0;
|
|
121
|
+
if (activeTransition && isEntering) {
|
|
122
|
+
transitionClass = getTransitionClass(activeTransition.type, true, activeTransition.direction);
|
|
123
|
+
transitionStyle["--transition-duration"] = `${resolveTransitionDuration(activeTransition)}s`;
|
|
124
|
+
} else if (activeTransition && isExiting) {
|
|
125
|
+
transitionClass = getTransitionClass(activeTransition.type, false, activeTransition.direction);
|
|
126
|
+
transitionStyle["--transition-duration"] = `${resolveTransitionDuration(activeTransition)}s`;
|
|
127
|
+
}
|
|
128
|
+
const instanceId = useId().replace(/:/g, "");
|
|
129
|
+
const clipId = `vb-clip-${instanceId}-${block.id}`;
|
|
130
|
+
const svgRef = useRef(null);
|
|
131
|
+
const [textScale, setTextScale] = useState(1);
|
|
132
|
+
const growText = growTextToFit && !isGeometryBoundTemplate(block.template);
|
|
133
|
+
useLayoutEffect(() => {
|
|
134
|
+
const svg = svgRef.current;
|
|
135
|
+
let cancelled = false;
|
|
136
|
+
if (!svg) return;
|
|
137
|
+
const measure = () => {
|
|
138
|
+
if (cancelled) return;
|
|
139
|
+
const targets = Array.from(svg.querySelectorAll("[data-squisq-text-fit]"));
|
|
140
|
+
if (!growText || targets.length === 0) {
|
|
141
|
+
applyTextScale(targets, 1);
|
|
142
|
+
setTextScale(1);
|
|
143
|
+
return;
|
|
144
|
+
}
|
|
145
|
+
applyTextScale(targets, 1);
|
|
146
|
+
const baselineOverlaps = overlapPairs(renderedTextRects(targets));
|
|
147
|
+
const fits = (scale) => {
|
|
148
|
+
applyTextScale(targets, scale);
|
|
149
|
+
if (targets.some(
|
|
150
|
+
(target) => target.dataset.squisqTextFit === "html" ? !htmlTargetFits(target) : !svgTargetFits(target, scale)
|
|
151
|
+
)) {
|
|
152
|
+
return false;
|
|
153
|
+
}
|
|
154
|
+
const candidateOverlaps = overlapPairs(renderedTextRects(targets));
|
|
155
|
+
for (const pair of candidateOverlaps) {
|
|
156
|
+
if (!baselineOverlaps.has(pair)) return false;
|
|
157
|
+
}
|
|
158
|
+
return true;
|
|
159
|
+
};
|
|
160
|
+
const nextScale = largestFittingTextScale(fits);
|
|
161
|
+
applyTextScale(targets, nextScale);
|
|
162
|
+
setTextScale((current) => current === nextScale ? current : nextScale);
|
|
163
|
+
};
|
|
164
|
+
measure();
|
|
165
|
+
const fonts = svg.ownerDocument?.fonts;
|
|
166
|
+
if (fonts && fonts.status !== "loaded") void fonts.ready.then(measure);
|
|
167
|
+
return () => {
|
|
168
|
+
cancelled = true;
|
|
169
|
+
};
|
|
170
|
+
}, [block.layers, growText, viewport.height, viewport.width]);
|
|
171
|
+
return /* @__PURE__ */ jsxs(
|
|
172
|
+
"svg",
|
|
173
|
+
{
|
|
174
|
+
ref: svgRef,
|
|
175
|
+
className: `block-svg ${transitionClass}`,
|
|
176
|
+
style: transitionStyle,
|
|
177
|
+
viewBox: `0 0 ${viewport.width} ${viewport.height}`,
|
|
178
|
+
preserveAspectRatio: "xMidYMid meet",
|
|
179
|
+
overflow: "hidden",
|
|
180
|
+
"data-block-id": block.id,
|
|
181
|
+
"data-squisq-text-scale": growText ? textScale : void 0,
|
|
182
|
+
children: [
|
|
183
|
+
/* @__PURE__ */ jsx("defs", { children: /* @__PURE__ */ jsx("clipPath", { id: clipId, children: /* @__PURE__ */ jsx("rect", { x: "0", y: "0", width: viewport.width, height: viewport.height }) }) }),
|
|
184
|
+
/* @__PURE__ */ jsx("g", { clipPath: `url(#${clipId})`, children: (block.layers ?? []).map((layer) => /* @__PURE__ */ jsx(
|
|
185
|
+
LayerRenderer,
|
|
186
|
+
{
|
|
187
|
+
block,
|
|
188
|
+
layer,
|
|
189
|
+
basePath,
|
|
190
|
+
viewport,
|
|
191
|
+
blockTime,
|
|
192
|
+
isPlaying,
|
|
193
|
+
muted,
|
|
194
|
+
animationsEnabled,
|
|
195
|
+
theme,
|
|
196
|
+
tableContentRenderer,
|
|
197
|
+
textScale
|
|
198
|
+
},
|
|
199
|
+
layer.id
|
|
200
|
+
)) })
|
|
201
|
+
]
|
|
202
|
+
}
|
|
203
|
+
);
|
|
204
|
+
}
|
|
205
|
+
function LayerRenderer({
|
|
206
|
+
block,
|
|
207
|
+
layer,
|
|
208
|
+
basePath,
|
|
209
|
+
viewport,
|
|
210
|
+
blockTime,
|
|
211
|
+
isPlaying,
|
|
212
|
+
muted,
|
|
213
|
+
animationsEnabled,
|
|
214
|
+
theme,
|
|
215
|
+
tableContentRenderer,
|
|
216
|
+
textScale
|
|
217
|
+
}) {
|
|
218
|
+
const renderedLayer = animationsEnabled || !layer.animation ? layer : { ...layer, animation: void 0 };
|
|
219
|
+
switch (renderedLayer.type) {
|
|
220
|
+
case "image":
|
|
221
|
+
return /* @__PURE__ */ jsx(
|
|
222
|
+
ImageLayer,
|
|
223
|
+
{
|
|
224
|
+
layer: renderedLayer,
|
|
225
|
+
basePath,
|
|
226
|
+
viewport,
|
|
227
|
+
blockTime,
|
|
228
|
+
animationsEnabled
|
|
229
|
+
}
|
|
230
|
+
);
|
|
231
|
+
case "text":
|
|
232
|
+
return /* @__PURE__ */ jsx(
|
|
233
|
+
TextLayer,
|
|
234
|
+
{
|
|
235
|
+
layer: renderedLayer,
|
|
236
|
+
viewport,
|
|
237
|
+
blockTime,
|
|
238
|
+
textScale
|
|
239
|
+
}
|
|
240
|
+
);
|
|
241
|
+
case "shape":
|
|
242
|
+
return /* @__PURE__ */ jsx(ShapeLayer, { layer: renderedLayer, viewport, blockTime });
|
|
243
|
+
case "path":
|
|
244
|
+
return /* @__PURE__ */ jsx(PathLayer, { layer: renderedLayer, viewport, blockTime });
|
|
245
|
+
case "map":
|
|
246
|
+
return /* @__PURE__ */ jsx(
|
|
247
|
+
MapLayer,
|
|
248
|
+
{
|
|
249
|
+
layer: renderedLayer,
|
|
250
|
+
basePath,
|
|
251
|
+
viewport,
|
|
252
|
+
blockTime
|
|
253
|
+
}
|
|
254
|
+
);
|
|
255
|
+
case "video":
|
|
256
|
+
return /* @__PURE__ */ jsx(
|
|
257
|
+
VideoLayer,
|
|
258
|
+
{
|
|
259
|
+
layer: renderedLayer,
|
|
260
|
+
basePath,
|
|
261
|
+
viewport,
|
|
262
|
+
blockTime,
|
|
263
|
+
isPlaying,
|
|
264
|
+
muted
|
|
265
|
+
}
|
|
266
|
+
);
|
|
267
|
+
case "table":
|
|
268
|
+
return /* @__PURE__ */ jsx(
|
|
269
|
+
TableLayer,
|
|
270
|
+
{
|
|
271
|
+
block,
|
|
272
|
+
layer: renderedLayer,
|
|
273
|
+
viewport,
|
|
274
|
+
blockTime,
|
|
275
|
+
contentRenderer: tableContentRenderer
|
|
276
|
+
}
|
|
277
|
+
);
|
|
278
|
+
case "tree":
|
|
279
|
+
return /* @__PURE__ */ jsx(TreeLayer, { layer: renderedLayer, viewport, blockTime });
|
|
280
|
+
case "mermaid":
|
|
281
|
+
return /* @__PURE__ */ jsx(
|
|
282
|
+
MermaidLayer,
|
|
283
|
+
{
|
|
284
|
+
layer: renderedLayer,
|
|
285
|
+
viewport,
|
|
286
|
+
blockTime,
|
|
287
|
+
theme
|
|
288
|
+
}
|
|
289
|
+
);
|
|
290
|
+
default:
|
|
291
|
+
console.warn(`Unknown layer type: ${renderedLayer.type}`);
|
|
292
|
+
return null;
|
|
293
|
+
}
|
|
294
|
+
}
|
|
295
|
+
|
|
296
|
+
export {
|
|
297
|
+
BlockRenderer
|
|
298
|
+
};
|
|
@@ -1,28 +1,30 @@
|
|
|
1
1
|
import {
|
|
2
|
-
BlockRenderer,
|
|
3
2
|
LinearDocView
|
|
4
|
-
} from "./chunk-
|
|
5
|
-
import {
|
|
6
|
-
isCaptureDrivenVideo,
|
|
7
|
-
seekVideoToFrame
|
|
8
|
-
} from "./chunk-WHVSQ42V.js";
|
|
3
|
+
} from "./chunk-2VSD55NT.js";
|
|
9
4
|
import {
|
|
10
5
|
useAudioSync,
|
|
11
6
|
useDocPlayback,
|
|
12
7
|
useMediaSchedule,
|
|
13
8
|
useViewportOrientation
|
|
14
|
-
} from "./chunk-
|
|
9
|
+
} from "./chunk-SVVPYDV3.js";
|
|
15
10
|
import {
|
|
16
11
|
useAutoSurface
|
|
17
12
|
} from "./chunk-TT6ENR6T.js";
|
|
18
13
|
import {
|
|
19
14
|
MarkdownRenderer
|
|
20
|
-
} from "./chunk-
|
|
15
|
+
} from "./chunk-2FZUFQO3.js";
|
|
16
|
+
import {
|
|
17
|
+
BlockRenderer
|
|
18
|
+
} from "./chunk-5FJZDX7H.js";
|
|
19
|
+
import {
|
|
20
|
+
isCaptureDrivenVideo,
|
|
21
|
+
seekVideoToFrame
|
|
22
|
+
} from "./chunk-PZCWGBRQ.js";
|
|
21
23
|
import {
|
|
22
24
|
useMediaProvider,
|
|
23
25
|
useMediaUrl,
|
|
24
26
|
useResourcePolicy
|
|
25
|
-
} from "./chunk-
|
|
27
|
+
} from "./chunk-63G5OJWY.js";
|
|
26
28
|
|
|
27
29
|
// src/MediaClipLayer.tsx
|
|
28
30
|
import { useEffect, useRef } from "react";
|
|
@@ -2833,6 +2835,7 @@ function DocPlayerContent({
|
|
|
2833
2835
|
blocks: expandedBlocks,
|
|
2834
2836
|
suppressOutgoingForNextBlock
|
|
2835
2837
|
} = useDocPlayback(doc, currentTime, {
|
|
2838
|
+
basePath,
|
|
2836
2839
|
viewport: activeViewport,
|
|
2837
2840
|
theme: effectiveTheme,
|
|
2838
2841
|
motion: motionProp,
|
|
@@ -0,0 +1,123 @@
|
|
|
1
|
+
// src/hooks/MediaContext.tsx
|
|
2
|
+
import { createContext, useContext, useState, useEffect, useMemo } from "react";
|
|
3
|
+
import {
|
|
4
|
+
DEFAULT_INTERACTIVE_RESOURCE_POLICY,
|
|
5
|
+
isResourceUrlAllowed
|
|
6
|
+
} from "@bendyline/squisq/markdown";
|
|
7
|
+
var MediaContext = createContext(null);
|
|
8
|
+
var ResourcePolicyContext = createContext(
|
|
9
|
+
DEFAULT_INTERACTIVE_RESOURCE_POLICY
|
|
10
|
+
);
|
|
11
|
+
function useResourcePolicy() {
|
|
12
|
+
return useContext(ResourcePolicyContext);
|
|
13
|
+
}
|
|
14
|
+
function useMediaProvider() {
|
|
15
|
+
return useContext(MediaContext);
|
|
16
|
+
}
|
|
17
|
+
function useMediaUrl(relativePath, basePath) {
|
|
18
|
+
const provider = useMediaProvider();
|
|
19
|
+
const resourcePolicy = useResourcePolicy();
|
|
20
|
+
const safePath = typeof relativePath === "string" ? relativePath : "";
|
|
21
|
+
const isAbsolute = !safePath || /^(?:[a-z][a-z0-9+.-]*:|\/\/|\/)/i.test(safePath);
|
|
22
|
+
const fallback = useMemo(() => {
|
|
23
|
+
const candidate = isAbsolute ? safePath : `${basePath.replace(/\/$/, "")}/${safePath}`;
|
|
24
|
+
return isResourceUrlAllowed(candidate, resourcePolicy) ? candidate : "";
|
|
25
|
+
}, [isAbsolute, safePath, basePath, resourcePolicy]);
|
|
26
|
+
const needsProvider = !isAbsolute && !!provider;
|
|
27
|
+
const [url, setUrl] = useState(fallback);
|
|
28
|
+
useEffect(() => {
|
|
29
|
+
if (!needsProvider) {
|
|
30
|
+
setUrl(fallback);
|
|
31
|
+
return;
|
|
32
|
+
}
|
|
33
|
+
let cancelled = false;
|
|
34
|
+
setUrl(fallback);
|
|
35
|
+
provider.resolveUrl(safePath).then(
|
|
36
|
+
(resolved) => {
|
|
37
|
+
if (!cancelled) {
|
|
38
|
+
setUrl(isResourceUrlAllowed(resolved, resourcePolicy) ? resolved : "");
|
|
39
|
+
}
|
|
40
|
+
},
|
|
41
|
+
() => {
|
|
42
|
+
if (!cancelled) setUrl(fallback);
|
|
43
|
+
}
|
|
44
|
+
);
|
|
45
|
+
return () => {
|
|
46
|
+
cancelled = true;
|
|
47
|
+
};
|
|
48
|
+
}, [needsProvider, provider, safePath, fallback, resourcePolicy]);
|
|
49
|
+
return needsProvider ? url : fallback;
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
// src/mermaid/mermaidRuntime.ts
|
|
53
|
+
import { buildMermaidThemeVariables } from "@bendyline/squisq/schemas";
|
|
54
|
+
import { DEFAULT_THEME } from "@bendyline/squisq/doc";
|
|
55
|
+
var mermaidPromise = null;
|
|
56
|
+
var MERMAID_BASE_CONFIG = {
|
|
57
|
+
startOnLoad: false,
|
|
58
|
+
securityLevel: "strict",
|
|
59
|
+
suppressErrorRendering: true,
|
|
60
|
+
deterministicIds: false,
|
|
61
|
+
logLevel: "error"
|
|
62
|
+
};
|
|
63
|
+
async function loadMermaid() {
|
|
64
|
+
if (!mermaidPromise) {
|
|
65
|
+
mermaidPromise = import("mermaid").then(({ default: mermaid }) => mermaid).catch((error) => {
|
|
66
|
+
mermaidPromise = null;
|
|
67
|
+
throw error;
|
|
68
|
+
});
|
|
69
|
+
}
|
|
70
|
+
return mermaidPromise;
|
|
71
|
+
}
|
|
72
|
+
function enqueue(run) {
|
|
73
|
+
const host = globalThis;
|
|
74
|
+
const previous = host.__squisqMermaidWorkQueue ?? Promise.resolve();
|
|
75
|
+
const result = previous.then(run, run);
|
|
76
|
+
host.__squisqMermaidWorkQueue = result.then(
|
|
77
|
+
() => void 0,
|
|
78
|
+
() => void 0
|
|
79
|
+
);
|
|
80
|
+
return result;
|
|
81
|
+
}
|
|
82
|
+
function renderMermaidSvg(id, source, container, theme = DEFAULT_THEME) {
|
|
83
|
+
return enqueue(async () => {
|
|
84
|
+
const mermaid = await loadMermaid();
|
|
85
|
+
mermaid.initialize({
|
|
86
|
+
...MERMAID_BASE_CONFIG,
|
|
87
|
+
theme: "base",
|
|
88
|
+
themeVariables: buildMermaidThemeVariables(theme)
|
|
89
|
+
});
|
|
90
|
+
const { svg, diagramType } = await mermaid.render(id, source, container);
|
|
91
|
+
return { svg, diagramType };
|
|
92
|
+
});
|
|
93
|
+
}
|
|
94
|
+
function renderMermaidSvgForExport(id, source, theme = DEFAULT_THEME, fontFamily) {
|
|
95
|
+
return enqueue(async () => {
|
|
96
|
+
const mermaid = await loadMermaid();
|
|
97
|
+
const themeVariables = buildMermaidThemeVariables(theme);
|
|
98
|
+
mermaid.initialize({
|
|
99
|
+
...MERMAID_BASE_CONFIG,
|
|
100
|
+
theme: "base",
|
|
101
|
+
themeVariables: fontFamily ? { ...themeVariables, fontFamily } : themeVariables,
|
|
102
|
+
htmlLabels: false,
|
|
103
|
+
journey: { textPlacement: "tspan" }
|
|
104
|
+
});
|
|
105
|
+
const { svg } = await mermaid.render(id, source);
|
|
106
|
+
return svg;
|
|
107
|
+
});
|
|
108
|
+
}
|
|
109
|
+
function mermaidRenderErrorMessage(error) {
|
|
110
|
+
const raw = error instanceof Error ? error.message : String(error);
|
|
111
|
+
return raw.split(/\r?\n/).map((line) => line.trimEnd()).filter(Boolean).slice(0, 6).join("\n") || "Unknown Mermaid rendering error.";
|
|
112
|
+
}
|
|
113
|
+
|
|
114
|
+
export {
|
|
115
|
+
MediaContext,
|
|
116
|
+
ResourcePolicyContext,
|
|
117
|
+
useResourcePolicy,
|
|
118
|
+
useMediaProvider,
|
|
119
|
+
useMediaUrl,
|
|
120
|
+
renderMermaidSvg,
|
|
121
|
+
renderMermaidSvgForExport,
|
|
122
|
+
mermaidRenderErrorMessage
|
|
123
|
+
};
|
|
@@ -1,62 +1,18 @@
|
|
|
1
|
+
import {
|
|
2
|
+
mermaidRenderErrorMessage,
|
|
3
|
+
renderMermaidSvg
|
|
4
|
+
} from "./chunk-63G5OJWY.js";
|
|
5
|
+
|
|
1
6
|
// src/mermaid/MermaidDiagram.tsx
|
|
2
7
|
import { useEffect, useState } from "react";
|
|
3
|
-
import { DEFAULT_THEME as DEFAULT_THEME2 } from "@bendyline/squisq/doc";
|
|
4
|
-
|
|
5
|
-
// src/mermaid/mermaidRuntime.ts
|
|
6
|
-
import { buildMermaidThemeVariables } from "@bendyline/squisq/schemas";
|
|
7
8
|
import { DEFAULT_THEME } from "@bendyline/squisq/doc";
|
|
8
|
-
var mermaidPromise = null;
|
|
9
|
-
var MERMAID_BASE_CONFIG = {
|
|
10
|
-
startOnLoad: false,
|
|
11
|
-
securityLevel: "strict",
|
|
12
|
-
suppressErrorRendering: true,
|
|
13
|
-
deterministicIds: false,
|
|
14
|
-
logLevel: "error"
|
|
15
|
-
};
|
|
16
|
-
async function loadMermaid() {
|
|
17
|
-
if (!mermaidPromise) {
|
|
18
|
-
mermaidPromise = import("mermaid").then(({ default: mermaid }) => mermaid).catch((error) => {
|
|
19
|
-
mermaidPromise = null;
|
|
20
|
-
throw error;
|
|
21
|
-
});
|
|
22
|
-
}
|
|
23
|
-
return mermaidPromise;
|
|
24
|
-
}
|
|
25
|
-
function enqueue(run) {
|
|
26
|
-
const host = globalThis;
|
|
27
|
-
const previous = host.__squisqMermaidWorkQueue ?? Promise.resolve();
|
|
28
|
-
const result = previous.then(run, run);
|
|
29
|
-
host.__squisqMermaidWorkQueue = result.then(
|
|
30
|
-
() => void 0,
|
|
31
|
-
() => void 0
|
|
32
|
-
);
|
|
33
|
-
return result;
|
|
34
|
-
}
|
|
35
|
-
function renderMermaidSvg(id, source, container, theme = DEFAULT_THEME) {
|
|
36
|
-
return enqueue(async () => {
|
|
37
|
-
const mermaid = await loadMermaid();
|
|
38
|
-
mermaid.initialize({
|
|
39
|
-
...MERMAID_BASE_CONFIG,
|
|
40
|
-
theme: "base",
|
|
41
|
-
themeVariables: buildMermaidThemeVariables(theme)
|
|
42
|
-
});
|
|
43
|
-
const { svg, diagramType } = await mermaid.render(id, source, container);
|
|
44
|
-
return { svg, diagramType };
|
|
45
|
-
});
|
|
46
|
-
}
|
|
47
|
-
function mermaidRenderErrorMessage(error) {
|
|
48
|
-
const raw = error instanceof Error ? error.message : String(error);
|
|
49
|
-
return raw.split(/\r?\n/).map((line) => line.trimEnd()).filter(Boolean).slice(0, 6).join("\n") || "Unknown Mermaid rendering error.";
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
// src/mermaid/MermaidDiagram.tsx
|
|
53
9
|
import { jsx, jsxs } from "react/jsx-runtime";
|
|
54
10
|
var renderSequence = 0;
|
|
55
11
|
function MermaidDiagram({
|
|
56
12
|
source,
|
|
57
13
|
className,
|
|
58
14
|
ariaLabel = "Mermaid diagram",
|
|
59
|
-
theme =
|
|
15
|
+
theme = DEFAULT_THEME
|
|
60
16
|
}) {
|
|
61
17
|
const [svg, setSvg] = useState("");
|
|
62
18
|
const [error, setError] = useState("");
|