@slidev/cli 52.0.1 → 52.2.3
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 +2 -2
- package/dist/build-DWALVMBw.js +110 -0
- package/dist/cli.d.ts +1 -1
- package/dist/cli.js +12 -13
- package/dist/{export-D1Zqc-n1.js → export-DCKSbBi5.js} +9 -18
- package/dist/index.js +3 -3
- package/dist/{resolver-BShaA6qw.js → resolver-3bFppHAb.js} +3 -6
- package/dist/{serve-w6U-hl_b.js → serve-CG6WbHRY.js} +1 -1
- package/dist/{shared-D-V1kZyI.js → shared-BjrV0NzM.js} +113 -103
- package/package.json +39 -39
- package/dist/build-DyiO9Vju.js +0 -62
package/README.md
CHANGED
|
@@ -26,9 +26,9 @@ Presentation <b>slide</b>s for <b>dev</b>elopers 🧑💻👩💻👨
|
|
|
26
26
|
<table>
|
|
27
27
|
<tbody>
|
|
28
28
|
<td align="center">
|
|
29
|
-
<img width="2000" height="0" alt="" aria-
|
|
29
|
+
<img width="2000" height="0" alt="" aria-hidden><br>
|
|
30
30
|
<sub>Made possible by my <a href="https://github.com/sponsors/antfu">Sponsor Program 💖</a></sub><br>
|
|
31
|
-
<img width="2000" height="0" alt="" aria-
|
|
31
|
+
<img width="2000" height="0" alt="" aria-hidden>
|
|
32
32
|
</td>
|
|
33
33
|
</tbody>
|
|
34
34
|
</table>
|
|
@@ -0,0 +1,110 @@
|
|
|
1
|
+
import { resolveViteConfigs } from "./shared-BjrV0NzM.js";
|
|
2
|
+
import "./resolver-3bFppHAb.js";
|
|
3
|
+
import fs from "node:fs/promises";
|
|
4
|
+
import { join, resolve } from "node:path";
|
|
5
|
+
import { build as build$1 } from "vite";
|
|
6
|
+
import { existsSync } from "node:fs";
|
|
7
|
+
import http from "node:http";
|
|
8
|
+
import connect from "connect";
|
|
9
|
+
import sirv from "sirv";
|
|
10
|
+
|
|
11
|
+
//#region node/commands/build.ts
|
|
12
|
+
async function build(options, viteConfig = {}, args) {
|
|
13
|
+
const indexPath = resolve(options.userRoot, "index.html");
|
|
14
|
+
let originalIndexHTML;
|
|
15
|
+
if (existsSync(indexPath)) originalIndexHTML = await fs.readFile(indexPath, "utf-8");
|
|
16
|
+
await fs.writeFile(indexPath, options.utils.indexHtml, "utf-8");
|
|
17
|
+
let config = void 0;
|
|
18
|
+
try {
|
|
19
|
+
const inlineConfig = await resolveViteConfigs(options, {
|
|
20
|
+
plugins: [{
|
|
21
|
+
name: "resolve-config",
|
|
22
|
+
configResolved(_config) {
|
|
23
|
+
config = _config;
|
|
24
|
+
}
|
|
25
|
+
}],
|
|
26
|
+
build: { chunkSizeWarningLimit: 2e3 }
|
|
27
|
+
}, viteConfig, "build");
|
|
28
|
+
await build$1(inlineConfig);
|
|
29
|
+
} finally {
|
|
30
|
+
if (originalIndexHTML != null) await fs.writeFile(indexPath, originalIndexHTML, "utf-8");
|
|
31
|
+
else await fs.unlink(indexPath);
|
|
32
|
+
}
|
|
33
|
+
const outDir = resolve(options.userRoot, config.build.outDir);
|
|
34
|
+
if (options.data.config.seoMeta?.ogImage === "auto" || options.data.config.seoMeta?.ogImage?.startsWith(".")) {
|
|
35
|
+
const filename = options.data.config.seoMeta?.ogImage === "auto" ? "og-image.png" : options.data.config.seoMeta.ogImage;
|
|
36
|
+
const projectOgImagePath = resolve(options.userRoot, filename);
|
|
37
|
+
const outputOgImagePath = resolve(outDir, filename);
|
|
38
|
+
if (await fs.access(projectOgImagePath).then(() => true).catch(() => false)) await fs.copyFile(projectOgImagePath, outputOgImagePath);
|
|
39
|
+
else if (options.data.config.seoMeta?.ogImage === "auto") {
|
|
40
|
+
const port = 12445;
|
|
41
|
+
const app = connect();
|
|
42
|
+
const server = http.createServer(app);
|
|
43
|
+
app.use(config.base, sirv(outDir, {
|
|
44
|
+
etag: true,
|
|
45
|
+
single: true,
|
|
46
|
+
dev: true
|
|
47
|
+
}));
|
|
48
|
+
server.listen(port);
|
|
49
|
+
const { exportSlides } = await import("./export-DCKSbBi5.js");
|
|
50
|
+
const tempDir = resolve(outDir, "temp");
|
|
51
|
+
await fs.mkdir(tempDir, { recursive: true });
|
|
52
|
+
await exportSlides({
|
|
53
|
+
port,
|
|
54
|
+
base: config.base,
|
|
55
|
+
slides: options.data.slides,
|
|
56
|
+
total: options.data.slides.length,
|
|
57
|
+
format: "png",
|
|
58
|
+
output: tempDir,
|
|
59
|
+
range: "1",
|
|
60
|
+
width: options.data.config.canvasWidth,
|
|
61
|
+
height: Math.round(options.data.config.canvasWidth / options.data.config.aspectRatio),
|
|
62
|
+
routerMode: options.data.config.routerMode,
|
|
63
|
+
waitUntil: "networkidle",
|
|
64
|
+
timeout: args.timeout || 3e4,
|
|
65
|
+
perSlide: true,
|
|
66
|
+
omitBackground: false,
|
|
67
|
+
dark: args.dark
|
|
68
|
+
});
|
|
69
|
+
const pngFile = (await fs.readdir(tempDir)).find((file) => file.endsWith(".png"));
|
|
70
|
+
if (pngFile) {
|
|
71
|
+
const generatedPath = resolve(tempDir, pngFile);
|
|
72
|
+
await fs.copyFile(generatedPath, projectOgImagePath);
|
|
73
|
+
await fs.copyFile(generatedPath, outputOgImagePath);
|
|
74
|
+
}
|
|
75
|
+
await fs.rm(tempDir, {
|
|
76
|
+
recursive: true,
|
|
77
|
+
force: true
|
|
78
|
+
});
|
|
79
|
+
server.close();
|
|
80
|
+
} else throw new Error(`[Slidev] ogImage: ${filename} not found`);
|
|
81
|
+
}
|
|
82
|
+
await fs.copyFile(resolve(outDir, "index.html"), resolve(outDir, "404.html"));
|
|
83
|
+
const redirectsPath = resolve(outDir, "_redirects");
|
|
84
|
+
if (!existsSync(redirectsPath)) await fs.writeFile(redirectsPath, `${config.base}* ${config.base}index.html 200\n`, "utf-8");
|
|
85
|
+
if ([
|
|
86
|
+
true,
|
|
87
|
+
"true",
|
|
88
|
+
"auto"
|
|
89
|
+
].includes(options.data.config.download)) {
|
|
90
|
+
const { exportSlides, getExportOptions } = await import("./export-DCKSbBi5.js");
|
|
91
|
+
const port = 12445;
|
|
92
|
+
const app = connect();
|
|
93
|
+
const server = http.createServer(app);
|
|
94
|
+
app.use(config.base, sirv(outDir, {
|
|
95
|
+
etag: true,
|
|
96
|
+
single: true,
|
|
97
|
+
dev: true
|
|
98
|
+
}));
|
|
99
|
+
server.listen(port);
|
|
100
|
+
await exportSlides({
|
|
101
|
+
port,
|
|
102
|
+
base: config.base,
|
|
103
|
+
...getExportOptions(args, options, join(outDir, "slidev-exported.pdf"))
|
|
104
|
+
});
|
|
105
|
+
server.close();
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
|
|
109
|
+
//#endregion
|
|
110
|
+
export { build };
|
package/dist/cli.d.ts
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
export {
|
|
1
|
+
export {};
|
package/dist/cli.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { getThemeMeta, loadSetups, parser, resolveAddons, resolveOptions, resolveTheme, updateFrontmatterPatch, version } from "./shared-
|
|
2
|
-
import { getRoots, isInstalledGlobally, resolveEntry } from "./resolver-
|
|
3
|
-
import { createServer } from "./serve-
|
|
1
|
+
import { getThemeMeta, loadSetups, parser, resolveAddons, resolveOptions, resolveTheme, updateFrontmatterPatch, version } from "./shared-BjrV0NzM.js";
|
|
2
|
+
import { getRoots, isInstalledGlobally, resolveEntry } from "./resolver-3bFppHAb.js";
|
|
3
|
+
import { createServer } from "./serve-CG6WbHRY.js";
|
|
4
4
|
import { exec } from "node:child_process";
|
|
5
5
|
import fs from "node:fs/promises";
|
|
6
6
|
import os from "node:os";
|
|
@@ -22,12 +22,11 @@ function setupPreparser() {
|
|
|
22
22
|
const addons = Array.isArray(headmatter?.addons) ? headmatter.addons : [];
|
|
23
23
|
const { userRoot } = await getRoots();
|
|
24
24
|
const roots = uniq([...await resolveAddons(addons), userRoot]);
|
|
25
|
-
|
|
25
|
+
return (await loadSetups(roots, "preparser.ts", [{
|
|
26
26
|
filepath,
|
|
27
27
|
headmatter,
|
|
28
28
|
mode
|
|
29
|
-
}]);
|
|
30
|
-
return returns.flat();
|
|
29
|
+
}])).flat();
|
|
31
30
|
});
|
|
32
31
|
}
|
|
33
32
|
|
|
@@ -180,11 +179,10 @@ cli.command("* [entry]", "Start a local server for Slidev", (args) => commonOpti
|
|
|
180
179
|
}
|
|
181
180
|
async function openTunnel(port$1) {
|
|
182
181
|
const { startTunnel } = await import("untun");
|
|
183
|
-
|
|
182
|
+
return await (await startTunnel({
|
|
184
183
|
port: port$1,
|
|
185
184
|
acceptCloudflareNotice: true
|
|
186
|
-
});
|
|
187
|
-
return await tunnel$1?.getURL() ?? "";
|
|
185
|
+
}))?.getURL() ?? "";
|
|
188
186
|
}
|
|
189
187
|
const SHORTCUTS = [
|
|
190
188
|
{
|
|
@@ -295,7 +293,7 @@ cli.command("build [entry..]", "Build hostable SPA", (args) => exportOptions(com
|
|
|
295
293
|
describe: "enable the inspect plugin for debugging"
|
|
296
294
|
}).strict().help(), async (args) => {
|
|
297
295
|
const { entry, theme, base, download, out, inspect } = args;
|
|
298
|
-
const { build } = await import("./build-
|
|
296
|
+
const { build } = await import("./build-DWALVMBw.js");
|
|
299
297
|
for (const entryFile of entry) {
|
|
300
298
|
const options = await resolveOptions({
|
|
301
299
|
entry: entryFile,
|
|
@@ -358,7 +356,7 @@ cli.command("theme [subcommand]", "Theme related operations", (command) => {
|
|
|
358
356
|
});
|
|
359
357
|
cli.command("export [entry..]", "Export slides to PDF", (args) => exportOptions(commonOptions(args)).strict().help(), async (args) => {
|
|
360
358
|
const { entry, theme } = args;
|
|
361
|
-
const { exportSlides, getExportOptions } = await import("./export-
|
|
359
|
+
const { exportSlides, getExportOptions } = await import("./export-DCKSbBi5.js");
|
|
362
360
|
const port = await getPort(12445);
|
|
363
361
|
let warned = false;
|
|
364
362
|
for (const entryFile of entry) {
|
|
@@ -405,7 +403,7 @@ cli.command("export-notes [entry..]", "Export slide notes to PDF", (args) => arg
|
|
|
405
403
|
type: "number",
|
|
406
404
|
describe: "wait for the specified ms before exporting"
|
|
407
405
|
}).strict().help(), async ({ entry, output, timeout, wait }) => {
|
|
408
|
-
const { exportNotes } = await import("./export-
|
|
406
|
+
const { exportNotes } = await import("./export-DCKSbBi5.js");
|
|
409
407
|
const port = await getPort(12445);
|
|
410
408
|
for (const entryFile of entry) {
|
|
411
409
|
const options = await resolveOptions({ entry: entryFile }, "export");
|
|
@@ -543,4 +541,5 @@ function printInfo(options, port, base, remote, tunnelUrl, publicIp) {
|
|
|
543
541
|
}
|
|
544
542
|
}
|
|
545
543
|
|
|
546
|
-
//#endregion
|
|
544
|
+
//#endregion
|
|
545
|
+
export { };
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { getRoots } from "./resolver-
|
|
1
|
+
import { getRoots } from "./resolver-3bFppHAb.js";
|
|
2
2
|
import fs from "node:fs/promises";
|
|
3
3
|
import path, { dirname, relative } from "node:path";
|
|
4
4
|
import process from "node:process";
|
|
@@ -74,8 +74,7 @@ function createSlidevProgress(indeterminate = false) {
|
|
|
74
74
|
async function exportNotes({ port = 18724, base = "/", output = "notes", timeout = 3e4, wait = 0 }) {
|
|
75
75
|
const { chromium } = await importPlaywright();
|
|
76
76
|
const browser = await chromium.launch();
|
|
77
|
-
const
|
|
78
|
-
const page = await context.newPage();
|
|
77
|
+
const page = await (await browser.newContext()).newPage();
|
|
79
78
|
const progress = createSlidevProgress(true);
|
|
80
79
|
progress.start(1);
|
|
81
80
|
if (!output.endsWith(".pdf")) output = `${output}.pdf`;
|
|
@@ -105,14 +104,13 @@ async function exportSlides({ port = 18724, total = 0, range: range$1, format =
|
|
|
105
104
|
const pages = parseRangeString(total, range$1);
|
|
106
105
|
const { chromium } = await importPlaywright();
|
|
107
106
|
const browser = await chromium.launch({ executablePath });
|
|
108
|
-
const
|
|
107
|
+
const page = await (await browser.newContext({
|
|
109
108
|
viewport: {
|
|
110
109
|
width,
|
|
111
110
|
height: perSlide ? height : height * pages.length
|
|
112
111
|
},
|
|
113
112
|
deviceScaleFactor: scale
|
|
114
|
-
});
|
|
115
|
-
const page = await context.newPage();
|
|
113
|
+
})).newPage();
|
|
116
114
|
const progress = createSlidevProgress(!perSlide);
|
|
117
115
|
progress.start(pages.length);
|
|
118
116
|
if (format === "pdf") await genPagePdf();
|
|
@@ -167,8 +165,7 @@ async function exportSlides({ port = 18724, total = 0, range: range$1, format =
|
|
|
167
165
|
}
|
|
168
166
|
{
|
|
169
167
|
const container = slide.locator("#mermaid-rendering-container");
|
|
170
|
-
|
|
171
|
-
if (count > 0) {
|
|
168
|
+
if (await container.count() > 0) {
|
|
172
169
|
while (true) {
|
|
173
170
|
const element = container.locator("div").first();
|
|
174
171
|
if (await element.count() === 0) break;
|
|
@@ -180,10 +177,7 @@ async function exportSlides({ port = 18724, total = 0, range: range$1, format =
|
|
|
180
177
|
{
|
|
181
178
|
const elements = slide.locator(".monaco-aria-container");
|
|
182
179
|
const count = await elements.count();
|
|
183
|
-
for (let index = 0; index < count; index++)
|
|
184
|
-
const element = elements.nth(index);
|
|
185
|
-
await element.evaluate((node) => node.style.display = "none");
|
|
186
|
-
}
|
|
180
|
+
for (let index = 0; index < count; index++) await elements.nth(index).evaluate((node) => node.style.display = "none");
|
|
187
181
|
}
|
|
188
182
|
if (wait) await page.waitForTimeout(wait);
|
|
189
183
|
}
|
|
@@ -196,11 +190,10 @@ async function exportSlides({ port = 18724, total = 0, range: range$1, format =
|
|
|
196
190
|
const path$1 = Number(id.split("-")[0]);
|
|
197
191
|
clicksBySlide[path$1] = (clicksBySlide[path$1] || 0) + 1;
|
|
198
192
|
}
|
|
199
|
-
|
|
193
|
+
return Object.fromEntries(Object.entries(clicksBySlide).reduce((acc, [path$1, clicks], i) => {
|
|
200
194
|
acc.push([path$1, clicks + (acc[i - 1]?.[1] ?? 0)]);
|
|
201
195
|
return acc;
|
|
202
196
|
}, []));
|
|
203
|
-
return slideIndexes;
|
|
204
197
|
}
|
|
205
198
|
function getClicksFromUrl(url) {
|
|
206
199
|
return url.match(/clicks=([1-9]\d*)/)?.[1];
|
|
@@ -240,8 +233,7 @@ async function exportSlides({ port = 18724, total = 0, range: range$1, format =
|
|
|
240
233
|
let mergedPdf = await PDFDocument.create({});
|
|
241
234
|
for (const pdfBytes of buffers) {
|
|
242
235
|
const pdf = await PDFDocument.load(pdfBytes);
|
|
243
|
-
|
|
244
|
-
copiedPages.forEach((page$1) => {
|
|
236
|
+
(await mergedPdf.copyPages(pdf, pdf.getPageIndices())).forEach((page$1) => {
|
|
245
237
|
mergedPdf.addPage(page$1);
|
|
246
238
|
});
|
|
247
239
|
}
|
|
@@ -375,7 +367,7 @@ async function exportSlides({ port = 18724, total = 0, range: range$1, format =
|
|
|
375
367
|
}
|
|
376
368
|
}
|
|
377
369
|
function getExportOptions(args, options, outFilename) {
|
|
378
|
-
const
|
|
370
|
+
const { entry, output, format, timeout, wait, waitUntil, range: range$1, dark, withClicks, executablePath, withToc, perSlide, scale, omitBackground } = {
|
|
379
371
|
...options.data.config.export,
|
|
380
372
|
...args,
|
|
381
373
|
...clearUndefined({
|
|
@@ -387,7 +379,6 @@ function getExportOptions(args, options, outFilename) {
|
|
|
387
379
|
omitBackground: args["omit-background"]
|
|
388
380
|
})
|
|
389
381
|
};
|
|
390
|
-
const { entry, output, format, timeout, wait, waitUntil, range: range$1, dark, withClicks, executablePath, withToc, perSlide, scale, omitBackground } = config;
|
|
391
382
|
outFilename = output || options.data.config.exportFilename || outFilename || `${path.basename(entry, ".md")}-export`;
|
|
392
383
|
return {
|
|
393
384
|
output: outFilename,
|
package/dist/index.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { ViteSlidevPlugin, createDataUtils, parser, resolveOptions } from "./shared-
|
|
2
|
-
import "./resolver-
|
|
3
|
-
import { createServer } from "./serve-
|
|
1
|
+
import { ViteSlidevPlugin, createDataUtils, parser, resolveOptions } from "./shared-BjrV0NzM.js";
|
|
2
|
+
import "./resolver-3bFppHAb.js";
|
|
3
|
+
import { createServer } from "./serve-CG6WbHRY.js";
|
|
4
4
|
|
|
5
5
|
export { ViteSlidevPlugin, createDataUtils, createServer, parser, resolveOptions };
|
|
@@ -82,8 +82,7 @@ function createResolver(type, officials) {
|
|
|
82
82
|
if (name.startsWith("@/")) return [name, resolve(userRoot, name.slice(2))];
|
|
83
83
|
if (name[0] === "." || name[0] !== "@" && name.includes("/")) return [name, resolve(dirname(importer), name)];
|
|
84
84
|
if (name.startsWith(`@slidev/${type}-`) || name.startsWith(`slidev-${type}-`)) {
|
|
85
|
-
|
|
86
|
-
if (!pkgRoot) await promptForInstallation(name);
|
|
85
|
+
if (!await findPkgRoot(name, importer)) await promptForInstallation(name);
|
|
87
86
|
return [name, await findPkgRoot(name, importer, true)];
|
|
88
87
|
}
|
|
89
88
|
{
|
|
@@ -114,12 +113,10 @@ function hasWorkspacePackageJSON(root) {
|
|
|
114
113
|
} catch {
|
|
115
114
|
return false;
|
|
116
115
|
}
|
|
117
|
-
|
|
118
|
-
return !!content.workspaces;
|
|
116
|
+
return !!(JSON.parse(fs$1.readFileSync(path$1, "utf-8")) || {}).workspaces;
|
|
119
117
|
}
|
|
120
118
|
function hasRootFile(root) {
|
|
121
|
-
|
|
122
|
-
return ROOT_FILES.some((file) => fs$1.existsSync(join(root, file)));
|
|
119
|
+
return ["pnpm-workspace.yaml"].some((file) => fs$1.existsSync(join(root, file)));
|
|
123
120
|
}
|
|
124
121
|
/**
|
|
125
122
|
* Search up for the nearest workspace root
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { createResolver, getRoots, isInstalledGlobally, resolveEntry, resolveImportPath, resolveImportUrl, toAtFS } from "./resolver-
|
|
1
|
+
import { createResolver, getRoots, isInstalledGlobally, resolveEntry, resolveImportPath, resolveImportUrl, toAtFS } from "./resolver-3bFppHAb.js";
|
|
2
2
|
import { builtinModules } from "node:module";
|
|
3
|
-
import fs from "node:fs/promises";
|
|
3
|
+
import fs, { readFile } from "node:fs/promises";
|
|
4
4
|
import path, { basename, dirname, join, resolve } from "node:path";
|
|
5
5
|
import { bold, gray, red, white, yellow } from "ansis";
|
|
6
6
|
import equal from "fast-deep-equal";
|
|
@@ -16,7 +16,6 @@ import Components from "unplugin-vue-components/vite";
|
|
|
16
16
|
import { createResolve } from "mlly";
|
|
17
17
|
import { findDepPkgJsonPath } from "vitefu";
|
|
18
18
|
import Icons from "unplugin-icons/vite";
|
|
19
|
-
import * as parser$1 from "@slidev/parser/fs";
|
|
20
19
|
import * as parser from "@slidev/parser/fs";
|
|
21
20
|
import Debug from "debug";
|
|
22
21
|
import fg from "fast-glob";
|
|
@@ -43,7 +42,7 @@ import Vue from "@vitejs/plugin-vue";
|
|
|
43
42
|
import VueJsx from "@vitejs/plugin-vue-jsx";
|
|
44
43
|
|
|
45
44
|
//#region package.json
|
|
46
|
-
var version = "52.
|
|
45
|
+
var version = "52.2.3";
|
|
47
46
|
|
|
48
47
|
//#endregion
|
|
49
48
|
//#region node/syntax/markdown-it/markdown-it-link.ts
|
|
@@ -78,8 +77,7 @@ function stringifyMarkdownTokens(tokens) {
|
|
|
78
77
|
}
|
|
79
78
|
function generateFontParams(options) {
|
|
80
79
|
const weights = options.weights.flatMap((i) => options.italic ? [`0,${i}`, `1,${i}`] : [`${i}`]).sort().join(";");
|
|
81
|
-
|
|
82
|
-
return fontParams;
|
|
80
|
+
return options.webfonts.map((i) => `family=${i.replace(/^(['"])(.*)\1$/, "$1").replace(/\s+/g, "+")}:${options.italic ? "ital," : ""}wght@${weights}`).join("&");
|
|
83
81
|
}
|
|
84
82
|
function generateGoogleFontsUrl(options) {
|
|
85
83
|
return `https://fonts.googleapis.com/css2?${generateFontParams(options)}&display=swap`;
|
|
@@ -141,14 +139,14 @@ function createVueCompilerFlagsPlugin(options) {
|
|
|
141
139
|
return {
|
|
142
140
|
name: "slidev:flags",
|
|
143
141
|
enforce: "pre",
|
|
144
|
-
transform(code, id) {
|
|
142
|
+
transform: { handler(code, id) {
|
|
145
143
|
if (!id.match(/\.vue($|\?)/) && !id.includes("?vue&")) return;
|
|
146
144
|
const original = code;
|
|
147
145
|
define.forEach(([from, to]) => {
|
|
148
146
|
code = code.replaceAll(from, to);
|
|
149
147
|
});
|
|
150
148
|
if (original !== code) return code;
|
|
151
|
-
}
|
|
149
|
+
} }
|
|
152
150
|
};
|
|
153
151
|
}
|
|
154
152
|
|
|
@@ -200,7 +198,7 @@ const templateInitContext = `const { $slidev, $nav, $clicksContext, $clicks, $pa
|
|
|
200
198
|
function createContextInjectionPlugin() {
|
|
201
199
|
return {
|
|
202
200
|
name: "slidev:context-injection",
|
|
203
|
-
async
|
|
201
|
+
transform: { async handler(code, id) {
|
|
204
202
|
if (!id.endsWith(".vue") || id.includes("/@slidev/client/") || id.includes("/packages/client/")) return;
|
|
205
203
|
if (code.includes(templateInjectionMarker) || code.includes("useSlideContext()")) return code;
|
|
206
204
|
const imports = [
|
|
@@ -208,18 +206,23 @@ function createContextInjectionPlugin() {
|
|
|
208
206
|
templateInitContext,
|
|
209
207
|
templateInjectionMarker
|
|
210
208
|
];
|
|
211
|
-
const
|
|
212
|
-
|
|
213
|
-
|
|
209
|
+
const matchScripts = [...code.matchAll(/<script([^>]*)>/g)];
|
|
210
|
+
const setupScriptMatch = [...code.matchAll(/<script([^>]*)setup([^>]*)>/g)].at(0);
|
|
211
|
+
if (setupScriptMatch) {
|
|
212
|
+
const setupTag = setupScriptMatch[0];
|
|
213
|
+
const setupTagEnd = (setupScriptMatch.index || 0) + setupTag.length;
|
|
214
|
+
return `${code.slice(0, setupTagEnd)}\n${imports.join("\n")}\n${code.slice(setupTagEnd)}`;
|
|
215
|
+
} else if (!setupScriptMatch && matchScripts.length === 1) {
|
|
214
216
|
const matchExport = code.match(/export\s+default\s+\{/);
|
|
215
217
|
if (matchExport) {
|
|
216
218
|
const exportIndex = (matchExport.index || 0) + matchExport[0].length;
|
|
217
219
|
let component = code.slice(exportIndex);
|
|
218
|
-
component = component.slice(0, component.indexOf("
|
|
219
|
-
const scriptIndex = (
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
220
|
+
component = component.slice(0, component.indexOf("<\/script>"));
|
|
221
|
+
const scriptIndex = (matchScripts[0].index || 0) + matchScripts[0][0].length;
|
|
222
|
+
code = `${code.slice(0, scriptIndex)}
|
|
223
|
+
import { injectionSlidevContext } from "@slidev/client/constants.ts"
|
|
224
|
+
${code.slice(scriptIndex)}`;
|
|
225
|
+
let injectIndex = exportIndex + 70;
|
|
223
226
|
let injectObject = "$slidev: { from: injectionSlidevContext },";
|
|
224
227
|
const matchInject = component.match(/.*inject\s*:\s*([[{])/);
|
|
225
228
|
if (matchInject) {
|
|
@@ -235,8 +238,8 @@ function createContextInjectionPlugin() {
|
|
|
235
238
|
return `${code.slice(0, injectIndex)}\ninject: { ${injectObject} },\n${code.slice(injectIndex)}`;
|
|
236
239
|
}
|
|
237
240
|
}
|
|
238
|
-
return `<script setup>\n${imports.join("\n")}\n
|
|
239
|
-
}
|
|
241
|
+
return `<script setup>\n${imports.join("\n")}\n<\/script>\n${code}`;
|
|
242
|
+
} }
|
|
240
243
|
};
|
|
241
244
|
}
|
|
242
245
|
|
|
@@ -396,9 +399,12 @@ function createConfigPlugin(options) {
|
|
|
396
399
|
function createHmrPatchPlugin() {
|
|
397
400
|
return {
|
|
398
401
|
name: "slidev:hmr-patch",
|
|
399
|
-
transform
|
|
400
|
-
|
|
401
|
-
|
|
402
|
+
transform: {
|
|
403
|
+
filter: { id: { include: regexSlideSourceId } },
|
|
404
|
+
handler(code, id) {
|
|
405
|
+
if (!id.match(regexSlideSourceId)) return;
|
|
406
|
+
return code.replace("if (_rerender_only)", "if (false)");
|
|
407
|
+
}
|
|
402
408
|
}
|
|
403
409
|
};
|
|
404
410
|
}
|
|
@@ -430,40 +436,42 @@ async function createInspectPlugin(options, pluginOptions) {
|
|
|
430
436
|
function createLayoutWrapperPlugin({ data, utils }) {
|
|
431
437
|
return {
|
|
432
438
|
name: "slidev:layout-wrapper",
|
|
433
|
-
|
|
434
|
-
|
|
435
|
-
|
|
436
|
-
|
|
437
|
-
|
|
438
|
-
|
|
439
|
-
|
|
440
|
-
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
|
|
439
|
+
transform: {
|
|
440
|
+
filter: { id: { include: regexSlideSourceId } },
|
|
441
|
+
async handler(code, id) {
|
|
442
|
+
const match = id.match(regexSlideSourceId);
|
|
443
|
+
if (!match) return;
|
|
444
|
+
const [, no, type] = match;
|
|
445
|
+
if (type !== "md") return;
|
|
446
|
+
const index = +no - 1;
|
|
447
|
+
const layouts = utils.getLayouts();
|
|
448
|
+
let layoutName = (data.slides[index]?.frontmatter?.layout ?? data.slides[0]?.frontmatter?.defaults?.layout) || (index === 0 ? "cover" : "default");
|
|
449
|
+
if (!layouts[layoutName]) {
|
|
450
|
+
console.error(red(`\nUnknown layout "${bold(layoutName)}".${yellow(" Available layouts are:")}`) + Object.keys(layouts).map((i, idx) => (idx % 3 === 0 ? "\n " : "") + gray(i.padEnd(15, " "))).join(" "));
|
|
451
|
+
console.error();
|
|
452
|
+
layoutName = "default";
|
|
453
|
+
}
|
|
454
|
+
const setupTag = code.match(/^<script setup.*>/m);
|
|
455
|
+
if (!setupTag) throw new Error(`[Slidev] Internal error: <script setup> block not found in slide ${index + 1}.`);
|
|
456
|
+
const templatePart = code.slice(0, setupTag.index);
|
|
457
|
+
const scriptPart = code.slice(setupTag.index);
|
|
458
|
+
const bodyStart = templatePart.indexOf("<template>") + 10;
|
|
459
|
+
const bodyEnd = templatePart.lastIndexOf("</template>");
|
|
460
|
+
let body = code.slice(bodyStart, bodyEnd).trim();
|
|
461
|
+
if (body.startsWith("<div>") && body.endsWith("</div>")) body = body.slice(5, -6);
|
|
462
|
+
return [
|
|
463
|
+
templatePart.slice(0, bodyStart),
|
|
464
|
+
`<InjectedLayout v-bind="_frontmatterToProps($frontmatter,${index})">\n${body}\n</InjectedLayout>`,
|
|
465
|
+
templatePart.slice(bodyEnd),
|
|
466
|
+
scriptPart.slice(0, setupTag[0].length),
|
|
467
|
+
`import InjectedLayout from "${toAtFS(layouts[layoutName])}"`,
|
|
468
|
+
templateImportContextUtils,
|
|
469
|
+
templateInitContext,
|
|
470
|
+
"$clicksContext.setup()",
|
|
471
|
+
templateInjectionMarker,
|
|
472
|
+
scriptPart.slice(setupTag[0].length)
|
|
473
|
+
].join("\n");
|
|
446
474
|
}
|
|
447
|
-
const setupTag = code.match(/^<script setup.*>/m);
|
|
448
|
-
if (!setupTag) throw new Error(`[Slidev] Internal error: <script setup> block not found in slide ${index + 1}.`);
|
|
449
|
-
const templatePart = code.slice(0, setupTag.index);
|
|
450
|
-
const scriptPart = code.slice(setupTag.index);
|
|
451
|
-
const bodyStart = templatePart.indexOf("<template>") + 10;
|
|
452
|
-
const bodyEnd = templatePart.lastIndexOf("</template>");
|
|
453
|
-
let body = code.slice(bodyStart, bodyEnd).trim();
|
|
454
|
-
if (body.startsWith("<div>") && body.endsWith("</div>")) body = body.slice(5, -6);
|
|
455
|
-
return [
|
|
456
|
-
templatePart.slice(0, bodyStart),
|
|
457
|
-
`<InjectedLayout v-bind="_frontmatterToProps($frontmatter,${index})">\n${body}\n</InjectedLayout>`,
|
|
458
|
-
templatePart.slice(bodyEnd),
|
|
459
|
-
scriptPart.slice(0, setupTag[0].length),
|
|
460
|
-
`import InjectedLayout from "${toAtFS(layouts[layoutName])}"`,
|
|
461
|
-
templateImportContextUtils,
|
|
462
|
-
templateInitContext,
|
|
463
|
-
"$clicksContext.setup()",
|
|
464
|
-
templateInjectionMarker,
|
|
465
|
-
scriptPart.slice(setupTag[0].length)
|
|
466
|
-
].join("\n");
|
|
467
475
|
}
|
|
468
476
|
};
|
|
469
477
|
}
|
|
@@ -518,16 +526,16 @@ async function setupIndexHtml({ mode, entry, clientRoot, userRoot, roots, data,
|
|
|
518
526
|
for (const root of roots) {
|
|
519
527
|
const path$1 = join(root, "index.html");
|
|
520
528
|
if (!existsSync(path$1)) continue;
|
|
521
|
-
const html
|
|
522
|
-
if (root === userRoot && html
|
|
529
|
+
const html = readFileSync(path$1, "utf-8");
|
|
530
|
+
if (root === userRoot && html.includes("<!DOCTYPE")) {
|
|
523
531
|
console.error(yellow(`[Slidev] Ignored provided index.html with doctype declaration. (${white(path$1)})`));
|
|
524
532
|
console.error(yellow("This file may be generated by Slidev, please remove it from your project."));
|
|
525
533
|
continue;
|
|
526
534
|
}
|
|
527
|
-
inputs.push(extractUnheadInputFromHtml(html
|
|
528
|
-
body += `\n${(html
|
|
535
|
+
inputs.push(extractUnheadInputFromHtml(html).input);
|
|
536
|
+
body += `\n${(html.match(/<body>([\s\S]*?)<\/body>/i)?.[1] || "").trim()}`;
|
|
529
537
|
}
|
|
530
|
-
if (data.features.tweet) body += "\n<script async src=\"https://platform.twitter.com/widgets.js\"
|
|
538
|
+
if (data.features.tweet) body += "\n<script async src=\"https://platform.twitter.com/widgets.js\"><\/script>";
|
|
531
539
|
const webFontsLink = [];
|
|
532
540
|
if (data.config.fonts.webfonts.length) {
|
|
533
541
|
const { provider } = data.config.fonts;
|
|
@@ -544,6 +552,7 @@ async function setupIndexHtml({ mode, entry, clientRoot, userRoot, roots, data,
|
|
|
544
552
|
}
|
|
545
553
|
const { info, author, keywords } = data.headmatter;
|
|
546
554
|
const seoMeta = data.headmatter.seoMeta ?? {};
|
|
555
|
+
const ogImage = seoMeta.ogImage === "auto" ? "./og-image.png" : seoMeta.ogImage ? seoMeta.ogImage : existsSync(join(userRoot, "og-image.png")) ? "./og-image.png" : void 0;
|
|
547
556
|
const title = getSlideTitle(data);
|
|
548
557
|
const description = info ? toAttrValue(info) : null;
|
|
549
558
|
const unhead = createHead({ init: [{
|
|
@@ -588,7 +597,7 @@ async function setupIndexHtml({ mode, entry, clientRoot, userRoot, roots, data,
|
|
|
588
597
|
},
|
|
589
598
|
{
|
|
590
599
|
property: "og:image",
|
|
591
|
-
content:
|
|
600
|
+
content: ogImage
|
|
592
601
|
},
|
|
593
602
|
{
|
|
594
603
|
property: "og:url",
|
|
@@ -622,8 +631,7 @@ async function setupIndexHtml({ mode, entry, clientRoot, userRoot, roots, data,
|
|
|
622
631
|
}, ...inputs] });
|
|
623
632
|
const baseInDev = mode === "dev" && base ? base.slice(0, -1) : "";
|
|
624
633
|
main = main.replace("__ENTRY__", baseInDev + encodeURI(toAtFS(join(clientRoot, "main.ts")))).replace("<!-- body -->", body);
|
|
625
|
-
|
|
626
|
-
return html;
|
|
634
|
+
return await transformHtmlTemplate(unhead, main);
|
|
627
635
|
}
|
|
628
636
|
|
|
629
637
|
//#endregion
|
|
@@ -689,13 +697,13 @@ const debug = Debug("slidev:options");
|
|
|
689
697
|
async function resolveOptions(entryOptions, mode) {
|
|
690
698
|
const entry = await resolveEntry(entryOptions.entry);
|
|
691
699
|
const rootsInfo = await getRoots(entry);
|
|
692
|
-
const loaded = await parser
|
|
700
|
+
const loaded = await parser.load(rootsInfo.userRoot, entry, void 0, mode);
|
|
693
701
|
let themeRaw = entryOptions.theme || loaded.headmatter.theme;
|
|
694
702
|
themeRaw = themeRaw === null ? "none" : themeRaw || "default";
|
|
695
703
|
const [theme, themeRoot] = await resolveTheme(themeRaw, entry);
|
|
696
704
|
const themeRoots = themeRoot ? [themeRoot] : [];
|
|
697
705
|
const themeMeta = themeRoot ? await getThemeMeta(theme, themeRoot) : void 0;
|
|
698
|
-
const config = parser
|
|
706
|
+
const config = parser.resolveConfig(loaded.headmatter, themeMeta, entryOptions.entry);
|
|
699
707
|
const addonRoots = await resolveAddons(config.addons);
|
|
700
708
|
const roots = uniq([
|
|
701
709
|
...themeRoots,
|
|
@@ -961,7 +969,7 @@ const templateLegacyTitles = {
|
|
|
961
969
|
import TitleRenderer from '#slidev/title-renderer'
|
|
962
970
|
defineProps<{ no: number | string }>()
|
|
963
971
|
console.warn('/@slidev/titles.md is deprecated, import from #slidev/title-renderer instead')
|
|
964
|
-
|
|
972
|
+
<\/script>
|
|
965
973
|
|
|
966
974
|
<TitleRenderer :no="no" />
|
|
967
975
|
`;
|
|
@@ -1060,8 +1068,7 @@ const templateMonacoTypes = {
|
|
|
1060
1068
|
const mainPackageName = moduleSpecifier.split("/")[0];
|
|
1061
1069
|
if (builtinModules.includes(mainPackageName) && !mainPackageName.startsWith("@")) return "node";
|
|
1062
1070
|
const [a = "", b = ""] = moduleSpecifier.split("/");
|
|
1063
|
-
|
|
1064
|
-
return moduleName;
|
|
1071
|
+
return a.startsWith("@") ? `${a}/${b}` : a;
|
|
1065
1072
|
}
|
|
1066
1073
|
let deps = [...data.config.monacoTypesAdditionalPackages];
|
|
1067
1074
|
if (data.config.monacoTypesSource === "local") deps.push(...data.features.monaco.types);
|
|
@@ -1173,10 +1180,9 @@ const VIRTUAL_SLIDE_PREFIX = "/@slidev/slides/";
|
|
|
1173
1180
|
const templateSlides = {
|
|
1174
1181
|
id: "/@slidev/slides",
|
|
1175
1182
|
getContent({ data, utils }) {
|
|
1176
|
-
const layouts = utils.getLayouts();
|
|
1177
1183
|
const statements = [
|
|
1178
1184
|
`import { defineAsyncComponent, shallowRef } from 'vue'`,
|
|
1179
|
-
`import SlideError from '${
|
|
1185
|
+
`import SlideError from '${utils.getLayouts().error}'`,
|
|
1180
1186
|
`import SlideLoading from '@slidev/client/internals/SlideLoading.vue'`,
|
|
1181
1187
|
`const componentsCache = new Array(${data.slides.length})`,
|
|
1182
1188
|
`const getAsyncComponent = (idx, loader) => defineAsyncComponent({`,
|
|
@@ -1248,7 +1254,7 @@ const templateTitleRendererMd = {
|
|
|
1248
1254
|
id: "/@slidev/title-renderer.md",
|
|
1249
1255
|
getContent({ data }) {
|
|
1250
1256
|
const lines = data.slides.map(({ title }, i) => `<template ${i === 0 ? "v-if" : "v-else-if"}="no === ${i + 1}">\n\n${title}\n\n</template>`);
|
|
1251
|
-
lines.push(`<script setup lang="ts">`, `import { useSlideContext } from '@slidev/client/context.ts'`, `import { computed } from 'vue'`, `const props = defineProps<{ no?: number | string }>()`, `const { $page } = useSlideContext()`, `const no = computed(() => +(props.no ?? $page.value))`,
|
|
1257
|
+
lines.push(`<script setup lang="ts">`, `import { useSlideContext } from '@slidev/client/context.ts'`, `import { computed } from 'vue'`, `const props = defineProps<{ no?: number | string }>()`, `const { $page } = useSlideContext()`, `const no = computed(() => +(props.no ?? $page.value))`, `<\/script>`);
|
|
1252
1258
|
return lines.join("\n");
|
|
1253
1259
|
}
|
|
1254
1260
|
};
|
|
@@ -1511,11 +1517,10 @@ function createSlidesLoader(options, serverOptions) {
|
|
|
1511
1517
|
};
|
|
1512
1518
|
function renderNote(text = "") {
|
|
1513
1519
|
let clickCount = 0;
|
|
1514
|
-
|
|
1520
|
+
return notesMd.render(text.replace(/\[click(?::(\d+))?\]/gi, (_, count = 1) => {
|
|
1515
1521
|
clickCount += Number(count);
|
|
1516
1522
|
return `<span class="slidev-note-click-mark" data-clicks="${clickCount}"></span>`;
|
|
1517
1523
|
}));
|
|
1518
|
-
return html;
|
|
1519
1524
|
}
|
|
1520
1525
|
function withRenderedNote(data$1) {
|
|
1521
1526
|
return {
|
|
@@ -1564,9 +1569,7 @@ function taskLists(md, options = {
|
|
|
1564
1569
|
return "</label>";
|
|
1565
1570
|
};
|
|
1566
1571
|
md.renderer.rules.taskListItemLabel_open = (tokens) => {
|
|
1567
|
-
|
|
1568
|
-
const id = token.attrGet("id");
|
|
1569
|
-
return `<label for="${id}">`;
|
|
1572
|
+
return `<label for="${tokens[0].attrGet("id")}">`;
|
|
1570
1573
|
};
|
|
1571
1574
|
}
|
|
1572
1575
|
function processToken(state, options) {
|
|
@@ -1577,8 +1580,7 @@ function processToken(state, options) {
|
|
|
1577
1580
|
allTokens[i - 2].attrJoin("class", `task-list-item ${options.enabled ? " enabled" : ""}`);
|
|
1578
1581
|
const parentToken = findParentToken(allTokens, i - 2);
|
|
1579
1582
|
if (parentToken) {
|
|
1580
|
-
|
|
1581
|
-
if (!classes.match(/(^| )contains-task-list/)) parentToken.attrJoin("class", "contains-task-list");
|
|
1583
|
+
if (!(parentToken.attrGet("class") ?? "").match(/(^| )contains-task-list/)) parentToken.attrJoin("class", "contains-task-list");
|
|
1582
1584
|
}
|
|
1583
1585
|
}
|
|
1584
1586
|
return false;
|
|
@@ -1586,7 +1588,6 @@ function processToken(state, options) {
|
|
|
1586
1588
|
function findParentToken(tokens, index) {
|
|
1587
1589
|
const targetLevel = tokens[index].level - 1;
|
|
1588
1590
|
for (let currentTokenIndex = index - 1; currentTokenIndex >= 0; currentTokenIndex--) if (tokens[currentTokenIndex].level === targetLevel) return tokens[currentTokenIndex];
|
|
1589
|
-
return void 0;
|
|
1590
1591
|
}
|
|
1591
1592
|
function isTodoItem(tokens, index) {
|
|
1592
1593
|
return isInline(tokens[index]) && isParagraph(tokens[index - 1]) && isListItem(tokens[index - 2]) && startsWithTodoMarkdown(tokens[index]);
|
|
@@ -1610,9 +1611,7 @@ function createCheckboxToken(token, enabled, id) {
|
|
|
1610
1611
|
if (!enabled) checkbox.attrSet("disabled", "true");
|
|
1611
1612
|
if (token.map) checkbox.attrSet("line", token.map[0].toString());
|
|
1612
1613
|
checkbox.attrSet("id", id);
|
|
1613
|
-
|
|
1614
|
-
const isChecked = checkboxRegexResult?.[1].toLowerCase() === "x";
|
|
1615
|
-
if (isChecked) checkbox.attrSet("checked", "true");
|
|
1614
|
+
if (checkboxRegex.exec(token.content)?.[1].toLowerCase() === "x") checkbox.attrSet("checked", "true");
|
|
1616
1615
|
return checkbox;
|
|
1617
1616
|
}
|
|
1618
1617
|
function createLabelBeginToken(id) {
|
|
@@ -1641,8 +1640,7 @@ function startsWithTodoMarkdown(token) {
|
|
|
1641
1640
|
function MarkdownItEscapeInlineCode(md) {
|
|
1642
1641
|
const codeInline = md.renderer.rules.code_inline;
|
|
1643
1642
|
md.renderer.rules.code_inline = (tokens, idx, options, env, self) => {
|
|
1644
|
-
|
|
1645
|
-
return result.replace(/^<code/, "<code v-pre");
|
|
1643
|
+
return codeInline(tokens, idx, options, env, self).replace(/^<code/, "<code v-pre");
|
|
1646
1644
|
};
|
|
1647
1645
|
}
|
|
1648
1646
|
|
|
@@ -1806,7 +1804,7 @@ async function setupTransformers(roots) {
|
|
|
1806
1804
|
|
|
1807
1805
|
//#endregion
|
|
1808
1806
|
//#region node/syntax/transform/code-wrapper.ts
|
|
1809
|
-
const reCodeBlock = /^```([\w'-]+)?\s*(?:\[(.*?)\])?\s*(?:\{([\w*,|-]+)\}\s*?(\{[^}]*\})?([^\r\n]*))?\r?\n([
|
|
1807
|
+
const reCodeBlock = /^```([\w'-]+)?\s*(?:\[(.*?)\])?\s*(?:\{([\w*,|-]+)\}\s*?(\{[^}]*\})?([^\r\n]*))?\r?\n((?:(?!^```)[\s\S])*?)^```$/gm;
|
|
1810
1808
|
/**
|
|
1811
1809
|
* Transform code block with wrapper
|
|
1812
1810
|
*/
|
|
@@ -1883,16 +1881,14 @@ function transformMermaid(ctx) {
|
|
|
1883
1881
|
ctx.s.replace(/^```mermaid *(\{[^\n]*\})?\n([\s\S]+?)\n```/gm, (full, options = "", code = "") => {
|
|
1884
1882
|
code = code.trim();
|
|
1885
1883
|
options = options.trim() || "{}";
|
|
1886
|
-
|
|
1887
|
-
return `<Mermaid code-lz="${encoded}" v-bind="${options}" />`;
|
|
1884
|
+
return `<Mermaid code-lz="${lz.compressToBase64(code)}" v-bind="${options}" />`;
|
|
1888
1885
|
});
|
|
1889
1886
|
}
|
|
1890
1887
|
|
|
1891
1888
|
//#endregion
|
|
1892
1889
|
//#region node/syntax/transform/monaco.ts
|
|
1893
1890
|
function transformMonaco(ctx) {
|
|
1894
|
-
|
|
1895
|
-
if (!enabled) {
|
|
1891
|
+
if (!(ctx.options.data.config.monaco === true || ctx.options.data.config.monaco === ctx.options.mode)) {
|
|
1896
1892
|
ctx.s.replace(/\{monaco([\w:,-]*)\}/g, "");
|
|
1897
1893
|
return;
|
|
1898
1894
|
}
|
|
@@ -1906,14 +1902,12 @@ function transformMonaco(ctx) {
|
|
|
1906
1902
|
ctx.s.replace(/^```(\w+) *\{monaco\} *(?:(\{[^\n]*\}) *)?\n([\s\S]+?)^```/gm, (full, lang = "ts", options = "{}", code) => {
|
|
1907
1903
|
lang = lang.trim();
|
|
1908
1904
|
options = options.trim() || "{}";
|
|
1909
|
-
|
|
1910
|
-
return `<Monaco code-lz="${encoded}" lang="${lang}" v-bind="${options}" />`;
|
|
1905
|
+
return `<Monaco code-lz="${lz.compressToBase64(code)}" lang="${lang}" v-bind="${options}" />`;
|
|
1911
1906
|
});
|
|
1912
1907
|
ctx.s.replace(/^```(\w+) *\{monaco-run\} *(?:(\{[^\n]*\}) *)?\n([\s\S]+?)^```/gm, (full, lang = "ts", options = "{}", code) => {
|
|
1913
1908
|
lang = lang.trim();
|
|
1914
1909
|
options = options.trim() || "{}";
|
|
1915
|
-
|
|
1916
|
-
return `<Monaco runnable code-lz="${encoded}" lang="${lang}" v-bind="${options}" />`;
|
|
1910
|
+
return `<Monaco runnable code-lz="${lz.compressToBase64(code)}" lang="${lang}" v-bind="${options}" />`;
|
|
1917
1911
|
});
|
|
1918
1912
|
}
|
|
1919
1913
|
|
|
@@ -2186,6 +2180,26 @@ function createMonacoTypesLoader({ userRoot, utils }) {
|
|
|
2186
2180
|
};
|
|
2187
2181
|
}
|
|
2188
2182
|
|
|
2183
|
+
//#endregion
|
|
2184
|
+
//#region node/vite/patchMonacoSourceMap.ts
|
|
2185
|
+
const postfixRE = /[?#].*$/;
|
|
2186
|
+
function cleanUrl(url) {
|
|
2187
|
+
return url.replace(postfixRE, "");
|
|
2188
|
+
}
|
|
2189
|
+
/**
|
|
2190
|
+
* Temporary workaround for https://github.com/microsoft/monaco-editor/issues/4712
|
|
2191
|
+
*/
|
|
2192
|
+
function createPatchMonacoSourceMapPlugin() {
|
|
2193
|
+
return {
|
|
2194
|
+
name: "slidev:patch-monaco-sourcemap",
|
|
2195
|
+
enforce: "pre",
|
|
2196
|
+
load(id) {
|
|
2197
|
+
if (!id.includes("node_modules/monaco-editor/esm/vs/base")) return;
|
|
2198
|
+
return readFile(cleanUrl(id), "utf-8");
|
|
2199
|
+
}
|
|
2200
|
+
};
|
|
2201
|
+
}
|
|
2202
|
+
|
|
2189
2203
|
//#endregion
|
|
2190
2204
|
//#region node/vite/remoteAssets.ts
|
|
2191
2205
|
async function createRemoteAssetsPlugin({ data: { config }, mode }, pluginOptions) {
|
|
@@ -2224,8 +2238,7 @@ async function loadDrawings(options) {
|
|
|
2224
2238
|
await Promise.all(files.map(async (path$1) => {
|
|
2225
2239
|
const num = +basename(path$1, ".svg");
|
|
2226
2240
|
if (Number.isNaN(num)) return;
|
|
2227
|
-
const
|
|
2228
|
-
const lines = content.split(/\n/g);
|
|
2241
|
+
const lines = (await fs.readFile(path$1, "utf8")).split(/\n/g);
|
|
2229
2242
|
obj[num.toString()] = lines.slice(1, -1).join("\n");
|
|
2230
2243
|
}));
|
|
2231
2244
|
return obj;
|
|
@@ -2347,10 +2360,7 @@ async function createUnocssPlugin(options, pluginOptions) {
|
|
|
2347
2360
|
async function createUserVitePlugins(options) {
|
|
2348
2361
|
const createPluginTasks = options.roots.map(async (root) => {
|
|
2349
2362
|
const modulePath = path.join(root, "setup", "vite-plugins.ts");
|
|
2350
|
-
if (existsSync(modulePath))
|
|
2351
|
-
const module = await loadModule(modulePath);
|
|
2352
|
-
return module.default(options);
|
|
2353
|
-
}
|
|
2363
|
+
if (existsSync(modulePath)) return (await loadModule(modulePath)).default(options);
|
|
2354
2364
|
return [];
|
|
2355
2365
|
});
|
|
2356
2366
|
return (await Promise.all(createPluginTasks)).flatMap((p) => p);
|
|
@@ -2409,8 +2419,7 @@ async function createVuePlugin(_options, pluginOptions) {
|
|
|
2409
2419
|
}
|
|
2410
2420
|
}
|
|
2411
2421
|
});
|
|
2412
|
-
|
|
2413
|
-
return [VueJsxPlugin, VuePlugin];
|
|
2422
|
+
return [VueJsx(vuejsxOptions), VuePlugin];
|
|
2414
2423
|
}
|
|
2415
2424
|
|
|
2416
2425
|
//#endregion
|
|
@@ -2434,7 +2443,8 @@ function ViteSlidevPlugin(options, pluginOptions = {}, serverOptions = {}) {
|
|
|
2434
2443
|
createUnocssPlugin(options, pluginOptions),
|
|
2435
2444
|
createStaticCopyPlugin(options, pluginOptions),
|
|
2436
2445
|
createInspectPlugin(options, pluginOptions),
|
|
2437
|
-
createUserVitePlugins(options)
|
|
2446
|
+
createUserVitePlugins(options),
|
|
2447
|
+
createPatchMonacoSourceMapPlugin()
|
|
2438
2448
|
]);
|
|
2439
2449
|
}
|
|
2440
2450
|
|
|
@@ -2471,4 +2481,4 @@ async function resolveViteConfigs(options, baseConfig, overrideConfigs, command,
|
|
|
2471
2481
|
}
|
|
2472
2482
|
|
|
2473
2483
|
//#endregion
|
|
2474
|
-
export { ViteSlidevPlugin, createDataUtils, getThemeMeta, loadSetups, parser
|
|
2484
|
+
export { ViteSlidevPlugin, createDataUtils, getThemeMeta, loadSetups, parser, resolveAddons, resolveOptions, resolveTheme, resolveViteConfigs, updateFrontmatterPatch, version };
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@slidev/cli",
|
|
3
3
|
"type": "module",
|
|
4
|
-
"version": "52.
|
|
4
|
+
"version": "52.2.3",
|
|
5
5
|
"description": "Presentation slides for developers",
|
|
6
6
|
"author": "Anthony Fu <anthonyfu117@hotmail.com>",
|
|
7
7
|
"license": "MIT",
|
|
@@ -44,42 +44,42 @@
|
|
|
44
44
|
"dependencies": {
|
|
45
45
|
"@antfu/ni": "^25.0.0",
|
|
46
46
|
"@antfu/utils": "^9.2.0",
|
|
47
|
-
"@iconify-json/carbon": "^1.2.
|
|
47
|
+
"@iconify-json/carbon": "^1.2.13",
|
|
48
48
|
"@iconify-json/ph": "^1.2.2",
|
|
49
|
-
"@iconify-json/svg-spinners": "^1.2.
|
|
49
|
+
"@iconify-json/svg-spinners": "^1.2.4",
|
|
50
50
|
"@lillallol/outline-pdf": "^4.0.0",
|
|
51
|
-
"@shikijs/markdown-it": "^3.
|
|
52
|
-
"@shikijs/twoslash": "^3.
|
|
53
|
-
"@shikijs/vitepress-twoslash": "^3.
|
|
54
|
-
"@unocss/extractor-mdc": "^66.
|
|
55
|
-
"@unocss/reset": "^66.
|
|
56
|
-
"@vitejs/plugin-vue": "^6.0.
|
|
57
|
-
"@vitejs/plugin-vue-jsx": "^5.
|
|
51
|
+
"@shikijs/markdown-it": "^3.13.0",
|
|
52
|
+
"@shikijs/twoslash": "^3.13.0",
|
|
53
|
+
"@shikijs/vitepress-twoslash": "^3.13.0",
|
|
54
|
+
"@unocss/extractor-mdc": "^66.5.1",
|
|
55
|
+
"@unocss/reset": "^66.5.1",
|
|
56
|
+
"@vitejs/plugin-vue": "^6.0.1",
|
|
57
|
+
"@vitejs/plugin-vue-jsx": "^5.1.1",
|
|
58
58
|
"ansis": "^4.1.0",
|
|
59
59
|
"chokidar": "^4.0.3",
|
|
60
60
|
"cli-progress": "^3.12.0",
|
|
61
61
|
"connect": "^3.7.0",
|
|
62
|
-
"debug": "^4.4.
|
|
62
|
+
"debug": "^4.4.3",
|
|
63
63
|
"fast-deep-equal": "^3.1.3",
|
|
64
64
|
"fast-glob": "^3.3.3",
|
|
65
|
-
"get-port-please": "^3.
|
|
65
|
+
"get-port-please": "^3.2.0",
|
|
66
66
|
"global-directory": "^4.0.1",
|
|
67
67
|
"htmlparser2": "^10.0.0",
|
|
68
68
|
"is-installed-globally": "^1.0.0",
|
|
69
|
-
"jiti": "^2.
|
|
69
|
+
"jiti": "^2.5.1",
|
|
70
70
|
"katex": "^0.16.22",
|
|
71
|
-
"local-pkg": "^1.1.
|
|
71
|
+
"local-pkg": "^1.1.2",
|
|
72
72
|
"lz-string": "^1.5.0",
|
|
73
|
-
"magic-string": "^0.30.
|
|
74
|
-
"magic-string-stack": "^1.
|
|
73
|
+
"magic-string": "^0.30.19",
|
|
74
|
+
"magic-string-stack": "^1.1.0",
|
|
75
75
|
"markdown-it": "^14.1.0",
|
|
76
76
|
"markdown-it-footnote": "^4.0.0",
|
|
77
|
-
"markdown-it-mdc": "^0.2.
|
|
78
|
-
"mlly": "^1.
|
|
79
|
-
"monaco-editor": "^0.
|
|
80
|
-
"open": "^10.
|
|
77
|
+
"markdown-it-mdc": "^0.2.6",
|
|
78
|
+
"mlly": "^1.8.0",
|
|
79
|
+
"monaco-editor": "^0.53.0",
|
|
80
|
+
"open": "^10.2.0",
|
|
81
81
|
"pdf-lib": "^1.17.1",
|
|
82
|
-
"picomatch": "^4.0.
|
|
82
|
+
"picomatch": "^4.0.3",
|
|
83
83
|
"plantuml-encoder": "^1.4.0",
|
|
84
84
|
"postcss-nested": "^7.0.2",
|
|
85
85
|
"pptxgenjs": "^4.0.1",
|
|
@@ -88,34 +88,34 @@
|
|
|
88
88
|
"resolve-from": "^5.0.0",
|
|
89
89
|
"resolve-global": "^2.0.0",
|
|
90
90
|
"semver": "^7.7.2",
|
|
91
|
-
"shiki": "^3.
|
|
91
|
+
"shiki": "^3.13.0",
|
|
92
92
|
"shiki-magic-move": "^1.1.0",
|
|
93
|
-
"sirv": "^3.0.
|
|
93
|
+
"sirv": "^3.0.2",
|
|
94
94
|
"source-map-js": "^1.2.1",
|
|
95
|
-
"typescript": "^5.
|
|
96
|
-
"unhead": "^2.0.
|
|
97
|
-
"unocss": "^66.
|
|
98
|
-
"unplugin-icons": "^22.
|
|
95
|
+
"typescript": "^5.9.2",
|
|
96
|
+
"unhead": "^2.0.17",
|
|
97
|
+
"unocss": "^66.5.1",
|
|
98
|
+
"unplugin-icons": "^22.3.0",
|
|
99
99
|
"unplugin-vue-components": "^28.8.0",
|
|
100
|
-
"unplugin-vue-markdown": "^29.
|
|
100
|
+
"unplugin-vue-markdown": "^29.1.0",
|
|
101
101
|
"untun": "^0.1.3",
|
|
102
102
|
"uqr": "^0.1.2",
|
|
103
|
-
"vite": "^7.
|
|
104
|
-
"vite-plugin-inspect": "^11.3.
|
|
105
|
-
"vite-plugin-remote-assets": "^2.
|
|
106
|
-
"vite-plugin-static-copy": "^3.1.
|
|
103
|
+
"vite": "^7.1.6",
|
|
104
|
+
"vite-plugin-inspect": "^11.3.3",
|
|
105
|
+
"vite-plugin-remote-assets": "^2.1.0",
|
|
106
|
+
"vite-plugin-static-copy": "^3.1.2",
|
|
107
107
|
"vite-plugin-vue-server-ref": "^1.0.0",
|
|
108
|
-
"vitefu": "^1.
|
|
109
|
-
"vue": "^3.5.
|
|
110
|
-
"yaml": "^2.8.
|
|
108
|
+
"vitefu": "^1.1.1",
|
|
109
|
+
"vue": "^3.5.21",
|
|
110
|
+
"yaml": "^2.8.1",
|
|
111
111
|
"yargs": "^18.0.0",
|
|
112
|
-
"@slidev/client": "52.
|
|
113
|
-
"@slidev/types": "52.
|
|
114
|
-
"@slidev/parser": "52.
|
|
112
|
+
"@slidev/client": "52.2.3",
|
|
113
|
+
"@slidev/types": "52.2.3",
|
|
114
|
+
"@slidev/parser": "52.2.3"
|
|
115
115
|
},
|
|
116
116
|
"devDependencies": {
|
|
117
117
|
"@hedgedoc/markdown-it-plugins": "^2.1.4",
|
|
118
|
-
"@types/picomatch": "^4.0.
|
|
118
|
+
"@types/picomatch": "^4.0.2",
|
|
119
119
|
"@types/plantuml-encoder": "^1.4.2"
|
|
120
120
|
},
|
|
121
121
|
"scripts": {
|
package/dist/build-DyiO9Vju.js
DELETED
|
@@ -1,62 +0,0 @@
|
|
|
1
|
-
import { resolveViteConfigs } from "./shared-D-V1kZyI.js";
|
|
2
|
-
import "./resolver-BShaA6qw.js";
|
|
3
|
-
import fs from "node:fs/promises";
|
|
4
|
-
import { join, resolve } from "node:path";
|
|
5
|
-
import { build as build$1 } from "vite";
|
|
6
|
-
import { existsSync } from "node:fs";
|
|
7
|
-
import http from "node:http";
|
|
8
|
-
import connect from "connect";
|
|
9
|
-
import sirv from "sirv";
|
|
10
|
-
|
|
11
|
-
//#region node/commands/build.ts
|
|
12
|
-
async function build(options, viteConfig = {}, args) {
|
|
13
|
-
const indexPath = resolve(options.userRoot, "index.html");
|
|
14
|
-
let originalIndexHTML;
|
|
15
|
-
if (existsSync(indexPath)) originalIndexHTML = await fs.readFile(indexPath, "utf-8");
|
|
16
|
-
await fs.writeFile(indexPath, options.utils.indexHtml, "utf-8");
|
|
17
|
-
let config = void 0;
|
|
18
|
-
try {
|
|
19
|
-
const inlineConfig = await resolveViteConfigs(options, {
|
|
20
|
-
plugins: [{
|
|
21
|
-
name: "resolve-config",
|
|
22
|
-
configResolved(_config) {
|
|
23
|
-
config = _config;
|
|
24
|
-
}
|
|
25
|
-
}],
|
|
26
|
-
build: { chunkSizeWarningLimit: 2e3 }
|
|
27
|
-
}, viteConfig, "build");
|
|
28
|
-
await build$1(inlineConfig);
|
|
29
|
-
} finally {
|
|
30
|
-
if (originalIndexHTML != null) await fs.writeFile(indexPath, originalIndexHTML, "utf-8");
|
|
31
|
-
else await fs.unlink(indexPath);
|
|
32
|
-
}
|
|
33
|
-
const outDir = resolve(options.userRoot, config.build.outDir);
|
|
34
|
-
await fs.copyFile(resolve(outDir, "index.html"), resolve(outDir, "404.html"));
|
|
35
|
-
const redirectsPath = resolve(outDir, "_redirects");
|
|
36
|
-
if (!existsSync(redirectsPath)) await fs.writeFile(redirectsPath, `${config.base}* ${config.base}index.html 200\n`, "utf-8");
|
|
37
|
-
if ([
|
|
38
|
-
true,
|
|
39
|
-
"true",
|
|
40
|
-
"auto"
|
|
41
|
-
].includes(options.data.config.download)) {
|
|
42
|
-
const { exportSlides, getExportOptions } = await import("./export-D1Zqc-n1.js");
|
|
43
|
-
const port = 12445;
|
|
44
|
-
const app = connect();
|
|
45
|
-
const server = http.createServer(app);
|
|
46
|
-
app.use(config.base, sirv(outDir, {
|
|
47
|
-
etag: true,
|
|
48
|
-
single: true,
|
|
49
|
-
dev: true
|
|
50
|
-
}));
|
|
51
|
-
server.listen(port);
|
|
52
|
-
await exportSlides({
|
|
53
|
-
port,
|
|
54
|
-
base: config.base,
|
|
55
|
-
...getExportOptions(args, options, join(outDir, "slidev-exported.pdf"))
|
|
56
|
-
});
|
|
57
|
-
server.close();
|
|
58
|
-
}
|
|
59
|
-
}
|
|
60
|
-
|
|
61
|
-
//#endregion
|
|
62
|
-
export { build };
|