@tomehq/theme 0.3.1 → 0.3.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/{chunk-YXKONM3A.js → chunk-2AXAEADQ.js} +471 -138
- package/dist/entry.js +1 -1
- package/dist/index.d.ts +21 -1
- package/dist/index.js +1 -1
- package/package.json +5 -5
- package/src/Shell.test.tsx +183 -0
- package/src/Shell.tsx +231 -21
- package/src/entry.tsx +173 -4
- package/src/global.d.ts +11 -0
- package/dist/chunk-2APCPR2Y.js +0 -2110
- package/dist/chunk-37JI6XGT.js +0 -1720
- package/dist/chunk-3A2LPGUL.js +0 -1991
- package/dist/chunk-3I2QTWTW.js +0 -1948
- package/dist/chunk-45M5UIAB.js +0 -2110
- package/dist/chunk-462AGU3S.js +0 -1959
- package/dist/chunk-7MUTU5D4.js +0 -1720
- package/dist/chunk-ABNPB6BB.js +0 -2133
- package/dist/chunk-BZGWSKT2.js +0 -573
- package/dist/chunk-CMQCNCSY.js +0 -2127
- package/dist/chunk-CTPOZMMK.js +0 -1703
- package/dist/chunk-DO544M3G.js +0 -1702
- package/dist/chunk-DPKZBFQP.js +0 -1777
- package/dist/chunk-EK7PZUEB.js +0 -2147
- package/dist/chunk-FMOLIHQF.js +0 -2182
- package/dist/chunk-FWBTK5TL.js +0 -1444
- package/dist/chunk-GDQIBNX5.js +0 -1962
- package/dist/chunk-GHQ2MODM.js +0 -2127
- package/dist/chunk-GR2WCRGK.js +0 -2182
- package/dist/chunk-HNLKDQ64.js +0 -2139
- package/dist/chunk-INUMUXN5.js +0 -2095
- package/dist/chunk-IW3NHNOQ.js +0 -2187
- package/dist/chunk-JA4PMX6M.js +0 -1500
- package/dist/chunk-JSPFS7G5.js +0 -2102
- package/dist/chunk-JZRT4WNC.js +0 -1441
- package/dist/chunk-KQBY2JDB.js +0 -2112
- package/dist/chunk-LIMYFTPC.js +0 -1468
- package/dist/chunk-MEP7P6A7.js +0 -1500
- package/dist/chunk-NOZBIES7.js +0 -1948
- package/dist/chunk-O4GH3KYX.js +0 -1712
- package/dist/chunk-OEXM3BEC.js +0 -1702
- package/dist/chunk-Q7PYTVW3.js +0 -1771
- package/dist/chunk-QCWZYABW.js +0 -1468
- package/dist/chunk-RDF25WB2.js +0 -2085
- package/dist/chunk-RKTT3ZEX.js +0 -1500
- package/dist/chunk-S47BRMNQ.js +0 -1715
- package/dist/chunk-S4ZH5F56.js +0 -1949
- package/dist/chunk-SRD7NJHS.js +0 -1949
- package/dist/chunk-SWFYJO5H.js +0 -2187
- package/dist/chunk-TQDWPSTO.js +0 -2087
- package/dist/chunk-TTRXRPP6.js +0 -1941
- package/dist/chunk-UKYFJSUA.js +0 -509
- package/dist/chunk-VKEQHP2E.js +0 -2133
- package/dist/chunk-VUT2FMSI.js +0 -1937
- package/dist/chunk-VVCC5JHK.js +0 -1949
- package/dist/chunk-W732TVBK.js +0 -1944
- package/dist/chunk-X4VQYPKO.js +0 -1768
- package/dist/chunk-YZ3P3TNS.js +0 -1760
package/src/entry.tsx
CHANGED
|
@@ -13,11 +13,13 @@ import {
|
|
|
13
13
|
// @ts-ignore — resolved by vite-plugin-tome
|
|
14
14
|
import config from "virtual:tome/config";
|
|
15
15
|
// @ts-ignore — resolved by vite-plugin-tome
|
|
16
|
-
import { routes, navigation, versions } from "virtual:tome/routes";
|
|
16
|
+
import { routes, navigation, versions, i18n } from "virtual:tome/routes";
|
|
17
17
|
// @ts-ignore — resolved by vite-plugin-tome
|
|
18
18
|
import loadPageModule from "virtual:tome/page-loader";
|
|
19
19
|
// @ts-ignore — resolved by vite-plugin-tome
|
|
20
20
|
import docContext from "virtual:tome/doc-context";
|
|
21
|
+
// @ts-ignore — resolved by vite-plugin-tome
|
|
22
|
+
import overrides from "virtual:tome/overrides";
|
|
21
23
|
|
|
22
24
|
// TOM-8: Built-in MDX components from @tomehq/components
|
|
23
25
|
// These are injected into every MDX page automatically
|
|
@@ -32,6 +34,9 @@ import {
|
|
|
32
34
|
PackageManager,
|
|
33
35
|
TypeTable,
|
|
34
36
|
FileTree,
|
|
37
|
+
CodeSamples,
|
|
38
|
+
LinkCard,
|
|
39
|
+
CardGrid,
|
|
35
40
|
} from "@tomehq/components";
|
|
36
41
|
|
|
37
42
|
const MDX_COMPONENTS: Record<string, React.ComponentType<any>> = {
|
|
@@ -45,6 +50,9 @@ const MDX_COMPONENTS: Record<string, React.ComponentType<any>> = {
|
|
|
45
50
|
PackageManager,
|
|
46
51
|
TypeTable,
|
|
47
52
|
FileTree, // Sub-components accessible as <FileTree.File /> and <FileTree.Folder /> in MDX
|
|
53
|
+
CodeSamples,
|
|
54
|
+
LinkCard,
|
|
55
|
+
CardGrid,
|
|
48
56
|
};
|
|
49
57
|
|
|
50
58
|
// ── CONTENT STYLES ───────────────────────────────────────
|
|
@@ -60,15 +68,15 @@ const contentStyles = `
|
|
|
60
68
|
.tome-content a { color: var(--ac); text-decoration: none; }
|
|
61
69
|
.tome-content a:hover { text-decoration: underline; }
|
|
62
70
|
.tome-content .heading-anchor { display: none; }
|
|
63
|
-
.tome-content ul, .tome-content ol { color: var(--tx2); padding-
|
|
71
|
+
.tome-content ul, .tome-content ol { color: var(--tx2); padding-inline-start: 1.5em; margin-bottom: 1em; }
|
|
64
72
|
.tome-content li { margin-bottom: 0.3em; line-height: 1.7; }
|
|
65
73
|
.tome-content code { font-family: var(--font-code); font-size: 0.88em; background: var(--cdBg); padding: 0.15em 0.4em; border-radius: 2px; color: var(--ac); }
|
|
66
74
|
.tome-content pre { margin-bottom: 1.2em; border-radius: 2px; overflow-x: auto; border: 1px solid var(--bd); }
|
|
67
75
|
.tome-content pre code { background: none; padding: 1em 1.2em; display: block; font-size: 12.5px; line-height: 1.7; color: var(--cdTx); }
|
|
68
|
-
.tome-content blockquote { border-
|
|
76
|
+
.tome-content blockquote { border-inline-start: 3px solid var(--ac); padding: 0.5em 1em; margin: 1em 0; background: var(--acD); border-radius: 0 2px 2px 0; }
|
|
69
77
|
.tome-content blockquote p { color: var(--tx2); margin: 0; }
|
|
70
78
|
.tome-content table { width: 100%; border-collapse: collapse; margin-bottom: 1em; }
|
|
71
|
-
.tome-content th, .tome-content td { padding: 0.5em 0.8em; border: 1px solid var(--bd); text-align:
|
|
79
|
+
.tome-content th, .tome-content td { padding: 0.5em 0.8em; border: 1px solid var(--bd); text-align: start; font-size: 0.9em; }
|
|
72
80
|
.tome-content th { background: var(--sf); font-weight: 600; }
|
|
73
81
|
.tome-content img { max-width: 100%; border-radius: 2px; cursor: zoom-in; }
|
|
74
82
|
.tome-content hr { border: none; border-top: 1px solid var(--bd); margin: 2em 0; }
|
|
@@ -122,6 +130,74 @@ const contentStyles = `
|
|
|
122
130
|
background-repeat: repeat; background-size: 256px;
|
|
123
131
|
}
|
|
124
132
|
|
|
133
|
+
/* ── Expressive code blocks ───────────────────────────── */
|
|
134
|
+
|
|
135
|
+
/* Code block wrapper (for titled blocks) */
|
|
136
|
+
.tome-code-block-wrapper { position: relative; margin-bottom: 1.2em; border: 1px solid var(--bd); border-radius: 2px; overflow: hidden; }
|
|
137
|
+
.tome-code-block-wrapper pre { margin-bottom: 0; border: none; border-radius: 0; }
|
|
138
|
+
.tome-code-title {
|
|
139
|
+
font-family: var(--font-code); font-size: 12px; color: var(--tx2);
|
|
140
|
+
background: var(--sf); padding: 6px 12px; border-bottom: 1px solid var(--bd);
|
|
141
|
+
letter-spacing: 0.01em; font-weight: 500;
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
/* Line highlighting */
|
|
145
|
+
.tome-content pre .line.tome-line-highlight {
|
|
146
|
+
background: rgba(139, 148, 158, 0.1);
|
|
147
|
+
display: inline-block; width: 100%; margin: 0 -1.2em; padding: 0 1.2em;
|
|
148
|
+
}
|
|
149
|
+
html.dark .tome-content pre .line.tome-line-highlight {
|
|
150
|
+
background: rgba(200, 210, 220, 0.08);
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
/* Diff lines */
|
|
154
|
+
.tome-content pre .line.tome-line-added {
|
|
155
|
+
background: rgba(34, 197, 94, 0.12);
|
|
156
|
+
display: inline-block; width: 100%; margin: 0 -1.2em; padding: 0 1.2em;
|
|
157
|
+
}
|
|
158
|
+
.tome-content pre .line.tome-line-removed {
|
|
159
|
+
background: rgba(239, 68, 68, 0.12);
|
|
160
|
+
display: inline-block; width: 100%; margin: 0 -1.2em; padding: 0 1.2em;
|
|
161
|
+
}
|
|
162
|
+
html.dark .tome-content pre .line.tome-line-added { background: rgba(34, 197, 94, 0.15); }
|
|
163
|
+
html.dark .tome-content pre .line.tome-line-removed { background: rgba(239, 68, 68, 0.15); }
|
|
164
|
+
|
|
165
|
+
/* Line numbers (CSS counter) */
|
|
166
|
+
.tome-content pre[data-line-numbers] code {
|
|
167
|
+
counter-reset: line;
|
|
168
|
+
}
|
|
169
|
+
.tome-content pre[data-line-numbers] .line::before {
|
|
170
|
+
counter-increment: line;
|
|
171
|
+
content: counter(line);
|
|
172
|
+
display: inline-block; width: 2.5em; margin-inline-end: 1em;
|
|
173
|
+
text-align: end; color: var(--txM); opacity: 0.4;
|
|
174
|
+
font-size: 0.85em; user-select: none;
|
|
175
|
+
border-inline-end: 1px solid var(--bd); padding-inline-end: 0.8em; margin-inline-end: 0.8em;
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
/* Word highlighting */
|
|
179
|
+
.tome-word-highlight {
|
|
180
|
+
background: rgba(139, 148, 158, 0.2); border-radius: 2px;
|
|
181
|
+
padding: 1px 3px; margin: 0 -1px;
|
|
182
|
+
}
|
|
183
|
+
html.dark .tome-word-highlight {
|
|
184
|
+
background: rgba(200, 210, 220, 0.15);
|
|
185
|
+
}
|
|
186
|
+
|
|
187
|
+
/* Copy button */
|
|
188
|
+
.tome-content pre { position: relative; }
|
|
189
|
+
.tome-copy-btn {
|
|
190
|
+
position: absolute; top: 8px; inset-inline-end: 8px;
|
|
191
|
+
font-family: var(--font-code); font-size: 11px;
|
|
192
|
+
color: var(--tx2); background: var(--sf); border: 1px solid var(--bd);
|
|
193
|
+
padding: 3px 8px; border-radius: 2px; cursor: pointer;
|
|
194
|
+
opacity: 0; transition: opacity 0.15s;
|
|
195
|
+
z-index: 2; line-height: 1.4;
|
|
196
|
+
}
|
|
197
|
+
.tome-content pre:hover .tome-copy-btn,
|
|
198
|
+
.tome-copy-btn:focus { opacity: 1; }
|
|
199
|
+
.tome-copy-btn:hover { background: var(--sfH); }
|
|
200
|
+
|
|
125
201
|
/* Shiki dual-theme support */
|
|
126
202
|
.shiki { background: var(--cdBg) !important; }
|
|
127
203
|
|
|
@@ -143,6 +219,57 @@ const contentStyles = `
|
|
|
143
219
|
html:not(.dark) .shiki span[style*="color:#22863A"] { color: #1a6e2e !important; }
|
|
144
220
|
html:not(.dark) .shiki span[style*="color:#D73A49"] { color: #b62324 !important; }
|
|
145
221
|
html:not(.dark) .shiki span[style*="color:#005CC5"] { color: #0349b4 !important; }
|
|
222
|
+
|
|
223
|
+
/* ── Twoslash type hover tooltips ───────────────────── */
|
|
224
|
+
.twoslash-hover {
|
|
225
|
+
position: relative;
|
|
226
|
+
border-bottom: 1px dotted var(--tx2);
|
|
227
|
+
cursor: help;
|
|
228
|
+
}
|
|
229
|
+
.twoslash-popup-container {
|
|
230
|
+
position: absolute;
|
|
231
|
+
opacity: 0;
|
|
232
|
+
display: none;
|
|
233
|
+
z-index: 10;
|
|
234
|
+
left: 0;
|
|
235
|
+
top: 100%;
|
|
236
|
+
margin-top: 4px;
|
|
237
|
+
padding: 6px 10px;
|
|
238
|
+
background: var(--sf);
|
|
239
|
+
border: 1px solid var(--bd);
|
|
240
|
+
border-radius: 6px;
|
|
241
|
+
font-size: 12px;
|
|
242
|
+
font-family: var(--font-code);
|
|
243
|
+
color: var(--tx);
|
|
244
|
+
white-space: pre-wrap;
|
|
245
|
+
max-width: 500px;
|
|
246
|
+
box-shadow: 0 4px 12px rgba(0,0,0,0.15);
|
|
247
|
+
pointer-events: none;
|
|
248
|
+
}
|
|
249
|
+
.twoslash-hover:hover .twoslash-popup-container {
|
|
250
|
+
opacity: 1;
|
|
251
|
+
display: block;
|
|
252
|
+
}
|
|
253
|
+
/* Twoslash error/warning underlines */
|
|
254
|
+
.twoslash-error {
|
|
255
|
+
position: relative;
|
|
256
|
+
background: rgba(239, 68, 68, 0.1);
|
|
257
|
+
border-bottom: 2px wavy rgba(239, 68, 68, 0.6);
|
|
258
|
+
}
|
|
259
|
+
/* Twoslash highlighted identifiers */
|
|
260
|
+
.twoslash-highlighted {
|
|
261
|
+
background: rgba(139, 148, 158, 0.15);
|
|
262
|
+
border-radius: 2px;
|
|
263
|
+
padding: 1px 2px;
|
|
264
|
+
}
|
|
265
|
+
/* Twoslash type annotation line (^?) */
|
|
266
|
+
.twoslash-popup-code .shiki { background: transparent !important; padding: 0; margin: 0; }
|
|
267
|
+
.twoslash-popup-code .shiki code { padding: 0; font-size: 12px; }
|
|
268
|
+
html.dark .twoslash-popup-container {
|
|
269
|
+
background: var(--sf);
|
|
270
|
+
border-color: var(--bd);
|
|
271
|
+
box-shadow: 0 4px 12px rgba(0,0,0,0.3);
|
|
272
|
+
}
|
|
146
273
|
`;
|
|
147
274
|
|
|
148
275
|
// ── ROUTING HELPERS ──────────────────────────────────────
|
|
@@ -309,6 +436,39 @@ function App() {
|
|
|
309
436
|
return () => { cancelled = true; };
|
|
310
437
|
}, [pageData, loading, mermaidTheme]);
|
|
311
438
|
|
|
439
|
+
// Add copy buttons to all pre blocks (expressive code blocks)
|
|
440
|
+
useEffect(() => {
|
|
441
|
+
if (loading) return;
|
|
442
|
+
const preBlocks = document.querySelectorAll(".tome-content pre");
|
|
443
|
+
const buttons: HTMLButtonElement[] = [];
|
|
444
|
+
preBlocks.forEach((pre) => {
|
|
445
|
+
// Skip if already has a copy button
|
|
446
|
+
if (pre.querySelector(".tome-copy-btn")) return;
|
|
447
|
+
const btn = document.createElement("button");
|
|
448
|
+
btn.className = "tome-copy-btn";
|
|
449
|
+
btn.textContent = "Copy";
|
|
450
|
+
btn.addEventListener("click", async () => {
|
|
451
|
+
const code = pre.querySelector("code");
|
|
452
|
+
if (code) {
|
|
453
|
+
try {
|
|
454
|
+
await navigator.clipboard.writeText(code.textContent || "");
|
|
455
|
+
btn.textContent = "Copied!";
|
|
456
|
+
setTimeout(() => { btn.textContent = "Copy"; }, 2000);
|
|
457
|
+
} catch {
|
|
458
|
+
// Fallback for non-HTTPS contexts
|
|
459
|
+
btn.textContent = "Failed";
|
|
460
|
+
setTimeout(() => { btn.textContent = "Copy"; }, 2000);
|
|
461
|
+
}
|
|
462
|
+
}
|
|
463
|
+
});
|
|
464
|
+
pre.appendChild(btn);
|
|
465
|
+
buttons.push(btn);
|
|
466
|
+
});
|
|
467
|
+
return () => {
|
|
468
|
+
buttons.forEach((btn) => btn.remove());
|
|
469
|
+
};
|
|
470
|
+
}, [pageData, loading]);
|
|
471
|
+
|
|
312
472
|
const allPages = routes.map((r: any) => ({
|
|
313
473
|
id: r.id,
|
|
314
474
|
title: r.frontmatter.title,
|
|
@@ -320,6 +480,10 @@ function App() {
|
|
|
320
480
|
const currentVersion = detectCurrentVersion(currentRoute, versions);
|
|
321
481
|
const editUrl = computeEditUrl(config.editLink, currentRoute?.filePath);
|
|
322
482
|
|
|
483
|
+
// RTL: detect current locale and compute text direction
|
|
484
|
+
const currentLocale = currentRoute?.locale || i18n?.defaultLocale || "en";
|
|
485
|
+
const dir: "ltr" | "rtl" = i18n?.localeDirs?.[currentLocale] || "ltr";
|
|
486
|
+
|
|
323
487
|
// KaTeX CSS: inject stylesheet when math is enabled or math placeholders exist
|
|
324
488
|
useEffect(() => {
|
|
325
489
|
const hasMathPlaceholders = document.querySelectorAll(".tome-math[data-math]").length > 0;
|
|
@@ -391,6 +555,11 @@ function App() {
|
|
|
391
555
|
versioning={versions || undefined}
|
|
392
556
|
currentVersion={currentVersion}
|
|
393
557
|
basePath={basePath}
|
|
558
|
+
isDraft={currentRoute?.frontmatter?.draft === true}
|
|
559
|
+
dir={dir}
|
|
560
|
+
i18n={i18n || undefined}
|
|
561
|
+
currentLocale={currentLocale}
|
|
562
|
+
overrides={overrides}
|
|
394
563
|
/>
|
|
395
564
|
</>
|
|
396
565
|
);
|
package/src/global.d.ts
CHANGED
|
@@ -21,3 +21,14 @@ declare module "virtual:tome/doc-context" {
|
|
|
21
21
|
const docContext: Array<{ id: string; title: string; content: string }>;
|
|
22
22
|
export default docContext;
|
|
23
23
|
}
|
|
24
|
+
|
|
25
|
+
declare module "virtual:tome/overrides" {
|
|
26
|
+
const overrides: {
|
|
27
|
+
Header?: React.ComponentType<any>;
|
|
28
|
+
Footer?: React.ComponentType<any>;
|
|
29
|
+
Sidebar?: React.ComponentType<any>;
|
|
30
|
+
Toc?: React.ComponentType<any>;
|
|
31
|
+
PageFooter?: React.ComponentType<any>;
|
|
32
|
+
};
|
|
33
|
+
export default overrides;
|
|
34
|
+
}
|