@pixldocs/canvas-renderer 0.4.0 → 0.4.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.cjs +835 -9
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +74 -0
- package/dist/index.js +835 -9
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -10755,14 +10755,14 @@ class PixldocsRenderer {
|
|
|
10755
10755
|
async renderPdf(templateConfig, options) {
|
|
10756
10756
|
const svgs = await this.renderAllPageSvgs(templateConfig);
|
|
10757
10757
|
const { assemblePdfFromSvgs: assemblePdfFromSvgs2 } = await Promise.resolve().then(() => pdfExport);
|
|
10758
|
-
return assemblePdfFromSvgs2(svgs, { title: options == null ? void 0 : options.title });
|
|
10758
|
+
return assemblePdfFromSvgs2(svgs, { title: options == null ? void 0 : options.title, fontBaseUrl: options == null ? void 0 : options.fontBaseUrl });
|
|
10759
10759
|
}
|
|
10760
10760
|
/**
|
|
10761
10761
|
* Resolve from V2 sectionState and render a vector PDF.
|
|
10762
10762
|
* This is the primary PDF export API — mirrors renderFromForm() but returns a PDF.
|
|
10763
10763
|
*/
|
|
10764
10764
|
async renderPdfFromForm(options) {
|
|
10765
|
-
const { templateId, formSchemaId, sectionState, themeId, watermark, title } = options;
|
|
10765
|
+
const { templateId, formSchemaId, sectionState, themeId, watermark, title, fontBaseUrl } = options;
|
|
10766
10766
|
const resolved = await resolveFromForm({
|
|
10767
10767
|
templateId,
|
|
10768
10768
|
formSchemaId,
|
|
@@ -10779,7 +10779,7 @@ class PixldocsRenderer {
|
|
|
10779
10779
|
}
|
|
10780
10780
|
const svgs = await this.renderAllPageSvgs(configToRender);
|
|
10781
10781
|
const { assemblePdfFromSvgs: assemblePdfFromSvgs2 } = await Promise.resolve().then(() => pdfExport);
|
|
10782
|
-
return assemblePdfFromSvgs2(svgs, { title: title ?? resolved.config.name });
|
|
10782
|
+
return assemblePdfFromSvgs2(svgs, { title: title ?? resolved.config.name, fontBaseUrl });
|
|
10783
10783
|
}
|
|
10784
10784
|
async renderById(templateId, formData, options) {
|
|
10785
10785
|
const resolved = await resolveTemplateData({
|
|
@@ -11233,6 +11233,740 @@ class PixldocsRenderer {
|
|
|
11233
11233
|
return null;
|
|
11234
11234
|
}
|
|
11235
11235
|
}
|
|
11236
|
+
const FONT_WEIGHT_LABELS = {
|
|
11237
|
+
300: "Light",
|
|
11238
|
+
400: "Regular",
|
|
11239
|
+
500: "Medium",
|
|
11240
|
+
600: "SemiBold",
|
|
11241
|
+
700: "Bold"
|
|
11242
|
+
};
|
|
11243
|
+
function resolveFontWeight(weight) {
|
|
11244
|
+
if (weight <= 350) return 300;
|
|
11245
|
+
if (weight <= 450) return 400;
|
|
11246
|
+
if (weight <= 550) return 500;
|
|
11247
|
+
if (weight <= 650) return 600;
|
|
11248
|
+
return 700;
|
|
11249
|
+
}
|
|
11250
|
+
const FONT_FALLBACK_SYMBOLS = "Noto Sans";
|
|
11251
|
+
const FONT_FALLBACK_DEVANAGARI = "Hind";
|
|
11252
|
+
const FONT_FILES = {
|
|
11253
|
+
"Playfair Display": {
|
|
11254
|
+
regular: "PlayfairDisplay-Regular.ttf",
|
|
11255
|
+
bold: "PlayfairDisplay-Bold.ttf",
|
|
11256
|
+
italic: "PlayfairDisplay-Italic.ttf",
|
|
11257
|
+
boldItalic: "PlayfairDisplay-BoldItalic.ttf"
|
|
11258
|
+
},
|
|
11259
|
+
"Merriweather": {
|
|
11260
|
+
regular: "Merriweather-Regular.ttf",
|
|
11261
|
+
bold: "Merriweather-Bold.ttf",
|
|
11262
|
+
light: "Merriweather-Light.ttf",
|
|
11263
|
+
italic: "Merriweather-Italic.ttf",
|
|
11264
|
+
boldItalic: "Merriweather-BoldItalic.ttf",
|
|
11265
|
+
lightItalic: "Merriweather-LightItalic.ttf"
|
|
11266
|
+
},
|
|
11267
|
+
"Lora": {
|
|
11268
|
+
regular: "Lora-Regular.ttf",
|
|
11269
|
+
bold: "Lora-Bold.ttf",
|
|
11270
|
+
italic: "Lora-Italic.ttf",
|
|
11271
|
+
boldItalic: "Lora-BoldItalic.ttf"
|
|
11272
|
+
},
|
|
11273
|
+
"Montserrat": {
|
|
11274
|
+
regular: "Montserrat-Regular.ttf",
|
|
11275
|
+
bold: "Montserrat-Bold.ttf",
|
|
11276
|
+
light: "Montserrat-Light.ttf",
|
|
11277
|
+
medium: "Montserrat-Medium.ttf",
|
|
11278
|
+
semibold: "Montserrat-SemiBold.ttf",
|
|
11279
|
+
italic: "Montserrat-Italic.ttf",
|
|
11280
|
+
boldItalic: "Montserrat-BoldItalic.ttf",
|
|
11281
|
+
lightItalic: "Montserrat-LightItalic.ttf",
|
|
11282
|
+
mediumItalic: "Montserrat-MediumItalic.ttf",
|
|
11283
|
+
semiboldItalic: "Montserrat-SemiBoldItalic.ttf"
|
|
11284
|
+
},
|
|
11285
|
+
"Open Sans": {
|
|
11286
|
+
regular: "OpenSans-Regular.ttf",
|
|
11287
|
+
bold: "OpenSans-Bold.ttf",
|
|
11288
|
+
light: "OpenSans-Light.ttf",
|
|
11289
|
+
semibold: "OpenSans-SemiBold.ttf",
|
|
11290
|
+
italic: "OpenSans-Italic.ttf",
|
|
11291
|
+
boldItalic: "OpenSans-BoldItalic.ttf",
|
|
11292
|
+
lightItalic: "OpenSans-LightItalic.ttf",
|
|
11293
|
+
semiboldItalic: "OpenSans-SemiBoldItalic.ttf"
|
|
11294
|
+
},
|
|
11295
|
+
"Roboto": {
|
|
11296
|
+
regular: "Roboto-Regular.ttf",
|
|
11297
|
+
bold: "Roboto-Bold.ttf",
|
|
11298
|
+
light: "Roboto-Light.ttf",
|
|
11299
|
+
medium: "Roboto-Medium.ttf",
|
|
11300
|
+
italic: "Roboto-Italic.ttf",
|
|
11301
|
+
boldItalic: "Roboto-BoldItalic.ttf",
|
|
11302
|
+
lightItalic: "Roboto-LightItalic.ttf",
|
|
11303
|
+
mediumItalic: "Roboto-MediumItalic.ttf"
|
|
11304
|
+
},
|
|
11305
|
+
"Lato": {
|
|
11306
|
+
regular: "Lato-Regular.ttf",
|
|
11307
|
+
bold: "Lato-Bold.ttf",
|
|
11308
|
+
light: "Lato-Light.ttf",
|
|
11309
|
+
italic: "Lato-Italic.ttf",
|
|
11310
|
+
boldItalic: "Lato-BoldItalic.ttf",
|
|
11311
|
+
lightItalic: "Lato-LightItalic.ttf"
|
|
11312
|
+
},
|
|
11313
|
+
"Raleway": {
|
|
11314
|
+
regular: "Raleway-Regular.ttf",
|
|
11315
|
+
bold: "Raleway-Bold.ttf",
|
|
11316
|
+
light: "Raleway-Light.ttf",
|
|
11317
|
+
medium: "Raleway-Medium.ttf",
|
|
11318
|
+
semibold: "Raleway-SemiBold.ttf",
|
|
11319
|
+
italic: "Raleway-Italic.ttf",
|
|
11320
|
+
boldItalic: "Raleway-BoldItalic.ttf",
|
|
11321
|
+
lightItalic: "Raleway-LightItalic.ttf"
|
|
11322
|
+
},
|
|
11323
|
+
"Poppins": {
|
|
11324
|
+
regular: "Poppins-Regular.ttf",
|
|
11325
|
+
bold: "Poppins-Bold.ttf",
|
|
11326
|
+
light: "Poppins-Light.ttf",
|
|
11327
|
+
medium: "Poppins-Medium.ttf",
|
|
11328
|
+
semibold: "Poppins-SemiBold.ttf",
|
|
11329
|
+
italic: "Poppins-Italic.ttf",
|
|
11330
|
+
boldItalic: "Poppins-BoldItalic.ttf",
|
|
11331
|
+
lightItalic: "Poppins-LightItalic.ttf",
|
|
11332
|
+
mediumItalic: "Poppins-MediumItalic.ttf",
|
|
11333
|
+
semiboldItalic: "Poppins-SemiBoldItalic.ttf"
|
|
11334
|
+
},
|
|
11335
|
+
"Inter": {
|
|
11336
|
+
regular: "Inter-Regular.ttf",
|
|
11337
|
+
bold: "Inter-Bold.ttf",
|
|
11338
|
+
italic: "Inter-Italic.ttf",
|
|
11339
|
+
boldItalic: "Inter-BoldItalic.ttf"
|
|
11340
|
+
},
|
|
11341
|
+
"Nunito": {
|
|
11342
|
+
regular: "Nunito-Regular.ttf",
|
|
11343
|
+
bold: "Nunito-Bold.ttf",
|
|
11344
|
+
light: "Nunito-Light.ttf",
|
|
11345
|
+
medium: "Nunito-Medium.ttf",
|
|
11346
|
+
semibold: "Nunito-SemiBold.ttf",
|
|
11347
|
+
italic: "Nunito-Italic.ttf",
|
|
11348
|
+
boldItalic: "Nunito-BoldItalic.ttf"
|
|
11349
|
+
},
|
|
11350
|
+
"Source Sans Pro": {
|
|
11351
|
+
regular: "SourceSansPro-Regular.ttf",
|
|
11352
|
+
bold: "SourceSansPro-Bold.ttf",
|
|
11353
|
+
light: "SourceSansPro-Light.ttf",
|
|
11354
|
+
italic: "SourceSansPro-Italic.ttf",
|
|
11355
|
+
boldItalic: "SourceSansPro-BoldItalic.ttf"
|
|
11356
|
+
},
|
|
11357
|
+
"Work Sans": {
|
|
11358
|
+
regular: "WorkSans-Regular.ttf",
|
|
11359
|
+
bold: "WorkSans-Bold.ttf",
|
|
11360
|
+
italic: "WorkSans-Italic.ttf",
|
|
11361
|
+
boldItalic: "WorkSans-BoldItalic.ttf"
|
|
11362
|
+
},
|
|
11363
|
+
"Oswald": { regular: "Oswald-Regular.ttf", bold: "Oswald-Bold.ttf" },
|
|
11364
|
+
"Bebas Neue": { regular: "BebasNeue-Regular.ttf" },
|
|
11365
|
+
"Abril Fatface": { regular: "AbrilFatface-Regular.ttf" },
|
|
11366
|
+
"Dancing Script": { regular: "DancingScript-Regular.ttf", bold: "DancingScript-Bold.ttf" },
|
|
11367
|
+
"Pacifico": { regular: "Pacifico-Regular.ttf" },
|
|
11368
|
+
"Great Vibes": { regular: "GreatVibes-Regular.ttf" },
|
|
11369
|
+
"DM Sans": {
|
|
11370
|
+
regular: "DMSans-Regular.ttf",
|
|
11371
|
+
bold: "DMSans-Bold.ttf",
|
|
11372
|
+
light: "DMSans-Light.ttf",
|
|
11373
|
+
medium: "DMSans-Medium.ttf",
|
|
11374
|
+
semibold: "DMSans-SemiBold.ttf",
|
|
11375
|
+
italic: "DMSans-RegularItalic.ttf",
|
|
11376
|
+
boldItalic: "DMSans-BoldItalic.ttf",
|
|
11377
|
+
lightItalic: "DMSans-LightItalic.ttf",
|
|
11378
|
+
mediumItalic: "DMSans-MediumItalic.ttf",
|
|
11379
|
+
semiboldItalic: "DMSans-SemiBoldItalic.ttf"
|
|
11380
|
+
},
|
|
11381
|
+
"Outfit": {
|
|
11382
|
+
regular: "Outfit-Regular.ttf",
|
|
11383
|
+
bold: "Outfit-Bold.ttf",
|
|
11384
|
+
light: "Outfit-Light.ttf",
|
|
11385
|
+
medium: "Outfit-Medium.ttf",
|
|
11386
|
+
semibold: "Outfit-SemiBold.ttf"
|
|
11387
|
+
},
|
|
11388
|
+
"Figtree": {
|
|
11389
|
+
regular: "Figtree-Regular.ttf",
|
|
11390
|
+
bold: "Figtree-Bold.ttf",
|
|
11391
|
+
light: "Figtree-Light.ttf",
|
|
11392
|
+
medium: "Figtree-Medium.ttf",
|
|
11393
|
+
semibold: "Figtree-SemiBold.ttf",
|
|
11394
|
+
italic: "Figtree-RegularItalic.ttf",
|
|
11395
|
+
boldItalic: "Figtree-BoldItalic.ttf",
|
|
11396
|
+
lightItalic: "Figtree-LightItalic.ttf",
|
|
11397
|
+
mediumItalic: "Figtree-MediumItalic.ttf",
|
|
11398
|
+
semiboldItalic: "Figtree-SemiBoldItalic.ttf"
|
|
11399
|
+
},
|
|
11400
|
+
"Manrope": {
|
|
11401
|
+
regular: "Manrope-Regular.ttf",
|
|
11402
|
+
bold: "Manrope-Bold.ttf",
|
|
11403
|
+
light: "Manrope-Light.ttf",
|
|
11404
|
+
medium: "Manrope-Medium.ttf",
|
|
11405
|
+
semibold: "Manrope-SemiBold.ttf"
|
|
11406
|
+
},
|
|
11407
|
+
"Space Grotesk": {
|
|
11408
|
+
regular: "SpaceGrotesk-Regular.ttf",
|
|
11409
|
+
bold: "SpaceGrotesk-Bold.ttf",
|
|
11410
|
+
light: "SpaceGrotesk-Light.ttf",
|
|
11411
|
+
medium: "SpaceGrotesk-Medium.ttf",
|
|
11412
|
+
semibold: "SpaceGrotesk-SemiBold.ttf"
|
|
11413
|
+
},
|
|
11414
|
+
"League Spartan": {
|
|
11415
|
+
regular: "LeagueSpartan-Regular.ttf",
|
|
11416
|
+
bold: "LeagueSpartan-Bold.ttf",
|
|
11417
|
+
light: "LeagueSpartan-Light.ttf",
|
|
11418
|
+
medium: "LeagueSpartan-Medium.ttf",
|
|
11419
|
+
semibold: "LeagueSpartan-SemiBold.ttf"
|
|
11420
|
+
},
|
|
11421
|
+
"EB Garamond": {
|
|
11422
|
+
regular: "EBGaramond-Regular.ttf",
|
|
11423
|
+
bold: "EBGaramond-Bold.ttf",
|
|
11424
|
+
medium: "EBGaramond-Medium.ttf",
|
|
11425
|
+
semibold: "EBGaramond-SemiBold.ttf",
|
|
11426
|
+
italic: "EBGaramond-RegularItalic.ttf",
|
|
11427
|
+
boldItalic: "EBGaramond-BoldItalic.ttf",
|
|
11428
|
+
mediumItalic: "EBGaramond-MediumItalic.ttf",
|
|
11429
|
+
semiboldItalic: "EBGaramond-SemiBoldItalic.ttf"
|
|
11430
|
+
},
|
|
11431
|
+
"Libre Baskerville": {
|
|
11432
|
+
regular: "LibreBaskerville-Regular.ttf",
|
|
11433
|
+
bold: "LibreBaskerville-Bold.ttf",
|
|
11434
|
+
italic: "LibreBaskerville-RegularItalic.ttf",
|
|
11435
|
+
boldItalic: "LibreBaskerville-BoldItalic.ttf"
|
|
11436
|
+
},
|
|
11437
|
+
"Crimson Text": {
|
|
11438
|
+
regular: "CrimsonText-Regular.ttf",
|
|
11439
|
+
bold: "CrimsonText-Bold.ttf",
|
|
11440
|
+
italic: "CrimsonText-Italic.ttf",
|
|
11441
|
+
boldItalic: "CrimsonText-BoldItalic.ttf"
|
|
11442
|
+
},
|
|
11443
|
+
"DM Serif Display": {
|
|
11444
|
+
regular: "DMSerifDisplay-Regular.ttf",
|
|
11445
|
+
italic: "DMSerifDisplay-Italic.ttf"
|
|
11446
|
+
},
|
|
11447
|
+
"Libre Franklin": {
|
|
11448
|
+
regular: "LibreFranklin-Regular.ttf",
|
|
11449
|
+
bold: "LibreFranklin-Bold.ttf",
|
|
11450
|
+
light: "LibreFranklin-Light.ttf",
|
|
11451
|
+
medium: "LibreFranklin-Medium.ttf",
|
|
11452
|
+
semibold: "LibreFranklin-SemiBold.ttf",
|
|
11453
|
+
italic: "LibreFranklin-RegularItalic.ttf",
|
|
11454
|
+
boldItalic: "LibreFranklin-BoldItalic.ttf",
|
|
11455
|
+
lightItalic: "LibreFranklin-LightItalic.ttf",
|
|
11456
|
+
mediumItalic: "LibreFranklin-MediumItalic.ttf",
|
|
11457
|
+
semiboldItalic: "LibreFranklin-SemiBoldItalic.ttf"
|
|
11458
|
+
},
|
|
11459
|
+
"Mulish": {
|
|
11460
|
+
regular: "Mulish-Regular.ttf",
|
|
11461
|
+
bold: "Mulish-Bold.ttf",
|
|
11462
|
+
light: "Mulish-Light.ttf",
|
|
11463
|
+
medium: "Mulish-Medium.ttf",
|
|
11464
|
+
semibold: "Mulish-SemiBold.ttf",
|
|
11465
|
+
italic: "Mulish-RegularItalic.ttf",
|
|
11466
|
+
boldItalic: "Mulish-BoldItalic.ttf",
|
|
11467
|
+
lightItalic: "Mulish-LightItalic.ttf",
|
|
11468
|
+
mediumItalic: "Mulish-MediumItalic.ttf",
|
|
11469
|
+
semiboldItalic: "Mulish-SemiBoldItalic.ttf"
|
|
11470
|
+
},
|
|
11471
|
+
"Quicksand": {
|
|
11472
|
+
regular: "Quicksand-Regular.ttf",
|
|
11473
|
+
bold: "Quicksand-Bold.ttf",
|
|
11474
|
+
light: "Quicksand-Light.ttf",
|
|
11475
|
+
medium: "Quicksand-Medium.ttf",
|
|
11476
|
+
semibold: "Quicksand-SemiBold.ttf"
|
|
11477
|
+
},
|
|
11478
|
+
"Rubik": {
|
|
11479
|
+
regular: "Rubik-Regular.ttf",
|
|
11480
|
+
bold: "Rubik-Bold.ttf",
|
|
11481
|
+
light: "Rubik-Light.ttf",
|
|
11482
|
+
medium: "Rubik-Medium.ttf",
|
|
11483
|
+
semibold: "Rubik-SemiBold.ttf",
|
|
11484
|
+
italic: "Rubik-RegularItalic.ttf",
|
|
11485
|
+
boldItalic: "Rubik-BoldItalic.ttf",
|
|
11486
|
+
lightItalic: "Rubik-LightItalic.ttf",
|
|
11487
|
+
mediumItalic: "Rubik-MediumItalic.ttf",
|
|
11488
|
+
semiboldItalic: "Rubik-SemiBoldItalic.ttf"
|
|
11489
|
+
},
|
|
11490
|
+
"Karla": {
|
|
11491
|
+
regular: "Karla-Regular.ttf",
|
|
11492
|
+
bold: "Karla-Bold.ttf",
|
|
11493
|
+
light: "Karla-Light.ttf",
|
|
11494
|
+
medium: "Karla-Medium.ttf",
|
|
11495
|
+
semibold: "Karla-SemiBold.ttf",
|
|
11496
|
+
italic: "Karla-RegularItalic.ttf",
|
|
11497
|
+
boldItalic: "Karla-BoldItalic.ttf",
|
|
11498
|
+
lightItalic: "Karla-LightItalic.ttf",
|
|
11499
|
+
mediumItalic: "Karla-MediumItalic.ttf",
|
|
11500
|
+
semiboldItalic: "Karla-SemiBoldItalic.ttf"
|
|
11501
|
+
},
|
|
11502
|
+
"Plus Jakarta Sans": {
|
|
11503
|
+
regular: "PlusJakartaSans-Regular.ttf",
|
|
11504
|
+
bold: "PlusJakartaSans-Bold.ttf",
|
|
11505
|
+
light: "PlusJakartaSans-Light.ttf",
|
|
11506
|
+
medium: "PlusJakartaSans-Medium.ttf",
|
|
11507
|
+
semibold: "PlusJakartaSans-SemiBold.ttf",
|
|
11508
|
+
italic: "PlusJakartaSans-RegularItalic.ttf",
|
|
11509
|
+
boldItalic: "PlusJakartaSans-BoldItalic.ttf",
|
|
11510
|
+
lightItalic: "PlusJakartaSans-LightItalic.ttf",
|
|
11511
|
+
mediumItalic: "PlusJakartaSans-MediumItalic.ttf",
|
|
11512
|
+
semiboldItalic: "PlusJakartaSans-SemiBoldItalic.ttf"
|
|
11513
|
+
},
|
|
11514
|
+
"Sora": {
|
|
11515
|
+
regular: "Sora-Regular.ttf",
|
|
11516
|
+
bold: "Sora-Bold.ttf",
|
|
11517
|
+
light: "Sora-Light.ttf",
|
|
11518
|
+
medium: "Sora-Medium.ttf",
|
|
11519
|
+
semibold: "Sora-SemiBold.ttf"
|
|
11520
|
+
},
|
|
11521
|
+
"Urbanist": {
|
|
11522
|
+
regular: "Urbanist-Regular.ttf",
|
|
11523
|
+
bold: "Urbanist-Bold.ttf",
|
|
11524
|
+
light: "Urbanist-Light.ttf",
|
|
11525
|
+
medium: "Urbanist-Medium.ttf",
|
|
11526
|
+
semibold: "Urbanist-SemiBold.ttf",
|
|
11527
|
+
italic: "Urbanist-RegularItalic.ttf",
|
|
11528
|
+
boldItalic: "Urbanist-BoldItalic.ttf",
|
|
11529
|
+
lightItalic: "Urbanist-LightItalic.ttf",
|
|
11530
|
+
mediumItalic: "Urbanist-MediumItalic.ttf",
|
|
11531
|
+
semiboldItalic: "Urbanist-SemiBoldItalic.ttf"
|
|
11532
|
+
},
|
|
11533
|
+
"Lexend": {
|
|
11534
|
+
regular: "Lexend-Regular.ttf",
|
|
11535
|
+
bold: "Lexend-Bold.ttf",
|
|
11536
|
+
light: "Lexend-Light.ttf",
|
|
11537
|
+
medium: "Lexend-Medium.ttf",
|
|
11538
|
+
semibold: "Lexend-SemiBold.ttf"
|
|
11539
|
+
},
|
|
11540
|
+
"Albert Sans": {
|
|
11541
|
+
regular: "AlbertSans-Regular.ttf",
|
|
11542
|
+
bold: "AlbertSans-Bold.ttf",
|
|
11543
|
+
light: "AlbertSans-Light.ttf",
|
|
11544
|
+
medium: "AlbertSans-Medium.ttf",
|
|
11545
|
+
semibold: "AlbertSans-SemiBold.ttf",
|
|
11546
|
+
italic: "AlbertSans-RegularItalic.ttf",
|
|
11547
|
+
boldItalic: "AlbertSans-BoldItalic.ttf",
|
|
11548
|
+
lightItalic: "AlbertSans-LightItalic.ttf",
|
|
11549
|
+
mediumItalic: "AlbertSans-MediumItalic.ttf",
|
|
11550
|
+
semiboldItalic: "AlbertSans-SemiBoldItalic.ttf"
|
|
11551
|
+
},
|
|
11552
|
+
"Noto Sans": {
|
|
11553
|
+
regular: "NotoSans-Regular.ttf",
|
|
11554
|
+
bold: "NotoSans-Bold.ttf",
|
|
11555
|
+
light: "NotoSans-Light.ttf",
|
|
11556
|
+
medium: "NotoSans-Medium.ttf",
|
|
11557
|
+
semibold: "NotoSans-SemiBold.ttf",
|
|
11558
|
+
italic: "NotoSans-RegularItalic.ttf",
|
|
11559
|
+
boldItalic: "NotoSans-BoldItalic.ttf",
|
|
11560
|
+
lightItalic: "NotoSans-LightItalic.ttf",
|
|
11561
|
+
mediumItalic: "NotoSans-MediumItalic.ttf",
|
|
11562
|
+
semiboldItalic: "NotoSans-SemiBoldItalic.ttf"
|
|
11563
|
+
},
|
|
11564
|
+
"Cabin": {
|
|
11565
|
+
regular: "Cabin-Regular.ttf",
|
|
11566
|
+
bold: "Cabin-Bold.ttf",
|
|
11567
|
+
medium: "Cabin-Medium.ttf",
|
|
11568
|
+
semibold: "Cabin-SemiBold.ttf",
|
|
11569
|
+
italic: "Cabin-RegularItalic.ttf",
|
|
11570
|
+
boldItalic: "Cabin-BoldItalic.ttf",
|
|
11571
|
+
mediumItalic: "Cabin-MediumItalic.ttf",
|
|
11572
|
+
semiboldItalic: "Cabin-SemiBoldItalic.ttf"
|
|
11573
|
+
},
|
|
11574
|
+
"Barlow": {
|
|
11575
|
+
regular: "Barlow-Regular.ttf",
|
|
11576
|
+
bold: "Barlow-Bold.ttf",
|
|
11577
|
+
light: "Barlow-Light.ttf",
|
|
11578
|
+
medium: "Barlow-Medium.ttf",
|
|
11579
|
+
semibold: "Barlow-SemiBold.ttf",
|
|
11580
|
+
italic: "Barlow-Italic.ttf",
|
|
11581
|
+
boldItalic: "Barlow-BoldItalic.ttf"
|
|
11582
|
+
},
|
|
11583
|
+
"Josefin Sans": {
|
|
11584
|
+
regular: "JosefinSans-Regular.ttf",
|
|
11585
|
+
bold: "JosefinSans-Bold.ttf",
|
|
11586
|
+
light: "JosefinSans-Light.ttf",
|
|
11587
|
+
medium: "JosefinSans-Medium.ttf",
|
|
11588
|
+
semibold: "JosefinSans-SemiBold.ttf",
|
|
11589
|
+
italic: "JosefinSans-RegularItalic.ttf",
|
|
11590
|
+
boldItalic: "JosefinSans-BoldItalic.ttf",
|
|
11591
|
+
lightItalic: "JosefinSans-LightItalic.ttf",
|
|
11592
|
+
mediumItalic: "JosefinSans-MediumItalic.ttf",
|
|
11593
|
+
semiboldItalic: "JosefinSans-SemiBoldItalic.ttf"
|
|
11594
|
+
},
|
|
11595
|
+
"Archivo": {
|
|
11596
|
+
regular: "Archivo-Regular.ttf",
|
|
11597
|
+
bold: "Archivo-Bold.ttf",
|
|
11598
|
+
light: "Archivo-Light.ttf",
|
|
11599
|
+
medium: "Archivo-Medium.ttf",
|
|
11600
|
+
semibold: "Archivo-SemiBold.ttf",
|
|
11601
|
+
italic: "Archivo-RegularItalic.ttf",
|
|
11602
|
+
boldItalic: "Archivo-BoldItalic.ttf",
|
|
11603
|
+
lightItalic: "Archivo-LightItalic.ttf",
|
|
11604
|
+
mediumItalic: "Archivo-MediumItalic.ttf",
|
|
11605
|
+
semiboldItalic: "Archivo-SemiBoldItalic.ttf"
|
|
11606
|
+
},
|
|
11607
|
+
"Overpass": {
|
|
11608
|
+
regular: "Overpass-Regular.ttf",
|
|
11609
|
+
bold: "Overpass-Bold.ttf",
|
|
11610
|
+
light: "Overpass-Light.ttf",
|
|
11611
|
+
medium: "Overpass-Medium.ttf",
|
|
11612
|
+
semibold: "Overpass-SemiBold.ttf",
|
|
11613
|
+
italic: "Overpass-RegularItalic.ttf",
|
|
11614
|
+
boldItalic: "Overpass-BoldItalic.ttf",
|
|
11615
|
+
lightItalic: "Overpass-LightItalic.ttf",
|
|
11616
|
+
mediumItalic: "Overpass-MediumItalic.ttf",
|
|
11617
|
+
semiboldItalic: "Overpass-SemiBoldItalic.ttf"
|
|
11618
|
+
},
|
|
11619
|
+
"Exo 2": {
|
|
11620
|
+
regular: "Exo2-Regular.ttf",
|
|
11621
|
+
bold: "Exo2-Bold.ttf",
|
|
11622
|
+
light: "Exo2-Light.ttf",
|
|
11623
|
+
medium: "Exo2-Medium.ttf",
|
|
11624
|
+
semibold: "Exo2-SemiBold.ttf",
|
|
11625
|
+
italic: "Exo2-RegularItalic.ttf",
|
|
11626
|
+
boldItalic: "Exo2-BoldItalic.ttf",
|
|
11627
|
+
lightItalic: "Exo2-LightItalic.ttf",
|
|
11628
|
+
mediumItalic: "Exo2-MediumItalic.ttf",
|
|
11629
|
+
semiboldItalic: "Exo2-SemiBoldItalic.ttf"
|
|
11630
|
+
},
|
|
11631
|
+
"Roboto Mono": {
|
|
11632
|
+
regular: "RobotoMono-Regular.ttf",
|
|
11633
|
+
bold: "RobotoMono-Bold.ttf",
|
|
11634
|
+
light: "RobotoMono-Light.ttf",
|
|
11635
|
+
medium: "RobotoMono-Medium.ttf",
|
|
11636
|
+
semibold: "RobotoMono-SemiBold.ttf",
|
|
11637
|
+
italic: "RobotoMono-RegularItalic.ttf",
|
|
11638
|
+
boldItalic: "RobotoMono-BoldItalic.ttf",
|
|
11639
|
+
lightItalic: "RobotoMono-LightItalic.ttf",
|
|
11640
|
+
mediumItalic: "RobotoMono-MediumItalic.ttf",
|
|
11641
|
+
semiboldItalic: "RobotoMono-SemiBoldItalic.ttf"
|
|
11642
|
+
},
|
|
11643
|
+
"Fira Code": {
|
|
11644
|
+
regular: "FiraCode-Regular.ttf",
|
|
11645
|
+
bold: "FiraCode-Bold.ttf",
|
|
11646
|
+
light: "FiraCode-Light.ttf",
|
|
11647
|
+
medium: "FiraCode-Medium.ttf",
|
|
11648
|
+
semibold: "FiraCode-SemiBold.ttf"
|
|
11649
|
+
},
|
|
11650
|
+
"JetBrains Mono": {
|
|
11651
|
+
regular: "JetBrainsMono-Regular.ttf",
|
|
11652
|
+
bold: "JetBrainsMono-Bold.ttf",
|
|
11653
|
+
light: "JetBrainsMono-Light.ttf",
|
|
11654
|
+
medium: "JetBrainsMono-Medium.ttf",
|
|
11655
|
+
semibold: "JetBrainsMono-SemiBold.ttf",
|
|
11656
|
+
italic: "JetBrainsMono-RegularItalic.ttf",
|
|
11657
|
+
boldItalic: "JetBrainsMono-BoldItalic.ttf",
|
|
11658
|
+
lightItalic: "JetBrainsMono-LightItalic.ttf",
|
|
11659
|
+
mediumItalic: "JetBrainsMono-MediumItalic.ttf",
|
|
11660
|
+
semiboldItalic: "JetBrainsMono-SemiBoldItalic.ttf"
|
|
11661
|
+
},
|
|
11662
|
+
"Source Code Pro": {
|
|
11663
|
+
regular: "SourceCodePro-Regular.ttf",
|
|
11664
|
+
bold: "SourceCodePro-Bold.ttf",
|
|
11665
|
+
light: "SourceCodePro-Light.ttf",
|
|
11666
|
+
medium: "SourceCodePro-Medium.ttf",
|
|
11667
|
+
semibold: "SourceCodePro-SemiBold.ttf",
|
|
11668
|
+
italic: "SourceCodePro-RegularItalic.ttf",
|
|
11669
|
+
boldItalic: "SourceCodePro-BoldItalic.ttf",
|
|
11670
|
+
lightItalic: "SourceCodePro-LightItalic.ttf",
|
|
11671
|
+
mediumItalic: "SourceCodePro-MediumItalic.ttf",
|
|
11672
|
+
semiboldItalic: "SourceCodePro-SemiBoldItalic.ttf"
|
|
11673
|
+
},
|
|
11674
|
+
"IBM Plex Mono": {
|
|
11675
|
+
regular: "IBMPlexMono-Regular.ttf",
|
|
11676
|
+
bold: "IBMPlexMono-Bold.ttf"
|
|
11677
|
+
},
|
|
11678
|
+
"Space Mono": {
|
|
11679
|
+
regular: "SpaceMono-Regular.ttf",
|
|
11680
|
+
bold: "SpaceMono-Bold.ttf",
|
|
11681
|
+
italic: "SpaceMono-Italic.ttf",
|
|
11682
|
+
boldItalic: "SpaceMono-BoldItalic.ttf"
|
|
11683
|
+
},
|
|
11684
|
+
"Sacramento": { regular: "Sacramento-Regular.ttf" },
|
|
11685
|
+
"Alex Brush": { regular: "AlexBrush-Regular.ttf" },
|
|
11686
|
+
"Allura": { regular: "Allura-Regular.ttf" },
|
|
11687
|
+
"Caveat": {
|
|
11688
|
+
regular: "Caveat-Regular.ttf",
|
|
11689
|
+
bold: "Caveat-Bold.ttf",
|
|
11690
|
+
medium: "Caveat-Medium.ttf",
|
|
11691
|
+
semibold: "Caveat-SemiBold.ttf"
|
|
11692
|
+
},
|
|
11693
|
+
"Lobster": { regular: "Lobster-Regular.ttf" },
|
|
11694
|
+
"Comfortaa": {
|
|
11695
|
+
regular: "Comfortaa-Regular.ttf",
|
|
11696
|
+
bold: "Comfortaa-Bold.ttf",
|
|
11697
|
+
light: "Comfortaa-Light.ttf",
|
|
11698
|
+
medium: "Comfortaa-Medium.ttf",
|
|
11699
|
+
semibold: "Comfortaa-SemiBold.ttf"
|
|
11700
|
+
},
|
|
11701
|
+
"Anton": { regular: "Anton-Regular.ttf" },
|
|
11702
|
+
"Teko": {
|
|
11703
|
+
regular: "Teko-Regular.ttf",
|
|
11704
|
+
bold: "Teko-Bold.ttf",
|
|
11705
|
+
light: "Teko-Light.ttf",
|
|
11706
|
+
medium: "Teko-Medium.ttf",
|
|
11707
|
+
semibold: "Teko-SemiBold.ttf"
|
|
11708
|
+
},
|
|
11709
|
+
"Noto Sans Devanagari": {
|
|
11710
|
+
regular: "NotoSansDevanagari-Regular.ttf",
|
|
11711
|
+
bold: "NotoSansDevanagari-Bold.ttf",
|
|
11712
|
+
light: "NotoSansDevanagari-Light.ttf",
|
|
11713
|
+
medium: "NotoSansDevanagari-Medium.ttf",
|
|
11714
|
+
semibold: "NotoSansDevanagari-SemiBold.ttf"
|
|
11715
|
+
},
|
|
11716
|
+
"Hind": {
|
|
11717
|
+
regular: "Hind-Regular.ttf",
|
|
11718
|
+
bold: "Hind-Bold.ttf",
|
|
11719
|
+
light: "Hind-Light.ttf",
|
|
11720
|
+
medium: "Hind-Medium.ttf",
|
|
11721
|
+
semibold: "Hind-SemiBold.ttf"
|
|
11722
|
+
},
|
|
11723
|
+
"Cinzel": { regular: "Cinzel-Regular.ttf", bold: "Cinzel-Bold.ttf" },
|
|
11724
|
+
"Cormorant Garamond": {
|
|
11725
|
+
regular: "CormorantGaramond-Regular.ttf",
|
|
11726
|
+
bold: "CormorantGaramond-Bold.ttf",
|
|
11727
|
+
light: "CormorantGaramond-Light.ttf",
|
|
11728
|
+
medium: "CormorantGaramond-Medium.ttf",
|
|
11729
|
+
semibold: "CormorantGaramond-SemiBold.ttf",
|
|
11730
|
+
italic: "CormorantGaramond-Italic.ttf",
|
|
11731
|
+
boldItalic: "CormorantGaramond-BoldItalic.ttf"
|
|
11732
|
+
}
|
|
11733
|
+
};
|
|
11734
|
+
const WEIGHT_TO_KEYS = {
|
|
11735
|
+
300: ["light", "regular"],
|
|
11736
|
+
400: ["regular"],
|
|
11737
|
+
500: ["medium", "regular"],
|
|
11738
|
+
600: ["semibold", "bold", "regular"],
|
|
11739
|
+
700: ["bold", "regular"]
|
|
11740
|
+
};
|
|
11741
|
+
const WEIGHT_TO_ITALIC_KEYS = {
|
|
11742
|
+
300: ["lightItalic", "italic", "light", "regular"],
|
|
11743
|
+
400: ["italic", "regular"],
|
|
11744
|
+
500: ["mediumItalic", "italic", "medium", "regular"],
|
|
11745
|
+
600: ["semiboldItalic", "boldItalic", "italic", "semibold", "bold", "regular"],
|
|
11746
|
+
700: ["boldItalic", "italic", "bold", "regular"]
|
|
11747
|
+
};
|
|
11748
|
+
function getFontPathForWeight(files, weight, isItalic = false) {
|
|
11749
|
+
const keys = isItalic ? WEIGHT_TO_ITALIC_KEYS[weight] : WEIGHT_TO_KEYS[weight];
|
|
11750
|
+
if (!keys) return files.regular;
|
|
11751
|
+
for (const k of keys) {
|
|
11752
|
+
const path = files[k];
|
|
11753
|
+
if (path) return path;
|
|
11754
|
+
}
|
|
11755
|
+
return files.regular;
|
|
11756
|
+
}
|
|
11757
|
+
function isItalicPath(files, path) {
|
|
11758
|
+
return path === files.italic || path === files.boldItalic || path === files.lightItalic || path === files.mediumItalic || path === files.semiboldItalic;
|
|
11759
|
+
}
|
|
11760
|
+
function getJsPDFFontName(fontName) {
|
|
11761
|
+
return fontName.replace(/\s+/g, "");
|
|
11762
|
+
}
|
|
11763
|
+
function getEmbeddedJsPDFFontName(fontName, weight, isItalic = false) {
|
|
11764
|
+
const resolved = resolveFontWeight(weight);
|
|
11765
|
+
const label = FONT_WEIGHT_LABELS[resolved];
|
|
11766
|
+
const italicSuffix = isItalic ? "Italic" : "";
|
|
11767
|
+
return `${getJsPDFFontName(fontName)}-${label}${italicSuffix}`;
|
|
11768
|
+
}
|
|
11769
|
+
function isFontAvailable(fontName) {
|
|
11770
|
+
return fontName in FONT_FILES;
|
|
11771
|
+
}
|
|
11772
|
+
const ttfCache = /* @__PURE__ */ new Map();
|
|
11773
|
+
async function fetchTTFAsBase64(url) {
|
|
11774
|
+
const cached = ttfCache.get(url);
|
|
11775
|
+
if (cached) return cached;
|
|
11776
|
+
try {
|
|
11777
|
+
const res = await fetch(url);
|
|
11778
|
+
if (!res.ok) return null;
|
|
11779
|
+
const buf = await res.arrayBuffer();
|
|
11780
|
+
const bytes = new Uint8Array(buf);
|
|
11781
|
+
let binary = "";
|
|
11782
|
+
for (let i = 0; i < bytes.length; i++) {
|
|
11783
|
+
binary += String.fromCharCode(bytes[i]);
|
|
11784
|
+
}
|
|
11785
|
+
const b64 = btoa(binary);
|
|
11786
|
+
ttfCache.set(url, b64);
|
|
11787
|
+
return b64;
|
|
11788
|
+
} catch {
|
|
11789
|
+
return null;
|
|
11790
|
+
}
|
|
11791
|
+
}
|
|
11792
|
+
async function embedFont(pdf, fontName, weight, fontBaseUrl, isItalic = false) {
|
|
11793
|
+
const fontFiles = FONT_FILES[fontName];
|
|
11794
|
+
if (!fontFiles) return false;
|
|
11795
|
+
const baseUrl = fontBaseUrl.endsWith("/") ? fontBaseUrl : fontBaseUrl + "/";
|
|
11796
|
+
const resolvedWeight = resolveFontWeight(weight);
|
|
11797
|
+
const fontPath = getFontPathForWeight(fontFiles, resolvedWeight, isItalic);
|
|
11798
|
+
if (!fontPath) return false;
|
|
11799
|
+
const hasItalicFile = isItalic && isItalicPath(fontFiles, fontPath);
|
|
11800
|
+
const jsPdfFontName = getEmbeddedJsPDFFontName(fontName, weight, hasItalicFile);
|
|
11801
|
+
const label = FONT_WEIGHT_LABELS[resolvedWeight];
|
|
11802
|
+
const italicSuffix = hasItalicFile ? "Italic" : "";
|
|
11803
|
+
const fileName = `${getJsPDFFontName(fontName)}-${label}${italicSuffix}.ttf`;
|
|
11804
|
+
const url = baseUrl + fontPath;
|
|
11805
|
+
try {
|
|
11806
|
+
const b64 = await fetchTTFAsBase64(url);
|
|
11807
|
+
if (!b64) return false;
|
|
11808
|
+
pdf.addFileToVFS(fileName, b64);
|
|
11809
|
+
pdf.addFont(fileName, jsPdfFontName, "normal");
|
|
11810
|
+
if (fontName !== jsPdfFontName) {
|
|
11811
|
+
try {
|
|
11812
|
+
pdf.addFont(fileName, fontName, "normal");
|
|
11813
|
+
} catch {
|
|
11814
|
+
}
|
|
11815
|
+
}
|
|
11816
|
+
return true;
|
|
11817
|
+
} catch (e) {
|
|
11818
|
+
console.warn(`[pdf-fonts] Failed to embed ${fontName} w${weight}:`, e);
|
|
11819
|
+
return false;
|
|
11820
|
+
}
|
|
11821
|
+
}
|
|
11822
|
+
async function embedFontsForConfig(pdf, config, fontBaseUrl) {
|
|
11823
|
+
const fontKeys = /* @__PURE__ */ new Set();
|
|
11824
|
+
const SEP = "";
|
|
11825
|
+
const walkElements = (elements) => {
|
|
11826
|
+
for (const el of elements) {
|
|
11827
|
+
if (el.fontFamily) {
|
|
11828
|
+
const w = resolveFontWeight(el.fontWeight ?? 400);
|
|
11829
|
+
fontKeys.add(`${el.fontFamily}${SEP}${w}`);
|
|
11830
|
+
}
|
|
11831
|
+
if (el.styles && typeof el.styles === "object") {
|
|
11832
|
+
for (const lineKey of Object.keys(el.styles)) {
|
|
11833
|
+
const lineStyles = el.styles[lineKey];
|
|
11834
|
+
if (lineStyles && typeof lineStyles === "object") {
|
|
11835
|
+
for (const charKey of Object.keys(lineStyles)) {
|
|
11836
|
+
const s = lineStyles[charKey];
|
|
11837
|
+
if (s == null ? void 0 : s.fontFamily) {
|
|
11838
|
+
const w = resolveFontWeight(s.fontWeight ?? 400);
|
|
11839
|
+
fontKeys.add(`${s.fontFamily}${SEP}${w}`);
|
|
11840
|
+
}
|
|
11841
|
+
}
|
|
11842
|
+
}
|
|
11843
|
+
}
|
|
11844
|
+
}
|
|
11845
|
+
if (el.children) walkElements(el.children);
|
|
11846
|
+
if (el.objects) walkElements(el.objects);
|
|
11847
|
+
}
|
|
11848
|
+
};
|
|
11849
|
+
for (const page of (config == null ? void 0 : config.pages) || []) {
|
|
11850
|
+
if (page.children) walkElements(page.children);
|
|
11851
|
+
if (page.elements) walkElements(page.elements);
|
|
11852
|
+
}
|
|
11853
|
+
fontKeys.add(`${FONT_FALLBACK_SYMBOLS}${SEP}400`);
|
|
11854
|
+
for (const w of [300, 400, 500, 600, 700]) {
|
|
11855
|
+
fontKeys.add(`${FONT_FALLBACK_DEVANAGARI}${SEP}${w}`);
|
|
11856
|
+
}
|
|
11857
|
+
const embedded = /* @__PURE__ */ new Set();
|
|
11858
|
+
const tasks = [];
|
|
11859
|
+
for (const key of fontKeys) {
|
|
11860
|
+
const sep = key.indexOf(SEP);
|
|
11861
|
+
const fontName = key.slice(0, sep);
|
|
11862
|
+
const weight = parseInt(key.slice(sep + 1), 10);
|
|
11863
|
+
if (!isFontAvailable(fontName)) continue;
|
|
11864
|
+
tasks.push(
|
|
11865
|
+
embedFont(pdf, fontName, weight, fontBaseUrl).then((ok) => {
|
|
11866
|
+
if (ok) embedded.add(key);
|
|
11867
|
+
})
|
|
11868
|
+
);
|
|
11869
|
+
}
|
|
11870
|
+
await Promise.all(tasks);
|
|
11871
|
+
console.log(`[pdf-fonts] Embedded ${embedded.size} font variants from config`);
|
|
11872
|
+
return embedded;
|
|
11873
|
+
}
|
|
11874
|
+
function rewriteSvgFontsForJsPDF(svgStr) {
|
|
11875
|
+
var _a;
|
|
11876
|
+
const parser = new DOMParser();
|
|
11877
|
+
const doc = parser.parseFromString(svgStr, "image/svg+xml");
|
|
11878
|
+
const textEls = doc.querySelectorAll("text, tspan, textPath");
|
|
11879
|
+
const readStyleToken = (style, prop) => {
|
|
11880
|
+
var _a2;
|
|
11881
|
+
const match = style.match(new RegExp(`${prop}\\s*:\\s*([^;]+)`, "i"));
|
|
11882
|
+
return ((_a2 = match == null ? void 0 : match[1]) == null ? void 0 : _a2.trim()) || null;
|
|
11883
|
+
};
|
|
11884
|
+
const resolveInheritedValue = (el, attr, styleProp = attr) => {
|
|
11885
|
+
var _a2;
|
|
11886
|
+
let current = el;
|
|
11887
|
+
while (current) {
|
|
11888
|
+
const attrVal = (_a2 = current.getAttribute(attr)) == null ? void 0 : _a2.trim();
|
|
11889
|
+
if (attrVal) return attrVal;
|
|
11890
|
+
const styleVal = readStyleToken(current.getAttribute("style") || "", styleProp);
|
|
11891
|
+
if (styleVal) return styleVal;
|
|
11892
|
+
current = current.parentElement;
|
|
11893
|
+
}
|
|
11894
|
+
return null;
|
|
11895
|
+
};
|
|
11896
|
+
for (const el of textEls) {
|
|
11897
|
+
const inlineStyle = el.getAttribute("style") || "";
|
|
11898
|
+
const rawFf = resolveInheritedValue(el, "font-family");
|
|
11899
|
+
if (!rawFf) continue;
|
|
11900
|
+
const clean = (_a = rawFf.split(",")[0]) == null ? void 0 : _a.replace(/['"]/g, "").trim();
|
|
11901
|
+
if (!isFontAvailable(clean)) continue;
|
|
11902
|
+
const weightRaw = resolveInheritedValue(el, "font-weight") || "400";
|
|
11903
|
+
const styleRaw = resolveInheritedValue(el, "font-style") || "normal";
|
|
11904
|
+
const parsedWeight = Number.parseInt(weightRaw, 10);
|
|
11905
|
+
const weight = Number.isFinite(parsedWeight) ? parsedWeight : /bold/i.test(weightRaw) ? 700 : /medium/i.test(weightRaw) ? 500 : /semi/i.test(weightRaw) ? 600 : /light/i.test(weightRaw) ? 300 : 400;
|
|
11906
|
+
const resolved = resolveFontWeight(weight);
|
|
11907
|
+
const isItalic = /italic|oblique/i.test(styleRaw);
|
|
11908
|
+
const jsPdfName = getEmbeddedJsPDFFontName(clean, resolved, isItalic);
|
|
11909
|
+
el.setAttribute("font-family", jsPdfName);
|
|
11910
|
+
el.setAttribute("font-weight", "normal");
|
|
11911
|
+
el.setAttribute("font-style", "normal");
|
|
11912
|
+
const stylePairs = inlineStyle.split(";").map((part) => part.trim()).filter(Boolean).filter((part) => !/^font-family\s*:/i.test(part) && !/^font-weight\s*:/i.test(part) && !/^font-style\s*:/i.test(part));
|
|
11913
|
+
stylePairs.push(`font-family: ${jsPdfName}`);
|
|
11914
|
+
stylePairs.push(`font-weight: normal`);
|
|
11915
|
+
stylePairs.push(`font-style: normal`);
|
|
11916
|
+
el.setAttribute("style", stylePairs.join("; "));
|
|
11917
|
+
}
|
|
11918
|
+
return new XMLSerializer().serializeToString(doc.documentElement);
|
|
11919
|
+
}
|
|
11920
|
+
function extractFontFamiliesFromSvgs(svgs) {
|
|
11921
|
+
const families = /* @__PURE__ */ new Set();
|
|
11922
|
+
const regex = /font-family[=:]\s*["']?([^"';},]+)/gi;
|
|
11923
|
+
for (const svg of svgs) {
|
|
11924
|
+
let m;
|
|
11925
|
+
while ((m = regex.exec(svg)) !== null) {
|
|
11926
|
+
const raw = m[1].trim().split(",")[0].trim().replace(/^['"]|['"]$/g, "");
|
|
11927
|
+
if (raw && raw !== "serif" && raw !== "sans-serif" && raw !== "monospace") {
|
|
11928
|
+
families.add(raw);
|
|
11929
|
+
}
|
|
11930
|
+
}
|
|
11931
|
+
}
|
|
11932
|
+
return families;
|
|
11933
|
+
}
|
|
11934
|
+
async function embedFontsInPdf(pdf, fontFamilies, fontBaseUrl) {
|
|
11935
|
+
const embedded = /* @__PURE__ */ new Set();
|
|
11936
|
+
const weights = [300, 400, 500, 600, 700];
|
|
11937
|
+
const tasks = [];
|
|
11938
|
+
for (const family of fontFamilies) {
|
|
11939
|
+
if (!isFontAvailable(family)) {
|
|
11940
|
+
console.warn(`[pdf-fonts] No TTF mapping for "${family}" — will use Helvetica fallback`);
|
|
11941
|
+
continue;
|
|
11942
|
+
}
|
|
11943
|
+
for (const w of weights) {
|
|
11944
|
+
tasks.push(
|
|
11945
|
+
embedFont(pdf, family, w, fontBaseUrl).then((ok) => {
|
|
11946
|
+
if (ok) embedded.add(`${family}${w}`);
|
|
11947
|
+
})
|
|
11948
|
+
);
|
|
11949
|
+
}
|
|
11950
|
+
}
|
|
11951
|
+
await Promise.all(tasks);
|
|
11952
|
+
console.log(`[pdf-fonts] Embedded ${embedded.size} font variants for ${fontFamilies.size} families`);
|
|
11953
|
+
return embedded;
|
|
11954
|
+
}
|
|
11955
|
+
const pdfFonts = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
11956
|
+
__proto__: null,
|
|
11957
|
+
FONT_FALLBACK_DEVANAGARI,
|
|
11958
|
+
FONT_FALLBACK_SYMBOLS,
|
|
11959
|
+
FONT_FILES,
|
|
11960
|
+
FONT_WEIGHT_LABELS,
|
|
11961
|
+
embedFont,
|
|
11962
|
+
embedFontsForConfig,
|
|
11963
|
+
embedFontsInPdf,
|
|
11964
|
+
extractFontFamiliesFromSvgs,
|
|
11965
|
+
getEmbeddedJsPDFFontName,
|
|
11966
|
+
isFontAvailable,
|
|
11967
|
+
resolveFontWeight,
|
|
11968
|
+
rewriteSvgFontsForJsPDF
|
|
11969
|
+
}, Symbol.toStringTag, { value: "Module" }));
|
|
11236
11970
|
const SVG_DRAWABLE_TAGS = /* @__PURE__ */ new Set([
|
|
11237
11971
|
"path",
|
|
11238
11972
|
"rect",
|
|
@@ -11494,8 +12228,9 @@ function inlineSvgStyleBlockDeclarations(svg) {
|
|
|
11494
12228
|
});
|
|
11495
12229
|
});
|
|
11496
12230
|
const normalizePresentationValue = (key, value) => {
|
|
11497
|
-
|
|
11498
|
-
return
|
|
12231
|
+
const cleaned = value.replace(/\s*!important\s*$/i, "").trim();
|
|
12232
|
+
if (["fill", "stroke", "clip-path", "mask", "filter"].includes(key)) return normalizeGradientPaintRef(cleaned);
|
|
12233
|
+
return cleaned;
|
|
11499
12234
|
};
|
|
11500
12235
|
const applyDeclarations = (elements, declarations) => {
|
|
11501
12236
|
for (const el of elements) {
|
|
@@ -11961,6 +12696,14 @@ function inlineComputedStyles(svg) {
|
|
|
11961
12696
|
if (wrap.parentNode) document.body.removeChild(wrap);
|
|
11962
12697
|
}
|
|
11963
12698
|
}
|
|
12699
|
+
function disambiguateNestedSvgIds(rootSvg) {
|
|
12700
|
+
const nestedSvgs = Array.from(rootSvg.querySelectorAll("svg"));
|
|
12701
|
+
const toProcess = nestedSvgs.filter((s) => s !== rootSvg);
|
|
12702
|
+
if (toProcess.length < 2) return;
|
|
12703
|
+
toProcess.forEach((nested, idx) => {
|
|
12704
|
+
prefixSvgIds(nested, `n${idx}`);
|
|
12705
|
+
});
|
|
12706
|
+
}
|
|
11964
12707
|
function prefixSvgIds(svg, prefix) {
|
|
11965
12708
|
const safePrefix = String(prefix).replace(/[^a-zA-Z0-9-]/g, "_");
|
|
11966
12709
|
const idMap = /* @__PURE__ */ new Map();
|
|
@@ -12112,6 +12855,63 @@ async function svg2pdfWithDomMount(svg, pdf, opts) {
|
|
|
12112
12855
|
if (wrap.parentNode) document.body.removeChild(wrap);
|
|
12113
12856
|
}
|
|
12114
12857
|
}
|
|
12858
|
+
function convertTextDecorationsToLines(svg) {
|
|
12859
|
+
const doc = svg.ownerDocument;
|
|
12860
|
+
if (!doc) return;
|
|
12861
|
+
let measureCanvas = null;
|
|
12862
|
+
let ctx = null;
|
|
12863
|
+
try {
|
|
12864
|
+
measureCanvas = doc.createElement("canvas");
|
|
12865
|
+
ctx = measureCanvas.getContext("2d");
|
|
12866
|
+
} catch {
|
|
12867
|
+
}
|
|
12868
|
+
const textEls = Array.from(svg.querySelectorAll("text"));
|
|
12869
|
+
for (const textEl of textEls) {
|
|
12870
|
+
const tspans = Array.from(textEl.querySelectorAll("tspan"));
|
|
12871
|
+
if (tspans.length === 0) continue;
|
|
12872
|
+
const textDecOnText = (textEl.getAttribute("text-decoration") || "").toLowerCase();
|
|
12873
|
+
const textStyleDec = (getInlineStyleValue(textEl, "text-decoration") || "").toLowerCase();
|
|
12874
|
+
const textHasUnderline = textDecOnText.includes("underline") || textStyleDec.includes("underline");
|
|
12875
|
+
for (const tspan of tspans) {
|
|
12876
|
+
const tspanDec = (tspan.getAttribute("text-decoration") || "").toLowerCase();
|
|
12877
|
+
const tspanStyleDec = (getInlineStyleValue(tspan, "text-decoration") || "").toLowerCase();
|
|
12878
|
+
const hasUnderline = tspanDec.includes("underline") || tspanStyleDec.includes("underline") || textHasUnderline;
|
|
12879
|
+
if (!hasUnderline) continue;
|
|
12880
|
+
const content = tspan.textContent || "";
|
|
12881
|
+
if (!content.trim()) continue;
|
|
12882
|
+
const xAttr = tspan.getAttribute("x") ?? textEl.getAttribute("x") ?? "0";
|
|
12883
|
+
const yAttr = tspan.getAttribute("y") ?? textEl.getAttribute("y") ?? "0";
|
|
12884
|
+
const x = parseFloat(xAttr) || 0;
|
|
12885
|
+
const y = parseFloat(yAttr) || 0;
|
|
12886
|
+
const fontSize = parseFloat(
|
|
12887
|
+
tspan.getAttribute("font-size") || textEl.getAttribute("font-size") || "16"
|
|
12888
|
+
);
|
|
12889
|
+
const fontFamily = tspan.getAttribute("font-family") || textEl.getAttribute("font-family") || "sans-serif";
|
|
12890
|
+
const fontWeight = tspan.getAttribute("font-weight") || textEl.getAttribute("font-weight") || "normal";
|
|
12891
|
+
const fill = tspan.getAttribute("fill") || textEl.getAttribute("fill") || "#000000";
|
|
12892
|
+
let textWidth;
|
|
12893
|
+
if (ctx) {
|
|
12894
|
+
ctx.font = `${fontWeight} ${fontSize}px ${fontFamily.replace(/'/g, "")}`;
|
|
12895
|
+
textWidth = ctx.measureText(content).width;
|
|
12896
|
+
} else {
|
|
12897
|
+
textWidth = content.length * fontSize * 0.6;
|
|
12898
|
+
}
|
|
12899
|
+
const underlineY = y + fontSize * 0.15;
|
|
12900
|
+
const thickness = Math.max(0.5, fontSize * 0.066667);
|
|
12901
|
+
const line = doc.createElementNS("http://www.w3.org/2000/svg", "line");
|
|
12902
|
+
line.setAttribute("x1", String(x));
|
|
12903
|
+
line.setAttribute("y1", String(underlineY));
|
|
12904
|
+
line.setAttribute("x2", String(x + textWidth));
|
|
12905
|
+
line.setAttribute("y2", String(underlineY));
|
|
12906
|
+
line.setAttribute("stroke", fill.startsWith("url(") ? "#000000" : fill);
|
|
12907
|
+
line.setAttribute("stroke-width", String(thickness));
|
|
12908
|
+
line.setAttribute("fill", "none");
|
|
12909
|
+
if (textEl.parentElement) {
|
|
12910
|
+
textEl.parentElement.insertBefore(line, textEl.nextSibling);
|
|
12911
|
+
}
|
|
12912
|
+
}
|
|
12913
|
+
}
|
|
12914
|
+
}
|
|
12115
12915
|
function prepareLiveCanvasSvgForPdf(rawSvg, pageWidth, pageHeight, pageKey, options) {
|
|
12116
12916
|
try {
|
|
12117
12917
|
const parser = new DOMParser();
|
|
@@ -12135,11 +12935,13 @@ function prepareLiveCanvasSvgForPdf(rawSvg, pageWidth, pageHeight, pageKey, opti
|
|
|
12135
12935
|
sanitizeSvgTreeForPdf(svgToDraw);
|
|
12136
12936
|
normalizeSvgGradientStopOffsets(svgToDraw);
|
|
12137
12937
|
expandSvgGradientHrefs(svgToDraw);
|
|
12938
|
+
disambiguateNestedSvgIds(svgToDraw);
|
|
12138
12939
|
prefixSvgIds(svgToDraw, pageKey);
|
|
12139
12940
|
bakeGroupOpacityIntoChildren(svgToDraw);
|
|
12140
12941
|
stripSuspiciousFullPageOverlayNodes(svgToDraw);
|
|
12141
12942
|
if (options == null ? void 0 : options.stripPageBackground) stripRootPageBackgroundFromSvg(svgToDraw);
|
|
12142
12943
|
sanitizeSvgTreeForPdf(svgToDraw);
|
|
12944
|
+
convertTextDecorationsToLines(svgToDraw);
|
|
12143
12945
|
return svgToDraw;
|
|
12144
12946
|
} catch {
|
|
12145
12947
|
return null;
|
|
@@ -12227,6 +13029,12 @@ async function assemblePdfFromSvgs(svgResults, options = {}) {
|
|
|
12227
13029
|
compress: true
|
|
12228
13030
|
});
|
|
12229
13031
|
if (title) pdf.setProperties({ title, creator: "Pixldocs" });
|
|
13032
|
+
const fontBaseUrl = options.fontBaseUrl ?? (typeof window !== "undefined" ? window.location.origin + "/fonts/" : "/fonts/");
|
|
13033
|
+
const { extractFontFamiliesFromSvgs: extractFontFamiliesFromSvgs2 } = await Promise.resolve().then(() => pdfFonts);
|
|
13034
|
+
const fontFamilies = extractFontFamiliesFromSvgs2(svgResults.map((s) => s.svg));
|
|
13035
|
+
if (fontFamilies.size > 0) {
|
|
13036
|
+
await embedFontsInPdf(pdf, fontFamilies, fontBaseUrl);
|
|
13037
|
+
}
|
|
12230
13038
|
for (let i = 0; i < svgResults.length; i++) {
|
|
12231
13039
|
const page = svgResults[i];
|
|
12232
13040
|
if (i > 0) {
|
|
@@ -12236,15 +13044,22 @@ async function assemblePdfFromSvgs(svgResults, options = {}) {
|
|
|
12236
13044
|
const hasGradient = !!((_b = (_a = page.backgroundGradient) == null ? void 0 : _a.stops) == null ? void 0 : _b.length);
|
|
12237
13045
|
drawPageBackground(pdf, i, page.width, page.height, page.backgroundColor, page.backgroundGradient);
|
|
12238
13046
|
const shouldStripBg = stripPageBackground ?? hasGradient;
|
|
12239
|
-
|
|
13047
|
+
let processedSvg = prepareLiveCanvasSvgForPdf(page.svg, page.width, page.height, `page-${i + 1}`, {
|
|
12240
13048
|
stripPageBackground: shouldStripBg
|
|
12241
13049
|
});
|
|
12242
|
-
if (
|
|
13050
|
+
if (processedSvg) {
|
|
13051
|
+
const svgStr = new XMLSerializer().serializeToString(processedSvg);
|
|
13052
|
+
const rewrittenSvg = rewriteSvgFontsForJsPDF(svgStr);
|
|
13053
|
+
const reParser = new DOMParser();
|
|
13054
|
+
const reDoc = reParser.parseFromString(rewrittenSvg, "image/svg+xml");
|
|
13055
|
+
processedSvg = reDoc.documentElement;
|
|
13056
|
+
}
|
|
13057
|
+
if (processedSvg) {
|
|
12243
13058
|
pdf.setFillColor(0, 0, 0);
|
|
12244
13059
|
pdf.setDrawColor(0, 0, 0);
|
|
12245
13060
|
pdf.saveGraphicsState();
|
|
12246
|
-
setPdfColorFromSvg(pdf,
|
|
12247
|
-
await svg2pdfWithDomMount(
|
|
13061
|
+
setPdfColorFromSvg(pdf, processedSvg);
|
|
13062
|
+
await svg2pdfWithDomMount(processedSvg, pdf, svg2pdfOpts(0, 0, page.width, page.height));
|
|
12248
13063
|
pdf.restoreGraphicsState();
|
|
12249
13064
|
pdf.setFillColor(0, 0, 0);
|
|
12250
13065
|
pdf.setDrawColor(0, 0, 0);
|
|
@@ -12340,6 +13155,9 @@ async function warmTemplateFromForm(options) {
|
|
|
12340
13155
|
await warmResolvedTemplateForPreview(resolved.config, { signal, imageProxyUrl });
|
|
12341
13156
|
}
|
|
12342
13157
|
export {
|
|
13158
|
+
FONT_FALLBACK_DEVANAGARI,
|
|
13159
|
+
FONT_FALLBACK_SYMBOLS,
|
|
13160
|
+
FONT_FILES,
|
|
12343
13161
|
PixldocsPreview,
|
|
12344
13162
|
PixldocsRenderer,
|
|
12345
13163
|
applyThemeToConfig,
|
|
@@ -12347,11 +13165,19 @@ export {
|
|
|
12347
13165
|
collectFontDescriptorsFromConfig,
|
|
12348
13166
|
collectFontsFromConfig,
|
|
12349
13167
|
collectImageUrls,
|
|
13168
|
+
embedFont,
|
|
13169
|
+
embedFontsForConfig,
|
|
13170
|
+
embedFontsInPdf,
|
|
12350
13171
|
ensureFontsForResolvedConfig,
|
|
13172
|
+
extractFontFamiliesFromSvgs,
|
|
13173
|
+
getEmbeddedJsPDFFontName,
|
|
13174
|
+
isFontAvailable,
|
|
12351
13175
|
loadGoogleFontCSS,
|
|
12352
13176
|
normalizeFontFamily,
|
|
13177
|
+
resolveFontWeight,
|
|
12353
13178
|
resolveFromForm,
|
|
12354
13179
|
resolveTemplateData,
|
|
13180
|
+
rewriteSvgFontsForJsPDF,
|
|
12355
13181
|
warmResolvedTemplateForPreview,
|
|
12356
13182
|
warmTemplateFromForm
|
|
12357
13183
|
};
|