@wdprlib/render 1.0.1 → 1.1.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/dist/index.cjs +63 -17
- package/dist/index.d.cts +6 -2
- package/dist/index.d.ts +6 -2
- package/dist/index.js +59 -13
- package/package.json +2 -2
package/dist/index.cjs
CHANGED
|
@@ -44,10 +44,15 @@ var __export = (target, all) => {
|
|
|
44
44
|
var exports_src = {};
|
|
45
45
|
__export(exports_src, {
|
|
46
46
|
renderToHtml: () => renderToHtml,
|
|
47
|
+
createSettings: () => import_ast3.createSettings,
|
|
48
|
+
DEFAULT_SETTINGS: () => import_ast3.DEFAULT_SETTINGS,
|
|
47
49
|
DEFAULT_EMBED_ALLOWLIST: () => DEFAULT_EMBED_ALLOWLIST
|
|
48
50
|
});
|
|
49
51
|
module.exports = __toCommonJS(exports_src);
|
|
50
52
|
|
|
53
|
+
// packages/render/src/context.ts
|
|
54
|
+
var import_ast = require("@wdprlib/ast");
|
|
55
|
+
|
|
51
56
|
// packages/render/src/escape.ts
|
|
52
57
|
function escapeHtml(text) {
|
|
53
58
|
return text.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">");
|
|
@@ -418,6 +423,8 @@ class RenderContext {
|
|
|
418
423
|
_equationIndex = 0;
|
|
419
424
|
_htmlBlockIndex = 0;
|
|
420
425
|
_bibciteCounter = 0;
|
|
426
|
+
_idSuffix;
|
|
427
|
+
settings;
|
|
421
428
|
options;
|
|
422
429
|
footnotes;
|
|
423
430
|
styles;
|
|
@@ -426,6 +433,8 @@ class RenderContext {
|
|
|
426
433
|
bibliographyMap;
|
|
427
434
|
bibliographyEntries;
|
|
428
435
|
constructor(tree, options = {}) {
|
|
436
|
+
this.settings = options.settings ?? import_ast.DEFAULT_SETTINGS;
|
|
437
|
+
this._idSuffix = this.settings.useTrueIds ? null : Math.random().toString(16).slice(2, 8);
|
|
429
438
|
this.options = options;
|
|
430
439
|
this.footnotes = options.footnotes ?? tree.footnotes ?? [];
|
|
431
440
|
this.styles = tree.styles ?? [];
|
|
@@ -479,6 +488,18 @@ class RenderContext {
|
|
|
479
488
|
nextBibciteCounter() {
|
|
480
489
|
return ++this._bibciteCounter;
|
|
481
490
|
}
|
|
491
|
+
generateId(prefix, index) {
|
|
492
|
+
if (this._idSuffix === null) {
|
|
493
|
+
return `${prefix}${index}`;
|
|
494
|
+
}
|
|
495
|
+
return `${prefix}${index}-${this._idSuffix}`;
|
|
496
|
+
}
|
|
497
|
+
generateFixedId(name) {
|
|
498
|
+
if (this._idSuffix === null) {
|
|
499
|
+
return name;
|
|
500
|
+
}
|
|
501
|
+
return `${name}-${this._idSuffix}`;
|
|
502
|
+
}
|
|
482
503
|
get page() {
|
|
483
504
|
return this.options.page;
|
|
484
505
|
}
|
|
@@ -488,15 +509,23 @@ class RenderContext {
|
|
|
488
509
|
case "url": {
|
|
489
510
|
const url = source.data;
|
|
490
511
|
if (url.startsWith("/") && !url.startsWith("//")) {
|
|
512
|
+
if (!this.settings.allowLocalPaths)
|
|
513
|
+
return null;
|
|
491
514
|
return `/local--files${url}`;
|
|
492
515
|
}
|
|
493
516
|
return url;
|
|
494
517
|
}
|
|
495
518
|
case "file1":
|
|
519
|
+
if (!this.settings.allowLocalPaths)
|
|
520
|
+
return null;
|
|
496
521
|
return pageName ? `/local--files/${pageName}/${source.data.file}` : `/local--files/${source.data.file}`;
|
|
497
522
|
case "file2":
|
|
523
|
+
if (!this.settings.allowLocalPaths)
|
|
524
|
+
return null;
|
|
498
525
|
return `/local--files/${source.data.page}/${source.data.file}`;
|
|
499
526
|
case "file3":
|
|
527
|
+
if (!this.settings.allowLocalPaths)
|
|
528
|
+
return null;
|
|
500
529
|
return `/local--files/${source.data.site}/${source.data.page}/${source.data.file}`;
|
|
501
530
|
}
|
|
502
531
|
}
|
|
@@ -548,28 +577,28 @@ class RenderContext {
|
|
|
548
577
|
}
|
|
549
578
|
|
|
550
579
|
// packages/render/src/elements/container.ts
|
|
551
|
-
var
|
|
580
|
+
var import_ast2 = require("@wdprlib/ast");
|
|
552
581
|
function renderContainer(ctx, data) {
|
|
553
582
|
const { type, attributes, elements } = data;
|
|
554
|
-
if (
|
|
583
|
+
if (import_ast2.isHeaderType(type)) {
|
|
555
584
|
renderHeader(ctx, type.header.level, type.header["has-toc"], attributes, elements);
|
|
556
585
|
return;
|
|
557
586
|
}
|
|
558
|
-
if (
|
|
587
|
+
if (import_ast2.isAlignType(type)) {
|
|
559
588
|
ctx.push(`<div style="text-align: ${type.align};">`);
|
|
560
589
|
renderElements(ctx, elements);
|
|
561
590
|
ctx.push("</div>");
|
|
562
591
|
return;
|
|
563
592
|
}
|
|
564
|
-
if (
|
|
593
|
+
if (import_ast2.isStringContainerType(type)) {
|
|
565
594
|
renderStringContainer(ctx, type, attributes, elements);
|
|
566
595
|
}
|
|
567
596
|
}
|
|
568
597
|
function renderHeader(ctx, level, hasToc, attributes, elements) {
|
|
569
598
|
const tag = `h${level}`;
|
|
570
599
|
if (hasToc) {
|
|
571
|
-
const tocId = ctx.nextTocIndex();
|
|
572
|
-
ctx.push(`<${tag} id="
|
|
600
|
+
const tocId = ctx.generateId("toc", ctx.nextTocIndex());
|
|
601
|
+
ctx.push(`<${tag} id="${tocId}"${renderAttrs(attributes)}>`);
|
|
573
602
|
} else {
|
|
574
603
|
ctx.push(`<${tag}${renderAttrs(attributes)}>`);
|
|
575
604
|
}
|
|
@@ -855,6 +884,8 @@ function renderAnchorName(ctx, name) {
|
|
|
855
884
|
// packages/render/src/elements/image.ts
|
|
856
885
|
function renderImage(ctx, data) {
|
|
857
886
|
let src = ctx.resolveImageSource(data.source);
|
|
887
|
+
if (src === null)
|
|
888
|
+
return;
|
|
858
889
|
if (isDangerousUrl(src)) {
|
|
859
890
|
src = "#invalid-url";
|
|
860
891
|
}
|
|
@@ -3939,7 +3970,7 @@ function fnv1aHash(input, hexLen) {
|
|
|
3939
3970
|
function renderTabView(ctx, tabs) {
|
|
3940
3971
|
const labelString = tabs.map((t) => t.label).join("");
|
|
3941
3972
|
const hash = md5Hash(labelString);
|
|
3942
|
-
const widgetId = `wiki-tabview-${hash}
|
|
3973
|
+
const widgetId = ctx.generateFixedId(`wiki-tabview-${hash}`);
|
|
3943
3974
|
ctx.push(`<div id="${widgetId}" class="yui-navset">`);
|
|
3944
3975
|
ctx.push(`<ul class="yui-nav">`);
|
|
3945
3976
|
for (let i = 0;i < tabs.length; i++) {
|
|
@@ -3954,7 +3985,8 @@ function renderTabView(ctx, tabs) {
|
|
|
3954
3985
|
for (let i = 0;i < tabs.length; i++) {
|
|
3955
3986
|
const tab = tabs[i];
|
|
3956
3987
|
const displayStyle = i === 0 ? "" : ` style="display:none"`;
|
|
3957
|
-
ctx.
|
|
3988
|
+
const tabId = ctx.generateId("wiki-tab-0-", i);
|
|
3989
|
+
ctx.push(`<div id="${tabId}"${displayStyle}>`);
|
|
3958
3990
|
renderElements(ctx, tab.elements);
|
|
3959
3991
|
ctx.push("</div>");
|
|
3960
3992
|
}
|
|
@@ -3967,8 +3999,9 @@ function md5Hash(input) {
|
|
|
3967
3999
|
|
|
3968
4000
|
// packages/render/src/elements/footnote.ts
|
|
3969
4001
|
function renderFootnoteRef(ctx, index) {
|
|
4002
|
+
const id = ctx.generateId("footnoteref-", index);
|
|
3970
4003
|
ctx.push(`<sup class="footnoteref">`);
|
|
3971
|
-
ctx.push(`<a id="
|
|
4004
|
+
ctx.push(`<a id="${id}" href="javascript:;" class="footnoteref">${index}</a>`);
|
|
3972
4005
|
ctx.push("</sup>");
|
|
3973
4006
|
}
|
|
3974
4007
|
function renderFootnoteBlock(ctx, data) {
|
|
@@ -3980,7 +4013,8 @@ function renderFootnoteBlock(ctx, data) {
|
|
|
3980
4013
|
for (let i = 0;i < ctx.footnotes.length; i++) {
|
|
3981
4014
|
const index = i + 1;
|
|
3982
4015
|
const elements = ctx.footnotes[i] ?? [];
|
|
3983
|
-
ctx.
|
|
4016
|
+
const fnId = ctx.generateId("footnote-", index);
|
|
4017
|
+
ctx.push(`<div class="footnote-footer" id="${fnId}">`);
|
|
3984
4018
|
ctx.push(`<a href="javascript:;">${index}</a>. `);
|
|
3985
4019
|
renderElements(ctx, elements);
|
|
3986
4020
|
ctx.push("</div>");
|
|
@@ -4018,7 +4052,7 @@ function renderMath(ctx, data) {
|
|
|
4018
4052
|
const index = ctx.nextEquationIndex() + 1;
|
|
4019
4053
|
const latex = data["latex-source"];
|
|
4020
4054
|
const mathml = renderLatexToMathML(latex, true);
|
|
4021
|
-
const id = data.name ?
|
|
4055
|
+
const id = data.name ? ctx.generateId("equation-", data.name) : ctx.generateId("equation-", index);
|
|
4022
4056
|
const dataName = data.name ? ` data-name="${escapeAttr(data.name)}"` : "";
|
|
4023
4057
|
ctx.push(`<div class="math-block" id="${escapeAttr(id)}"${dataName}>`);
|
|
4024
4058
|
if (data.name) {
|
|
@@ -4057,7 +4091,7 @@ function renderMathInline(ctx, data) {
|
|
|
4057
4091
|
ctx.push("</span>");
|
|
4058
4092
|
}
|
|
4059
4093
|
function renderEquationRef(ctx, name) {
|
|
4060
|
-
const id =
|
|
4094
|
+
const id = ctx.generateId("equation-", name);
|
|
4061
4095
|
ctx.push(`<span class="eref" data-target="${escapeAttr(id)}">`);
|
|
4062
4096
|
ctx.push(`<a class="eref-link" href="#${escapeAttr(id)}">`);
|
|
4063
4097
|
ctx.push(escapeHtml(name));
|
|
@@ -4412,8 +4446,9 @@ function renderBibliographyCite(ctx, data) {
|
|
|
4412
4446
|
return;
|
|
4413
4447
|
}
|
|
4414
4448
|
const idSuffix = generateIdSuffix(data.label, counter);
|
|
4415
|
-
const id = `bibcite-${number}
|
|
4416
|
-
const
|
|
4449
|
+
const id = ctx.generateId(`bibcite-${number}-`, idSuffix);
|
|
4450
|
+
const bibitemId = ctx.generateId("bibitem-", number);
|
|
4451
|
+
const onclick = `WIKIDOT.page.utils.scrollToReference('${bibitemId}')`;
|
|
4417
4452
|
ctx.push(`<a href="javascript:;" class="bibcite" id="${id}" onclick="${escapeAttr(onclick)}">`);
|
|
4418
4453
|
ctx.push(String(number));
|
|
4419
4454
|
ctx.push("</a>");
|
|
@@ -4426,7 +4461,8 @@ function renderBibliographyBlock(ctx, data, renderElements2) {
|
|
|
4426
4461
|
ctx.push(`<div class="title">${escapeHtml(title)}</div>`);
|
|
4427
4462
|
let index = 1;
|
|
4428
4463
|
for (const entry of data.entries) {
|
|
4429
|
-
ctx.
|
|
4464
|
+
const itemId = ctx.generateId("bibitem-", index);
|
|
4465
|
+
ctx.push(`<div class="bibitem" id="${itemId}">`);
|
|
4430
4466
|
ctx.push(`${index}. `);
|
|
4431
4467
|
renderElements2(ctx, entry.value);
|
|
4432
4468
|
ctx.push("</div>");
|
|
@@ -4459,12 +4495,19 @@ function renderTocList(ctx, listData, depth) {
|
|
|
4459
4495
|
renderTocItem(ctx, item, depth);
|
|
4460
4496
|
}
|
|
4461
4497
|
}
|
|
4498
|
+
function rewriteTocAnchor(ctx, href) {
|
|
4499
|
+
const match = /^#toc(\d+)$/.exec(href);
|
|
4500
|
+
if (!match)
|
|
4501
|
+
return href;
|
|
4502
|
+
return `#${ctx.generateId("toc", Number(match[1]))}`;
|
|
4503
|
+
}
|
|
4462
4504
|
function renderTocItem(ctx, item, depth) {
|
|
4463
4505
|
if (item["item-type"] === "elements") {
|
|
4464
4506
|
for (const el of item.elements) {
|
|
4465
4507
|
const link = extractLinkText(el);
|
|
4466
4508
|
if (link) {
|
|
4467
|
-
|
|
4509
|
+
const href = rewriteTocAnchor(ctx, link.href);
|
|
4510
|
+
ctx.push(`<div style="margin-left: ${depth}em;"><a href="${escapeAttr(href)}">${escapeHtml(link.text)}</a></div>`);
|
|
4468
4511
|
}
|
|
4469
4512
|
}
|
|
4470
4513
|
} else if (item["item-type"] === "sub-list") {
|
|
@@ -5029,7 +5072,7 @@ function formatNumber(n) {
|
|
|
5029
5072
|
function renderToHtml(tree, options = {}) {
|
|
5030
5073
|
const ctx = new RenderContext(tree, options);
|
|
5031
5074
|
renderElements(ctx, tree.elements);
|
|
5032
|
-
if (tree.styles?.length) {
|
|
5075
|
+
if (ctx.settings.allowStyleElements && tree.styles?.length) {
|
|
5033
5076
|
for (const style of tree.styles) {
|
|
5034
5077
|
ctx.push(`<style>${escapeStyleContent(style)}</style>`);
|
|
5035
5078
|
}
|
|
@@ -5173,3 +5216,6 @@ function renderElement(ctx, element) {
|
|
|
5173
5216
|
break;
|
|
5174
5217
|
}
|
|
5175
5218
|
}
|
|
5219
|
+
|
|
5220
|
+
// packages/render/src/index.ts
|
|
5221
|
+
var import_ast3 = require("@wdprlib/ast");
|
package/dist/index.d.cts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { SyntaxTree as SyntaxTree2 } from "@wdprlib/ast";
|
|
2
|
-
import { Element } from "@wdprlib/ast";
|
|
2
|
+
import { Element, WikitextSettings } from "@wdprlib/ast";
|
|
3
3
|
/**
|
|
4
4
|
* Allowlist entry for embed content validation
|
|
5
5
|
* Each entry specifies a host pattern and optional path prefix
|
|
@@ -70,6 +70,8 @@ interface RenderResolvers {
|
|
|
70
70
|
* Options for HTML rendering
|
|
71
71
|
*/
|
|
72
72
|
interface RenderOptions {
|
|
73
|
+
/** Wikitext settings controlling rendering behavior */
|
|
74
|
+
settings?: WikitextSettings;
|
|
73
75
|
/** Page context for resolving file paths, links, etc. */
|
|
74
76
|
page?: PageContext;
|
|
75
77
|
/** Pre-collected footnote elements from SyntaxTree.footnotes */
|
|
@@ -100,4 +102,6 @@ interface RenderOptions {
|
|
|
100
102
|
* Render a SyntaxTree to HTML string
|
|
101
103
|
*/
|
|
102
104
|
declare function renderToHtml(tree: SyntaxTree2, options?: RenderOptions): string;
|
|
103
|
-
|
|
105
|
+
import { WikitextMode, WikitextSettings as WikitextSettings3 } from "@wdprlib/ast";
|
|
106
|
+
import { createSettings, DEFAULT_SETTINGS } from "@wdprlib/ast";
|
|
107
|
+
export { renderToHtml, createSettings, WikitextSettings3 as WikitextSettings, WikitextMode, ResolvedUser, RenderResolvers, RenderOptions, PageContext, DEFAULT_SETTINGS, DEFAULT_EMBED_ALLOWLIST };
|
package/dist/index.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { SyntaxTree as SyntaxTree2 } from "@wdprlib/ast";
|
|
2
|
-
import { Element } from "@wdprlib/ast";
|
|
2
|
+
import { Element, WikitextSettings } from "@wdprlib/ast";
|
|
3
3
|
/**
|
|
4
4
|
* Allowlist entry for embed content validation
|
|
5
5
|
* Each entry specifies a host pattern and optional path prefix
|
|
@@ -70,6 +70,8 @@ interface RenderResolvers {
|
|
|
70
70
|
* Options for HTML rendering
|
|
71
71
|
*/
|
|
72
72
|
interface RenderOptions {
|
|
73
|
+
/** Wikitext settings controlling rendering behavior */
|
|
74
|
+
settings?: WikitextSettings;
|
|
73
75
|
/** Page context for resolving file paths, links, etc. */
|
|
74
76
|
page?: PageContext;
|
|
75
77
|
/** Pre-collected footnote elements from SyntaxTree.footnotes */
|
|
@@ -100,4 +102,6 @@ interface RenderOptions {
|
|
|
100
102
|
* Render a SyntaxTree to HTML string
|
|
101
103
|
*/
|
|
102
104
|
declare function renderToHtml(tree: SyntaxTree2, options?: RenderOptions): string;
|
|
103
|
-
|
|
105
|
+
import { WikitextMode, WikitextSettings as WikitextSettings3 } from "@wdprlib/ast";
|
|
106
|
+
import { createSettings, DEFAULT_SETTINGS } from "@wdprlib/ast";
|
|
107
|
+
export { renderToHtml, createSettings, WikitextSettings3 as WikitextSettings, WikitextMode, ResolvedUser, RenderResolvers, RenderOptions, PageContext, DEFAULT_SETTINGS, DEFAULT_EMBED_ALLOWLIST };
|
package/dist/index.js
CHANGED
|
@@ -1,3 +1,6 @@
|
|
|
1
|
+
// packages/render/src/context.ts
|
|
2
|
+
import { DEFAULT_SETTINGS } from "@wdprlib/ast";
|
|
3
|
+
|
|
1
4
|
// packages/render/src/escape.ts
|
|
2
5
|
function escapeHtml(text) {
|
|
3
6
|
return text.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">");
|
|
@@ -368,6 +371,8 @@ class RenderContext {
|
|
|
368
371
|
_equationIndex = 0;
|
|
369
372
|
_htmlBlockIndex = 0;
|
|
370
373
|
_bibciteCounter = 0;
|
|
374
|
+
_idSuffix;
|
|
375
|
+
settings;
|
|
371
376
|
options;
|
|
372
377
|
footnotes;
|
|
373
378
|
styles;
|
|
@@ -376,6 +381,8 @@ class RenderContext {
|
|
|
376
381
|
bibliographyMap;
|
|
377
382
|
bibliographyEntries;
|
|
378
383
|
constructor(tree, options = {}) {
|
|
384
|
+
this.settings = options.settings ?? DEFAULT_SETTINGS;
|
|
385
|
+
this._idSuffix = this.settings.useTrueIds ? null : Math.random().toString(16).slice(2, 8);
|
|
379
386
|
this.options = options;
|
|
380
387
|
this.footnotes = options.footnotes ?? tree.footnotes ?? [];
|
|
381
388
|
this.styles = tree.styles ?? [];
|
|
@@ -429,6 +436,18 @@ class RenderContext {
|
|
|
429
436
|
nextBibciteCounter() {
|
|
430
437
|
return ++this._bibciteCounter;
|
|
431
438
|
}
|
|
439
|
+
generateId(prefix, index) {
|
|
440
|
+
if (this._idSuffix === null) {
|
|
441
|
+
return `${prefix}${index}`;
|
|
442
|
+
}
|
|
443
|
+
return `${prefix}${index}-${this._idSuffix}`;
|
|
444
|
+
}
|
|
445
|
+
generateFixedId(name) {
|
|
446
|
+
if (this._idSuffix === null) {
|
|
447
|
+
return name;
|
|
448
|
+
}
|
|
449
|
+
return `${name}-${this._idSuffix}`;
|
|
450
|
+
}
|
|
432
451
|
get page() {
|
|
433
452
|
return this.options.page;
|
|
434
453
|
}
|
|
@@ -438,15 +457,23 @@ class RenderContext {
|
|
|
438
457
|
case "url": {
|
|
439
458
|
const url = source.data;
|
|
440
459
|
if (url.startsWith("/") && !url.startsWith("//")) {
|
|
460
|
+
if (!this.settings.allowLocalPaths)
|
|
461
|
+
return null;
|
|
441
462
|
return `/local--files${url}`;
|
|
442
463
|
}
|
|
443
464
|
return url;
|
|
444
465
|
}
|
|
445
466
|
case "file1":
|
|
467
|
+
if (!this.settings.allowLocalPaths)
|
|
468
|
+
return null;
|
|
446
469
|
return pageName ? `/local--files/${pageName}/${source.data.file}` : `/local--files/${source.data.file}`;
|
|
447
470
|
case "file2":
|
|
471
|
+
if (!this.settings.allowLocalPaths)
|
|
472
|
+
return null;
|
|
448
473
|
return `/local--files/${source.data.page}/${source.data.file}`;
|
|
449
474
|
case "file3":
|
|
475
|
+
if (!this.settings.allowLocalPaths)
|
|
476
|
+
return null;
|
|
450
477
|
return `/local--files/${source.data.site}/${source.data.page}/${source.data.file}`;
|
|
451
478
|
}
|
|
452
479
|
}
|
|
@@ -518,8 +545,8 @@ function renderContainer(ctx, data) {
|
|
|
518
545
|
function renderHeader(ctx, level, hasToc, attributes, elements) {
|
|
519
546
|
const tag = `h${level}`;
|
|
520
547
|
if (hasToc) {
|
|
521
|
-
const tocId = ctx.nextTocIndex();
|
|
522
|
-
ctx.push(`<${tag} id="
|
|
548
|
+
const tocId = ctx.generateId("toc", ctx.nextTocIndex());
|
|
549
|
+
ctx.push(`<${tag} id="${tocId}"${renderAttrs(attributes)}>`);
|
|
523
550
|
} else {
|
|
524
551
|
ctx.push(`<${tag}${renderAttrs(attributes)}>`);
|
|
525
552
|
}
|
|
@@ -805,6 +832,8 @@ function renderAnchorName(ctx, name) {
|
|
|
805
832
|
// packages/render/src/elements/image.ts
|
|
806
833
|
function renderImage(ctx, data) {
|
|
807
834
|
let src = ctx.resolveImageSource(data.source);
|
|
835
|
+
if (src === null)
|
|
836
|
+
return;
|
|
808
837
|
if (isDangerousUrl(src)) {
|
|
809
838
|
src = "#invalid-url";
|
|
810
839
|
}
|
|
@@ -3889,7 +3918,7 @@ function fnv1aHash(input, hexLen) {
|
|
|
3889
3918
|
function renderTabView(ctx, tabs) {
|
|
3890
3919
|
const labelString = tabs.map((t) => t.label).join("");
|
|
3891
3920
|
const hash = md5Hash(labelString);
|
|
3892
|
-
const widgetId = `wiki-tabview-${hash}
|
|
3921
|
+
const widgetId = ctx.generateFixedId(`wiki-tabview-${hash}`);
|
|
3893
3922
|
ctx.push(`<div id="${widgetId}" class="yui-navset">`);
|
|
3894
3923
|
ctx.push(`<ul class="yui-nav">`);
|
|
3895
3924
|
for (let i = 0;i < tabs.length; i++) {
|
|
@@ -3904,7 +3933,8 @@ function renderTabView(ctx, tabs) {
|
|
|
3904
3933
|
for (let i = 0;i < tabs.length; i++) {
|
|
3905
3934
|
const tab = tabs[i];
|
|
3906
3935
|
const displayStyle = i === 0 ? "" : ` style="display:none"`;
|
|
3907
|
-
ctx.
|
|
3936
|
+
const tabId = ctx.generateId("wiki-tab-0-", i);
|
|
3937
|
+
ctx.push(`<div id="${tabId}"${displayStyle}>`);
|
|
3908
3938
|
renderElements(ctx, tab.elements);
|
|
3909
3939
|
ctx.push("</div>");
|
|
3910
3940
|
}
|
|
@@ -3917,8 +3947,9 @@ function md5Hash(input) {
|
|
|
3917
3947
|
|
|
3918
3948
|
// packages/render/src/elements/footnote.ts
|
|
3919
3949
|
function renderFootnoteRef(ctx, index) {
|
|
3950
|
+
const id = ctx.generateId("footnoteref-", index);
|
|
3920
3951
|
ctx.push(`<sup class="footnoteref">`);
|
|
3921
|
-
ctx.push(`<a id="
|
|
3952
|
+
ctx.push(`<a id="${id}" href="javascript:;" class="footnoteref">${index}</a>`);
|
|
3922
3953
|
ctx.push("</sup>");
|
|
3923
3954
|
}
|
|
3924
3955
|
function renderFootnoteBlock(ctx, data) {
|
|
@@ -3930,7 +3961,8 @@ function renderFootnoteBlock(ctx, data) {
|
|
|
3930
3961
|
for (let i = 0;i < ctx.footnotes.length; i++) {
|
|
3931
3962
|
const index = i + 1;
|
|
3932
3963
|
const elements = ctx.footnotes[i] ?? [];
|
|
3933
|
-
ctx.
|
|
3964
|
+
const fnId = ctx.generateId("footnote-", index);
|
|
3965
|
+
ctx.push(`<div class="footnote-footer" id="${fnId}">`);
|
|
3934
3966
|
ctx.push(`<a href="javascript:;">${index}</a>. `);
|
|
3935
3967
|
renderElements(ctx, elements);
|
|
3936
3968
|
ctx.push("</div>");
|
|
@@ -3968,7 +4000,7 @@ function renderMath(ctx, data) {
|
|
|
3968
4000
|
const index = ctx.nextEquationIndex() + 1;
|
|
3969
4001
|
const latex = data["latex-source"];
|
|
3970
4002
|
const mathml = renderLatexToMathML(latex, true);
|
|
3971
|
-
const id = data.name ?
|
|
4003
|
+
const id = data.name ? ctx.generateId("equation-", data.name) : ctx.generateId("equation-", index);
|
|
3972
4004
|
const dataName = data.name ? ` data-name="${escapeAttr(data.name)}"` : "";
|
|
3973
4005
|
ctx.push(`<div class="math-block" id="${escapeAttr(id)}"${dataName}>`);
|
|
3974
4006
|
if (data.name) {
|
|
@@ -4007,7 +4039,7 @@ function renderMathInline(ctx, data) {
|
|
|
4007
4039
|
ctx.push("</span>");
|
|
4008
4040
|
}
|
|
4009
4041
|
function renderEquationRef(ctx, name) {
|
|
4010
|
-
const id =
|
|
4042
|
+
const id = ctx.generateId("equation-", name);
|
|
4011
4043
|
ctx.push(`<span class="eref" data-target="${escapeAttr(id)}">`);
|
|
4012
4044
|
ctx.push(`<a class="eref-link" href="#${escapeAttr(id)}">`);
|
|
4013
4045
|
ctx.push(escapeHtml(name));
|
|
@@ -4362,8 +4394,9 @@ function renderBibliographyCite(ctx, data) {
|
|
|
4362
4394
|
return;
|
|
4363
4395
|
}
|
|
4364
4396
|
const idSuffix = generateIdSuffix(data.label, counter);
|
|
4365
|
-
const id = `bibcite-${number}
|
|
4366
|
-
const
|
|
4397
|
+
const id = ctx.generateId(`bibcite-${number}-`, idSuffix);
|
|
4398
|
+
const bibitemId = ctx.generateId("bibitem-", number);
|
|
4399
|
+
const onclick = `WIKIDOT.page.utils.scrollToReference('${bibitemId}')`;
|
|
4367
4400
|
ctx.push(`<a href="javascript:;" class="bibcite" id="${id}" onclick="${escapeAttr(onclick)}">`);
|
|
4368
4401
|
ctx.push(String(number));
|
|
4369
4402
|
ctx.push("</a>");
|
|
@@ -4376,7 +4409,8 @@ function renderBibliographyBlock(ctx, data, renderElements2) {
|
|
|
4376
4409
|
ctx.push(`<div class="title">${escapeHtml(title)}</div>`);
|
|
4377
4410
|
let index = 1;
|
|
4378
4411
|
for (const entry of data.entries) {
|
|
4379
|
-
ctx.
|
|
4412
|
+
const itemId = ctx.generateId("bibitem-", index);
|
|
4413
|
+
ctx.push(`<div class="bibitem" id="${itemId}">`);
|
|
4380
4414
|
ctx.push(`${index}. `);
|
|
4381
4415
|
renderElements2(ctx, entry.value);
|
|
4382
4416
|
ctx.push("</div>");
|
|
@@ -4409,12 +4443,19 @@ function renderTocList(ctx, listData, depth) {
|
|
|
4409
4443
|
renderTocItem(ctx, item, depth);
|
|
4410
4444
|
}
|
|
4411
4445
|
}
|
|
4446
|
+
function rewriteTocAnchor(ctx, href) {
|
|
4447
|
+
const match = /^#toc(\d+)$/.exec(href);
|
|
4448
|
+
if (!match)
|
|
4449
|
+
return href;
|
|
4450
|
+
return `#${ctx.generateId("toc", Number(match[1]))}`;
|
|
4451
|
+
}
|
|
4412
4452
|
function renderTocItem(ctx, item, depth) {
|
|
4413
4453
|
if (item["item-type"] === "elements") {
|
|
4414
4454
|
for (const el of item.elements) {
|
|
4415
4455
|
const link = extractLinkText(el);
|
|
4416
4456
|
if (link) {
|
|
4417
|
-
|
|
4457
|
+
const href = rewriteTocAnchor(ctx, link.href);
|
|
4458
|
+
ctx.push(`<div style="margin-left: ${depth}em;"><a href="${escapeAttr(href)}">${escapeHtml(link.text)}</a></div>`);
|
|
4418
4459
|
}
|
|
4419
4460
|
}
|
|
4420
4461
|
} else if (item["item-type"] === "sub-list") {
|
|
@@ -4979,7 +5020,7 @@ function formatNumber(n) {
|
|
|
4979
5020
|
function renderToHtml(tree, options = {}) {
|
|
4980
5021
|
const ctx = new RenderContext(tree, options);
|
|
4981
5022
|
renderElements(ctx, tree.elements);
|
|
4982
|
-
if (tree.styles?.length) {
|
|
5023
|
+
if (ctx.settings.allowStyleElements && tree.styles?.length) {
|
|
4983
5024
|
for (const style of tree.styles) {
|
|
4984
5025
|
ctx.push(`<style>${escapeStyleContent(style)}</style>`);
|
|
4985
5026
|
}
|
|
@@ -5123,7 +5164,12 @@ function renderElement(ctx, element) {
|
|
|
5123
5164
|
break;
|
|
5124
5165
|
}
|
|
5125
5166
|
}
|
|
5167
|
+
|
|
5168
|
+
// packages/render/src/index.ts
|
|
5169
|
+
import { createSettings, DEFAULT_SETTINGS as DEFAULT_SETTINGS2 } from "@wdprlib/ast";
|
|
5126
5170
|
export {
|
|
5127
5171
|
renderToHtml,
|
|
5172
|
+
createSettings,
|
|
5173
|
+
DEFAULT_SETTINGS2 as DEFAULT_SETTINGS,
|
|
5128
5174
|
DEFAULT_EMBED_ALLOWLIST
|
|
5129
5175
|
};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@wdprlib/render",
|
|
3
|
-
"version": "1.0
|
|
3
|
+
"version": "1.1.0",
|
|
4
4
|
"description": "HTML renderer for Wikidot markup",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"html",
|
|
@@ -39,7 +39,7 @@
|
|
|
39
39
|
"access": "public"
|
|
40
40
|
},
|
|
41
41
|
"dependencies": {
|
|
42
|
-
"@wdprlib/ast": "1.
|
|
42
|
+
"@wdprlib/ast": "1.1.0",
|
|
43
43
|
"domhandler": "^5.0.3",
|
|
44
44
|
"htmlparser2": "^10.0.0",
|
|
45
45
|
"sanitize-html": "^2.14.0",
|