@stackone/malachite 2.33.2 → 2.35.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/COMPONENTS.md +5 -5
- package/dist/components/Alert.js +77 -72
- package/dist/components/Alert.js.map +1 -1
- package/dist/components/Button.js +27 -30
- package/dist/components/Button.js.map +1 -1
- package/dist/components/Dropdown.js +254 -236
- package/dist/components/Dropdown.js.map +1 -1
- package/dist/components/Input/Input.js +47 -46
- package/dist/components/Input/Input.js.map +1 -1
- package/dist/components/PillButton.js +52 -33
- package/dist/components/PillButton.js.map +1 -1
- package/dist/components/Surface.js +100 -94
- package/dist/components/Surface.js.map +1 -1
- package/dist/components/Typography/MarkdownBlock.js +146 -119
- package/dist/components/Typography/MarkdownBlock.js.map +1 -1
- package/dist/components/Typography/index.js.map +1 -1
- package/dist/components/Typography/inlineMarkdown.js +23 -0
- package/dist/components/Typography/inlineMarkdown.js.map +1 -0
- package/dist/components/linkRel.js +9 -0
- package/dist/components/linkRel.js.map +1 -0
- package/dist/index.d.ts +16 -3
- package/dist/tailwind.css.js +1 -1
- package/package.json +2 -1
|
@@ -1,21 +1,27 @@
|
|
|
1
|
-
import { jsx as
|
|
2
|
-
import
|
|
3
|
-
import
|
|
4
|
-
import { FOCUS_RING as
|
|
5
|
-
import
|
|
6
|
-
import
|
|
7
|
-
import
|
|
8
|
-
import {
|
|
9
|
-
|
|
1
|
+
import { jsx as i, jsxs as c } from "react/jsx-runtime";
|
|
2
|
+
import I from "marked-react";
|
|
3
|
+
import d from "react";
|
|
4
|
+
import { FOCUS_RING as g } from "../focusRing.js";
|
|
5
|
+
import u from "./CodeText.js";
|
|
6
|
+
import b from "./PageTitle.js";
|
|
7
|
+
import E from "./SectionTitle.js";
|
|
8
|
+
import { getInlineMarked as k } from "./inlineMarkdown.js";
|
|
9
|
+
import { getFontSize as x, getTextColor as y } from "./textStyles.js";
|
|
10
|
+
const L = "• ", R = {
|
|
11
|
+
color: "inherit",
|
|
12
|
+
textDecoration: "underline",
|
|
13
|
+
fontWeight: 600
|
|
14
|
+
}, _ = /* @__PURE__ */ new Set(["http:", "https:", "mailto:", "tel:"]), p = (e) => {
|
|
10
15
|
if (typeof e != "string")
|
|
11
16
|
return !1;
|
|
12
|
-
const
|
|
13
|
-
return !
|
|
14
|
-
},
|
|
15
|
-
omitMargin: e
|
|
17
|
+
const r = /^([a-z][a-z0-9+.-]*):/i.exec(e.replace(/[\u0000-\u0020]/g, ""));
|
|
18
|
+
return !r || _.has(`${r[1].toLowerCase()}:`);
|
|
19
|
+
}, T = ({
|
|
20
|
+
omitMargin: e,
|
|
21
|
+
links: r
|
|
16
22
|
}) => ({
|
|
17
23
|
blockquote(t) {
|
|
18
|
-
return /* @__PURE__ */
|
|
24
|
+
return /* @__PURE__ */ i(
|
|
19
25
|
"div",
|
|
20
26
|
{
|
|
21
27
|
style: {
|
|
@@ -31,14 +37,14 @@ const L = "• ", R = /* @__PURE__ */ new Set(["http:", "https:", "mailto:", "te
|
|
|
31
37
|
);
|
|
32
38
|
},
|
|
33
39
|
paragraph(t) {
|
|
34
|
-
return /* @__PURE__ */
|
|
40
|
+
return /* @__PURE__ */ i("div", { style: { marginBottom: e ? "0px" : "16px" }, children: t }, this.elementId);
|
|
35
41
|
},
|
|
36
42
|
codespan(t) {
|
|
37
|
-
return /* @__PURE__ */
|
|
43
|
+
return /* @__PURE__ */ i(u, { variant: "inline", children: t }, this.elementId);
|
|
38
44
|
},
|
|
39
45
|
code(t) {
|
|
40
|
-
return /* @__PURE__ */
|
|
41
|
-
|
|
46
|
+
return /* @__PURE__ */ i("pre", { style: { margin: e ? 0 : "16px 0" }, children: /* @__PURE__ */ i(
|
|
47
|
+
u,
|
|
42
48
|
{
|
|
43
49
|
style: {
|
|
44
50
|
display: "block",
|
|
@@ -51,21 +57,21 @@ const L = "• ", R = /* @__PURE__ */ new Set(["http:", "https:", "mailto:", "te
|
|
|
51
57
|
) }, this.elementId);
|
|
52
58
|
},
|
|
53
59
|
heading(t, n) {
|
|
54
|
-
return n === 1 ? /* @__PURE__ */
|
|
60
|
+
return n === 1 ? /* @__PURE__ */ i(b, { children: t }, this.elementId) : /* @__PURE__ */ i(E, { children: t }, this.elementId);
|
|
55
61
|
},
|
|
56
62
|
br() {
|
|
57
|
-
return /* @__PURE__ */
|
|
63
|
+
return /* @__PURE__ */ i("br", {}, this.elementId);
|
|
58
64
|
},
|
|
59
65
|
// `text`/`strong` are deliberately NOT overridden: a wrapping Text emits a font-weight, and
|
|
60
66
|
// the nested 400 beat strong's 600 — which is why bold never rendered.
|
|
61
67
|
link(t, n) {
|
|
62
|
-
return
|
|
68
|
+
return p(t) ? r === "inert" ? /* @__PURE__ */ i("span", { style: R, children: n }, this.elementId) : (
|
|
63
69
|
// Hover is in tailwind.css: CLAUDE.md forbids JS for styling, and JS misses keyboard.
|
|
64
70
|
// FOCUS_RING because a colour change alone is not a focus indicator.
|
|
65
|
-
/* @__PURE__ */
|
|
71
|
+
/* @__PURE__ */ i(
|
|
66
72
|
"a",
|
|
67
73
|
{
|
|
68
|
-
className: `md-link rounded-xs ${
|
|
74
|
+
className: `md-link rounded-xs ${g}`,
|
|
69
75
|
href: t,
|
|
70
76
|
target: "_blank",
|
|
71
77
|
rel: "noopener noreferrer",
|
|
@@ -73,11 +79,11 @@ const L = "• ", R = /* @__PURE__ */ new Set(["http:", "https:", "mailto:", "te
|
|
|
73
79
|
},
|
|
74
80
|
this.elementId
|
|
75
81
|
)
|
|
76
|
-
) : /* @__PURE__ */
|
|
82
|
+
) : /* @__PURE__ */ i(d.Fragment, { children: n }, this.elementId);
|
|
77
83
|
},
|
|
78
84
|
// Overridden only to vet `src`. Alt text stands in for a rejected image.
|
|
79
85
|
image(t, n, s) {
|
|
80
|
-
return
|
|
86
|
+
return p(t) ? /* @__PURE__ */ i(
|
|
81
87
|
"img",
|
|
82
88
|
{
|
|
83
89
|
src: t,
|
|
@@ -86,11 +92,11 @@ const L = "• ", R = /* @__PURE__ */ new Set(["http:", "https:", "mailto:", "te
|
|
|
86
92
|
style: { maxWidth: "100%" }
|
|
87
93
|
},
|
|
88
94
|
this.elementId
|
|
89
|
-
) : /* @__PURE__ */
|
|
95
|
+
) : /* @__PURE__ */ i("span", { children: n ?? "" }, this.elementId);
|
|
90
96
|
},
|
|
91
97
|
// Preflight resets list-style/margin/padding; padding-left on the LIST is the hanging indent.
|
|
92
98
|
list(t, n, s) {
|
|
93
|
-
return /* @__PURE__ */
|
|
99
|
+
return /* @__PURE__ */ i(
|
|
94
100
|
n ? "ol" : "ul",
|
|
95
101
|
{
|
|
96
102
|
start: n && s !== 1 ? s : void 0,
|
|
@@ -107,23 +113,23 @@ const L = "• ", R = /* @__PURE__ */ new Set(["http:", "https:", "mailto:", "te
|
|
|
107
113
|
listItem(t) {
|
|
108
114
|
return (
|
|
109
115
|
// Padding too: it pushes line boxes off ClampText's line grid, slicing the last line.
|
|
110
|
-
/* @__PURE__ */
|
|
116
|
+
/* @__PURE__ */ i("li", { style: { padding: e ? "0px" : "2px 0px" }, children: t }, this.elementId)
|
|
111
117
|
);
|
|
112
118
|
}
|
|
113
119
|
}), w = () => ({
|
|
114
120
|
paragraph(e) {
|
|
115
|
-
return /* @__PURE__ */
|
|
121
|
+
return /* @__PURE__ */ c("span", { children: [
|
|
116
122
|
e,
|
|
117
123
|
" "
|
|
118
124
|
] }, this.elementId);
|
|
119
125
|
},
|
|
120
126
|
// Roles are pinned: without the real <h*> the heading leaves the a11y tree entirely.
|
|
121
|
-
heading(e,
|
|
122
|
-
return /* @__PURE__ */
|
|
127
|
+
heading(e, r) {
|
|
128
|
+
return /* @__PURE__ */ c(
|
|
123
129
|
"span",
|
|
124
130
|
{
|
|
125
131
|
role: "heading",
|
|
126
|
-
"aria-level":
|
|
132
|
+
"aria-level": r,
|
|
127
133
|
style: { fontWeight: 600 },
|
|
128
134
|
children: [
|
|
129
135
|
e,
|
|
@@ -136,169 +142,190 @@ const L = "• ", R = /* @__PURE__ */ new Set(["http:", "https:", "mailto:", "te
|
|
|
136
142
|
// The list owns markers and breaks — ordered numbering needs `start` plus the item index.
|
|
137
143
|
// A <br> opens a line box (what -webkit-line-clamp counts); `display: block` would not.
|
|
138
144
|
// Items OPEN with it, so tailwind.css suppresses the leading one on a first-child list.
|
|
139
|
-
list(e,
|
|
140
|
-
const
|
|
141
|
-
return /* @__PURE__ */
|
|
142
|
-
|
|
145
|
+
list(e, r, t) {
|
|
146
|
+
const n = d.Children.toArray(e);
|
|
147
|
+
return /* @__PURE__ */ c("span", { role: "list", style: { display: "inline" }, children: [
|
|
148
|
+
n.map((s, l) => (
|
|
143
149
|
// Index as key: one list node's rendered children never reorder.
|
|
144
|
-
/* @__PURE__ */
|
|
145
|
-
/* @__PURE__ */
|
|
146
|
-
/* @__PURE__ */
|
|
147
|
-
|
|
150
|
+
/* @__PURE__ */ c("span", { role: "listitem", style: { display: "inline" }, children: [
|
|
151
|
+
/* @__PURE__ */ i("br", {}),
|
|
152
|
+
/* @__PURE__ */ i("span", { "aria-hidden": "true", children: r ? `${(t ?? 1) + l}. ` : L }),
|
|
153
|
+
s
|
|
148
154
|
] }, l)
|
|
149
155
|
)),
|
|
150
|
-
/* @__PURE__ */
|
|
156
|
+
/* @__PURE__ */ i("br", {})
|
|
151
157
|
] }, this.elementId);
|
|
152
158
|
},
|
|
153
159
|
listItem(e) {
|
|
154
|
-
return /* @__PURE__ */
|
|
160
|
+
return /* @__PURE__ */ i(d.Fragment, { children: e }, this.elementId);
|
|
155
161
|
},
|
|
156
162
|
blockquote(e) {
|
|
157
|
-
return /* @__PURE__ */
|
|
163
|
+
return /* @__PURE__ */ c("span", { children: [
|
|
158
164
|
e,
|
|
159
165
|
" "
|
|
160
166
|
] }, this.elementId);
|
|
161
167
|
},
|
|
162
168
|
// A hard break here is incidental wrapping; honouring it spends a clamped line on nothing.
|
|
163
169
|
br() {
|
|
164
|
-
return /* @__PURE__ */
|
|
170
|
+
return /* @__PURE__ */ i("span", { children: " " }, this.elementId);
|
|
165
171
|
},
|
|
166
172
|
// Whitespace collapses, so a multi-line snippet becomes one run instead of the whole budget.
|
|
167
173
|
code(e) {
|
|
168
|
-
return /* @__PURE__ */ d
|
|
169
|
-
/* @__PURE__ */
|
|
174
|
+
return /* @__PURE__ */ c(d.Fragment, { children: [
|
|
175
|
+
/* @__PURE__ */ i(u, { variant: "inline", children: e }),
|
|
170
176
|
" "
|
|
171
177
|
] }, this.elementId);
|
|
172
178
|
},
|
|
173
179
|
hr() {
|
|
174
|
-
return /* @__PURE__ */
|
|
180
|
+
return /* @__PURE__ */ i("span", { children: " " }, this.elementId);
|
|
175
181
|
},
|
|
176
182
|
// Flattened to cell text: rows would each cost a line while carrying little at preview width.
|
|
177
183
|
table(e) {
|
|
178
|
-
return /* @__PURE__ */
|
|
184
|
+
return /* @__PURE__ */ c("span", { children: [
|
|
179
185
|
e,
|
|
180
186
|
" "
|
|
181
187
|
] }, this.elementId);
|
|
182
188
|
},
|
|
183
189
|
tableHeader(e) {
|
|
184
|
-
return /* @__PURE__ */
|
|
190
|
+
return /* @__PURE__ */ i("span", { children: e }, this.elementId);
|
|
185
191
|
},
|
|
186
192
|
tableBody(e) {
|
|
187
|
-
return /* @__PURE__ */
|
|
193
|
+
return /* @__PURE__ */ i("span", { children: e }, this.elementId);
|
|
188
194
|
},
|
|
189
195
|
tableRow(e) {
|
|
190
|
-
return /* @__PURE__ */
|
|
196
|
+
return /* @__PURE__ */ i("span", { children: e }, this.elementId);
|
|
191
197
|
},
|
|
192
198
|
tableCell(e) {
|
|
193
|
-
return /* @__PURE__ */
|
|
199
|
+
return /* @__PURE__ */ c("span", { children: [
|
|
194
200
|
e,
|
|
195
201
|
" "
|
|
196
202
|
] }, this.elementId);
|
|
197
203
|
},
|
|
198
204
|
// Replaced content grows the line box and breaks the grid the clamp measures against.
|
|
199
205
|
checkbox(e) {
|
|
200
|
-
return /* @__PURE__ */
|
|
206
|
+
return /* @__PURE__ */ i("span", { children: e ? "[x] " : "[ ] " }, this.elementId);
|
|
201
207
|
},
|
|
202
|
-
image(e,
|
|
203
|
-
return /* @__PURE__ */
|
|
208
|
+
image(e, r) {
|
|
209
|
+
return /* @__PURE__ */ i("span", { children: r ? `${r} ` : "" }, this.elementId);
|
|
204
210
|
}
|
|
205
|
-
}),
|
|
206
|
-
|
|
207
|
-
|
|
211
|
+
}), F = () => ({
|
|
212
|
+
image(e, r) {
|
|
213
|
+
return /* @__PURE__ */ i(d.Fragment, { children: r ?? "" }, this.elementId);
|
|
214
|
+
},
|
|
215
|
+
br() {
|
|
216
|
+
return /* @__PURE__ */ i(d.Fragment, { children: " " }, this.elementId);
|
|
217
|
+
}
|
|
218
|
+
}), f = (e) => {
|
|
219
|
+
const r = e.split(`
|
|
220
|
+
`), t = r.reduce((s, l) => {
|
|
208
221
|
var o;
|
|
209
|
-
return l.trim() !== "" &&
|
|
222
|
+
return l.trim() !== "" && s.push(((o = l.match(/^[ \t]*(?=\S)/gm)) == null ? void 0 : o[0].length) ?? 0), s;
|
|
210
223
|
}, []);
|
|
211
|
-
if (
|
|
224
|
+
if (t.length === 0)
|
|
212
225
|
return e;
|
|
213
|
-
const
|
|
214
|
-
return
|
|
226
|
+
const n = Math.min(...t);
|
|
227
|
+
return r.map((s) => s.replace(new RegExp(`^[ \\t]{${n}}`, "gm"), "")).join(`
|
|
215
228
|
`);
|
|
216
|
-
},
|
|
229
|
+
}, N = /^ {0,3}(?:```|~~~)/, S = /^ {2,}\S/, B = /^ {0,3}(?:=+|-+)\s*$/, C = /^ {0,3}(?:(?:-\s*){3,}|(?:\*\s*){3,}|(?:_\s*){3,})$/, A = /^[-*+]\s/, $ = /^(\d{1,9})[.)]\s/, D = /^\*\*[^*]+:\*\*$|^\*\*[^*]+\*\*:$/, h = /\*\*[^*\n]+?:\*\*|\*\*[^*\n]+?\*\*:/g, M = /^\s*(?:[-*+]|\d{1,9}[.)])\s+/, O = (e) => {
|
|
217
230
|
var l;
|
|
218
|
-
const
|
|
219
|
-
let
|
|
220
|
-
const
|
|
221
|
-
let
|
|
231
|
+
const r = ((l = M.exec(e)) == null ? void 0 : l[0]) ?? "";
|
|
232
|
+
let t = e.slice(r.length);
|
|
233
|
+
const n = [];
|
|
234
|
+
let s = !0;
|
|
222
235
|
for (; ; ) {
|
|
223
236
|
h.lastIndex = 0;
|
|
224
|
-
let o = null,
|
|
225
|
-
for (;
|
|
226
|
-
if (
|
|
227
|
-
o =
|
|
237
|
+
let o = null, a = h.exec(t);
|
|
238
|
+
for (; a; ) {
|
|
239
|
+
if (a.index > 0) {
|
|
240
|
+
o = a;
|
|
228
241
|
break;
|
|
229
242
|
}
|
|
230
|
-
|
|
243
|
+
a = h.exec(t);
|
|
231
244
|
}
|
|
232
245
|
if (!o)
|
|
233
246
|
break;
|
|
234
|
-
const m =
|
|
235
|
-
m && (
|
|
247
|
+
const m = t.slice(0, o.index).trimEnd();
|
|
248
|
+
m && (n.push((s ? r : "") + m), s = !1), t = t.slice(o.index);
|
|
236
249
|
}
|
|
237
|
-
return
|
|
238
|
-
},
|
|
239
|
-
const
|
|
240
|
-
if (!
|
|
250
|
+
return n.push((s ? r : "") + t), n;
|
|
251
|
+
}, v = (e, r) => {
|
|
252
|
+
const t = e.trim();
|
|
253
|
+
if (!t)
|
|
241
254
|
return "blank";
|
|
242
|
-
if (
|
|
243
|
-
return
|
|
244
|
-
if (
|
|
255
|
+
if (C.test(e) || B.test(e))
|
|
256
|
+
return r === "blank" ? "prose" : r;
|
|
257
|
+
if (A.test(t))
|
|
245
258
|
return "item";
|
|
246
|
-
const
|
|
247
|
-
return
|
|
248
|
-
},
|
|
249
|
-
const
|
|
250
|
-
`),
|
|
251
|
-
let
|
|
252
|
-
for (const l of
|
|
253
|
-
if (
|
|
254
|
-
|
|
259
|
+
const n = $.exec(t);
|
|
260
|
+
return n && (r !== "prose" || n[1] === "1") ? "item" : D.test(t) ? "label" : "prose";
|
|
261
|
+
}, K = (e) => {
|
|
262
|
+
const r = e.split(`
|
|
263
|
+
`), t = [];
|
|
264
|
+
let n = "blank", s = !1;
|
|
265
|
+
for (const l of r) {
|
|
266
|
+
if (N.test(l)) {
|
|
267
|
+
s = !s, t.push(l), n = "blank";
|
|
255
268
|
continue;
|
|
256
269
|
}
|
|
257
|
-
if (
|
|
258
|
-
|
|
270
|
+
if (s) {
|
|
271
|
+
t.push(l);
|
|
259
272
|
continue;
|
|
260
273
|
}
|
|
261
|
-
if (
|
|
262
|
-
|
|
274
|
+
if (S.test(l)) {
|
|
275
|
+
t.push(l);
|
|
263
276
|
continue;
|
|
264
277
|
}
|
|
265
|
-
for (const o of
|
|
266
|
-
|
|
278
|
+
for (const o of O(l))
|
|
279
|
+
n = W(o, n, t);
|
|
267
280
|
}
|
|
268
|
-
return
|
|
281
|
+
return t.join(`
|
|
269
282
|
`);
|
|
270
|
-
},
|
|
271
|
-
const
|
|
272
|
-
return
|
|
273
|
-
},
|
|
283
|
+
}, W = (e, r, t) => {
|
|
284
|
+
const n = v(e, r);
|
|
285
|
+
return n !== "blank" && r !== "blank" && n !== r && t.push(""), t.push(e), n;
|
|
286
|
+
}, j = ({
|
|
274
287
|
text: e,
|
|
275
|
-
color:
|
|
276
|
-
size:
|
|
277
|
-
omitMargin:
|
|
278
|
-
variant:
|
|
279
|
-
normalizeSource: l = !1
|
|
288
|
+
color: r,
|
|
289
|
+
size: t,
|
|
290
|
+
omitMargin: n,
|
|
291
|
+
variant: s = "block",
|
|
292
|
+
normalizeSource: l = !1,
|
|
293
|
+
links: o = "interactive"
|
|
280
294
|
}) => {
|
|
281
|
-
const
|
|
282
|
-
() => l ?
|
|
295
|
+
const a = d.useMemo(
|
|
296
|
+
() => l ? K(f(e ?? "")) : f(e ?? ""),
|
|
283
297
|
[e, l]
|
|
284
|
-
),
|
|
285
|
-
() =>
|
|
286
|
-
|
|
298
|
+
), m = d.useMemo(
|
|
299
|
+
() => ({
|
|
300
|
+
...T({ omitMargin: n, links: o }),
|
|
301
|
+
...s === "flow" ? w() : {},
|
|
302
|
+
...s === "inline" ? F() : {}
|
|
303
|
+
}),
|
|
304
|
+
[n, s, o]
|
|
287
305
|
);
|
|
288
|
-
return e ? /* @__PURE__ */
|
|
289
|
-
|
|
306
|
+
return e ? /* @__PURE__ */ i(
|
|
307
|
+
s === "block" ? "div" : "span",
|
|
290
308
|
{
|
|
291
|
-
className:
|
|
309
|
+
className: s === "flow" ? "md-root md-flow" : "md-root",
|
|
292
310
|
style: {
|
|
293
311
|
display: "contents",
|
|
294
|
-
color: y(
|
|
295
|
-
fontSize:
|
|
312
|
+
color: y(r ?? "primary"),
|
|
313
|
+
fontSize: t === "inherit" ? "inherit" : x(t ?? "small")
|
|
296
314
|
},
|
|
297
|
-
children: /* @__PURE__ */
|
|
315
|
+
children: /* @__PURE__ */ i(
|
|
316
|
+
I,
|
|
317
|
+
{
|
|
318
|
+
value: a,
|
|
319
|
+
renderer: m,
|
|
320
|
+
isInline: s === "inline",
|
|
321
|
+
gfm: s !== "inline",
|
|
322
|
+
instance: s === "inline" ? k() : void 0
|
|
323
|
+
}
|
|
324
|
+
)
|
|
298
325
|
}
|
|
299
326
|
) : null;
|
|
300
|
-
},
|
|
327
|
+
}, V = d.memo(j);
|
|
301
328
|
export {
|
|
302
|
-
|
|
329
|
+
V as default
|
|
303
330
|
};
|
|
304
331
|
//# sourceMappingURL=MarkdownBlock.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MarkdownBlock.js","sources":["../../../src/components/Typography/MarkdownBlock.tsx"],"sourcesContent":["import Markdown, { ReactRenderer } from 'marked-react';\nimport React from 'react';\nimport { FOCUS_RING } from '../focusRing';\nimport CodeText from './CodeText';\nimport PageTitle from './PageTitle';\nimport SectionTitle from './SectionTitle';\nimport type { FontSize, TextColor } from './Text';\nimport { getFontSize, getTextColor } from './textStyles';\n\nexport type MarkdownVariant = 'block' | 'flow';\n\nexport interface MarkdownProps {\n text: string;\n color?: TextColor;\n size?: FontSize;\n omitMargin?: boolean;\n variant?: MarkdownVariant;\n normalizeSource?: boolean;\n}\n\nconst FLOW_BULLET = '• ';\n\n// Third-party content, and React does not sanitize href — `javascript:` would execute.\nconst ALLOWED_SCHEMES = new Set(['http:', 'https:', 'mailto:', 'tel:']);\n\nconst isSafeHref = (href: unknown): href is string => {\n if (typeof href !== 'string') {\n return false;\n }\n const scheme = /^([a-z][a-z0-9+.-]*):/i.exec(href.replace(/[\\u0000-\\u0020]/g, ''));\n // No scheme means relative or fragment, which has nothing to vet.\n return !scheme || ALLOWED_SCHEMES.has(`${scheme[1].toLowerCase()}:`);\n};\n\n// Renderer args are always arrays: never unwrap with `x[0]`, it drops all tokens after the first.\nconst getRendererFunction = ({\n omitMargin,\n}: Pick<MarkdownProps, 'omitMargin'>): Partial<ReactRenderer> => ({\n blockquote(this: ReactRenderer, quote) {\n return (\n <div\n key={this.elementId}\n style={{\n backgroundColor: 'var(--malachite-card-dimmed-background)',\n padding: '20px',\n borderRadius: '20px',\n border: '1px solid var(--malachite-card-border)',\n margin: '16px 0',\n }}\n >\n {quote}\n </div>\n );\n },\n\n paragraph(this: ReactRenderer, text) {\n return (\n <div key={this.elementId} style={{ marginBottom: omitMargin ? '0px' : '16px' }}>\n {text}\n </div>\n );\n },\n\n codespan(this: ReactRenderer, code) {\n return (\n <CodeText key={this.elementId} variant=\"inline\">\n {code}\n </CodeText>\n );\n },\n\n code(this: ReactRenderer, code) {\n return (\n <pre key={this.elementId} style={{ margin: omitMargin ? 0 : '16px 0' }}>\n <CodeText\n style={{\n display: 'block',\n whiteSpace: 'pre',\n overflowX: 'auto',\n padding: '12px',\n }}\n >\n {code}\n </CodeText>\n </pre>\n );\n },\n\n heading(this: ReactRenderer, text, level) {\n return level === 1 ? (\n <PageTitle key={this.elementId}>{text}</PageTitle>\n ) : (\n <SectionTitle key={this.elementId}>{text}</SectionTitle>\n );\n },\n\n br(this: ReactRenderer) {\n return <br key={this.elementId} />;\n },\n\n // `text`/`strong` are deliberately NOT overridden: a wrapping Text emits a font-weight, and\n // the nested 400 beat strong's 600 — which is why bold never rendered.\n\n link(this: ReactRenderer, href, children) {\n // Keep the label for a rejected scheme rather than deleting content.\n if (!isSafeHref(href)) {\n return <React.Fragment key={this.elementId}>{children}</React.Fragment>;\n }\n return (\n // Hover is in tailwind.css: CLAUDE.md forbids JS for styling, and JS misses keyboard.\n // FOCUS_RING because a colour change alone is not a focus indicator.\n <a\n key={this.elementId}\n className={`md-link rounded-xs ${FOCUS_RING}`}\n href={href}\n target=\"_blank\"\n rel=\"noopener noreferrer\"\n >\n {children}\n </a>\n );\n },\n\n // Overridden only to vet `src`. Alt text stands in for a rejected image.\n image(this: ReactRenderer, src, alt, title) {\n if (!isSafeHref(src)) {\n return <span key={this.elementId}>{alt ?? ''}</span>;\n }\n return (\n <img\n key={this.elementId}\n src={src}\n alt={alt ?? ''}\n title={title ?? undefined}\n style={{ maxWidth: '100%' }}\n />\n );\n },\n\n // Preflight resets list-style/margin/padding; padding-left on the LIST is the hanging indent.\n list(this: ReactRenderer, children, ordered, start) {\n const Tag = ordered ? 'ol' : 'ul';\n return (\n <Tag\n key={this.elementId}\n // Forward `start` or `3. three` silently renumbers from 1.\n start={ordered && start !== 1 ? start : undefined}\n style={{\n listStyle: ordered ? 'decimal' : 'disc',\n paddingLeft: '1.25em',\n margin: 0,\n }}\n >\n {children}\n </Tag>\n );\n },\n\n listItem(this: ReactRenderer, children) {\n return (\n // Padding too: it pushes line boxes off ClampText's line grid, slicing the last line.\n <li key={this.elementId} style={{ padding: omitMargin ? '0px' : '2px 0px' }}>\n {children}\n </li>\n );\n },\n});\n\n/** Turns every block-level node inline for `flow`. Every block renderer must appear here, or the\n * one invariant — no block children — breaks silently. */\nconst getFlowOverrides = (): Partial<ReactRenderer> => ({\n paragraph(this: ReactRenderer, text) {\n return <span key={this.elementId}>{text} </span>;\n },\n\n // Roles are pinned: without the real <h*> the heading leaves the a11y tree entirely.\n heading(this: ReactRenderer, text, level) {\n return (\n <span\n key={this.elementId}\n role=\"heading\"\n aria-level={level}\n style={{ fontWeight: 600 }}\n >\n {text}{' '}\n </span>\n );\n },\n\n // The list owns markers and breaks — ordered numbering needs `start` plus the item index.\n // A <br> opens a line box (what -webkit-line-clamp counts); `display: block` would not.\n // Items OPEN with it, so tailwind.css suppresses the leading one on a first-child list.\n list(this: ReactRenderer, children, ordered, start) {\n const items = React.Children.toArray(children);\n return (\n <span key={this.elementId} role=\"list\" style={{ display: 'inline' }}>\n {items.map((item, index) => (\n // Index as key: one list node's rendered children never reorder.\n <span key={index} role=\"listitem\" style={{ display: 'inline' }}>\n <br />\n {/* Decoration — the role already conveys position. */}\n <span aria-hidden=\"true\">\n {ordered ? `${(start ?? 1) + index}. ` : FLOW_BULLET}\n </span>\n {item}\n </span>\n ))}\n {/* Closes the list so following prose starts on its own line. */}\n <br />\n </span>\n );\n },\n\n listItem(this: ReactRenderer, children) {\n return <React.Fragment key={this.elementId}>{children}</React.Fragment>;\n },\n\n blockquote(this: ReactRenderer, quote) {\n return <span key={this.elementId}>{quote} </span>;\n },\n\n // A hard break here is incidental wrapping; honouring it spends a clamped line on nothing.\n br(this: ReactRenderer) {\n return <span key={this.elementId}> </span>;\n },\n\n // Whitespace collapses, so a multi-line snippet becomes one run instead of the whole budget.\n code(this: ReactRenderer, code) {\n return (\n <React.Fragment key={this.elementId}>\n <CodeText variant=\"inline\">{code}</CodeText>{' '}\n </React.Fragment>\n );\n },\n\n hr(this: ReactRenderer) {\n return <span key={this.elementId}> </span>;\n },\n\n // Flattened to cell text: rows would each cost a line while carrying little at preview width.\n table(this: ReactRenderer, children) {\n return <span key={this.elementId}>{children} </span>;\n },\n tableHeader(this: ReactRenderer, children) {\n return <span key={this.elementId}>{children}</span>;\n },\n tableBody(this: ReactRenderer, children) {\n return <span key={this.elementId}>{children}</span>;\n },\n tableRow(this: ReactRenderer, children) {\n return <span key={this.elementId}>{children}</span>;\n },\n tableCell(this: ReactRenderer, children) {\n return <span key={this.elementId}>{children} </span>;\n },\n\n // Replaced content grows the line box and breaks the grid the clamp measures against.\n checkbox(this: ReactRenderer, checked) {\n return <span key={this.elementId}>{checked ? '[x] ' : '[ ] '}</span>;\n },\n\n image(this: ReactRenderer, _src, alt) {\n return <span key={this.elementId}>{alt ? `${alt} ` : ''}</span>;\n },\n});\n\nconst dedent = (str: string) => {\n const lines = str.split('\\n');\n const indents = lines.reduce<number[]>((acc, line) => {\n if (line.trim() !== '') {\n acc.push(line.match(/^[ \\t]*(?=\\S)/gm)?.[0].length ?? 0);\n }\n return acc;\n }, []);\n // Blank-only input has no indents to measure, and Math.min() would return Infinity — which\n // reads as a literal `{Infinity}` quantifier today, but throws the moment the `u` flag is added.\n if (indents.length === 0) {\n return str;\n }\n const indent = Math.min(...indents);\n return lines.map((line) => line.replace(new RegExp(`^[ \\\\t]{${indent}}`, 'gm'), '')).join('\\n');\n};\n\ntype BlockKind = 'blank' | 'item' | 'label' | 'prose';\n\nconst FENCE = /^ {0,3}(?:```|~~~)/;\n/** Lazy continuation or indented code — either way not a new block of a different kind. */\nconst INDENTED = /^ {2,}\\S/;\n/** Belongs to the line ABOVE; a break between them demotes the heading to a thematic rule. */\nconst SETEXT_UNDERLINE = /^ {0,3}(?:=+|-+)\\s*$/;\n/** Tested before the bullet rule so `---` is not read as a list item. */\nconst THEMATIC_BREAK = /^ {0,3}(?:(?:-\\s*){3,}|(?:\\*\\s*){3,}|(?:_\\s*){3,})$/;\nconst BULLET_MARKER = /^[-*+]\\s/;\nconst ORDERED_MARKER = /^(\\d{1,9})[.)]\\s/;\n/** The colon is REQUIRED: emphasis mid-sentence looks identical, and splitting it would turn\n * one paragraph into three. */\nconst BOLD_LABEL = /^\\*\\*[^*]+:\\*\\*$|^\\*\\*[^*]+\\*\\*:$/;\n\nconst INLINE_LABEL = /\\*\\*[^*\\n]+?:\\*\\*|\\*\\*[^*\\n]+?\\*\\*:/g;\nconst LEADING_MARKER = /^\\s*(?:[-*+]|\\d{1,9}[.)])\\s+/;\n\n/** Splits a bold label that TRAILS other text onto its own line — `...support. **Pagination\n * Mode:**`. Line classification alone cannot fix it: the whole line is prose. A label that\n * OPENS its line, or a list item, is a lead-in and left alone. */\nconst splitTrailingLabels = (line: string): string[] => {\n const marker = LEADING_MARKER.exec(line)?.[0] ?? '';\n let rest = line.slice(marker.length);\n const out: string[] = [];\n let isFirst = true;\n\n while (true) {\n INLINE_LABEL.lastIndex = 0;\n let found: RegExpExecArray | null = null;\n let match = INLINE_LABEL.exec(rest);\n while (match) {\n // index 0 means the label opens the chunk — a lead-in, not a new block.\n if (match.index > 0) {\n found = match;\n break;\n }\n match = INLINE_LABEL.exec(rest);\n }\n if (!found) {\n break;\n }\n const before = rest.slice(0, found.index).trimEnd();\n if (before) {\n out.push((isFirst ? marker : '') + before);\n isFirst = false;\n }\n rest = rest.slice(found.index);\n }\n\n out.push((isFirst ? marker : '') + rest);\n return out;\n};\n\nconst classifyLine = (line: string, previous: BlockKind): BlockKind => {\n const trimmed = line.trim();\n if (!trimmed) {\n return 'blank';\n }\n if (THEMATIC_BREAK.test(line) || SETEXT_UNDERLINE.test(line)) {\n // Continues what came before, so nothing is inserted above it.\n return previous === 'blank' ? 'prose' : previous;\n }\n if (BULLET_MARKER.test(trimmed)) {\n return 'item';\n }\n const ordered = ORDERED_MARKER.exec(trimmed);\n if (ordered) {\n // Only a list starting at 1 may interrupt a paragraph, else \"Released in\\n2024.\" would\n // become `<ol start=\"2024\">`.\n if (previous !== 'prose' || ordered[1] === '1') {\n return 'item';\n }\n }\n if (BOLD_LABEL.test(trimmed)) {\n return 'label';\n }\n return 'prose';\n};\n\n/** Inserts the blank line CommonMark needs between blocks of different kinds — generated\n * descriptions separate them with a single `\\n`, which reads as lazy continuation. Only a\n * CHANGE of kind breaks, so tight lists and wrapped paragraphs survive. Skips fences, indented\n * lines and setext underlines, where a blank line changes meaning. */\nconst explicitBlocks = (text: string): string => {\n const lines = text.split('\\n');\n const out: string[] = [];\n let previous: BlockKind = 'blank';\n let inFence = false;\n\n for (const line of lines) {\n if (FENCE.test(line)) {\n inFence = !inFence;\n out.push(line);\n // A fence is its own block on both sides.\n previous = 'blank';\n continue;\n }\n if (inFence) {\n out.push(line);\n continue;\n }\n if (INDENTED.test(line)) {\n out.push(line);\n continue;\n }\n // One line can hold a block AND a trailing label, so split before classifying.\n for (const piece of splitTrailingLabels(line)) {\n previous = pushClassified(piece, previous, out);\n }\n }\n return out.join('\\n');\n};\n\nconst pushClassified = (line: string, previous: BlockKind, out: string[]): BlockKind => {\n const kind = classifyLine(line, previous);\n if (kind !== 'blank' && previous !== 'blank' && kind !== previous) {\n out.push('');\n }\n out.push(line);\n return kind;\n};\n\nconst MarkdownBlock: React.FC<MarkdownProps> = ({\n text,\n color,\n size,\n omitMargin,\n variant = 'block',\n normalizeSource = false,\n}) => {\n // Hooks before the early return so hook order stays stable. marked-react re-lexes on every\n // render, and this can land in a virtualized Table cell.\n const source = React.useMemo(\n () => (normalizeSource ? explicitBlocks(dedent(text ?? '')) : dedent(text ?? '')),\n [text, normalizeSource],\n );\n const renderer = React.useMemo(\n () =>\n variant === 'flow'\n ? { ...getRendererFunction({ omitMargin }), ...getFlowOverrides() }\n : getRendererFunction({ omitMargin }),\n [omitMargin, variant],\n );\n\n if (!text) {\n return null;\n }\n\n // `display: contents` generates no box, so this only propagates colour and size — a real box\n // would be a block child for -webkit-line-clamp to count, and a stray div inside Alert. The\n // tag still switches: `display` does not change content-model validity.\n const Root = variant === 'flow' ? 'span' : 'div';\n return (\n <Root\n className={variant === 'flow' ? 'md-root md-flow' : 'md-root'}\n style={{\n display: 'contents',\n color: getTextColor(color ?? 'primary'),\n fontSize: getFontSize(size ?? 'small'),\n }}\n >\n <Markdown value={source} renderer={renderer} />\n </Root>\n );\n};\n\n// marked-react re-parses on every render; every prop is a primitive, so shallow equality is exact.\nexport default React.memo(MarkdownBlock);\n"],"names":["FLOW_BULLET","ALLOWED_SCHEMES","isSafeHref","href","scheme","getRendererFunction","omitMargin","quote","jsx","text","code","CodeText","level","PageTitle","SectionTitle","children","FOCUS_RING","React","src","alt","title","ordered","start","getFlowOverrides","jsxs","items","item","index","checked","_src","dedent","str","lines","indents","acc","line","_a","indent","FENCE","INDENTED","SETEXT_UNDERLINE","THEMATIC_BREAK","BULLET_MARKER","ORDERED_MARKER","BOLD_LABEL","INLINE_LABEL","LEADING_MARKER","splitTrailingLabels","marker","rest","out","isFirst","found","match","before","classifyLine","previous","trimmed","explicitBlocks","inFence","piece","pushClassified","kind","MarkdownBlock","color","size","variant","normalizeSource","source","renderer","getTextColor","getFontSize","Markdown","MarkdownBlock$1"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"MarkdownBlock.js","sources":["../../../src/components/Typography/MarkdownBlock.tsx"],"sourcesContent":["import Markdown, { ReactRenderer } from 'marked-react';\nimport React from 'react';\nimport { FOCUS_RING } from '../focusRing';\nimport CodeText from './CodeText';\nimport PageTitle from './PageTitle';\nimport SectionTitle from './SectionTitle';\nimport type { FontSize, TextColor } from './Text';\nimport { getInlineMarked } from './inlineMarkdown';\nimport { getFontSize, getTextColor } from './textStyles';\n\n/** `inline`: one line of inline syntax, with no autolinked emails or URLs. */\nexport type MarkdownVariant = 'block' | 'flow' | 'inline';\n\n/** `inert` draws links without an anchor, for markdown inside a <button>. */\nexport type MarkdownLinks = 'interactive' | 'inert';\n\nexport interface MarkdownProps {\n text: string;\n color?: TextColor;\n size?: FontSize | 'inherit';\n omitMargin?: boolean;\n variant?: MarkdownVariant;\n normalizeSource?: boolean;\n links?: MarkdownLinks;\n}\n\nconst FLOW_BULLET = '• ';\n\n// Inline, not `md-link`, for portals outside the shadow root; the link token is unreadable on tooltips.\nconst INERT_LINK_STYLE: React.CSSProperties = {\n color: 'inherit',\n textDecoration: 'underline',\n fontWeight: 600,\n};\n\n// Third-party content, and React does not sanitize href — `javascript:` would execute.\nconst ALLOWED_SCHEMES = new Set(['http:', 'https:', 'mailto:', 'tel:']);\n\nconst isSafeHref = (href: unknown): href is string => {\n if (typeof href !== 'string') {\n return false;\n }\n const scheme = /^([a-z][a-z0-9+.-]*):/i.exec(href.replace(/[\\u0000-\\u0020]/g, ''));\n // No scheme means relative or fragment, which has nothing to vet.\n return !scheme || ALLOWED_SCHEMES.has(`${scheme[1].toLowerCase()}:`);\n};\n\n// Renderer args are always arrays: never unwrap with `x[0]`, it drops all tokens after the first.\nconst getRendererFunction = ({\n omitMargin,\n links,\n}: Pick<MarkdownProps, 'omitMargin' | 'links'>): Partial<ReactRenderer> => ({\n blockquote(this: ReactRenderer, quote) {\n return (\n <div\n key={this.elementId}\n style={{\n backgroundColor: 'var(--malachite-card-dimmed-background)',\n padding: '20px',\n borderRadius: '20px',\n border: '1px solid var(--malachite-card-border)',\n margin: '16px 0',\n }}\n >\n {quote}\n </div>\n );\n },\n\n paragraph(this: ReactRenderer, text) {\n return (\n <div key={this.elementId} style={{ marginBottom: omitMargin ? '0px' : '16px' }}>\n {text}\n </div>\n );\n },\n\n codespan(this: ReactRenderer, code) {\n return (\n <CodeText key={this.elementId} variant=\"inline\">\n {code}\n </CodeText>\n );\n },\n\n code(this: ReactRenderer, code) {\n return (\n <pre key={this.elementId} style={{ margin: omitMargin ? 0 : '16px 0' }}>\n <CodeText\n style={{\n display: 'block',\n whiteSpace: 'pre',\n overflowX: 'auto',\n padding: '12px',\n }}\n >\n {code}\n </CodeText>\n </pre>\n );\n },\n\n heading(this: ReactRenderer, text, level) {\n return level === 1 ? (\n <PageTitle key={this.elementId}>{text}</PageTitle>\n ) : (\n <SectionTitle key={this.elementId}>{text}</SectionTitle>\n );\n },\n\n br(this: ReactRenderer) {\n return <br key={this.elementId} />;\n },\n\n // `text`/`strong` are deliberately NOT overridden: a wrapping Text emits a font-weight, and\n // the nested 400 beat strong's 600 — which is why bold never rendered.\n\n link(this: ReactRenderer, href, children) {\n // Keep the label for a rejected scheme rather than deleting content.\n if (!isSafeHref(href)) {\n return <React.Fragment key={this.elementId}>{children}</React.Fragment>;\n }\n if (links === 'inert') {\n return (\n <span key={this.elementId} style={INERT_LINK_STYLE}>\n {children}\n </span>\n );\n }\n return (\n // Hover is in tailwind.css: CLAUDE.md forbids JS for styling, and JS misses keyboard.\n // FOCUS_RING because a colour change alone is not a focus indicator.\n <a\n key={this.elementId}\n className={`md-link rounded-xs ${FOCUS_RING}`}\n href={href}\n target=\"_blank\"\n rel=\"noopener noreferrer\"\n >\n {children}\n </a>\n );\n },\n\n // Overridden only to vet `src`. Alt text stands in for a rejected image.\n image(this: ReactRenderer, src, alt, title) {\n if (!isSafeHref(src)) {\n return <span key={this.elementId}>{alt ?? ''}</span>;\n }\n return (\n <img\n key={this.elementId}\n src={src}\n alt={alt ?? ''}\n title={title ?? undefined}\n style={{ maxWidth: '100%' }}\n />\n );\n },\n\n // Preflight resets list-style/margin/padding; padding-left on the LIST is the hanging indent.\n list(this: ReactRenderer, children, ordered, start) {\n const Tag = ordered ? 'ol' : 'ul';\n return (\n <Tag\n key={this.elementId}\n // Forward `start` or `3. three` silently renumbers from 1.\n start={ordered && start !== 1 ? start : undefined}\n style={{\n listStyle: ordered ? 'decimal' : 'disc',\n paddingLeft: '1.25em',\n margin: 0,\n }}\n >\n {children}\n </Tag>\n );\n },\n\n listItem(this: ReactRenderer, children) {\n return (\n // Padding too: it pushes line boxes off ClampText's line grid, slicing the last line.\n <li key={this.elementId} style={{ padding: omitMargin ? '0px' : '2px 0px' }}>\n {children}\n </li>\n );\n },\n});\n\n/** Turns every block-level node inline for `flow`. Every block renderer must appear here, or the\n * one invariant — no block children — breaks silently. */\nconst getFlowOverrides = (): Partial<ReactRenderer> => ({\n paragraph(this: ReactRenderer, text) {\n return <span key={this.elementId}>{text} </span>;\n },\n\n // Roles are pinned: without the real <h*> the heading leaves the a11y tree entirely.\n heading(this: ReactRenderer, text, level) {\n return (\n <span\n key={this.elementId}\n role=\"heading\"\n aria-level={level}\n style={{ fontWeight: 600 }}\n >\n {text}{' '}\n </span>\n );\n },\n\n // The list owns markers and breaks — ordered numbering needs `start` plus the item index.\n // A <br> opens a line box (what -webkit-line-clamp counts); `display: block` would not.\n // Items OPEN with it, so tailwind.css suppresses the leading one on a first-child list.\n list(this: ReactRenderer, children, ordered, start) {\n const items = React.Children.toArray(children);\n return (\n <span key={this.elementId} role=\"list\" style={{ display: 'inline' }}>\n {items.map((item, index) => (\n // Index as key: one list node's rendered children never reorder.\n <span key={index} role=\"listitem\" style={{ display: 'inline' }}>\n <br />\n {/* Decoration — the role already conveys position. */}\n <span aria-hidden=\"true\">\n {ordered ? `${(start ?? 1) + index}. ` : FLOW_BULLET}\n </span>\n {item}\n </span>\n ))}\n {/* Closes the list so following prose starts on its own line. */}\n <br />\n </span>\n );\n },\n\n listItem(this: ReactRenderer, children) {\n return <React.Fragment key={this.elementId}>{children}</React.Fragment>;\n },\n\n blockquote(this: ReactRenderer, quote) {\n return <span key={this.elementId}>{quote} </span>;\n },\n\n // A hard break here is incidental wrapping; honouring it spends a clamped line on nothing.\n br(this: ReactRenderer) {\n return <span key={this.elementId}> </span>;\n },\n\n // Whitespace collapses, so a multi-line snippet becomes one run instead of the whole budget.\n code(this: ReactRenderer, code) {\n return (\n <React.Fragment key={this.elementId}>\n <CodeText variant=\"inline\">{code}</CodeText>{' '}\n </React.Fragment>\n );\n },\n\n hr(this: ReactRenderer) {\n return <span key={this.elementId}> </span>;\n },\n\n // Flattened to cell text: rows would each cost a line while carrying little at preview width.\n table(this: ReactRenderer, children) {\n return <span key={this.elementId}>{children} </span>;\n },\n tableHeader(this: ReactRenderer, children) {\n return <span key={this.elementId}>{children}</span>;\n },\n tableBody(this: ReactRenderer, children) {\n return <span key={this.elementId}>{children}</span>;\n },\n tableRow(this: ReactRenderer, children) {\n return <span key={this.elementId}>{children}</span>;\n },\n tableCell(this: ReactRenderer, children) {\n return <span key={this.elementId}>{children} </span>;\n },\n\n // Replaced content grows the line box and breaks the grid the clamp measures against.\n checkbox(this: ReactRenderer, checked) {\n return <span key={this.elementId}>{checked ? '[x] ' : '[ ] '}</span>;\n },\n\n image(this: ReactRenderer, _src, alt) {\n return <span key={this.elementId}>{alt ? `${alt} ` : ''}</span>;\n },\n});\n\n// An image would fetch a third-party URL and a break would wrap the line.\nconst getInlineOverrides = (): Partial<ReactRenderer> => ({\n image(this: ReactRenderer, _src, alt) {\n return <React.Fragment key={this.elementId}>{alt ?? ''}</React.Fragment>;\n },\n\n br(this: ReactRenderer) {\n return <React.Fragment key={this.elementId}> </React.Fragment>;\n },\n});\n\nconst dedent = (str: string) => {\n const lines = str.split('\\n');\n const indents = lines.reduce<number[]>((acc, line) => {\n if (line.trim() !== '') {\n acc.push(line.match(/^[ \\t]*(?=\\S)/gm)?.[0].length ?? 0);\n }\n return acc;\n }, []);\n // Blank-only input has no indents to measure, and Math.min() would return Infinity — which\n // reads as a literal `{Infinity}` quantifier today, but throws the moment the `u` flag is added.\n if (indents.length === 0) {\n return str;\n }\n const indent = Math.min(...indents);\n return lines.map((line) => line.replace(new RegExp(`^[ \\\\t]{${indent}}`, 'gm'), '')).join('\\n');\n};\n\ntype BlockKind = 'blank' | 'item' | 'label' | 'prose';\n\nconst FENCE = /^ {0,3}(?:```|~~~)/;\n/** Lazy continuation or indented code — either way not a new block of a different kind. */\nconst INDENTED = /^ {2,}\\S/;\n/** Belongs to the line ABOVE; a break between them demotes the heading to a thematic rule. */\nconst SETEXT_UNDERLINE = /^ {0,3}(?:=+|-+)\\s*$/;\n/** Tested before the bullet rule so `---` is not read as a list item. */\nconst THEMATIC_BREAK = /^ {0,3}(?:(?:-\\s*){3,}|(?:\\*\\s*){3,}|(?:_\\s*){3,})$/;\nconst BULLET_MARKER = /^[-*+]\\s/;\nconst ORDERED_MARKER = /^(\\d{1,9})[.)]\\s/;\n/** The colon is REQUIRED: emphasis mid-sentence looks identical, and splitting it would turn\n * one paragraph into three. */\nconst BOLD_LABEL = /^\\*\\*[^*]+:\\*\\*$|^\\*\\*[^*]+\\*\\*:$/;\n\nconst INLINE_LABEL = /\\*\\*[^*\\n]+?:\\*\\*|\\*\\*[^*\\n]+?\\*\\*:/g;\nconst LEADING_MARKER = /^\\s*(?:[-*+]|\\d{1,9}[.)])\\s+/;\n\n/** Splits a bold label that TRAILS other text onto its own line — `...support. **Pagination\n * Mode:**`. Line classification alone cannot fix it: the whole line is prose. A label that\n * OPENS its line, or a list item, is a lead-in and left alone. */\nconst splitTrailingLabels = (line: string): string[] => {\n const marker = LEADING_MARKER.exec(line)?.[0] ?? '';\n let rest = line.slice(marker.length);\n const out: string[] = [];\n let isFirst = true;\n\n while (true) {\n INLINE_LABEL.lastIndex = 0;\n let found: RegExpExecArray | null = null;\n let match = INLINE_LABEL.exec(rest);\n while (match) {\n // index 0 means the label opens the chunk — a lead-in, not a new block.\n if (match.index > 0) {\n found = match;\n break;\n }\n match = INLINE_LABEL.exec(rest);\n }\n if (!found) {\n break;\n }\n const before = rest.slice(0, found.index).trimEnd();\n if (before) {\n out.push((isFirst ? marker : '') + before);\n isFirst = false;\n }\n rest = rest.slice(found.index);\n }\n\n out.push((isFirst ? marker : '') + rest);\n return out;\n};\n\nconst classifyLine = (line: string, previous: BlockKind): BlockKind => {\n const trimmed = line.trim();\n if (!trimmed) {\n return 'blank';\n }\n if (THEMATIC_BREAK.test(line) || SETEXT_UNDERLINE.test(line)) {\n // Continues what came before, so nothing is inserted above it.\n return previous === 'blank' ? 'prose' : previous;\n }\n if (BULLET_MARKER.test(trimmed)) {\n return 'item';\n }\n const ordered = ORDERED_MARKER.exec(trimmed);\n if (ordered) {\n // Only a list starting at 1 may interrupt a paragraph, else \"Released in\\n2024.\" would\n // become `<ol start=\"2024\">`.\n if (previous !== 'prose' || ordered[1] === '1') {\n return 'item';\n }\n }\n if (BOLD_LABEL.test(trimmed)) {\n return 'label';\n }\n return 'prose';\n};\n\n/** Inserts the blank line CommonMark needs between blocks of different kinds — generated\n * descriptions separate them with a single `\\n`, which reads as lazy continuation. Only a\n * CHANGE of kind breaks, so tight lists and wrapped paragraphs survive. Skips fences, indented\n * lines and setext underlines, where a blank line changes meaning. */\nconst explicitBlocks = (text: string): string => {\n const lines = text.split('\\n');\n const out: string[] = [];\n let previous: BlockKind = 'blank';\n let inFence = false;\n\n for (const line of lines) {\n if (FENCE.test(line)) {\n inFence = !inFence;\n out.push(line);\n // A fence is its own block on both sides.\n previous = 'blank';\n continue;\n }\n if (inFence) {\n out.push(line);\n continue;\n }\n if (INDENTED.test(line)) {\n out.push(line);\n continue;\n }\n // One line can hold a block AND a trailing label, so split before classifying.\n for (const piece of splitTrailingLabels(line)) {\n previous = pushClassified(piece, previous, out);\n }\n }\n return out.join('\\n');\n};\n\nconst pushClassified = (line: string, previous: BlockKind, out: string[]): BlockKind => {\n const kind = classifyLine(line, previous);\n if (kind !== 'blank' && previous !== 'blank' && kind !== previous) {\n out.push('');\n }\n out.push(line);\n return kind;\n};\n\nconst MarkdownBlock: React.FC<MarkdownProps> = ({\n text,\n color,\n size,\n omitMargin,\n variant = 'block',\n normalizeSource = false,\n links = 'interactive',\n}) => {\n // Hooks before the early return so hook order stays stable. marked-react re-lexes on every\n // render, and this can land in a virtualized Table cell.\n const source = React.useMemo(\n () => (normalizeSource ? explicitBlocks(dedent(text ?? '')) : dedent(text ?? '')),\n [text, normalizeSource],\n );\n const renderer = React.useMemo(\n () => ({\n ...getRendererFunction({ omitMargin, links }),\n ...(variant === 'flow' ? getFlowOverrides() : {}),\n ...(variant === 'inline' ? getInlineOverrides() : {}),\n }),\n [omitMargin, variant, links],\n );\n\n if (!text) {\n return null;\n }\n\n // `display: contents` generates no box, so this only propagates colour and size — a real box\n // would be a block child for -webkit-line-clamp to count, and a stray div inside Alert. The\n // tag still switches: `display` does not change content-model validity.\n const Root = variant === 'block' ? 'div' : 'span';\n return (\n <Root\n className={variant === 'flow' ? 'md-root md-flow' : 'md-root'}\n style={{\n display: 'contents',\n color: getTextColor(color ?? 'primary'),\n fontSize: size === 'inherit' ? 'inherit' : getFontSize(size ?? 'small'),\n }}\n >\n <Markdown\n value={source}\n renderer={renderer}\n isInline={variant === 'inline'}\n gfm={variant !== 'inline'}\n instance={variant === 'inline' ? getInlineMarked() : undefined}\n />\n </Root>\n );\n};\n\n// marked-react re-parses on every render; every prop is a primitive, so shallow equality is exact.\nexport default React.memo(MarkdownBlock);\n"],"names":["FLOW_BULLET","INERT_LINK_STYLE","ALLOWED_SCHEMES","isSafeHref","href","scheme","getRendererFunction","omitMargin","links","quote","jsx","text","code","CodeText","level","PageTitle","SectionTitle","children","FOCUS_RING","React","src","alt","title","ordered","start","getFlowOverrides","jsxs","items","item","index","checked","_src","getInlineOverrides","dedent","str","lines","indents","acc","line","_a","indent","FENCE","INDENTED","SETEXT_UNDERLINE","THEMATIC_BREAK","BULLET_MARKER","ORDERED_MARKER","BOLD_LABEL","INLINE_LABEL","LEADING_MARKER","splitTrailingLabels","marker","rest","out","isFirst","found","match","before","classifyLine","previous","trimmed","explicitBlocks","inFence","piece","pushClassified","kind","MarkdownBlock","color","size","variant","normalizeSource","source","renderer","getTextColor","getFontSize","Markdown","getInlineMarked","MarkdownBlock$1"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sources":["../../../src/components/Typography/index.tsx"],"sourcesContent":["import { default as CodeText } from './CodeText';\nimport { default as EllipsisText } from './EllipsisText';\nimport { default as FormSectionTitle } from './FormSectionTitle';\nimport { default as LinkText } from './LinkText';\nimport { default as MarkdownBlock } from './MarkdownBlock';\nimport { default as PageTitle } from './PageTitle';\nimport { default as SecondaryText } from './SecondaryText';\nimport { default as SectionTitle } from './SectionTitle';\nimport { default as StatisticLabel } from './StatisticLabel';\nimport { default as StatisticValue } from './StatisticValue';\nimport { default as TerminalText } from './TerminalText';\nimport { default as Text } from './Text';\n\nexport type { CodeTextProps, CodeTextVariant } from './CodeText';\nexport type { MarkdownProps, MarkdownVariant } from './MarkdownBlock';\nexport type { FontSize, FontWeight, TextColor, TextProps } from './Text';\n\nexport const Typography = {\n CodeText,\n EllipsisText,\n FormSectionTitle,\n LinkText,\n MarkdownBlock,\n PageTitle,\n SecondaryText,\n SectionTitle,\n StatisticLabel,\n StatisticValue,\n TerminalText,\n Text,\n};\n\nexport default Typography;\n"],"names":["Typography","CodeText","EllipsisText","FormSectionTitle","LinkText","MarkdownBlock","PageTitle","SecondaryText","SectionTitle","StatisticLabel","StatisticValue","TerminalText","Text"],"mappings":";;;;;;;;;;;;AAiBO,MAAMA,IAAa;AAAA,EACtB,UAAAC;AAAA,EACA,cAAAC;AAAA,EACA,kBAAAC;AAAA,EACA,UAAAC;AAAA,EACA,eAAAC;AAAA,EACA,WAAAC;AAAA,EACA,eAAAC;AAAA,EACA,cAAAC;AAAA,EACA,gBAAAC;AAAA,EACA,gBAAAC;AAAA,EACA,cAAAC;AAAA,EACA,MAAAC;AACJ;"}
|
|
1
|
+
{"version":3,"file":"index.js","sources":["../../../src/components/Typography/index.tsx"],"sourcesContent":["import { default as CodeText } from './CodeText';\nimport { default as EllipsisText } from './EllipsisText';\nimport { default as FormSectionTitle } from './FormSectionTitle';\nimport { default as LinkText } from './LinkText';\nimport { default as MarkdownBlock } from './MarkdownBlock';\nimport { default as PageTitle } from './PageTitle';\nimport { default as SecondaryText } from './SecondaryText';\nimport { default as SectionTitle } from './SectionTitle';\nimport { default as StatisticLabel } from './StatisticLabel';\nimport { default as StatisticValue } from './StatisticValue';\nimport { default as TerminalText } from './TerminalText';\nimport { default as Text } from './Text';\n\nexport type { CodeTextProps, CodeTextVariant } from './CodeText';\nexport type { MarkdownLinks, MarkdownProps, MarkdownVariant } from './MarkdownBlock';\nexport type { FontSize, FontWeight, TextColor, TextProps } from './Text';\n\nexport const Typography = {\n CodeText,\n EllipsisText,\n FormSectionTitle,\n LinkText,\n MarkdownBlock,\n PageTitle,\n SecondaryText,\n SectionTitle,\n StatisticLabel,\n StatisticValue,\n TerminalText,\n Text,\n};\n\nexport default Typography;\n"],"names":["Typography","CodeText","EllipsisText","FormSectionTitle","LinkText","MarkdownBlock","PageTitle","SecondaryText","SectionTitle","StatisticLabel","StatisticValue","TerminalText","Text"],"mappings":";;;;;;;;;;;;AAiBO,MAAMA,IAAa;AAAA,EACtB,UAAAC;AAAA,EACA,cAAAC;AAAA,EACA,kBAAAC;AAAA,EACA,UAAAC;AAAA,EACA,eAAAC;AAAA,EACA,WAAAC;AAAA,EACA,eAAAC;AAAA,EACA,cAAAC;AAAA,EACA,gBAAAC;AAAA,EACA,gBAAAC;AAAA,EACA,cAAAC;AAAA,EACA,MAAAC;AACJ;"}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import { Marked as i } from "marked";
|
|
2
|
+
let r;
|
|
3
|
+
const s = () => (r ?? (r = new i({
|
|
4
|
+
gfm: !1,
|
|
5
|
+
tokenizer: {
|
|
6
|
+
// `undefined` is "no match"; `false` would fall back to the built-in, which takes `_`.
|
|
7
|
+
emStrong: (e) => e.startsWith("_") ? void 0 : !1
|
|
8
|
+
}
|
|
9
|
+
})), r), a = {
|
|
10
|
+
"&": "&",
|
|
11
|
+
"<": "<",
|
|
12
|
+
">": ">",
|
|
13
|
+
""": '"',
|
|
14
|
+
"'": "'"
|
|
15
|
+
}, o = (e) => e.replace(/&(?:amp|lt|gt|quot|#0*39);/g, (t) => a[t] ?? "'"), n = (e) => e.type === "br" ? " " : e.type === "text" || e.type === "codespan" ? o(e.text) : e.type === "image" ? e.text : "tokens" in e && e.tokens ? e.tokens.map(n).join("") : "text" in e ? e.text : "", l = (e) => {
|
|
16
|
+
const t = s();
|
|
17
|
+
return t.Lexer.lexInline(e, t.defaults).map(n).join("").replace(/\s+/g, " ");
|
|
18
|
+
};
|
|
19
|
+
export {
|
|
20
|
+
s as getInlineMarked,
|
|
21
|
+
l as inlineMarkdownText
|
|
22
|
+
};
|
|
23
|
+
//# sourceMappingURL=inlineMarkdown.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"inlineMarkdown.js","sources":["../../../src/components/Typography/inlineMarkdown.ts"],"sourcesContent":["import { Marked, type Token } from 'marked';\n\nlet instance: Marked | undefined;\n\n/** One line of inline markdown with `_` kept literal: authored copy emphasises with `*`, and the\n * ids, emails and URLs set in such a line are full of underscores. */\nexport const getInlineMarked = (): Marked => {\n instance ??= new Marked({\n gfm: false,\n tokenizer: {\n // `undefined` is \"no match\"; `false` would fall back to the built-in, which takes `_`.\n emStrong: (src) => (src.startsWith('_') ? undefined : false),\n },\n });\n return instance;\n};\n\n// The entities marked-react decodes in text and code spans, and only those.\nconst RENDERED_ENTITIES: Record<string, string> = {\n '&': '&',\n '<': '<',\n '>': '>',\n '"': '\"',\n ''': \"'\",\n};\n\nconst decodeRenderedEntities = (text: string) =>\n text.replace(/&(?:amp|lt|gt|quot|#0*39);/g, (entity) => RENDERED_ENTITIES[entity] ?? \"'\");\n\nconst tokenText = (token: Token): string => {\n if (token.type === 'br') {\n return ' ';\n }\n if (token.type === 'text' || token.type === 'codespan') {\n return decodeRenderedEntities(token.text);\n }\n if (token.type === 'image') {\n return token.text;\n }\n if ('tokens' in token && token.tokens) {\n return token.tokens.map(tokenText).join('');\n }\n return 'text' in token ? token.text : '';\n};\n\n/** The text a line of inline markdown shows, for matching what a reader typed. */\nexport const inlineMarkdownText = (markdown: string): string => {\n const marked = getInlineMarked();\n return marked.Lexer.lexInline(markdown, marked.defaults)\n .map(tokenText)\n .join('')\n .replace(/\\s+/g, ' ');\n};\n"],"names":["instance","getInlineMarked","Marked","src","RENDERED_ENTITIES","decodeRenderedEntities","text","entity","tokenText","token","inlineMarkdownText","markdown","marked"],"mappings":";AAEA,IAAIA;AAIG,MAAMC,IAAkB,OAC3BD,UAAa,IAAIE,EAAO;AAAA,EACpB,KAAK;AAAA,EACL,WAAW;AAAA;AAAA,IAEP,UAAU,CAACC,MAASA,EAAI,WAAW,GAAG,IAAI,SAAY;AAAA,EAAA;AAC1D,CACH,IACMH,IAILI,IAA4C;AAAA,EAC9C,SAAS;AAAA,EACT,QAAQ;AAAA,EACR,QAAQ;AAAA,EACR,UAAU;AAAA,EACV,SAAS;AACb,GAEMC,IAAyB,CAACC,MAC5BA,EAAK,QAAQ,+BAA+B,CAACC,MAAWH,EAAkBG,CAAM,KAAK,GAAG,GAEtFC,IAAY,CAACC,MACXA,EAAM,SAAS,OACR,MAEPA,EAAM,SAAS,UAAUA,EAAM,SAAS,aACjCJ,EAAuBI,EAAM,IAAI,IAExCA,EAAM,SAAS,UACRA,EAAM,OAEb,YAAYA,KAASA,EAAM,SACpBA,EAAM,OAAO,IAAID,CAAS,EAAE,KAAK,EAAE,IAEvC,UAAUC,IAAQA,EAAM,OAAO,IAI7BC,IAAqB,CAACC,MAA6B;AAC5D,QAAMC,IAASX,EAAA;AACf,SAAOW,EAAO,MAAM,UAAUD,GAAUC,EAAO,QAAQ,EAClD,IAAIJ,CAAS,EACb,KAAK,EAAE,EACP,QAAQ,QAAQ,GAAG;AAC5B;"}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
const s = (o, n) => {
|
|
2
|
+
if ((n == null ? void 0 : n.toLowerCase()) !== "_blank") return o;
|
|
3
|
+
const e = new Set(o == null ? void 0 : o.split(/\s+/).filter(Boolean));
|
|
4
|
+
return e.add("noopener"), e.add("noreferrer"), [...e].join(" ");
|
|
5
|
+
};
|
|
6
|
+
export {
|
|
7
|
+
s as resolveRel
|
|
8
|
+
};
|
|
9
|
+
//# sourceMappingURL=linkRel.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"linkRel.js","sources":["../../src/components/linkRel.ts"],"sourcesContent":["import type { HTMLAttributeAnchorTarget } from 'react';\n\n// Merged, never replaced: a caller's own `rel` must not drop `_blank`'s noopener/noreferrer.\nexport const resolveRel = (\n rel: string | undefined,\n target: HTMLAttributeAnchorTarget | undefined,\n): string | undefined => {\n // Browsers match the `_blank` keyword case-insensitively, so this must too.\n if (target?.toLowerCase() !== '_blank') return rel;\n\n const tokens = new Set(rel?.split(/\\s+/).filter(Boolean));\n tokens.add('noopener');\n tokens.add('noreferrer');\n return [...tokens].join(' ');\n};\n"],"names":["resolveRel","rel","target","tokens"],"mappings":"AAGO,MAAMA,IAAa,CACtBC,GACAC,MACqB;AAErB,OAAIA,KAAA,gBAAAA,EAAQ,mBAAkB,SAAU,QAAOD;AAE/C,QAAME,IAAS,IAAI,IAAIF,KAAA,gBAAAA,EAAK,MAAM,OAAO,OAAO,QAAQ;AACxD,SAAAE,EAAO,IAAI,UAAU,GACrBA,EAAO,IAAI,YAAY,GAChB,CAAC,GAAGA,CAAM,EAAE,KAAK,GAAG;AAC/B;"}
|