@json-to-office/core-docx 1.10.0 → 2.0.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.
Files changed (42) hide show
  1. package/dist/core/generateFromIr.d.ts +8 -0
  2. package/dist/core/generateFromIr.d.ts.map +1 -1
  3. package/dist/core/generator.d.ts +8 -0
  4. package/dist/core/generator.d.ts.map +1 -1
  5. package/dist/core/tableModel.d.ts +1 -1
  6. package/dist/core/tableModel.d.ts.map +1 -1
  7. package/dist/index.d.ts +1 -1
  8. package/dist/index.d.ts.map +1 -1
  9. package/dist/index.js +491 -591
  10. package/dist/index.js.map +1 -1
  11. package/dist/ir/inline.d.ts.map +1 -1
  12. package/dist/plugin/createDocumentGenerator.d.ts +8 -0
  13. package/dist/plugin/createDocumentGenerator.d.ts.map +1 -1
  14. package/dist/plugin/example/index.js +487 -588
  15. package/dist/plugin/example/index.js.map +1 -1
  16. package/dist/renderers/docxjs/emit.d.ts.map +1 -1
  17. package/dist/renderers/docxjs/index.d.ts.map +1 -1
  18. package/dist/renderers/office-open/index.d.ts +1 -1
  19. package/dist/renderers/office-open/index.d.ts.map +1 -1
  20. package/dist/renderers/types.d.ts +9 -0
  21. package/dist/renderers/types.d.ts.map +1 -1
  22. package/dist/styles/index.d.ts +1 -1
  23. package/dist/styles/index.d.ts.map +1 -1
  24. package/dist/templates/documents/field-review.docx.json +1148 -0
  25. package/dist/templates/documents/index.d.ts +2 -2
  26. package/dist/templates/documents/index.d.ts.map +1 -1
  27. package/dist/templates/documents/practice-note.docx.json +917 -0
  28. package/dist/templates/themes/devportal.docx.theme.json +110 -44
  29. package/dist/templates/themes/index.d.ts +2 -2
  30. package/dist/templates/themes/index.d.ts.map +1 -1
  31. package/dist/templates/themes/minimal.docx.theme.json +124 -127
  32. package/dist/templates/themes/vermilion.docx.theme.json +82 -1
  33. package/dist/tsconfig.tsbuildinfo +1 -1
  34. package/dist/utils/imageUtils.d.ts +19 -0
  35. package/dist/utils/imageUtils.d.ts.map +1 -1
  36. package/dist/utils/listLevels.d.ts.map +1 -1
  37. package/package.json +3 -3
  38. package/dist/templates/documents/proposal.docx.json +0 -1723
  39. package/dist/templates/documents/technical-guide.docx.json +0 -2040
  40. package/dist/templates/themes/apex.docx.theme.json +0 -117
  41. package/dist/templates/themes/corporate.docx.theme.json +0 -114
  42. package/dist/templates/themes/modern.docx.theme.json +0 -109
package/dist/index.js CHANGED
@@ -257,545 +257,181 @@ var minimal_docx_theme_default;
257
257
  var init_minimal_docx_theme = __esm({
258
258
  "src/templates/themes/minimal.docx.theme.json"() {
259
259
  minimal_docx_theme_default = {
260
- $schema: "../../../../shared/json-schemas/theme.schema.json",
261
260
  name: "minimal",
262
261
  displayName: "Minimal Clean",
263
- description: "A clean, minimalist theme focused on readability and elegant simplicity",
264
- version: "2.0.0",
262
+ description: "A quiet, warm minimal theme \u2014 Calibri throughout, sage-green ink on ivory neutrals, a large tracked-tight bold title, wide margins and hairline rules",
263
+ version: "4.0.0",
265
264
  colors: {
266
- primary: "#000000",
267
- secondary: "#666666",
268
- accent: "#2c3e50",
269
- background: "#ffffff",
270
- text: "#2c2c2c",
271
- border: "#f0f0f0",
272
- textPrimary: "#000000",
273
- textSecondary: "#4a4a4a",
274
- textMuted: "#999999",
275
- borderPrimary: "#e0e0e0",
276
- borderSecondary: "#f5f5f5",
277
- backgroundPrimary: "#ffffff",
278
- backgroundSecondary: "#fafafa"
279
- },
280
- fonts: {
281
- heading: {
282
- family: "Arial",
283
- size: 24
284
- },
285
- body: {
286
- family: "Arial",
287
- size: 11
288
- },
289
- mono: {
290
- family: "Menlo",
291
- size: 10
292
- },
293
- light: {
294
- family: "Arial",
295
- size: 24
296
- }
297
- },
298
- page: {
299
- size: "A4",
300
- margins: {
301
- top: 1440,
302
- bottom: 1440,
303
- left: 1080,
304
- right: 1080,
305
- header: 720,
306
- footer: 720,
307
- gutter: 0
308
- }
309
- },
310
- styles: {
311
- normal: {
312
- font: "body",
313
- color: "#000000",
314
- lineSpacing: {
315
- type: "multiple",
316
- value: 1.5
317
- },
318
- alignment: "justify",
319
- spacing: {
320
- after: 9
321
- }
322
- },
323
- heading1: {
324
- font: "light",
325
- size: 24,
326
- bold: false,
327
- color: "#000000",
328
- spacing: {
329
- before: 18,
330
- after: 12
331
- },
332
- keepNext: true,
333
- alignment: "left",
334
- characterSpacing: {
335
- type: "expanded",
336
- value: 1.2
337
- }
338
- },
339
- heading2: {
340
- font: "light",
341
- size: 20,
342
- bold: false,
343
- color: "#000000",
344
- spacing: {
345
- before: 12,
346
- after: 9
347
- },
348
- keepNext: true,
349
- alignment: "left",
350
- characterSpacing: {
351
- type: "expanded",
352
- value: 0.8
353
- }
354
- },
355
- heading3: {
356
- font: "heading",
357
- size: 16,
358
- bold: false,
359
- color: "#2c2c2c",
360
- spacing: {
361
- before: 9,
362
- after: 6
363
- },
364
- keepNext: true,
365
- alignment: "left"
366
- },
367
- heading4: {
368
- font: "heading",
369
- size: 14,
370
- bold: true,
371
- color: "#4a4a4a",
372
- spacing: {
373
- before: 6,
374
- after: 4
375
- },
376
- keepNext: true
377
- },
378
- heading5: {
379
- font: "heading",
380
- size: 12,
381
- bold: false,
382
- italic: true,
383
- color: "#666666",
384
- spacing: {
385
- before: 4,
386
- after: 3
387
- }
388
- },
389
- heading6: {
390
- font: "light",
391
- size: 11,
392
- bold: false,
393
- color: "#999999",
394
- spacing: {
395
- before: 3,
396
- after: 2
397
- }
398
- },
399
- title: {
400
- font: "light",
401
- bold: false,
402
- color: "#000000",
403
- alignment: "left",
404
- spacing: {
405
- before: 0,
406
- after: 24
407
- },
408
- characterSpacing: {
409
- type: "condensed",
410
- value: 20
411
- }
412
- },
413
- subtitle: {
414
- font: "light",
415
- size: 16,
416
- italic: false,
417
- color: "#666666",
418
- alignment: "left",
419
- spacing: {
420
- before: 0,
421
- after: 18
422
- }
423
- }
424
- },
425
- componentDefaults: {
426
- table: {
427
- borderColor: "#f0f0f0"
428
- },
429
- list: {
430
- format: "bullet",
431
- bullet: "\u2022"
432
- },
433
- image: {
434
- alignment: "left"
435
- },
436
- statistic: {
437
- alignment: "left"
438
- },
439
- section: {
440
- pageBreak: false
441
- }
442
- }
443
- };
444
- }
445
- });
446
-
447
- // src/templates/themes/corporate.docx.theme.json
448
- var corporate_docx_theme_default;
449
- var init_corporate_docx_theme = __esm({
450
- "src/templates/themes/corporate.docx.theme.json"() {
451
- corporate_docx_theme_default = {
452
- name: "corporate",
453
- displayName: "Corporate Professional",
454
- description: "A polished corporate theme with blue accents and structured typography",
455
- version: "2.0.0",
456
- colors: {
457
- primary: "#1a365d",
458
- secondary: "#2D3748",
459
- accent: "#3182CE",
460
- text: "#1A202C",
265
+ primary: "#2B302B",
266
+ secondary: "#4A5B4E",
267
+ accent: "#6E7F71",
268
+ text: "#3B3C38",
461
269
  background: "#FFFFFF",
462
- border: "#E2E8F0",
463
- textPrimary: "#1A202C",
464
- textSecondary: "#4A5568",
465
- textMuted: "#A0AEC0",
466
- borderPrimary: "#CBD5E0",
467
- borderSecondary: "#E2E8F0",
270
+ border: "#D8D3C8",
271
+ textPrimary: "#3B3C38",
272
+ textSecondary: "#5B5B54",
273
+ textMuted: "#75726A",
274
+ borderPrimary: "#D8D3C8",
275
+ borderSecondary: "#E9E6DE",
468
276
  backgroundPrimary: "#FFFFFF",
469
- backgroundSecondary: "#F7FAFC"
277
+ backgroundSecondary: "#F1EFE9",
278
+ accent4: "#9AA69C",
279
+ accent5: "#C9CFC7",
280
+ accent6: "#B5AC9D"
470
281
  },
471
282
  fonts: {
472
- heading: { family: "Georgia", size: 26 },
473
- body: { family: "Calibri", size: 11 },
474
- mono: { family: "Consolas", size: 10 },
475
- light: { family: "Georgia", size: 26 }
283
+ heading: { family: "Calibri", size: 21 },
284
+ body: { family: "Calibri", size: 10 },
285
+ mono: { family: "Courier New", size: 10 },
286
+ light: { family: "Calibri", size: 21 }
476
287
  },
477
288
  page: {
478
289
  size: "A4",
479
290
  margins: {
480
- top: 1440,
481
- bottom: 1440,
482
- left: 1200,
483
- right: 1200,
484
- header: 720,
485
- footer: 720,
291
+ top: 1700,
292
+ bottom: 1700,
293
+ left: 1700,
294
+ right: 1700,
295
+ header: 850,
296
+ footer: 850,
486
297
  gutter: 0
487
298
  }
488
299
  },
489
300
  styles: {
490
301
  normal: {
491
302
  font: "body",
492
- color: "#1A202C",
493
- lineSpacing: { type: "multiple", value: 1.4 },
494
- alignment: "justify",
495
- spacing: { after: 8 }
496
- },
497
- heading1: {
498
- font: "heading",
499
- size: 26,
500
- bold: false,
501
- color: "primary",
502
- spacing: { before: 24, after: 12 },
503
- keepNext: true,
303
+ color: "textPrimary",
304
+ lineSpacing: { type: "multiple", value: 1.35 },
504
305
  alignment: "left",
505
- borders: {
506
- bottom: {
507
- style: "single",
508
- size: 2,
509
- color: "primary",
510
- space: 6
511
- }
512
- }
306
+ spacing: { after: 8 }
513
307
  },
514
- heading2: {
308
+ title: {
515
309
  font: "heading",
516
- size: 18,
517
- bold: false,
518
- color: "secondary",
519
- spacing: { before: 18, after: 8 },
520
- keepNext: true,
521
- alignment: "left"
522
- },
523
- heading3: {
524
- font: "body",
525
- size: 13,
310
+ size: 34,
526
311
  bold: true,
527
- color: "accent",
528
- spacing: { before: 12, after: 6 },
529
- keepNext: true,
530
- alignment: "left"
531
- },
532
- title: {
533
- font: "light",
534
- size: 32,
535
- bold: false,
536
312
  color: "primary",
537
313
  alignment: "left",
538
- spacing: { before: 0, after: 18 }
314
+ lineSpacing: { type: "multiple", value: 1 },
315
+ characterSpacing: { type: "condensed", value: 20 },
316
+ spacing: { before: 0, after: 11 }
539
317
  },
540
318
  subtitle: {
541
319
  font: "body",
542
- size: 16,
320
+ size: 13,
543
321
  italic: false,
544
322
  color: "textSecondary",
545
323
  alignment: "left",
546
- spacing: { before: 0, after: 24 }
547
- }
548
- },
549
- componentDefaults: {
550
- table: {
551
- borderColor: "#E2E8F0"
552
- },
553
- list: {
554
- format: "bullet",
555
- bullet: "\u2022"
556
- },
557
- statistic: {
558
- alignment: "center"
559
- },
560
- section: {
561
- pageBreak: false
562
- }
563
- }
564
- };
565
- }
566
- });
567
-
568
- // src/templates/themes/modern.docx.theme.json
569
- var modern_docx_theme_default;
570
- var init_modern_docx_theme = __esm({
571
- "src/templates/themes/modern.docx.theme.json"() {
572
- modern_docx_theme_default = {
573
- name: "modern",
574
- displayName: "Modern Clean",
575
- description: "A contemporary theme with vibrant accents and generous whitespace",
576
- version: "2.0.0",
577
- colors: {
578
- primary: "#6D28D9",
579
- secondary: "#1E293B",
580
- accent: "#0891B2",
581
- text: "#0F172A",
582
- background: "#FFFFFF",
583
- border: "#E2E8F0",
584
- textPrimary: "#0F172A",
585
- textSecondary: "#475569",
586
- textMuted: "#94A3B8",
587
- borderPrimary: "#CBD5E1",
588
- borderSecondary: "#E2E8F0",
589
- backgroundPrimary: "#FFFFFF",
590
- backgroundSecondary: "#F8FAFC"
591
- },
592
- fonts: {
593
- heading: { family: "Helvetica", size: 28 },
594
- body: { family: "Helvetica", size: 11 },
595
- mono: { family: "Menlo", size: 10 },
596
- light: { family: "Helvetica", size: 28 }
597
- },
598
- page: {
599
- size: "A4",
600
- margins: {
601
- top: 1440,
602
- bottom: 1440,
603
- left: 1080,
604
- right: 1080,
605
- header: 720,
606
- footer: 720,
607
- gutter: 0
608
- }
609
- },
610
- styles: {
611
- normal: {
612
- font: "body",
613
- color: "#0F172A",
614
- lineSpacing: { type: "multiple", value: 1.5 },
615
- alignment: "left",
616
- spacing: { after: 10 }
324
+ lineSpacing: { type: "multiple", value: 1.2 },
325
+ spacing: { before: 0, after: 22 }
617
326
  },
618
327
  heading1: {
619
328
  font: "heading",
620
- size: 28,
329
+ size: 21,
621
330
  bold: true,
622
331
  color: "primary",
623
- spacing: { before: 24, after: 14 },
332
+ lineSpacing: { type: "multiple", value: 1.15 },
333
+ spacing: { before: 30, after: 10 },
624
334
  keepNext: true,
625
335
  alignment: "left"
626
336
  },
627
337
  heading2: {
628
338
  font: "heading",
629
- size: 20,
339
+ size: 14.5,
630
340
  bold: true,
631
- color: "secondary",
632
- spacing: { before: 18, after: 10 },
341
+ color: "primary",
342
+ lineSpacing: { type: "multiple", value: 1.15 },
343
+ spacing: { before: 22, after: 8 },
633
344
  keepNext: true,
634
345
  alignment: "left"
635
346
  },
636
347
  heading3: {
637
- font: "body",
638
- size: 14,
348
+ font: "heading",
349
+ size: 12,
639
350
  bold: true,
640
- color: "accent",
641
- spacing: { before: 12, after: 6 },
351
+ color: "primary",
352
+ spacing: { before: 16, after: 6 },
642
353
  keepNext: true,
643
354
  alignment: "left"
644
355
  },
645
- title: {
646
- font: "heading",
647
- size: 36,
356
+ heading4: {
357
+ font: "body",
358
+ size: 10.5,
648
359
  bold: true,
649
360
  color: "primary",
650
- alignment: "left",
651
- spacing: { before: 0, after: 12 }
652
- },
653
- subtitle: {
654
- font: "light",
655
- size: 18,
656
- italic: false,
657
- color: "textSecondary",
658
- alignment: "left",
659
- spacing: { before: 0, after: 24 }
660
- }
661
- },
662
- componentDefaults: {
663
- table: {
664
- borderColor: "#E2E8F0"
665
- },
666
- list: {
667
- format: "bullet",
668
- bullet: "\u2013"
669
- },
670
- image: {
671
- alignment: "center"
672
- },
673
- statistic: {
674
- alignment: "center"
361
+ spacing: { before: 12, after: 4 },
362
+ keepNext: true,
363
+ alignment: "left"
675
364
  },
676
- section: {
677
- pageBreak: false
678
- }
679
- }
680
- };
681
- }
682
- });
683
-
684
- // src/templates/themes/apex.docx.theme.json
685
- var apex_docx_theme_default;
686
- var init_apex_docx_theme = __esm({
687
- "src/templates/themes/apex.docx.theme.json"() {
688
- apex_docx_theme_default = {
689
- name: "apex",
690
- displayName: "Apex Consulting",
691
- description: "A premium consulting theme with deep navy, warm amber accents, and authoritative typography",
692
- version: "2.0.0",
693
- colors: {
694
- primary: "#0C2340",
695
- secondary: "#1B3A5C",
696
- accent: "#D4A843",
697
- text: "#1A1A2E",
698
- background: "#FFFFFF",
699
- border: "#D6DAE0",
700
- textPrimary: "#1A1A2E",
701
- textSecondary: "#4A5066",
702
- textMuted: "#8B91A0",
703
- borderPrimary: "#B8BCC6",
704
- borderSecondary: "#E8EAF0",
705
- backgroundPrimary: "#FFFFFF",
706
- backgroundSecondary: "#F4F5F8"
707
- },
708
- fonts: {
709
- heading: { family: "Georgia", size: 26 },
710
- body: { family: "Calibri", size: 11 },
711
- mono: { family: "Consolas", size: 10 },
712
- light: { family: "Georgia", size: 26 }
713
- },
714
- page: {
715
- size: "A4",
716
- margins: {
717
- top: 1440,
718
- bottom: 1440,
719
- left: 1200,
720
- right: 1200,
721
- header: 720,
722
- footer: 720,
723
- gutter: 0
724
- }
725
- },
726
- styles: {
727
- normal: {
365
+ heading5: {
728
366
  font: "body",
729
- color: "textPrimary",
730
- lineSpacing: { type: "multiple", value: 1.4 },
731
- alignment: "justify",
732
- spacing: { after: 8 }
733
- },
734
- heading1: {
735
- font: "heading",
736
- size: 26,
367
+ size: 10.5,
737
368
  bold: false,
738
- color: "primary",
739
- spacing: { before: 24, after: 12 },
369
+ italic: true,
370
+ color: "textSecondary",
371
+ spacing: { before: 10, after: 4 },
740
372
  keepNext: true,
741
- alignment: "left",
742
- borders: {
743
- bottom: {
744
- style: "single",
745
- size: 2,
746
- color: "accent",
747
- space: 6
748
- }
749
- }
373
+ alignment: "left"
750
374
  },
751
- heading2: {
752
- font: "heading",
753
- size: 18,
375
+ heading6: {
376
+ font: "body",
377
+ size: 10,
754
378
  bold: false,
755
- color: "secondary",
756
- spacing: { before: 18, after: 8 },
379
+ color: "textMuted",
380
+ characterSpacing: { type: "expanded", value: 20 },
381
+ spacing: { before: 10, after: 4 },
757
382
  keepNext: true,
758
383
  alignment: "left"
759
384
  },
760
- heading3: {
385
+ TOC1: {
761
386
  font: "body",
762
- size: 13,
387
+ size: 10.5,
763
388
  bold: true,
764
- color: "accent",
765
- spacing: { before: 12, after: 6 },
766
- keepNext: true,
767
- alignment: "left"
768
- },
769
- title: {
770
- font: "light",
771
- size: 36,
772
- bold: false,
773
- color: "primary",
774
- alignment: "left",
775
- spacing: { before: 0, after: 18 }
389
+ color: "textPrimary",
390
+ spacing: { before: 4, after: 3 },
391
+ tabStops: [{ type: "right", position: 8506, leader: "none" }]
776
392
  },
777
- subtitle: {
393
+ TOC2: {
778
394
  font: "body",
779
- size: 16,
780
- italic: false,
395
+ size: 10.5,
781
396
  color: "textSecondary",
782
- alignment: "left",
783
- spacing: { before: 0, after: 24 }
397
+ indent: { left: 240 },
398
+ spacing: { after: 2 },
399
+ tabStops: [{ type: "right", position: 8506, leader: "none" }]
400
+ },
401
+ TOC3: {
402
+ font: "body",
403
+ size: 10,
404
+ color: "textMuted",
405
+ indent: { left: 480 },
406
+ spacing: { after: 2 },
407
+ tabStops: [{ type: "right", position: 8506, leader: "none" }]
784
408
  }
785
409
  },
786
410
  componentDefaults: {
787
411
  table: {
788
- borderColor: "#D6DAE0"
412
+ borderColor: "#D8D3C8",
413
+ borderSize: 0.5,
414
+ hideBorders: { left: true, right: true, insideVertical: true },
415
+ cellDefaults: {
416
+ padding: { top: 3, bottom: 3 }
417
+ },
418
+ headerCellDefaults: {
419
+ font: { bold: true },
420
+ color: "#2B302B",
421
+ borderColor: { bottom: "#2B302B" },
422
+ borderSize: { bottom: 1 }
423
+ }
789
424
  },
790
425
  list: {
791
426
  format: "bullet",
792
- bullet: "\u2022"
427
+ bullet: "\u2013",
428
+ spacing: { item: 2 }
793
429
  },
794
430
  image: {
795
- alignment: "center"
431
+ alignment: "left"
796
432
  },
797
433
  statistic: {
798
- alignment: "center"
434
+ alignment: "left"
799
435
  },
800
436
  section: {
801
437
  pageBreak: false
@@ -811,29 +447,32 @@ var init_devportal_docx_theme = __esm({
811
447
  "src/templates/themes/devportal.docx.theme.json"() {
812
448
  devportal_docx_theme_default = {
813
449
  name: "devportal",
814
- displayName: "Developer Portal",
815
- description: "A modern developer-focused theme with cool grays, teal accents, and monospace code styling",
816
- version: "2.0.0",
450
+ displayName: "Field Editorial",
451
+ description: "A compact editorial theme \u2014 Helvetica in near-black ink with a burnt-orange accent, tight condensed titles, letterspaced labels, warm tinted fills and hairline rules",
452
+ version: "4.0.0",
817
453
  colors: {
818
- primary: "#0F172A",
819
- secondary: "#334155",
820
- accent: "#0D9488",
821
- text: "#0F172A",
454
+ primary: "#12191F",
455
+ secondary: "#172028",
456
+ accent: "#E35B3F",
457
+ text: "#232323",
822
458
  background: "#FFFFFF",
823
- border: "#E2E8F0",
824
- textPrimary: "#0F172A",
825
- textSecondary: "#475569",
826
- textMuted: "#94A3B8",
827
- borderPrimary: "#CBD5E1",
828
- borderSecondary: "#F1F5F9",
459
+ border: "#E2E0DD",
460
+ textPrimary: "#232323",
461
+ textSecondary: "#46494C",
462
+ textMuted: "#737373",
463
+ borderPrimary: "#D8D5D1",
464
+ borderSecondary: "#F2F3F3",
829
465
  backgroundPrimary: "#FFFFFF",
830
- backgroundSecondary: "#F8FAFC"
466
+ backgroundSecondary: "#F7ECE7",
467
+ accent4: "#46494C",
468
+ accent5: "#8A9299",
469
+ accent6: "#E8A18D"
831
470
  },
832
471
  fonts: {
833
- heading: { family: "Helvetica", size: 24 },
834
- body: { family: "Calibri", size: 11 },
835
- mono: { family: "Consolas", size: 10 },
836
- light: { family: "Helvetica", size: 24 }
472
+ heading: { family: "Helvetica", size: 23 },
473
+ body: { family: "Helvetica", size: 9.5 },
474
+ mono: { family: "Courier New", size: 10 },
475
+ light: { family: "Helvetica", size: 23 }
837
476
  },
838
477
  page: {
839
478
  size: "A4",
@@ -851,22 +490,42 @@ var init_devportal_docx_theme = __esm({
851
490
  normal: {
852
491
  font: "body",
853
492
  color: "textPrimary",
854
- lineSpacing: { type: "multiple", value: 1.5 },
493
+ lineSpacing: { type: "multiple", value: 1.3 },
855
494
  alignment: "left",
856
- spacing: { after: 8 }
495
+ spacing: { after: 7 }
496
+ },
497
+ title: {
498
+ font: "heading",
499
+ size: 29,
500
+ bold: true,
501
+ color: "primary",
502
+ alignment: "left",
503
+ lineSpacing: { type: "multiple", value: 1.02 },
504
+ characterSpacing: { type: "condensed", value: 8 },
505
+ spacing: { before: 0, after: 10 }
506
+ },
507
+ subtitle: {
508
+ font: "body",
509
+ size: 10.5,
510
+ italic: false,
511
+ color: "textSecondary",
512
+ alignment: "left",
513
+ lineSpacing: { type: "multiple", value: 1.25 },
514
+ spacing: { before: 0, after: 12 }
857
515
  },
858
516
  heading1: {
859
517
  font: "heading",
860
- size: 24,
518
+ size: 21,
861
519
  bold: true,
862
520
  color: "primary",
863
- spacing: { before: 24, after: 12 },
521
+ lineSpacing: { type: "multiple", value: 1.15 },
522
+ spacing: { before: 26, after: 12 },
864
523
  keepNext: true,
865
524
  alignment: "left",
866
525
  borders: {
867
526
  bottom: {
868
527
  style: "single",
869
- size: 1,
528
+ size: 4,
870
529
  color: "accent",
871
530
  space: 6
872
531
  }
@@ -874,54 +533,97 @@ var init_devportal_docx_theme = __esm({
874
533
  },
875
534
  heading2: {
876
535
  font: "heading",
877
- size: 18,
536
+ size: 15.5,
878
537
  bold: true,
879
538
  color: "secondary",
880
- spacing: { before: 18, after: 8 },
539
+ lineSpacing: { type: "multiple", value: 1.15 },
540
+ spacing: { before: 20, after: 8 },
881
541
  keepNext: true,
882
542
  alignment: "left"
883
543
  },
884
544
  heading3: {
885
545
  font: "body",
886
- size: 13,
546
+ size: 12.5,
887
547
  bold: true,
888
- color: "accent",
889
- spacing: { before: 12, after: 6 },
548
+ color: "secondary",
549
+ spacing: { before: 14, after: 6 },
890
550
  keepNext: true,
891
551
  alignment: "left"
892
552
  },
893
553
  heading4: {
894
554
  font: "body",
895
- size: 12,
555
+ size: 11.5,
896
556
  bold: true,
557
+ color: "textPrimary",
558
+ spacing: { before: 12, after: 4 },
559
+ keepNext: true,
560
+ alignment: "left"
561
+ },
562
+ heading5: {
563
+ font: "mono",
564
+ size: 10.5,
565
+ bold: true,
566
+ color: "secondary",
567
+ spacing: { before: 10, after: 4 },
568
+ keepNext: true,
569
+ alignment: "left"
570
+ },
571
+ heading6: {
572
+ font: "body",
573
+ size: 10.5,
574
+ bold: false,
897
575
  color: "textSecondary",
898
- spacing: { before: 8, after: 4 },
899
- keepNext: true
576
+ characterSpacing: { type: "expanded", value: 20 },
577
+ spacing: { before: 10, after: 4 },
578
+ keepNext: true,
579
+ alignment: "left"
900
580
  },
901
- title: {
902
- font: "heading",
903
- size: 32,
581
+ TOC1: {
582
+ font: "body",
583
+ size: 11,
904
584
  bold: true,
905
585
  color: "primary",
906
- alignment: "left",
907
- spacing: { before: 0, after: 12 }
586
+ spacing: { before: 5, after: 3 },
587
+ tabStops: [{ type: "right", position: 9746, leader: "dot" }]
908
588
  },
909
- subtitle: {
910
- font: "light",
911
- size: 16,
912
- italic: false,
589
+ TOC2: {
590
+ font: "body",
591
+ size: 10.5,
592
+ color: "textPrimary",
593
+ indent: { left: 240 },
594
+ spacing: { after: 2 },
595
+ tabStops: [{ type: "right", position: 9746, leader: "dot" }]
596
+ },
597
+ TOC3: {
598
+ font: "body",
599
+ size: 10,
913
600
  color: "textSecondary",
914
- alignment: "left",
915
- spacing: { before: 0, after: 24 }
601
+ indent: { left: 480 },
602
+ spacing: { after: 2 },
603
+ tabStops: [{ type: "right", position: 9746, leader: "dot" }]
916
604
  }
917
605
  },
918
606
  componentDefaults: {
919
607
  table: {
920
- borderColor: "#E2E8F0"
608
+ width: 100,
609
+ borderColor: "#E2E0DD",
610
+ borderSize: 0.5,
611
+ hideBorders: { left: true, right: true, insideVertical: true },
612
+ cellDefaults: {
613
+ padding: { top: 3, bottom: 3 }
614
+ },
615
+ headerCellDefaults: {
616
+ font: { bold: true },
617
+ color: "#172028",
618
+ backgroundColor: "#F7ECE7",
619
+ borderColor: { bottom: "#D8D5D1" },
620
+ borderSize: { bottom: 1 }
621
+ }
921
622
  },
922
623
  list: {
923
624
  format: "bullet",
924
- bullet: "\u2013"
625
+ bullet: "\u2014",
626
+ spacing: { item: 2 }
925
627
  },
926
628
  image: {
927
629
  alignment: "center"
@@ -971,7 +673,7 @@ var init_vermilion_docx_theme = __esm({
971
673
  size: 10.5
972
674
  },
973
675
  mono: {
974
- family: "Consolas",
676
+ family: "Courier New",
975
677
  size: 10
976
678
  },
977
679
  light: {
@@ -1048,6 +750,47 @@ var init_vermilion_docx_theme = __esm({
1048
750
  keepNext: true,
1049
751
  alignment: "left"
1050
752
  },
753
+ heading4: {
754
+ font: "body",
755
+ size: 10.5,
756
+ bold: true,
757
+ color: "textSecondary",
758
+ spacing: {
759
+ before: 10,
760
+ after: 4
761
+ },
762
+ keepNext: true,
763
+ alignment: "left"
764
+ },
765
+ heading5: {
766
+ font: "body",
767
+ size: 10.5,
768
+ bold: false,
769
+ italic: true,
770
+ color: "textSecondary",
771
+ spacing: {
772
+ before: 9,
773
+ after: 4
774
+ },
775
+ keepNext: true,
776
+ alignment: "left"
777
+ },
778
+ heading6: {
779
+ font: "body",
780
+ size: 10,
781
+ bold: true,
782
+ color: "textMuted",
783
+ characterSpacing: {
784
+ type: "expanded",
785
+ value: 30
786
+ },
787
+ spacing: {
788
+ before: 9,
789
+ after: 4
790
+ },
791
+ keepNext: true,
792
+ alignment: "left"
793
+ },
1051
794
  title: {
1052
795
  font: "heading",
1053
796
  size: 38,
@@ -1069,6 +812,46 @@ var init_vermilion_docx_theme = __esm({
1069
812
  after: 10
1070
813
  }
1071
814
  }
815
+ },
816
+ componentDefaults: {
817
+ table: {
818
+ width: 100,
819
+ borderColor: "#C7C8CA",
820
+ borderSize: 0.5,
821
+ hideBorders: {
822
+ top: true,
823
+ left: true,
824
+ right: true,
825
+ insideVertical: true
826
+ },
827
+ cellDefaults: {
828
+ font: { size: 9.5 },
829
+ padding: { top: 7, bottom: 7 },
830
+ verticalAlignment: "middle"
831
+ },
832
+ headerCellDefaults: {
833
+ color: "#EF4130",
834
+ font: { size: 9.5, bold: true },
835
+ padding: { top: 0, bottom: 8 },
836
+ verticalAlignment: "bottom",
837
+ borderColor: { bottom: "#EF4130" },
838
+ borderSize: { bottom: 0.5 }
839
+ }
840
+ },
841
+ list: {
842
+ format: "bullet",
843
+ bullet: "\u2014",
844
+ spacing: { item: 2 }
845
+ },
846
+ image: {
847
+ alignment: "center"
848
+ },
849
+ statistic: {
850
+ alignment: "center"
851
+ },
852
+ section: {
853
+ pageBreak: false
854
+ }
1072
855
  }
1073
856
  };
1074
857
  }
@@ -1087,9 +870,6 @@ function loadThemesFromJson() {
1087
870
  }
1088
871
  const themes2 = {
1089
872
  minimal: ensureThemeDefaults(minimal_docx_theme_default),
1090
- corporate: ensureThemeDefaults(corporate_docx_theme_default),
1091
- modern: ensureThemeDefaults(modern_docx_theme_default),
1092
- apex: ensureThemeDefaults(apex_docx_theme_default),
1093
873
  devportal: ensureThemeDefaults(devportal_docx_theme_default),
1094
874
  vermilion: ensureThemeDefaults(vermilion_docx_theme_default)
1095
875
  };
@@ -1129,15 +909,12 @@ function loadThemesFromJson() {
1129
909
  _themesCache = themes2;
1130
910
  return themes2;
1131
911
  }
1132
- var _themesCache, themes, getTheme, getThemeWithFallback, hasTheme, getThemeNames, minimalTheme, corporateTheme, modernTheme;
912
+ var _themesCache, themes, getTheme, getThemeWithFallback, hasTheme, getThemeNames, minimalTheme, devportalTheme, vermilionTheme;
1133
913
  var init_themes = __esm({
1134
914
  "src/templates/themes/index.ts"() {
1135
915
  "use strict";
1136
916
  init_defaults();
1137
917
  init_minimal_docx_theme();
1138
- init_corporate_docx_theme();
1139
- init_modern_docx_theme();
1140
- init_apex_docx_theme();
1141
918
  init_devportal_docx_theme();
1142
919
  init_vermilion_docx_theme();
1143
920
  _themesCache = null;
@@ -1161,8 +938,8 @@ var init_themes = __esm({
1161
938
  return Object.keys(themes);
1162
939
  };
1163
940
  minimalTheme = themes["minimal"];
1164
- corporateTheme = themes["corporate"];
1165
- modernTheme = themes["modern"];
941
+ devportalTheme = themes["devportal"];
942
+ vermilionTheme = themes["vermilion"];
1166
943
  }
1167
944
  });
1168
945
 
@@ -1862,6 +1639,7 @@ var init_widthUtils = __esm({
1862
1639
 
1863
1640
  // src/utils/imageUtils.ts
1864
1641
  import { readFileSync } from "fs";
1642
+ import { availableParallelism } from "os";
1865
1643
  import probe from "probe-image-size";
1866
1644
  function loadResvg() {
1867
1645
  resvgModule ??= import("@resvg/resvg-js");
@@ -1880,10 +1658,36 @@ function capToPixelBudget(edge, aspect) {
1880
1658
  const scaled = Math.floor(edge * Math.sqrt(SVG_MAX_TOTAL_PX / total));
1881
1659
  return scaled >= SVG_MIN_EDGE_PX ? scaled : void 0;
1882
1660
  }
1661
+ function fallbackConcurrency() {
1662
+ const cpus = availableParallelism?.() ?? 4;
1663
+ return Math.max(1, Math.min(8, cpus));
1664
+ }
1665
+ async function rasterizeSvgFallbacks(jobs, enabled = true) {
1666
+ const out = /* @__PURE__ */ new Map();
1667
+ if (!enabled || jobs.length === 0) return out;
1668
+ let next = 0;
1669
+ const worker = async () => {
1670
+ for (let i = next++; i < jobs.length; i = next++) {
1671
+ const job = jobs[i];
1672
+ out.set(
1673
+ job.key,
1674
+ await rasterizeSvgFallback(job.svg, {
1675
+ width: job.width,
1676
+ height: job.height
1677
+ })
1678
+ );
1679
+ }
1680
+ };
1681
+ await Promise.all(
1682
+ Array.from({ length: Math.min(fallbackConcurrency(), jobs.length) }, worker)
1683
+ );
1684
+ return out;
1685
+ }
1883
1686
  async function rasterizeSvgFallback(svg, transformation) {
1884
1687
  let Resvg;
1688
+ let renderAsync;
1885
1689
  try {
1886
- ({ Resvg } = await loadResvg());
1690
+ ({ Resvg, renderAsync } = await loadResvg());
1887
1691
  } catch (error) {
1888
1692
  reportWarning(
1889
1693
  "image",
@@ -1918,7 +1722,7 @@ async function rasterizeSvgFallback(svg, transformation) {
1918
1722
  return void 0;
1919
1723
  }
1920
1724
  return Buffer.from(
1921
- new Resvg(markup, { fitTo: { mode, value } }).render().asPng()
1725
+ (await renderAsync(markup, { fitTo: { mode, value } })).asPng()
1922
1726
  );
1923
1727
  } catch (error) {
1924
1728
  reportWarning(
@@ -2207,10 +2011,10 @@ import {
2207
2011
  EndnoteReferenceRun,
2208
2012
  ExternalHyperlink,
2209
2013
  FootnoteReferenceRun,
2014
+ ImportedXmlComponent,
2210
2015
  InsertedTextRun,
2211
2016
  InternalHyperlink,
2212
2017
  OverlapType,
2213
- PageNumber,
2214
2018
  Paragraph,
2215
2019
  RelativeHorizontalPosition,
2216
2020
  RelativeVerticalPosition,
@@ -2230,6 +2034,28 @@ import {
2230
2034
  WpsShapeRun
2231
2035
  } from "docx";
2232
2036
  import { assertNever } from "@json-to-office/shared/rendering";
2037
+ function complexField(instruction, formatting, leading) {
2038
+ const options = runOptions(formatting);
2039
+ const fieldChar = (type, extra = {}) => new TextRun({
2040
+ children: [
2041
+ new ImportedXmlComponent("w:fldChar", { "w:fldCharType": type })
2042
+ ],
2043
+ ...options,
2044
+ ...extra
2045
+ });
2046
+ const instrText = new ImportedXmlComponent("w:instrText", {
2047
+ "xml:space": "preserve"
2048
+ });
2049
+ instrText.push(instruction);
2050
+ return [
2051
+ // A pending line break rides on the first run of the field, the same way
2052
+ // it rides on the single run every other inline node emits.
2053
+ fieldChar("begin", leading),
2054
+ new TextRun({ children: [instrText], ...options }),
2055
+ fieldChar("separate"),
2056
+ fieldChar("end")
2057
+ ];
2058
+ }
2233
2059
  function runOptions(formatting) {
2234
2060
  if (!formatting) return {};
2235
2061
  const options = {};
@@ -2334,18 +2160,13 @@ function inlineChildren(children, resources = /* @__PURE__ */ new Map()) {
2334
2160
  out.push(new SimpleField(child.instruction, child.cachedText));
2335
2161
  break;
2336
2162
  }
2337
- const page = PAGE_FIELD[child.instruction];
2338
- if (!page) {
2163
+ if (!PAGE_FIELDS.has(child.instruction)) {
2339
2164
  throw new Error(
2340
2165
  `the docxjs renderer has no emitter for the field "${child.instruction}"`
2341
2166
  );
2342
2167
  }
2343
2168
  out.push(
2344
- new TextRun({
2345
- children: [page],
2346
- ...runOptions(child.formatting),
2347
- ...breakOption()
2348
- })
2169
+ ...complexField(child.instruction, child.formatting, breakOption())
2349
2170
  );
2350
2171
  break;
2351
2172
  }
@@ -2719,7 +2540,7 @@ function emitBorder(border3) {
2719
2540
  ...border3.spacePoints !== void 0 ? { space: border3.spacePoints } : {}
2720
2541
  };
2721
2542
  }
2722
- var ALIGNMENT2, PAGE_FIELD, WRAP_TYPE, VERTICAL_ALIGN, TABLE_ANCHOR, HORIZONTAL_POSITION, VERTICAL_POSITION, BORDER_STYLE;
2543
+ var ALIGNMENT2, PAGE_FIELDS, WRAP_TYPE, VERTICAL_ALIGN, TABLE_ANCHOR, HORIZONTAL_POSITION, VERTICAL_POSITION, BORDER_STYLE;
2723
2544
  var init_emit = __esm({
2724
2545
  "src/renderers/docxjs/emit.ts"() {
2725
2546
  "use strict";
@@ -2731,10 +2552,7 @@ var init_emit = __esm({
2731
2552
  start: AlignmentType.START,
2732
2553
  end: AlignmentType.END
2733
2554
  };
2734
- PAGE_FIELD = {
2735
- PAGE: PageNumber.CURRENT,
2736
- NUMPAGES: PageNumber.TOTAL_PAGES
2737
- };
2555
+ PAGE_FIELDS = /* @__PURE__ */ new Set(["PAGE", "NUMPAGES"]);
2738
2556
  WRAP_TYPE = {
2739
2557
  none: TextWrappingType.NONE,
2740
2558
  square: TextWrappingType.SQUARE,
@@ -3081,7 +2899,10 @@ function createDocxJsRenderer() {
3081
2899
  format: "docx",
3082
2900
  capabilities: DOCXJS_CAPABILITIES,
3083
2901
  async render(ir, renderOptions) {
3084
- const resources = await prepareImages(ir);
2902
+ const resources = await prepareImages(
2903
+ ir,
2904
+ renderOptions?.svgRasterFallback
2905
+ );
3085
2906
  const document = buildDocument(ir, resources);
3086
2907
  const packed = await Packer.toBuffer(document);
3087
2908
  const fixed = fixFloatingImageIdsInBuffer(packed);
@@ -3166,22 +2987,22 @@ function numberingConfig(numbering) {
3166
2987
  }))
3167
2988
  };
3168
2989
  }
3169
- async function prepareImages(ir) {
2990
+ async function prepareImages(ir, svgRasterFallback) {
3170
2991
  const placements = collectImagePlacements(ir);
3171
- const rasters = /* @__PURE__ */ new Map();
2992
+ const jobs = [];
3172
2993
  for (const resource of ir.resources) {
3173
2994
  if (resource.kind !== "image" || resource.mediaType !== "svg") continue;
3174
2995
  for (const size of placements.get(resource.id) ?? []) {
3175
2996
  const [width, height] = size.split("x").map(Number);
3176
- rasters.set(
3177
- `${resource.id}:${size}`,
3178
- await rasterizeSvgFallback(Buffer.from(resource.bytes), {
3179
- width,
3180
- height
3181
- })
3182
- );
2997
+ jobs.push({
2998
+ key: `${resource.id}:${size}`,
2999
+ svg: Buffer.from(resource.bytes),
3000
+ width,
3001
+ height
3002
+ });
3183
3003
  }
3184
3004
  }
3005
+ const rasters = await rasterizeSvgFallbacks(jobs, svgRasterFallback);
3185
3006
  const resources = /* @__PURE__ */ new Map();
3186
3007
  for (const resource of ir.resources) {
3187
3008
  if (resource.kind !== "image") continue;
@@ -4348,7 +4169,11 @@ async function createOfficeOpenDocxRenderer() {
4348
4169
  capabilities: OFFICE_OPEN_CAPABILITIES,
4349
4170
  async render(ir, options) {
4350
4171
  const charts = [];
4351
- const document = await buildDocumentOptions(ir, charts);
4172
+ const document = await buildDocumentOptions(
4173
+ ir,
4174
+ charts,
4175
+ options?.svgRasterFallback
4176
+ );
4352
4177
  const bytes = await backend.generateDocument(document, {
4353
4178
  type: "uint8array"
4354
4179
  });
@@ -4373,10 +4198,10 @@ async function createOfficeOpenDocxRenderer() {
4373
4198
  }
4374
4199
  };
4375
4200
  }
4376
- async function buildDocumentOptions(ir, charts = []) {
4201
+ async function buildDocumentOptions(ir, charts = [], svgRasterFallback) {
4377
4202
  let nextDrawingId = 1;
4378
4203
  const ctx = {
4379
- pictures: await prepareImages2(ir),
4204
+ pictures: await prepareImages2(ir, svgRasterFallback),
4380
4205
  nextDrawingId: () => nextDrawingId++,
4381
4206
  charts
4382
4207
  };
@@ -4425,22 +4250,22 @@ function noteBodies2(notes, ctx) {
4425
4250
  }
4426
4251
  return bodies;
4427
4252
  }
4428
- async function prepareImages2(ir) {
4253
+ async function prepareImages2(ir, svgRasterFallback) {
4429
4254
  const placements = collectImagePlacements2(ir);
4430
- const rasters = /* @__PURE__ */ new Map();
4255
+ const jobs = [];
4431
4256
  for (const resource of ir.resources) {
4432
4257
  if (resource.kind !== "image" || resource.mediaType !== "svg") continue;
4433
4258
  for (const size of placements.get(resource.id) ?? []) {
4434
4259
  const [width, height] = size.split("x").map(Number);
4435
- rasters.set(
4436
- `${resource.id}:${size}`,
4437
- await rasterizeSvgFallback(Buffer.from(resource.bytes), {
4438
- width,
4439
- height
4440
- })
4441
- );
4260
+ jobs.push({
4261
+ key: `${resource.id}:${size}`,
4262
+ svg: Buffer.from(resource.bytes),
4263
+ width,
4264
+ height
4265
+ });
4442
4266
  }
4443
4267
  }
4268
+ const rasters = await rasterizeSvgFallbacks(jobs, svgRasterFallback);
4444
4269
  const resources = /* @__PURE__ */ new Map();
4445
4270
  for (const resource of ir.resources) {
4446
4271
  if (resource.kind !== "image") continue;
@@ -6796,6 +6621,9 @@ function createLevelsFromSimplifiedProps(props) {
6796
6621
  text = "";
6797
6622
  } else {
6798
6623
  format2 = props.format;
6624
+ if (format2 === "bullet") {
6625
+ text = props.bullet || "\u2022";
6626
+ }
6799
6627
  }
6800
6628
  } else {
6801
6629
  format2 = "bullet";
@@ -7007,7 +6835,7 @@ function outerBorderOverride(position, tableBorderColor, tableBorderSize) {
7007
6835
  const color = normalizeBorderColor(tableBorderColor);
7008
6836
  if (tableBorderColor && color) {
7009
6837
  result.borderColor = {};
7010
- if (position.isHeader && color.top !== UNSET_COLOR) {
6838
+ if ((position.isHeader || position.isFirstRow) && color.top !== UNSET_COLOR) {
7011
6839
  result.borderColor.top = color.top;
7012
6840
  }
7013
6841
  if (position.isFirstCol && color.left !== UNSET_COLOR) {
@@ -7023,7 +6851,7 @@ function outerBorderOverride(position, tableBorderColor, tableBorderSize) {
7023
6851
  const size = normalizeBorderSize(tableBorderSize);
7024
6852
  if (tableBorderSize && size) {
7025
6853
  result.borderSize = {};
7026
- if (position.isHeader && size.top !== UNSET_SIZE) {
6854
+ if ((position.isHeader || position.isFirstRow) && size.top !== UNSET_SIZE) {
7027
6855
  result.borderSize.top = size.top;
7028
6856
  }
7029
6857
  if (position.isFirstCol && size.left !== UNSET_SIZE) {
@@ -7243,6 +7071,7 @@ function resolveTableModel(source, theme, themeName, options = {}) {
7243
7071
  (max, height) => height === void 0 ? max : max === void 0 ? height : Math.max(max, height),
7244
7072
  void 0
7245
7073
  );
7074
+ const hasHeader = columns.some((column) => column.header !== void 0);
7246
7075
  const headerMerges = columns.map(
7247
7076
  (column, colIndex) => mergeHeaderCellDefaults(
7248
7077
  source.cellDefaults,
@@ -7284,6 +7113,7 @@ function resolveTableModel(source, theme, themeName, options = {}) {
7284
7113
  };
7285
7114
  const rows = Array.from({ length: rowCount }, (_, rowIndex) => {
7286
7115
  const isLastRow = rowIndex === rowCount - 1;
7116
+ const isFirstRow = !hasHeader && rowIndex === 0;
7287
7117
  const rowProps = source.rows?.[rowIndex];
7288
7118
  const merges = columns.map(
7289
7119
  (column, colIndex) => mergeCellDefaults(
@@ -7291,6 +7121,7 @@ function resolveTableModel(source, theme, themeName, options = {}) {
7291
7121
  column.cellDefaults,
7292
7122
  column.cells?.[rowIndex],
7293
7123
  {
7124
+ isFirstRow,
7294
7125
  isFirstCol: colIndex === 0,
7295
7126
  isLastCol: colIndex === columnCount - 1,
7296
7127
  isLastRow
@@ -7317,8 +7148,7 @@ function resolveTableModel(source, theme, themeName, options = {}) {
7317
7148
  const cell = column.cells?.[rowIndex];
7318
7149
  const merged = merges[colIndex];
7319
7150
  const position = {
7320
- // Data rows are never the first row; the header is.
7321
- isFirstRow: false,
7151
+ isFirstRow,
7322
7152
  isFirstCol: colIndex === 0,
7323
7153
  isLastCol: colIndex === columnCount - 1,
7324
7154
  isLastRow
@@ -7348,10 +7178,10 @@ function resolveTableModel(source, theme, themeName, options = {}) {
7348
7178
  };
7349
7179
  return row;
7350
7180
  });
7351
- adjudicateInteriorEdges([header, ...rows]);
7181
+ adjudicateInteriorEdges([...hasHeader ? [header] : [], ...rows]);
7352
7182
  return {
7353
7183
  ...resolveWidths(source, columns, theme, themeName),
7354
- header,
7184
+ ...hasHeader ? { header } : {},
7355
7185
  rows,
7356
7186
  repeatHeader: source.repeatHeaderOnPageBreak ?? true
7357
7187
  };
@@ -7819,6 +7649,44 @@ function buildNoProofWordsRegex(noProofWords2) {
7819
7649
  );
7820
7650
  }
7821
7651
  var DECORATOR = /(\*\*\*|___)([\s\S]*?)\1|(\*\*|__)([\s\S]*?)\3|(\*|_)([\s\S]*?)\5/g;
7652
+ var ESCAPABLE = "*_[]{}\\";
7653
+ var ESCAPE = /\\([*_[\]{}\\])/g;
7654
+ var SENTINEL = "\uE000";
7655
+ var SENTINEL_SELF = "x";
7656
+ var SENTINEL_DIGIT_BASE = 48;
7657
+ function encodeEscapes(text) {
7658
+ const authored = text.includes(SENTINEL);
7659
+ if (!authored && !text.includes("\\")) return text;
7660
+ const guarded = authored ? text.split(SENTINEL).join(SENTINEL + SENTINEL_SELF) : text;
7661
+ return guarded.replace(
7662
+ ESCAPE,
7663
+ (_whole, char) => SENTINEL + String.fromCharCode(SENTINEL_DIGIT_BASE + ESCAPABLE.indexOf(char))
7664
+ );
7665
+ }
7666
+ function decodeEscapes(text) {
7667
+ if (!text.includes(SENTINEL)) return text;
7668
+ let out = "";
7669
+ for (let i = 0; i < text.length; i += 1) {
7670
+ if (text[i] !== SENTINEL) {
7671
+ out += text[i];
7672
+ continue;
7673
+ }
7674
+ const marker = text[i + 1];
7675
+ if (marker === SENTINEL_SELF) {
7676
+ out += SENTINEL;
7677
+ i += 1;
7678
+ continue;
7679
+ }
7680
+ const index = marker === void 0 ? -1 : marker.charCodeAt(0) - SENTINEL_DIGIT_BASE;
7681
+ if (index >= 0 && index < ESCAPABLE.length) {
7682
+ out += ESCAPABLE[index];
7683
+ i += 1;
7684
+ continue;
7685
+ }
7686
+ out += text[i];
7687
+ }
7688
+ return out;
7689
+ }
7822
7690
  var LINK = /\[([^\]]+)\]\(([^)]+)\)/g;
7823
7691
  var DECORATOR_OR_PLACEHOLDER = /(\*\*\*|___)([\s\S]*?)\1|(\*\*|__)([\s\S]*?)\3|(\*|_)([\s\S]*?)\5|\{([^}]+)\}/g;
7824
7692
  var PLACEHOLDER = /\{([^}]+)\}/;
@@ -7845,7 +7713,7 @@ function containsUnsupportedSyntax(text) {
7845
7713
  return void 0;
7846
7714
  }
7847
7715
  function parseInline(text, options) {
7848
- const normalized = normalizeUnicodeText(text);
7716
+ const normalized = encodeEscapes(normalizeUnicodeText(text));
7849
7717
  if (!normalized) {
7850
7718
  return [
7851
7719
  { kind: "text", text: "", formatting: emptyToUndefined(options.base) }
@@ -7943,7 +7811,7 @@ function parseLinks(normalized, options) {
7943
7811
  lastIndex = match.index + match[0].length;
7944
7812
  if (match[1] === void 0) {
7945
7813
  const resolved = options.resolveCrossReference?.(
7946
- match[3],
7814
+ decodeEscapes(match[3]),
7947
7815
  match[4] ?? "relative",
7948
7816
  match[0]
7949
7817
  );
@@ -7951,7 +7819,8 @@ function parseLinks(normalized, options) {
7951
7819
  else out.push(...parseDecorated(match[0], options));
7952
7820
  continue;
7953
7821
  }
7954
- const [, linkText, target] = match;
7822
+ const [, linkText] = match;
7823
+ const target = decodeEscapes(match[2]);
7955
7824
  out.push({
7956
7825
  kind: "hyperlink",
7957
7826
  // A `#anchor` target names a bookmark in this document and needs no
@@ -8007,7 +7876,7 @@ function pushSegment(out, text, options, override = {}) {
8007
7876
  const bold = override.bold ?? options.base.bold;
8008
7877
  const italic = override.italic ?? options.base.italic;
8009
7878
  const formatting = runFormatting2(options, { bold, italic });
8010
- const lines = text.split("\n");
7879
+ const lines = decodeEscapes(text).split("\n");
8011
7880
  for (const [lineIndex, line] of lines.entries()) {
8012
7881
  if (!line && lineIndex === 0) continue;
8013
7882
  if (lineIndex > 0) out.push({ kind: "lineBreak" });
@@ -8193,18 +8062,32 @@ function compileDocument(structure, layout, warnings = [], images = /* @__PURE__
8193
8062
  };
8194
8063
  }
8195
8064
  var AFTER_TABLE_TWIPS = 120;
8065
+ var BEFORE_TABLE_TWIPS = 240;
8196
8066
  var BODY_STYLE_IDS = /* @__PURE__ */ new Set([void 0, "Normal"]);
8197
- function separateFromTables(blocks) {
8067
+ function separateFromTables(blocks, bodyAfterTwips) {
8198
8068
  for (let i = 1; i < blocks.length; i += 1) {
8199
8069
  const block2 = blocks[i];
8200
- if (blocks[i - 1].kind !== "table") continue;
8201
- if (block2.kind !== "paragraph") continue;
8202
- if (!BODY_STYLE_IDS.has(block2.styleId)) continue;
8203
- if (block2.formatting?.spacing?.beforeTwips !== void 0) continue;
8204
- block2.formatting = {
8205
- ...block2.formatting,
8206
- spacing: { ...block2.formatting?.spacing, beforeTwips: AFTER_TABLE_TWIPS }
8207
- };
8070
+ const previous = blocks[i - 1];
8071
+ if (previous.kind === "table" && block2.kind === "paragraph" && BODY_STYLE_IDS.has(block2.styleId) && // An author who stated their own space-before has already answered this.
8072
+ block2.formatting?.spacing?.beforeTwips === void 0) {
8073
+ block2.formatting = {
8074
+ ...block2.formatting,
8075
+ spacing: {
8076
+ ...block2.formatting?.spacing,
8077
+ beforeTwips: AFTER_TABLE_TWIPS
8078
+ }
8079
+ };
8080
+ }
8081
+ if (block2.kind === "table" && previous.kind === "paragraph" && BODY_STYLE_IDS.has(previous.styleId) && // Same rule as below: a stated space-after is the author's answer.
8082
+ previous.formatting?.spacing?.afterTwips === void 0) {
8083
+ previous.formatting = {
8084
+ ...previous.formatting,
8085
+ spacing: {
8086
+ ...previous.formatting?.spacing,
8087
+ afterTwips: Math.max(bodyAfterTwips, BEFORE_TABLE_TWIPS)
8088
+ }
8089
+ };
8090
+ }
8208
8091
  }
8209
8092
  }
8210
8093
  function collectOutline(layout, warnings) {
@@ -8283,7 +8166,10 @@ function compileSection(section2, index, ordinal, chrome, ctx) {
8283
8166
  })
8284
8167
  );
8285
8168
  });
8286
- separateFromTables(children);
8169
+ separateFromTables(
8170
+ children,
8171
+ pointsToTwips2(getNormalStyle(ctx.theme).spacing?.after ?? 0)
8172
+ );
8287
8173
  const compiled = {
8288
8174
  id: `s${index}`,
8289
8175
  path: path4,
@@ -9302,8 +9188,10 @@ function itemSpacing(spacing, index, count) {
9302
9188
  if (index === 0 && spacing?.before !== void 0) {
9303
9189
  out.beforeTwips = pointsToTwips2(spacing.before);
9304
9190
  }
9305
- if (index === count - 1 && spacing?.after !== void 0) {
9306
- out.afterTwips = pointsToTwips2(spacing.after);
9191
+ if (index === count - 1) {
9192
+ if (spacing?.after !== void 0) {
9193
+ out.afterTwips = pointsToTwips2(spacing.after);
9194
+ }
9307
9195
  } else if (spacing?.item !== void 0) {
9308
9196
  out.afterTwips = pointsToTwips2(spacing.item);
9309
9197
  }
@@ -10383,13 +10271,20 @@ function compileTable(component, scope) {
10383
10271
  return [];
10384
10272
  }
10385
10273
  const rows = [
10386
- compileTableRow(model.header, style.headerParagraph, style.tableHeader, {
10387
- ctx,
10388
- path: `${path4}.header`,
10389
- id: `${scope.id}:h`,
10390
- // Headers repeat across page breaks unless the source disabled it.
10391
- isHeader: model.repeatHeader
10392
- }),
10274
+ ...model.header ? [
10275
+ compileTableRow(
10276
+ model.header,
10277
+ style.headerParagraph,
10278
+ style.tableHeader,
10279
+ {
10280
+ ctx,
10281
+ path: `${path4}.header`,
10282
+ id: `${scope.id}:h`,
10283
+ // Headers repeat across page breaks unless the source disabled it.
10284
+ isHeader: model.repeatHeader
10285
+ }
10286
+ )
10287
+ ] : [],
10393
10288
  ...model.rows.map(
10394
10289
  (row, index) => compileTableRow(row, style.cellParagraph, style.tableCell, {
10395
10290
  ctx,
@@ -10451,9 +10346,10 @@ function tableSource(props) {
10451
10346
  };
10452
10347
  }
10453
10348
  function tableBlocker(model, path4) {
10454
- const rows = [model.header, ...model.rows];
10349
+ const headerRows = model.header ? [model.header] : [];
10350
+ const rows = [...headerRows, ...model.rows];
10455
10351
  for (const [rowIndex, row] of rows.entries()) {
10456
- const rowPath = row.isHeader ? `${path4}.header` : `${path4}.rows[${rowIndex - 1}]`;
10352
+ const rowPath = row.isHeader ? `${path4}.header` : `${path4}.rows[${rowIndex - headerRows.length}]`;
10457
10353
  for (const [colIndex, cell] of row.cells.entries()) {
10458
10354
  const cellPath = `${rowPath}.cells[${colIndex}]`;
10459
10355
  const content = cell.content;
@@ -12029,6 +11925,7 @@ async function renderScoped(document, options, warnings) {
12029
11925
  const bytes = await renderer.render(compiled.ir, {
12030
11926
  ...options.deterministic !== void 0 ? { deterministic: options.deterministic } : {},
12031
11927
  ...options.generatedAt !== void 0 ? { generatedAt: toDate(options.generatedAt) } : {},
11928
+ ...options.svgRasterFallback !== void 0 ? { svgRasterFallback: options.svgRasterFallback } : {},
12032
11929
  warnings: compiled.warnings
12033
11930
  });
12034
11931
  return { buffer: Buffer.from(bytes), warnings: compiled.warnings };
@@ -12146,6 +12043,7 @@ async function generateBufferWithWarnings(jsonConfig, options) {
12146
12043
  ...options?.deterministic !== void 0 ? { deterministic: options.deterministic } : {},
12147
12044
  ...options?.generatedAt !== void 0 ? { generatedAt: options.generatedAt } : {},
12148
12045
  ...renderer ? { renderer } : {},
12046
+ ...options?.svgRasterFallback !== void 0 ? { svgRasterFallback: options.svgRasterFallback } : {},
12149
12047
  ...options?.prepared ? { prepared: options.prepared } : {}
12150
12048
  });
12151
12049
  }
@@ -13504,7 +13402,8 @@ function createBuilderImpl(state) {
13504
13402
  deterministic: state.deterministic,
13505
13403
  generatedAt: state.generatedAt,
13506
13404
  baseDir: state.baseDir,
13507
- renderer: state.renderer
13405
+ renderer: state.renderer,
13406
+ svgRasterFallback: state.svgRasterFallback
13508
13407
  };
13509
13408
  return createBuilderImpl(
13510
13409
  newState
@@ -13761,7 +13660,8 @@ function createDocumentGenerator(options) {
13761
13660
  deterministic: options.deterministic ?? true,
13762
13661
  generatedAt: options.generatedAt,
13763
13662
  baseDir: options.baseDir,
13764
- renderer: options.renderer
13663
+ renderer: options.renderer,
13664
+ svgRasterFallback: options.svgRasterFallback
13765
13665
  };
13766
13666
  return createBuilderImpl(initialState);
13767
13667
  }
@@ -13784,11 +13684,11 @@ export {
13784
13684
  UnknownPreservedComponentError,
13785
13685
  analyzeDocxQuality,
13786
13686
  cleanComponentProps,
13787
- corporateTheme,
13788
13687
  createComponent,
13789
13688
  createDocumentGenerator,
13790
13689
  createMinimalTheme,
13791
13690
  createVersion,
13691
+ devportalTheme,
13792
13692
  docxQualityEngine,
13793
13693
  docxRendererIds,
13794
13694
  docxRendererStatuses,
@@ -13831,7 +13731,6 @@ export {
13831
13731
  loadThemeFromJson,
13832
13732
  mergeSchemas,
13833
13733
  minimalTheme,
13834
- modernTheme,
13835
13734
  prepareDocxQualityDocument,
13836
13735
  resetVisualPrepassStats,
13837
13736
  resolveDocxQualityProfile,
@@ -13840,6 +13739,7 @@ export {
13840
13739
  validateComponentProps,
13841
13740
  validateDocument,
13842
13741
  validateJsonSchema,
13843
- validateThemeJsonString
13742
+ validateThemeJsonString,
13743
+ vermilionTheme
13844
13744
  };
13845
13745
  //# sourceMappingURL=index.js.map