subfont 7.1.0 → 7.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +19 -1
- package/README.md +2 -0
- package/lib/parseCommandLineOptions.js +2 -2
- package/lib/subfont.js +23 -1
- package/lib/subsetFonts.js +48 -33
- package/package.json +2 -2
package/CHANGELOG.md
CHANGED
|
@@ -1,3 +1,17 @@
|
|
|
1
|
+
### v7.2.0 (2024-03-24)
|
|
2
|
+
|
|
3
|
+
#### Pull requests
|
|
4
|
+
|
|
5
|
+
- [#172](https://github.com/Munter/subfont/pull/172) Support partial instancing of variable fonts ([Andreas Lind](mailto:andreaslindpetersen@gmail.com))
|
|
6
|
+
|
|
7
|
+
#### Commits to master
|
|
8
|
+
|
|
9
|
+
- [Update subset-font to ^2.2.0](https://github.com/Munter/subfont/commit/1cf16cb1769c65e3a5b34d440b619b238a27141b) ([Andreas Lind](mailto:andreaslindpetersen@gmail.com))
|
|
10
|
+
|
|
11
|
+
### v7.1.1 (2023-05-08)
|
|
12
|
+
|
|
13
|
+
- [Fix file name generation when the font-family contains backslash Fixes \#171](https://github.com/Munter/subfont/commit/1cff3c4095680569ecf50d017035730eb4bd0cc0) ([Andreas Lind](mailto:andreaslindpetersen@gmail.com))
|
|
14
|
+
|
|
1
15
|
### v7.1.0 (2023-04-15)
|
|
2
16
|
|
|
3
17
|
- [#170](https://github.com/Munter/subfont/pull/170) Use harfbuzzjs instead of fontkit ([Andreas Lind](mailto:andreaslindpetersen@gmail.com))
|
|
@@ -15,7 +29,11 @@
|
|
|
15
29
|
- [Tell eslint to ignore the puppeteer-browsers dir](https://github.com/Munter/subfont/commit/99bca776a0bd7fab4c3e9c1084c23ae5f7c4e18b) ([Andreas Lind](mailto:andreaslindpetersen@gmail.com))
|
|
16
30
|
- [Drop node.js 14](https://github.com/Munter/subfont/commit/0dcf1ed53fa20f7eb4585e6e3813fa8d97aefae5) ([Andreas Lind](mailto:andreaslindpetersen@gmail.com))
|
|
17
31
|
- [Tolerate different moch console call orders](https://github.com/Munter/subfont/commit/046971fa1b9fb4096b108cd777f18c34bb938438) ([Andreas Lind](mailto:andreaslindpetersen@gmail.com))
|
|
18
|
-
- [+10 more](https://github.com/Munter/subfont/compare/v6.12.
|
|
32
|
+
- [+10 more](https://github.com/Munter/subfont/compare/v6.12.5...v7.0.0)
|
|
33
|
+
|
|
34
|
+
### v6.12.5 (2023-05-08)
|
|
35
|
+
|
|
36
|
+
- [Fix file name generation when the font-family contains backslash Fixes \#171](https://github.com/Munter/subfont/commit/5619db3bbbcffa41871b2bc04d4cafa15d409bde) ([Andreas Lind](mailto:andreaslindpetersen@gmail.com))
|
|
19
37
|
|
|
20
38
|
### v6.12.4 (2023-01-06)
|
|
21
39
|
|
package/README.md
CHANGED
|
@@ -107,6 +107,8 @@ Options:
|
|
|
107
107
|
[boolean] [default: false]
|
|
108
108
|
--relative-urls Issue relative urls instead of root-relative ones
|
|
109
109
|
[boolean] [default: false]
|
|
110
|
+
--instance Experimentally instance variable fonts when the variation
|
|
111
|
+
space isn't fully used [boolean] [default: false]
|
|
110
112
|
--silent, -s Do not write anything to stdout [boolean] [default: false]
|
|
111
113
|
--debug, -d Verbose insights into font glyph detection
|
|
112
114
|
[boolean] [default: false]
|
|
@@ -75,7 +75,7 @@ module.exports = function parseCommandLineOptions(argv) {
|
|
|
75
75
|
default: false,
|
|
76
76
|
})
|
|
77
77
|
.options('font-display', {
|
|
78
|
-
describe: 'Injects a font-display value into the @font-face CSS
|
|
78
|
+
describe: 'Injects a font-display value into the @font-face CSS',
|
|
79
79
|
type: 'string',
|
|
80
80
|
default: 'swap',
|
|
81
81
|
choices: ['auto', 'block', 'swap', 'fallback', 'optional'],
|
|
@@ -94,7 +94,7 @@ module.exports = function parseCommandLineOptions(argv) {
|
|
|
94
94
|
})
|
|
95
95
|
.options('instance', {
|
|
96
96
|
describe:
|
|
97
|
-
|
|
97
|
+
"Experimentally instance variable fonts when the variation space isn't fully used",
|
|
98
98
|
type: 'boolean',
|
|
99
99
|
default: false,
|
|
100
100
|
})
|
package/lib/subfont.js
CHANGED
|
@@ -359,8 +359,30 @@ module.exports = async function subfont(
|
|
|
359
359
|
fontUsage.smallestOriginalSize !== undefined &&
|
|
360
360
|
fontUsage.smallestSubsetSize !== undefined
|
|
361
361
|
) {
|
|
362
|
-
if (fontUsage.
|
|
362
|
+
if (fontUsage.fullyInstanced) {
|
|
363
363
|
status += ', fully instanced';
|
|
364
|
+
} else if (fontUsage.numAxesReduced > 0 || fontUsage.numAxesPinned) {
|
|
365
|
+
const instancingInfos = [];
|
|
366
|
+
if (fontUsage.numAxesPinned > 0) {
|
|
367
|
+
instancingInfos.push(
|
|
368
|
+
`${fontUsage.numAxesPinned} ${
|
|
369
|
+
fontUsage.numAxesPinned === 1 ? 'axis' : 'axes'
|
|
370
|
+
} pinned`
|
|
371
|
+
);
|
|
372
|
+
}
|
|
373
|
+
if (fontUsage.numAxesReduced) {
|
|
374
|
+
instancingInfos.push(
|
|
375
|
+
`${fontUsage.numAxesReduced}${
|
|
376
|
+
fontUsage.numAxesPinned > 0
|
|
377
|
+
? ''
|
|
378
|
+
: fontUsage.numAxesReduced === 1
|
|
379
|
+
? ' axis'
|
|
380
|
+
: ' axes'
|
|
381
|
+
} reduced`
|
|
382
|
+
);
|
|
383
|
+
}
|
|
384
|
+
|
|
385
|
+
status += `, partially instanced (${instancingInfos.join(', ')})`;
|
|
364
386
|
}
|
|
365
387
|
status += `, ${prettyBytes(fontUsage.smallestOriginalSize)} (${
|
|
366
388
|
fontUsage.smallestOriginalFormat
|
package/lib/subsetFonts.js
CHANGED
|
@@ -383,7 +383,7 @@ function getSubsetPromiseId(fontUsage, format, variationAxes = null) {
|
|
|
383
383
|
].join('\x1d');
|
|
384
384
|
}
|
|
385
385
|
|
|
386
|
-
async function
|
|
386
|
+
async function getVariationAxisBounds(
|
|
387
387
|
assetGraph,
|
|
388
388
|
fontUrl,
|
|
389
389
|
seenAxisValuesByFontUrlAndAxisName
|
|
@@ -392,13 +392,14 @@ async function getFullyPinnedVariationAxes(
|
|
|
392
392
|
assetGraph.findAssets({ url: fontUrl })[0].rawSrc
|
|
393
393
|
);
|
|
394
394
|
|
|
395
|
-
|
|
395
|
+
const variationAxes = {};
|
|
396
|
+
let fullyInstanced = true;
|
|
397
|
+
let numAxesPinned = 0;
|
|
398
|
+
let numAxesReduced = 0;
|
|
396
399
|
const fontVariationEntries = Object.entries(fontInfo.variationAxes);
|
|
397
400
|
const seenAxisValuesByAxisName =
|
|
398
401
|
seenAxisValuesByFontUrlAndAxisName.get(fontUrl);
|
|
399
402
|
if (fontVariationEntries.length > 0 && seenAxisValuesByAxisName) {
|
|
400
|
-
variationAxes = {};
|
|
401
|
-
let everyAxisPinned = true;
|
|
402
403
|
for (const [
|
|
403
404
|
axisName,
|
|
404
405
|
{ min, max, default: defaultValue },
|
|
@@ -409,16 +410,27 @@ async function getFullyPinnedVariationAxes(
|
|
|
409
410
|
}
|
|
410
411
|
if (seenAxisValues && seenAxisValues.size === 1) {
|
|
411
412
|
variationAxes[axisName] = _.clamp([...seenAxisValues][0], min, max);
|
|
412
|
-
|
|
413
|
-
|
|
413
|
+
numAxesPinned += 1;
|
|
414
|
+
} else if (seenAxisValues) {
|
|
415
|
+
const minSeenValue = Math.min(...seenAxisValues);
|
|
416
|
+
const maxSeenValue = Math.max(...seenAxisValues);
|
|
417
|
+
variationAxes[axisName] = {
|
|
418
|
+
min: Math.min(minSeenValue, min),
|
|
419
|
+
max: Math.min(maxSeenValue, max),
|
|
420
|
+
};
|
|
421
|
+
fullyInstanced = false;
|
|
422
|
+
if (minSeenValue > min || maxSeenValue < max) {
|
|
423
|
+
numAxesReduced += 1;
|
|
424
|
+
}
|
|
414
425
|
}
|
|
415
426
|
}
|
|
416
|
-
if (!everyAxisPinned) {
|
|
417
|
-
// Not all variation axes can be fully pinned, bail out
|
|
418
|
-
variationAxes = undefined;
|
|
419
|
-
}
|
|
420
427
|
}
|
|
421
|
-
return
|
|
428
|
+
return {
|
|
429
|
+
fullyInstanced,
|
|
430
|
+
numAxesReduced,
|
|
431
|
+
numAxesPinned,
|
|
432
|
+
variationAxes,
|
|
433
|
+
};
|
|
422
434
|
}
|
|
423
435
|
|
|
424
436
|
async function getSubsetsForFontUsage(
|
|
@@ -462,22 +474,25 @@ async function getSubsetsForFontUsage(
|
|
|
462
474
|
}, {});
|
|
463
475
|
|
|
464
476
|
const subsetPromiseMap = {};
|
|
465
|
-
const notFullyInstancedFontUrls = new Set();
|
|
466
477
|
|
|
467
478
|
for (const item of htmlOrSvgAssetTextsWithProps) {
|
|
468
479
|
for (const fontUsage of item.fontUsages) {
|
|
469
480
|
const fontBuffer = originalFontBuffers[fontUsage.fontUrl];
|
|
470
481
|
const text = fontUsage.text;
|
|
471
482
|
let variationAxes;
|
|
483
|
+
let fullyInstanced = false;
|
|
484
|
+
let numAxesReduced = 0;
|
|
485
|
+
let numAxesPinned = 0;
|
|
472
486
|
if (instance) {
|
|
473
|
-
|
|
487
|
+
const res = await getVariationAxisBounds(
|
|
474
488
|
assetGraph,
|
|
475
489
|
fontUsage.fontUrl,
|
|
476
490
|
seenAxisValuesByFontUrlAndAxisName
|
|
477
491
|
);
|
|
478
|
-
|
|
479
|
-
|
|
480
|
-
|
|
492
|
+
variationAxes = res.variationAxes;
|
|
493
|
+
fullyInstanced = res.fullyInstanced;
|
|
494
|
+
numAxesReduced = res.numAxesReduced;
|
|
495
|
+
numAxesPinned = res.numAxesPinned;
|
|
481
496
|
}
|
|
482
497
|
|
|
483
498
|
for (const targetFormat of formats) {
|
|
@@ -515,6 +530,9 @@ async function getSubsetsForFontUsage(
|
|
|
515
530
|
fontUsage.smallestSubsetSize = size;
|
|
516
531
|
fontUsage.smallestSubsetFormat = targetFormat;
|
|
517
532
|
fontUsage.variationAxes = variationAxes;
|
|
533
|
+
fontUsage.fullyInstanced = fullyInstanced;
|
|
534
|
+
fontUsage.numAxesPinned = numAxesPinned;
|
|
535
|
+
fontUsage.numAxesReduced = numAxesReduced;
|
|
518
536
|
}
|
|
519
537
|
}
|
|
520
538
|
});
|
|
@@ -523,8 +541,6 @@ async function getSubsetsForFontUsage(
|
|
|
523
541
|
}
|
|
524
542
|
|
|
525
543
|
await Promise.all(Object.values(subsetPromiseMap));
|
|
526
|
-
|
|
527
|
-
return { notFullyInstancedFontUrls };
|
|
528
544
|
}
|
|
529
545
|
|
|
530
546
|
const fontOrder = ['woff2', 'woff', 'truetype'];
|
|
@@ -949,17 +965,13 @@ function getVariationAxisUsage(htmlOrSvgAssetTextsWithProps) {
|
|
|
949
965
|
async function warnAboutUnusedVariationAxes(
|
|
950
966
|
assetGraph,
|
|
951
967
|
seenAxisValuesByFontUrlAndAxisName,
|
|
952
|
-
outOfBoundsAxesByFontUrl
|
|
953
|
-
notFullyInstancedFontUrls
|
|
968
|
+
outOfBoundsAxesByFontUrl
|
|
954
969
|
) {
|
|
955
970
|
const warnings = [];
|
|
956
971
|
for (const [
|
|
957
972
|
fontUrl,
|
|
958
973
|
seenAxisValuesByAxisName,
|
|
959
974
|
] of seenAxisValuesByFontUrlAndAxisName.entries()) {
|
|
960
|
-
if (!notFullyInstancedFontUrls.has(fontUrl)) {
|
|
961
|
-
continue;
|
|
962
|
-
}
|
|
963
975
|
const outOfBoundsAxes = outOfBoundsAxesByFontUrl.get(fontUrl) || new Set();
|
|
964
976
|
let fontInfo;
|
|
965
977
|
try {
|
|
@@ -1030,7 +1042,7 @@ async function warnAboutUnusedVariationAxes(
|
|
|
1030
1042
|
new Error(`🪓 Unused variation axes detected in your variable fonts.
|
|
1031
1043
|
The below variable fonts contain custom axes that do not appear to be fully used on any of your pages.
|
|
1032
1044
|
This bloats your fonts and also the subset fonts that subfont creates.
|
|
1033
|
-
Consider removing the unused axis ranges
|
|
1045
|
+
Consider removing the unused axis ranges by specifying the --instance switch
|
|
1034
1046
|
${warnings.join('\n')}`)
|
|
1035
1047
|
);
|
|
1036
1048
|
}
|
|
@@ -1320,7 +1332,7 @@ async function subsetFonts(
|
|
|
1320
1332
|
getVariationAxisUsage(htmlOrSvgAssetTextsWithProps);
|
|
1321
1333
|
|
|
1322
1334
|
// Generate subsets:
|
|
1323
|
-
|
|
1335
|
+
await getSubsetsForFontUsage(
|
|
1324
1336
|
assetGraph,
|
|
1325
1337
|
htmlOrSvgAssetTextsWithProps,
|
|
1326
1338
|
formats,
|
|
@@ -1329,12 +1341,13 @@ async function subsetFonts(
|
|
|
1329
1341
|
);
|
|
1330
1342
|
|
|
1331
1343
|
await warnAboutMissingGlyphs(htmlOrSvgAssetTextsWithProps, assetGraph);
|
|
1332
|
-
|
|
1333
|
-
|
|
1334
|
-
|
|
1335
|
-
|
|
1336
|
-
|
|
1337
|
-
|
|
1344
|
+
if (!instance) {
|
|
1345
|
+
await warnAboutUnusedVariationAxes(
|
|
1346
|
+
assetGraph,
|
|
1347
|
+
seenAxisValuesByFontUrlAndAxisName,
|
|
1348
|
+
outOfBoundsAxesByFontUrl
|
|
1349
|
+
);
|
|
1350
|
+
}
|
|
1338
1351
|
|
|
1339
1352
|
// Insert subsets:
|
|
1340
1353
|
|
|
@@ -1475,9 +1488,11 @@ async function subsetFonts(
|
|
|
1475
1488
|
.split(/\s+/)
|
|
1476
1489
|
.map((token) => normalizeFontPropertyValue('font-weight', token))
|
|
1477
1490
|
.join('_');
|
|
1478
|
-
const fileNamePrefix = `${unquote(
|
|
1491
|
+
const fileNamePrefix = `${unquote(
|
|
1492
|
+
cssFontParser.parseFontFamily(nameProps[0])[0]
|
|
1493
|
+
)
|
|
1479
1494
|
.replace(/__subset$/, '')
|
|
1480
|
-
.replace(/
|
|
1495
|
+
.replace(/[^a-z0-9_-]/gi, '_')}-${fontWeightRangeStr}${
|
|
1481
1496
|
nameProps[2] === 'italic' ? 'i' : ''
|
|
1482
1497
|
}`;
|
|
1483
1498
|
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "subfont",
|
|
3
|
-
"version": "7.
|
|
3
|
+
"version": "7.2.0",
|
|
4
4
|
"description": "Speeds up your pages initial paint by automatically subsetting local or Google fonts and loading them optimally",
|
|
5
5
|
"engines": {
|
|
6
6
|
"node": ">=10.0.0"
|
|
@@ -66,7 +66,7 @@
|
|
|
66
66
|
"pretty-bytes": "^5.1.0",
|
|
67
67
|
"puppeteer-core": "^19.8.5",
|
|
68
68
|
"specificity": "^0.4.1",
|
|
69
|
-
"subset-font": "^2.
|
|
69
|
+
"subset-font": "^2.2.0",
|
|
70
70
|
"urltools": "^0.4.1",
|
|
71
71
|
"yargs": "^15.4.0"
|
|
72
72
|
},
|