@json-to-office/core-docx 0.17.1 → 0.17.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/dist/core/render.d.ts.map +1 -1
- package/dist/index.js +286 -282
- package/dist/index.js.map +1 -1
- package/dist/plugin/example/index.js +286 -282
- package/dist/plugin/example/index.js.map +1 -1
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/package.json +3 -3
package/dist/index.js
CHANGED
|
@@ -3469,216 +3469,116 @@ function getStyleIdForLevel(level) {
|
|
|
3469
3469
|
return styleMap[level] || "Heading1";
|
|
3470
3470
|
}
|
|
3471
3471
|
|
|
3472
|
-
// src/
|
|
3473
|
-
|
|
3474
|
-
|
|
3475
|
-
// src/utils/placeholderProcessor.ts
|
|
3476
|
-
import {
|
|
3477
|
-
TextRun,
|
|
3478
|
-
PageNumber
|
|
3479
|
-
} from "docx";
|
|
3472
|
+
// src/core/render.ts
|
|
3473
|
+
init_styleHelpers();
|
|
3474
|
+
init_layoutUtils();
|
|
3480
3475
|
|
|
3481
|
-
// src/
|
|
3482
|
-
|
|
3483
|
-
|
|
3484
|
-
|
|
3476
|
+
// src/cache/index.ts
|
|
3477
|
+
var cache_exports = {};
|
|
3478
|
+
__export(cache_exports, {
|
|
3479
|
+
CacheKeyGenerator: () => CacheKeyGenerator
|
|
3480
|
+
});
|
|
3481
|
+
__reExport(cache_exports, cache_star);
|
|
3482
|
+
import * as cache_star from "@json-to-office/shared/cache";
|
|
3485
3483
|
|
|
3486
|
-
// src/
|
|
3487
|
-
|
|
3488
|
-
|
|
3489
|
-
|
|
3490
|
-
|
|
3491
|
-
|
|
3492
|
-
static register(name, handler) {
|
|
3493
|
-
this.handlers.set(name.toUpperCase(), handler);
|
|
3484
|
+
// src/cache/key-generator.ts
|
|
3485
|
+
import { createHash } from "crypto";
|
|
3486
|
+
var CacheKeyGenerator = class {
|
|
3487
|
+
version;
|
|
3488
|
+
constructor(version = "1.0") {
|
|
3489
|
+
this.version = version;
|
|
3494
3490
|
}
|
|
3495
3491
|
/**
|
|
3496
|
-
*
|
|
3492
|
+
* Generate cache key for a component
|
|
3497
3493
|
*/
|
|
3498
|
-
|
|
3499
|
-
|
|
3494
|
+
generateKey(component, context, options = {}) {
|
|
3495
|
+
const parts = [
|
|
3496
|
+
this.version,
|
|
3497
|
+
component.name,
|
|
3498
|
+
this.hashProps(component.props)
|
|
3499
|
+
];
|
|
3500
|
+
if (options.includeTheme !== false) {
|
|
3501
|
+
parts.push(context.theme.name);
|
|
3502
|
+
}
|
|
3503
|
+
if (options.includeContext) {
|
|
3504
|
+
parts.push(this.hashContext(context));
|
|
3505
|
+
}
|
|
3506
|
+
if (options.additionalKeys) {
|
|
3507
|
+
parts.push(...options.additionalKeys);
|
|
3508
|
+
}
|
|
3509
|
+
if (options.version) {
|
|
3510
|
+
parts.push(options.version);
|
|
3511
|
+
}
|
|
3512
|
+
return parts.join(":");
|
|
3500
3513
|
}
|
|
3501
3514
|
/**
|
|
3502
|
-
*
|
|
3515
|
+
* Hash component props
|
|
3503
3516
|
*/
|
|
3504
|
-
|
|
3505
|
-
|
|
3517
|
+
hashProps(props) {
|
|
3518
|
+
if (!props) return "null";
|
|
3519
|
+
const normalized = this.normalizeObject(props);
|
|
3520
|
+
const json = JSON.stringify(normalized);
|
|
3521
|
+
return this.hash(json);
|
|
3506
3522
|
}
|
|
3507
3523
|
/**
|
|
3508
|
-
*
|
|
3524
|
+
* Hash render context
|
|
3509
3525
|
*/
|
|
3510
|
-
|
|
3511
|
-
|
|
3526
|
+
hashContext(context) {
|
|
3527
|
+
const relevant = {
|
|
3528
|
+
theme: context.theme.name,
|
|
3529
|
+
document: context.document
|
|
3530
|
+
// Exclude runtime properties like sectionIndex, componentIndex
|
|
3531
|
+
};
|
|
3532
|
+
return this.hash(JSON.stringify(relevant));
|
|
3512
3533
|
}
|
|
3513
3534
|
/**
|
|
3514
|
-
*
|
|
3535
|
+
* Normalize object for consistent hashing
|
|
3515
3536
|
*/
|
|
3516
|
-
|
|
3517
|
-
|
|
3518
|
-
|
|
3519
|
-
|
|
3520
|
-
function processTextWithPlaceholders(text, baseStyle = {}, context = {}) {
|
|
3521
|
-
const normalizedText = normalizeUnicodeText(text);
|
|
3522
|
-
const combinedRegex = /(\*\*\*|___)([\s\S]*?)\1|(\*\*|__)([\s\S]*?)\3|(\*|_)([\s\S]*?)\5|\{([^}]+)\}/g;
|
|
3523
|
-
const result = [];
|
|
3524
|
-
let lastIndex = 0;
|
|
3525
|
-
let match;
|
|
3526
|
-
while ((match = combinedRegex.exec(normalizedText)) !== null) {
|
|
3527
|
-
if (match.index > lastIndex) {
|
|
3528
|
-
const beforeText = normalizedText.substring(lastIndex, match.index);
|
|
3529
|
-
if (beforeText) {
|
|
3530
|
-
result.push(...createTextRunsWithNewlines(beforeText, baseStyle));
|
|
3531
|
-
}
|
|
3537
|
+
normalizeObject(obj) {
|
|
3538
|
+
if (obj === null || obj === void 0) return obj;
|
|
3539
|
+
if (Array.isArray(obj)) {
|
|
3540
|
+
return obj.map((item) => this.normalizeObject(item));
|
|
3532
3541
|
}
|
|
3533
|
-
if (
|
|
3534
|
-
|
|
3535
|
-
const handler = PlaceholderRegistry.get(placeholderName);
|
|
3536
|
-
if (handler) {
|
|
3537
|
-
const placeholderResult = handler({ ...context, style: baseStyle });
|
|
3538
|
-
if (Array.isArray(placeholderResult)) {
|
|
3539
|
-
result.push(...placeholderResult);
|
|
3540
|
-
} else if (placeholderResult instanceof TextRun) {
|
|
3541
|
-
result.push(placeholderResult);
|
|
3542
|
-
} else if (typeof placeholderResult === "string") {
|
|
3543
|
-
result.push(
|
|
3544
|
-
...createTextRunsWithNewlines(placeholderResult, baseStyle)
|
|
3545
|
-
);
|
|
3546
|
-
}
|
|
3547
|
-
} else {
|
|
3548
|
-
result.push(...createTextRunsWithNewlines(match[0], baseStyle));
|
|
3549
|
-
}
|
|
3550
|
-
} else {
|
|
3551
|
-
let decoratedText;
|
|
3552
|
-
let bold = baseStyle.bold || false;
|
|
3553
|
-
let italics = baseStyle.italics || false;
|
|
3554
|
-
if (match[1] === "***" || match[1] === "___") {
|
|
3555
|
-
decoratedText = match[2];
|
|
3556
|
-
bold = true;
|
|
3557
|
-
italics = true;
|
|
3558
|
-
} else if (match[3] === "**" || match[3] === "__") {
|
|
3559
|
-
decoratedText = match[4];
|
|
3560
|
-
bold = true;
|
|
3561
|
-
} else if (match[5] === "*" || match[5] === "_") {
|
|
3562
|
-
decoratedText = match[6];
|
|
3563
|
-
italics = true;
|
|
3564
|
-
} else {
|
|
3565
|
-
decoratedText = match[0];
|
|
3566
|
-
}
|
|
3567
|
-
const decoratedTextRuns = processTextWithPlaceholders(
|
|
3568
|
-
decoratedText,
|
|
3569
|
-
{
|
|
3570
|
-
...baseStyle,
|
|
3571
|
-
bold,
|
|
3572
|
-
italics
|
|
3573
|
-
},
|
|
3574
|
-
context
|
|
3575
|
-
);
|
|
3576
|
-
result.push(...decoratedTextRuns);
|
|
3542
|
+
if (obj instanceof Date) {
|
|
3543
|
+
return obj.toISOString();
|
|
3577
3544
|
}
|
|
3578
|
-
|
|
3579
|
-
|
|
3580
|
-
|
|
3581
|
-
|
|
3582
|
-
|
|
3583
|
-
|
|
3545
|
+
if (typeof obj === "object") {
|
|
3546
|
+
const sorted = {};
|
|
3547
|
+
const keys = Object.keys(obj).sort();
|
|
3548
|
+
for (const key of keys) {
|
|
3549
|
+
sorted[key] = this.normalizeObject(obj[key]);
|
|
3550
|
+
}
|
|
3551
|
+
return sorted;
|
|
3584
3552
|
}
|
|
3553
|
+
return obj;
|
|
3585
3554
|
}
|
|
3586
|
-
|
|
3587
|
-
|
|
3588
|
-
|
|
3589
|
-
|
|
3590
|
-
|
|
3591
|
-
function createTextRunsWithNewlines(text, baseStyle) {
|
|
3592
|
-
const runs = [];
|
|
3593
|
-
const lines = text.split("\n");
|
|
3594
|
-
for (let lineIndex = 0; lineIndex < lines.length; lineIndex++) {
|
|
3595
|
-
const line = lines[lineIndex];
|
|
3596
|
-
const needsLineBreak = lineIndex > 0;
|
|
3597
|
-
if (line || needsLineBreak) {
|
|
3598
|
-
runs.push(
|
|
3599
|
-
new TextRun({
|
|
3600
|
-
text: line,
|
|
3601
|
-
font: baseStyle.font,
|
|
3602
|
-
size: baseStyle.size,
|
|
3603
|
-
color: baseStyle.color,
|
|
3604
|
-
bold: baseStyle.bold,
|
|
3605
|
-
italics: baseStyle.italics,
|
|
3606
|
-
underline: baseStyle.underline,
|
|
3607
|
-
break: needsLineBreak ? 1 : void 0
|
|
3608
|
-
})
|
|
3609
|
-
);
|
|
3610
|
-
}
|
|
3555
|
+
/**
|
|
3556
|
+
* Create hash
|
|
3557
|
+
*/
|
|
3558
|
+
hash(input) {
|
|
3559
|
+
return createHash("sha256").update(input).digest("hex").substring(0, 16);
|
|
3611
3560
|
}
|
|
3612
|
-
|
|
3613
|
-
|
|
3614
|
-
|
|
3615
|
-
|
|
3616
|
-
|
|
3617
|
-
|
|
3618
|
-
|
|
3619
|
-
|
|
3620
|
-
color: context?.style?.color,
|
|
3621
|
-
bold: context?.style?.bold,
|
|
3622
|
-
italics: context?.style?.italics,
|
|
3623
|
-
underline: context?.style?.underline
|
|
3624
|
-
});
|
|
3625
|
-
});
|
|
3626
|
-
PlaceholderRegistry.register("TOTAL_PAGES", (context) => {
|
|
3627
|
-
return new TextRun({
|
|
3628
|
-
children: [PageNumber.TOTAL_PAGES],
|
|
3629
|
-
font: context?.style?.font,
|
|
3630
|
-
size: context?.style?.size,
|
|
3631
|
-
color: context?.style?.color,
|
|
3632
|
-
bold: context?.style?.bold,
|
|
3633
|
-
italics: context?.style?.italics,
|
|
3634
|
-
underline: context?.style?.underline
|
|
3635
|
-
});
|
|
3636
|
-
});
|
|
3637
|
-
PlaceholderRegistry.register("DATE", (context) => {
|
|
3638
|
-
const today = /* @__PURE__ */ new Date();
|
|
3639
|
-
const dateString = today.toLocaleDateString();
|
|
3640
|
-
return new TextRun({
|
|
3641
|
-
text: dateString,
|
|
3642
|
-
font: context?.style?.font,
|
|
3643
|
-
size: context?.style?.size,
|
|
3644
|
-
color: context?.style?.color,
|
|
3645
|
-
bold: context?.style?.bold,
|
|
3646
|
-
italics: context?.style?.italics,
|
|
3647
|
-
underline: context?.style?.underline
|
|
3648
|
-
});
|
|
3649
|
-
});
|
|
3650
|
-
PlaceholderRegistry.register("DATETIME", (context) => {
|
|
3651
|
-
const now = /* @__PURE__ */ new Date();
|
|
3652
|
-
const dateTimeString = now.toLocaleString();
|
|
3653
|
-
return new TextRun({
|
|
3654
|
-
text: dateTimeString,
|
|
3655
|
-
font: context?.style?.font,
|
|
3656
|
-
size: context?.style?.size,
|
|
3657
|
-
color: context?.style?.color,
|
|
3658
|
-
bold: context?.style?.bold,
|
|
3659
|
-
italics: context?.style?.italics,
|
|
3660
|
-
underline: context?.style?.underline
|
|
3661
|
-
});
|
|
3662
|
-
});
|
|
3663
|
-
PlaceholderRegistry.register("YEAR", (context) => {
|
|
3664
|
-
const year = (/* @__PURE__ */ new Date()).getFullYear().toString();
|
|
3665
|
-
return new TextRun({
|
|
3666
|
-
text: year,
|
|
3667
|
-
font: context?.style?.font,
|
|
3668
|
-
size: context?.style?.size,
|
|
3669
|
-
color: context?.style?.color,
|
|
3670
|
-
bold: context?.style?.bold,
|
|
3671
|
-
italics: context?.style?.italics,
|
|
3672
|
-
underline: context?.style?.underline
|
|
3673
|
-
});
|
|
3674
|
-
});
|
|
3561
|
+
};
|
|
3562
|
+
|
|
3563
|
+
// src/utils/revisionUtils.ts
|
|
3564
|
+
import { TextRun as TextRun3, InsertedTextRun, DeletedTextRun } from "docx";
|
|
3565
|
+
|
|
3566
|
+
// src/utils/unicode.ts
|
|
3567
|
+
function normalizeUnicodeText(text) {
|
|
3568
|
+
return (text ?? "").normalize("NFC");
|
|
3675
3569
|
}
|
|
3676
|
-
|
|
3570
|
+
|
|
3571
|
+
// src/utils/placeholderProcessor.ts
|
|
3572
|
+
import {
|
|
3573
|
+
TextRun as TextRun2,
|
|
3574
|
+
PageNumber
|
|
3575
|
+
} from "docx";
|
|
3677
3576
|
|
|
3678
3577
|
// src/utils/textParser.ts
|
|
3578
|
+
import { TextRun, ExternalHyperlink, InternalHyperlink } from "docx";
|
|
3679
3579
|
function parseTextWithDecorators(text, baseStyle = {}, options = {}) {
|
|
3680
3580
|
if (!text) {
|
|
3681
|
-
return [new
|
|
3581
|
+
return [new TextRun({ text: "", ...baseStyle })];
|
|
3682
3582
|
}
|
|
3683
3583
|
const normalizedText = normalizeUnicodeText(text);
|
|
3684
3584
|
const hasPlaceholders = /\{[^}]+\}/.test(normalizedText);
|
|
@@ -3700,7 +3600,7 @@ function parseTextWithDecorators(text, baseStyle = {}, options = {}) {
|
|
|
3700
3600
|
if (match.index > lastIndex) {
|
|
3701
3601
|
const plainText = normalizedText.substring(lastIndex, match.index);
|
|
3702
3602
|
if (plainText) {
|
|
3703
|
-
runs.push(...
|
|
3603
|
+
runs.push(...createTextRunsWithNewlines(plainText, baseStyle, options));
|
|
3704
3604
|
}
|
|
3705
3605
|
}
|
|
3706
3606
|
let decoratedText;
|
|
@@ -3719,7 +3619,7 @@ function parseTextWithDecorators(text, baseStyle = {}, options = {}) {
|
|
|
3719
3619
|
} else {
|
|
3720
3620
|
decoratedText = match[0];
|
|
3721
3621
|
}
|
|
3722
|
-
const decoratedRuns =
|
|
3622
|
+
const decoratedRuns = createTextRunsWithNewlines(
|
|
3723
3623
|
decoratedText,
|
|
3724
3624
|
baseStyle,
|
|
3725
3625
|
options,
|
|
@@ -3735,18 +3635,18 @@ function parseTextWithDecorators(text, baseStyle = {}, options = {}) {
|
|
|
3735
3635
|
const remainingText = normalizedText.substring(lastIndex);
|
|
3736
3636
|
if (remainingText) {
|
|
3737
3637
|
runs.push(
|
|
3738
|
-
...
|
|
3638
|
+
...createTextRunsWithNewlines(remainingText, baseStyle, options)
|
|
3739
3639
|
);
|
|
3740
3640
|
}
|
|
3741
3641
|
}
|
|
3742
3642
|
if (runs.length === 0 && normalizedText) {
|
|
3743
3643
|
runs.push(
|
|
3744
|
-
...
|
|
3644
|
+
...createTextRunsWithNewlines(normalizedText, baseStyle, options)
|
|
3745
3645
|
);
|
|
3746
3646
|
}
|
|
3747
3647
|
return runs;
|
|
3748
3648
|
}
|
|
3749
|
-
function
|
|
3649
|
+
function createTextRunsWithNewlines(text, baseStyle, options, overrideStyle) {
|
|
3750
3650
|
const runs = [];
|
|
3751
3651
|
const lines = text.split("\n");
|
|
3752
3652
|
for (let lineIndex = 0; lineIndex < lines.length; lineIndex++) {
|
|
@@ -3758,7 +3658,7 @@ function createTextRunsWithNewlines2(text, baseStyle, options, overrideStyle) {
|
|
|
3758
3658
|
italics: overrideStyle?.italics ?? baseStyle.italics
|
|
3759
3659
|
};
|
|
3760
3660
|
runs.push(
|
|
3761
|
-
new
|
|
3661
|
+
new TextRun({
|
|
3762
3662
|
text: line,
|
|
3763
3663
|
...baseStyle.font && { font: baseStyle.font },
|
|
3764
3664
|
...baseStyle.size && { size: baseStyle.size },
|
|
@@ -3804,7 +3704,7 @@ function parseTextWithHyperlinks(text, baseStyle = {}, options = {}) {
|
|
|
3804
3704
|
if (isInternal) {
|
|
3805
3705
|
const bookmarkId = linkUrl.substring(1);
|
|
3806
3706
|
runs.push(
|
|
3807
|
-
new
|
|
3707
|
+
new InternalHyperlink({
|
|
3808
3708
|
children: linkTextRuns,
|
|
3809
3709
|
// Cast needed for docx types
|
|
3810
3710
|
anchor: bookmarkId
|
|
@@ -3812,7 +3712,7 @@ function parseTextWithHyperlinks(text, baseStyle = {}, options = {}) {
|
|
|
3812
3712
|
);
|
|
3813
3713
|
} else {
|
|
3814
3714
|
runs.push(
|
|
3815
|
-
new
|
|
3715
|
+
new ExternalHyperlink({
|
|
3816
3716
|
children: linkTextRuns,
|
|
3817
3717
|
// Cast needed for docx types
|
|
3818
3718
|
link: linkUrl
|
|
@@ -3841,100 +3741,199 @@ function parseTextWithHyperlinks(text, baseStyle = {}, options = {}) {
|
|
|
3841
3741
|
return runs;
|
|
3842
3742
|
}
|
|
3843
3743
|
|
|
3844
|
-
// src/
|
|
3845
|
-
|
|
3846
|
-
|
|
3847
|
-
|
|
3848
|
-
|
|
3849
|
-
|
|
3850
|
-
|
|
3851
|
-
|
|
3852
|
-
CacheKeyGenerator: () => CacheKeyGenerator
|
|
3853
|
-
});
|
|
3854
|
-
__reExport(cache_exports, cache_star);
|
|
3855
|
-
import * as cache_star from "@json-to-office/shared/cache";
|
|
3856
|
-
|
|
3857
|
-
// src/cache/key-generator.ts
|
|
3858
|
-
import { createHash } from "crypto";
|
|
3859
|
-
var CacheKeyGenerator = class {
|
|
3860
|
-
version;
|
|
3861
|
-
constructor(version = "1.0") {
|
|
3862
|
-
this.version = version;
|
|
3744
|
+
// src/utils/placeholderProcessor.ts
|
|
3745
|
+
var PlaceholderRegistry = class {
|
|
3746
|
+
static handlers = /* @__PURE__ */ new Map();
|
|
3747
|
+
/**
|
|
3748
|
+
* Register a placeholder handler
|
|
3749
|
+
*/
|
|
3750
|
+
static register(name, handler) {
|
|
3751
|
+
this.handlers.set(name.toUpperCase(), handler);
|
|
3863
3752
|
}
|
|
3864
3753
|
/**
|
|
3865
|
-
*
|
|
3754
|
+
* Get a placeholder handler
|
|
3866
3755
|
*/
|
|
3867
|
-
|
|
3868
|
-
|
|
3869
|
-
this.version,
|
|
3870
|
-
component.name,
|
|
3871
|
-
this.hashProps(component.props)
|
|
3872
|
-
];
|
|
3873
|
-
if (options.includeTheme !== false) {
|
|
3874
|
-
parts.push(context.theme.name);
|
|
3875
|
-
}
|
|
3876
|
-
if (options.includeContext) {
|
|
3877
|
-
parts.push(this.hashContext(context));
|
|
3878
|
-
}
|
|
3879
|
-
if (options.additionalKeys) {
|
|
3880
|
-
parts.push(...options.additionalKeys);
|
|
3881
|
-
}
|
|
3882
|
-
if (options.version) {
|
|
3883
|
-
parts.push(options.version);
|
|
3884
|
-
}
|
|
3885
|
-
return parts.join(":");
|
|
3756
|
+
static get(name) {
|
|
3757
|
+
return this.handlers.get(name.toUpperCase());
|
|
3886
3758
|
}
|
|
3887
3759
|
/**
|
|
3888
|
-
*
|
|
3760
|
+
* Check if a placeholder is registered
|
|
3889
3761
|
*/
|
|
3890
|
-
|
|
3891
|
-
|
|
3892
|
-
const normalized = this.normalizeObject(props);
|
|
3893
|
-
const json = JSON.stringify(normalized);
|
|
3894
|
-
return this.hash(json);
|
|
3762
|
+
static has(name) {
|
|
3763
|
+
return this.handlers.has(name.toUpperCase());
|
|
3895
3764
|
}
|
|
3896
3765
|
/**
|
|
3897
|
-
*
|
|
3766
|
+
* Get all registered placeholder names
|
|
3898
3767
|
*/
|
|
3899
|
-
|
|
3900
|
-
|
|
3901
|
-
theme: context.theme.name,
|
|
3902
|
-
document: context.document
|
|
3903
|
-
// Exclude runtime properties like sectionIndex, componentIndex
|
|
3904
|
-
};
|
|
3905
|
-
return this.hash(JSON.stringify(relevant));
|
|
3768
|
+
static getRegisteredNames() {
|
|
3769
|
+
return Array.from(this.handlers.keys());
|
|
3906
3770
|
}
|
|
3907
3771
|
/**
|
|
3908
|
-
*
|
|
3772
|
+
* Clear all registered placeholders
|
|
3909
3773
|
*/
|
|
3910
|
-
|
|
3911
|
-
|
|
3912
|
-
|
|
3913
|
-
|
|
3914
|
-
|
|
3915
|
-
|
|
3916
|
-
|
|
3774
|
+
static clear() {
|
|
3775
|
+
this.handlers.clear();
|
|
3776
|
+
}
|
|
3777
|
+
};
|
|
3778
|
+
function processTextWithPlaceholders(text, baseStyle = {}, context = {}) {
|
|
3779
|
+
const normalizedText = normalizeUnicodeText(text);
|
|
3780
|
+
const combinedRegex = /(\*\*\*|___)([\s\S]*?)\1|(\*\*|__)([\s\S]*?)\3|(\*|_)([\s\S]*?)\5|\{([^}]+)\}/g;
|
|
3781
|
+
const result = [];
|
|
3782
|
+
let lastIndex = 0;
|
|
3783
|
+
let match;
|
|
3784
|
+
while ((match = combinedRegex.exec(normalizedText)) !== null) {
|
|
3785
|
+
if (match.index > lastIndex) {
|
|
3786
|
+
const beforeText = normalizedText.substring(lastIndex, match.index);
|
|
3787
|
+
if (beforeText) {
|
|
3788
|
+
result.push(...createTextRunsWithNewlines2(beforeText, baseStyle));
|
|
3789
|
+
}
|
|
3917
3790
|
}
|
|
3918
|
-
if (
|
|
3919
|
-
const
|
|
3920
|
-
const
|
|
3921
|
-
|
|
3922
|
-
|
|
3791
|
+
if (match[7]) {
|
|
3792
|
+
const placeholderName = match[7];
|
|
3793
|
+
const handler = PlaceholderRegistry.get(placeholderName);
|
|
3794
|
+
if (handler) {
|
|
3795
|
+
const placeholderResult = handler({ ...context, style: baseStyle });
|
|
3796
|
+
if (Array.isArray(placeholderResult)) {
|
|
3797
|
+
result.push(...placeholderResult);
|
|
3798
|
+
} else if (placeholderResult instanceof TextRun2) {
|
|
3799
|
+
result.push(placeholderResult);
|
|
3800
|
+
} else if (typeof placeholderResult === "string") {
|
|
3801
|
+
result.push(
|
|
3802
|
+
...createTextRunsWithNewlines2(placeholderResult, baseStyle)
|
|
3803
|
+
);
|
|
3804
|
+
}
|
|
3805
|
+
} else {
|
|
3806
|
+
result.push(...createTextRunsWithNewlines2(match[0], baseStyle));
|
|
3923
3807
|
}
|
|
3924
|
-
|
|
3808
|
+
} else {
|
|
3809
|
+
let decoratedText;
|
|
3810
|
+
let bold = baseStyle.bold || false;
|
|
3811
|
+
let italics = baseStyle.italics || false;
|
|
3812
|
+
if (match[1] === "***" || match[1] === "___") {
|
|
3813
|
+
decoratedText = match[2];
|
|
3814
|
+
bold = true;
|
|
3815
|
+
italics = true;
|
|
3816
|
+
} else if (match[3] === "**" || match[3] === "__") {
|
|
3817
|
+
decoratedText = match[4];
|
|
3818
|
+
bold = true;
|
|
3819
|
+
} else if (match[5] === "*" || match[5] === "_") {
|
|
3820
|
+
decoratedText = match[6];
|
|
3821
|
+
italics = true;
|
|
3822
|
+
} else {
|
|
3823
|
+
decoratedText = match[0];
|
|
3824
|
+
}
|
|
3825
|
+
const decoratedTextRuns = processTextWithPlaceholders(
|
|
3826
|
+
decoratedText,
|
|
3827
|
+
{
|
|
3828
|
+
...baseStyle,
|
|
3829
|
+
bold,
|
|
3830
|
+
italics
|
|
3831
|
+
},
|
|
3832
|
+
context
|
|
3833
|
+
);
|
|
3834
|
+
result.push(...decoratedTextRuns);
|
|
3925
3835
|
}
|
|
3926
|
-
|
|
3836
|
+
lastIndex = match.index + match[0].length;
|
|
3927
3837
|
}
|
|
3928
|
-
|
|
3929
|
-
|
|
3930
|
-
|
|
3931
|
-
|
|
3932
|
-
|
|
3838
|
+
if (lastIndex < normalizedText.length) {
|
|
3839
|
+
const remainingText = normalizedText.substring(lastIndex);
|
|
3840
|
+
if (remainingText) {
|
|
3841
|
+
result.push(...createTextRunsWithNewlines2(remainingText, baseStyle));
|
|
3842
|
+
}
|
|
3933
3843
|
}
|
|
3934
|
-
|
|
3844
|
+
if (result.length === 0 && normalizedText) {
|
|
3845
|
+
result.push(...createTextRunsWithNewlines2(normalizedText, baseStyle));
|
|
3846
|
+
}
|
|
3847
|
+
return result;
|
|
3848
|
+
}
|
|
3849
|
+
function createTextRunsWithNewlines2(text, baseStyle) {
|
|
3850
|
+
const runs = [];
|
|
3851
|
+
const lines = text.split("\n");
|
|
3852
|
+
for (let lineIndex = 0; lineIndex < lines.length; lineIndex++) {
|
|
3853
|
+
const line = lines[lineIndex];
|
|
3854
|
+
const needsLineBreak = lineIndex > 0;
|
|
3855
|
+
if (line || needsLineBreak) {
|
|
3856
|
+
runs.push(
|
|
3857
|
+
new TextRun2({
|
|
3858
|
+
text: line,
|
|
3859
|
+
font: baseStyle.font,
|
|
3860
|
+
size: baseStyle.size,
|
|
3861
|
+
color: baseStyle.color,
|
|
3862
|
+
bold: baseStyle.bold,
|
|
3863
|
+
italics: baseStyle.italics,
|
|
3864
|
+
underline: baseStyle.underline,
|
|
3865
|
+
break: needsLineBreak ? 1 : void 0
|
|
3866
|
+
})
|
|
3867
|
+
);
|
|
3868
|
+
}
|
|
3869
|
+
}
|
|
3870
|
+
return runs;
|
|
3871
|
+
}
|
|
3872
|
+
function initializeBuiltinPlaceholders() {
|
|
3873
|
+
PlaceholderRegistry.register("PAGE", (context) => {
|
|
3874
|
+
return new TextRun2({
|
|
3875
|
+
children: [PageNumber.CURRENT],
|
|
3876
|
+
font: context?.style?.font,
|
|
3877
|
+
size: context?.style?.size,
|
|
3878
|
+
color: context?.style?.color,
|
|
3879
|
+
bold: context?.style?.bold,
|
|
3880
|
+
italics: context?.style?.italics,
|
|
3881
|
+
underline: context?.style?.underline
|
|
3882
|
+
});
|
|
3883
|
+
});
|
|
3884
|
+
PlaceholderRegistry.register("TOTAL_PAGES", (context) => {
|
|
3885
|
+
return new TextRun2({
|
|
3886
|
+
children: [PageNumber.TOTAL_PAGES],
|
|
3887
|
+
font: context?.style?.font,
|
|
3888
|
+
size: context?.style?.size,
|
|
3889
|
+
color: context?.style?.color,
|
|
3890
|
+
bold: context?.style?.bold,
|
|
3891
|
+
italics: context?.style?.italics,
|
|
3892
|
+
underline: context?.style?.underline
|
|
3893
|
+
});
|
|
3894
|
+
});
|
|
3895
|
+
PlaceholderRegistry.register("DATE", (context) => {
|
|
3896
|
+
const today = /* @__PURE__ */ new Date();
|
|
3897
|
+
const dateString = today.toLocaleDateString();
|
|
3898
|
+
return new TextRun2({
|
|
3899
|
+
text: dateString,
|
|
3900
|
+
font: context?.style?.font,
|
|
3901
|
+
size: context?.style?.size,
|
|
3902
|
+
color: context?.style?.color,
|
|
3903
|
+
bold: context?.style?.bold,
|
|
3904
|
+
italics: context?.style?.italics,
|
|
3905
|
+
underline: context?.style?.underline
|
|
3906
|
+
});
|
|
3907
|
+
});
|
|
3908
|
+
PlaceholderRegistry.register("DATETIME", (context) => {
|
|
3909
|
+
const now = /* @__PURE__ */ new Date();
|
|
3910
|
+
const dateTimeString = now.toLocaleString();
|
|
3911
|
+
return new TextRun2({
|
|
3912
|
+
text: dateTimeString,
|
|
3913
|
+
font: context?.style?.font,
|
|
3914
|
+
size: context?.style?.size,
|
|
3915
|
+
color: context?.style?.color,
|
|
3916
|
+
bold: context?.style?.bold,
|
|
3917
|
+
italics: context?.style?.italics,
|
|
3918
|
+
underline: context?.style?.underline
|
|
3919
|
+
});
|
|
3920
|
+
});
|
|
3921
|
+
PlaceholderRegistry.register("YEAR", (context) => {
|
|
3922
|
+
const year = (/* @__PURE__ */ new Date()).getFullYear().toString();
|
|
3923
|
+
return new TextRun2({
|
|
3924
|
+
text: year,
|
|
3925
|
+
font: context?.style?.font,
|
|
3926
|
+
size: context?.style?.size,
|
|
3927
|
+
color: context?.style?.color,
|
|
3928
|
+
bold: context?.style?.bold,
|
|
3929
|
+
italics: context?.style?.italics,
|
|
3930
|
+
underline: context?.style?.underline
|
|
3931
|
+
});
|
|
3932
|
+
});
|
|
3933
|
+
}
|
|
3934
|
+
initializeBuiltinPlaceholders();
|
|
3935
3935
|
|
|
3936
3936
|
// src/utils/revisionUtils.ts
|
|
3937
|
-
import { TextRun as TextRun3, InsertedTextRun, DeletedTextRun } from "docx";
|
|
3938
3937
|
var DEFAULT_REVISION_AUTHOR = "json-to-office";
|
|
3939
3938
|
var DEFAULT_REVISION_DATE = "1970-01-01T00:00:00Z";
|
|
3940
3939
|
var RevisionIdRegistry = class {
|
|
@@ -6736,21 +6735,26 @@ async function renderHeaderFooterComponents(components, theme, themeName, contex
|
|
|
6736
6735
|
for (const component of activeComponents) {
|
|
6737
6736
|
if (isParagraphComponent(component)) {
|
|
6738
6737
|
const textComp = component;
|
|
6738
|
+
const font = textComp.props.font;
|
|
6739
6739
|
const normalStyle = getNormalStyle(theme);
|
|
6740
|
-
const textStyle = {
|
|
6741
|
-
font: textComp.props.font?.family || resolveFontFamily(theme, normalStyle.font) || getThemeFonts(theme).body.family,
|
|
6742
|
-
size: (textComp.props.font?.size ?? normalStyle.size ?? 11) * 2,
|
|
6743
|
-
// Convert to half-points
|
|
6744
|
-
bold: textComp.props.font?.bold ?? false,
|
|
6745
|
-
italics: textComp.props.font?.italic ?? false,
|
|
6746
|
-
color: textComp.props.font?.color && resolveColor(textComp.props.font.color, theme) || normalStyle.color && resolveColor(normalStyle.color, theme) || getThemeColors(theme).textPrimary
|
|
6747
|
-
};
|
|
6748
|
-
const textRuns = parseTextWithDecorators(textComp.props.text, textStyle);
|
|
6749
6740
|
elements.push(
|
|
6750
|
-
|
|
6751
|
-
|
|
6752
|
-
alignment: textComp.props.alignment
|
|
6753
|
-
style
|
|
6741
|
+
createText(textComp.props.text, theme, themeName, {
|
|
6742
|
+
style: "Normal",
|
|
6743
|
+
alignment: textComp.props.alignment,
|
|
6744
|
+
// Resolve explicit run styling against the Normal style, preserving
|
|
6745
|
+
// prior header/footer rendering for these properties.
|
|
6746
|
+
fontFamily: font?.family || resolveFontFamily(theme, normalStyle.font) || getThemeFonts(theme).body.family,
|
|
6747
|
+
fontSize: font?.size ?? normalStyle.size ?? 11,
|
|
6748
|
+
// Pass the raw color/token; createText resolves it. Fall back to the
|
|
6749
|
+
// Normal style color, then the theme's primary text color.
|
|
6750
|
+
fontColor: font?.color || normalStyle.color || "textPrimary",
|
|
6751
|
+
bold: font?.bold ?? false,
|
|
6752
|
+
italic: font?.italic ?? false,
|
|
6753
|
+
underline: font?.underline,
|
|
6754
|
+
fontWeight: font?.fontWeight,
|
|
6755
|
+
boldColor: textComp.props.boldColor,
|
|
6756
|
+
spacing: textComp.props.spacing,
|
|
6757
|
+
lineSpacing: font?.lineSpacing
|
|
6754
6758
|
})
|
|
6755
6759
|
);
|
|
6756
6760
|
} else if (isImageComponent(component)) {
|