@quillmark/wasm 0.129.0 → 0.131.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 +126 -0
- package/README.md +33 -23
- package/THIRD_PARTY_LICENSES.md +18 -17
- package/core/wasm.d.ts +25 -13
- package/core/wasm.js +8 -5
- package/core/wasm_bg.wasm +0 -0
- package/package.json +1 -1
- package/render/wasm.d.ts +52 -15
- package/render/wasm.js +60 -10
- package/render/wasm_bg.wasm +0 -0
- package/render/wasm_bg.wasm.d.ts +2 -1
- package/runtime/runtime.d.ts +34 -0
- package/runtime/runtime.js +62 -8
- package/sbom.cdx.json +183 -101
package/render/wasm.js
CHANGED
|
@@ -441,8 +441,11 @@ export class Document {
|
|
|
441
441
|
return Document.__wrap(ret);
|
|
442
442
|
}
|
|
443
443
|
/**
|
|
444
|
-
*
|
|
445
|
-
*
|
|
444
|
+
* The newest storage version this build writes via
|
|
445
|
+
* [`toStored`](Document::to_stored): a document spelling a font mark, a
|
|
446
|
+
* `table` element, a merged table cell or a table head 0.130 cannot draw
|
|
447
|
+
* carries it, every other the tag before it, which a 0.130 build reads. The tag advances only when the wire format changes, not on
|
|
448
|
+
* every release.
|
|
446
449
|
* @returns {string}
|
|
447
450
|
*/
|
|
448
451
|
static currentStorageVersion() {
|
|
@@ -978,9 +981,9 @@ export class Document {
|
|
|
978
981
|
}
|
|
979
982
|
/**
|
|
980
983
|
* Read the storage version tag from a raw storage DTO string without a full
|
|
981
|
-
* parse, or `undefined`.
|
|
982
|
-
*
|
|
983
|
-
* throws. This is the storage version, not a field schema, though the JSON
|
|
984
|
+
* parse, or `undefined`. A tag this build does not read, newer or retired,
|
|
985
|
+
* comes back as-is, which tells a version mismatch from a corrupt payload
|
|
986
|
+
* when `fromStored` throws. This is the storage version, not a field schema, though the JSON
|
|
984
987
|
* key is spelled `"schema"`: that is the DTO's serde tag.
|
|
985
988
|
* @param {string} json
|
|
986
989
|
* @returns {string | undefined}
|
|
@@ -1203,11 +1206,51 @@ export class Engine {
|
|
|
1203
1206
|
const ptr = this.__destroy_into_raw();
|
|
1204
1207
|
wasm.__wbg_engine_free(ptr, 0);
|
|
1205
1208
|
}
|
|
1206
|
-
|
|
1207
|
-
|
|
1208
|
-
|
|
1209
|
-
|
|
1210
|
-
|
|
1209
|
+
/**
|
|
1210
|
+
* The text faces a `font_family` mark may set in a session of `quill`:
|
|
1211
|
+
* the host library's, in library order.
|
|
1212
|
+
* @param {Quill} quill
|
|
1213
|
+
* @returns {FontFace[]}
|
|
1214
|
+
*/
|
|
1215
|
+
fontFaces(quill) {
|
|
1216
|
+
try {
|
|
1217
|
+
const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
|
|
1218
|
+
_assertClass(quill, Quill);
|
|
1219
|
+
wasm.engine_fontFaces(retptr, this.__wbg_ptr, quill.__wbg_ptr);
|
|
1220
|
+
var r0 = getDataViewMemory0().getInt32(retptr + 4 * 0, true);
|
|
1221
|
+
var r1 = getDataViewMemory0().getInt32(retptr + 4 * 1, true);
|
|
1222
|
+
var r2 = getDataViewMemory0().getInt32(retptr + 4 * 2, true);
|
|
1223
|
+
if (r2) {
|
|
1224
|
+
throw takeObject(r1);
|
|
1225
|
+
}
|
|
1226
|
+
return takeObject(r0);
|
|
1227
|
+
} finally {
|
|
1228
|
+
wasm.__wbindgen_add_to_stack_pointer(16);
|
|
1229
|
+
}
|
|
1230
|
+
}
|
|
1231
|
+
/**
|
|
1232
|
+
* An engine whose sessions also set text in `fonts`, the host's font
|
|
1233
|
+
* library: each a `.ttf`, `.otf`, `.ttc` or `.otc` file, parsed once
|
|
1234
|
+
* here. A file in another format throws `engine::font_unsupported`, and
|
|
1235
|
+
* one holding no readable face `engine::font_unreadable`.
|
|
1236
|
+
* @param {Uint8Array[] | undefined} fonts
|
|
1237
|
+
*/
|
|
1238
|
+
constructor(fonts) {
|
|
1239
|
+
try {
|
|
1240
|
+
const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
|
|
1241
|
+
wasm.engine_new(retptr, addHeapObject(fonts));
|
|
1242
|
+
var r0 = getDataViewMemory0().getInt32(retptr + 4 * 0, true);
|
|
1243
|
+
var r1 = getDataViewMemory0().getInt32(retptr + 4 * 1, true);
|
|
1244
|
+
var r2 = getDataViewMemory0().getInt32(retptr + 4 * 2, true);
|
|
1245
|
+
if (r2) {
|
|
1246
|
+
throw takeObject(r1);
|
|
1247
|
+
}
|
|
1248
|
+
this.__wbg_ptr = r0;
|
|
1249
|
+
EngineFinalization.register(this, this.__wbg_ptr, this);
|
|
1250
|
+
return this;
|
|
1251
|
+
} finally {
|
|
1252
|
+
wasm.__wbindgen_add_to_stack_pointer(16);
|
|
1253
|
+
}
|
|
1211
1254
|
}
|
|
1212
1255
|
/**
|
|
1213
1256
|
* Open a live render session for `doc` against `quill`'s backend, on the
|
|
@@ -2452,6 +2495,9 @@ function __wbg_get_imports() {
|
|
|
2452
2495
|
const ret = Reflect.getPrototypeOf(getObject(arg0));
|
|
2453
2496
|
return addHeapObject(ret);
|
|
2454
2497
|
}, arguments); },
|
|
2498
|
+
__wbg_getRandomValues_436a51d0629d84e1: function() { return handleError(function (arg0, arg1) {
|
|
2499
|
+
globalThis.crypto.getRandomValues(getArrayU8FromWasm0(arg0, arg1));
|
|
2500
|
+
}, arguments); },
|
|
2455
2501
|
__wbg_get_658f6698067d9515: function() { return handleError(function (arg0, arg1) {
|
|
2456
2502
|
const ret = Reflect.get(getObject(arg0), getObject(arg1));
|
|
2457
2503
|
return addHeapObject(ret);
|
|
@@ -2603,6 +2649,10 @@ function __wbg_get_imports() {
|
|
|
2603
2649
|
__wbg_prototypesetcall_bc27214492979395: function(arg0, arg1, arg2) {
|
|
2604
2650
|
Uint8Array.prototype.set.call(getArrayU8FromWasm0(arg0, arg1), getObject(arg2));
|
|
2605
2651
|
},
|
|
2652
|
+
__wbg_push_2baf45db356cf468: function(arg0, arg1) {
|
|
2653
|
+
const ret = getObject(arg0).push(getObject(arg1));
|
|
2654
|
+
return ret;
|
|
2655
|
+
},
|
|
2606
2656
|
__wbg_putImageData_11570c06086c9e05: function() { return handleError(function (arg0, arg1, arg2, arg3) {
|
|
2607
2657
|
getObject(arg0).putImageData(getObject(arg1), arg2, arg3);
|
|
2608
2658
|
}, arguments); },
|
package/render/wasm_bg.wasm
CHANGED
|
Binary file
|
package/render/wasm_bg.wasm.d.ts
CHANGED
|
@@ -52,7 +52,8 @@ export const document_toAnnotatedMarkdown: (a: number, b: number) => void;
|
|
|
52
52
|
export const document_toMarkdown: (a: number, b: number) => void;
|
|
53
53
|
export const document_toStored: (a: number, b: number) => void;
|
|
54
54
|
export const document_warnings: (a: number, b: number) => void;
|
|
55
|
-
export const
|
|
55
|
+
export const engine_fontFaces: (a: number, b: number, c: number) => void;
|
|
56
|
+
export const engine_new: (a: number, b: number) => void;
|
|
56
57
|
export const engine_open: (a: number, b: number, c: number, d: number, e: number, f: number) => void;
|
|
57
58
|
export const engine_render: (a: number, b: number, c: number, d: number, e: number, f: number, g: number) => void;
|
|
58
59
|
export const engine_supportedFormats: (a: number, b: number, c: number) => void;
|
package/runtime/runtime.d.ts
CHANGED
|
@@ -415,6 +415,31 @@ export interface EngineOptions {
|
|
|
415
415
|
* `"typst"` and `"acroform"` to the bundled render build.
|
|
416
416
|
*/
|
|
417
417
|
backends?: Record<string, BackendDescriptor>;
|
|
418
|
+
|
|
419
|
+
/**
|
|
420
|
+
* The host's font library: each a `.ttf`, `.otf`, `.ttc` or `.otc` file,
|
|
421
|
+
* whose faces set only text a `font_family` mark sets. The bytes are
|
|
422
|
+
* copied at construction, cross into the render build once, when it loads,
|
|
423
|
+
* and are parsed there once. A file it refuses rejects every verb that
|
|
424
|
+
* needs that build, the first and each later one, with the same error:
|
|
425
|
+
* `engine::font_unsupported` for another format, `engine::font_unreadable`
|
|
426
|
+
* for a file holding no readable face. A value that is not an array of
|
|
427
|
+
* `Uint8Array` throws at construction.
|
|
428
|
+
*/
|
|
429
|
+
fonts?: Uint8Array[];
|
|
430
|
+
}
|
|
431
|
+
|
|
432
|
+
/**
|
|
433
|
+
* One face a session sets text in, with what an editor needs for an
|
|
434
|
+
* `@font-face` rule: the family, the CSS weight and style, and the font file.
|
|
435
|
+
* `index` is the face's place in `data` where the file is a collection.
|
|
436
|
+
*/
|
|
437
|
+
export interface FontFace {
|
|
438
|
+
family: string;
|
|
439
|
+
weight: number;
|
|
440
|
+
style: 'normal' | 'italic' | 'oblique';
|
|
441
|
+
index: number;
|
|
442
|
+
data: Uint8Array;
|
|
418
443
|
}
|
|
419
444
|
|
|
420
445
|
/**
|
|
@@ -485,6 +510,15 @@ export declare class Engine {
|
|
|
485
510
|
* backend binary or cloning the quill. Async for API stability.
|
|
486
511
|
*/
|
|
487
512
|
supportedFormats(quill: Quill): Promise<OutputFormat[]>;
|
|
513
|
+
|
|
514
|
+
/**
|
|
515
|
+
* The text faces a `font_family` mark may set in a session of `quill`: the
|
|
516
|
+
* host library's, in the order of `fonts`. A quill's own fonts and the
|
|
517
|
+
* embedded fallback set its plate, never a mark. Loads the backend and
|
|
518
|
+
* clones the quill as `open` does; a backend that reads no fonts answers
|
|
519
|
+
* `[]`.
|
|
520
|
+
*/
|
|
521
|
+
fontFaces(quill: Quill): Promise<FontFace[]>;
|
|
488
522
|
}
|
|
489
523
|
|
|
490
524
|
/**
|
package/runtime/runtime.js
CHANGED
|
@@ -470,10 +470,22 @@ export class Engine {
|
|
|
470
470
|
*/
|
|
471
471
|
/** load → Promise<build module>, memoized so each build loads once. */
|
|
472
472
|
#modules = new Map();
|
|
473
|
-
/**
|
|
473
|
+
/**
|
|
474
|
+
* load → `{ engine }`, that build's engine instance (the WASM backend
|
|
475
|
+
* registry), or `{ refused }`, the error its construction threw. A refusal
|
|
476
|
+
* is the font library's, which every retry would parse and refuse again.
|
|
477
|
+
*/
|
|
474
478
|
#engines = new Map();
|
|
475
479
|
/** backendId → descriptor `{ load, formats }`. */
|
|
476
480
|
#loaders;
|
|
481
|
+
/**
|
|
482
|
+
* The host's font library, copied at construction and handed to each
|
|
483
|
+
* build's engine as it loads; `null` once every build has had it.
|
|
484
|
+
* @type {Uint8Array[] | null}
|
|
485
|
+
*/
|
|
486
|
+
#fonts;
|
|
487
|
+
/** How many distinct builds the loaders name. */
|
|
488
|
+
#builds;
|
|
477
489
|
/**
|
|
478
490
|
* load → WeakMap<canonical Quill, build-memory clone>, caching the
|
|
479
491
|
* expensive materialization. WeakMap so dropping the canonical quill makes
|
|
@@ -486,10 +498,15 @@ export class Engine {
|
|
|
486
498
|
* `load` must resolve to a READY module: a registrant shipping its own
|
|
487
499
|
* `--target web` build instantiates inside the thunk, and more than one
|
|
488
500
|
* `Engine` may call it, so memoize (the built-ins do, at module scope).
|
|
489
|
-
* @param {{ backends?: Record<string, { load: () => Promise<unknown>, formats: string[] }
|
|
501
|
+
* @param {{ backends?: Record<string, { load: () => Promise<unknown>, formats: string[] }>, fonts?: Uint8Array[] }} [options]
|
|
490
502
|
*/
|
|
491
503
|
constructor(options) {
|
|
492
|
-
rejectUnknownKeys(options, ['backends'], 'Engine options');
|
|
504
|
+
rejectUnknownKeys(options, ['backends', 'fonts'], 'Engine options');
|
|
505
|
+
const fonts = options?.fonts ?? [];
|
|
506
|
+
if (!Array.isArray(fonts) || !fonts.every((font) => font instanceof Uint8Array)) {
|
|
507
|
+
throw new Error('Engine: `fonts` must be an array of Uint8Array.');
|
|
508
|
+
}
|
|
509
|
+
this.#fonts = fonts.map((font) => font.slice());
|
|
493
510
|
const merged = { ...DEFAULT_BACKENDS, ...(options?.backends ?? {}) };
|
|
494
511
|
/** @type {Record<string, { load: () => Promise<unknown>, formats: string[] }>} */
|
|
495
512
|
const loaders = {};
|
|
@@ -497,6 +514,7 @@ export class Engine {
|
|
|
497
514
|
loaders[id] = validateBackend(id, entry);
|
|
498
515
|
}
|
|
499
516
|
this.#loaders = loaders;
|
|
517
|
+
this.#builds = new Set(Object.values(loaders).map((descriptor) => descriptor.load)).size;
|
|
500
518
|
}
|
|
501
519
|
|
|
502
520
|
/**
|
|
@@ -554,12 +572,18 @@ export class Engine {
|
|
|
554
572
|
}
|
|
555
573
|
const mod = await modPromise;
|
|
556
574
|
|
|
557
|
-
let
|
|
558
|
-
if (!
|
|
559
|
-
|
|
560
|
-
|
|
575
|
+
let built = this.#engines.get(load);
|
|
576
|
+
if (!built) {
|
|
577
|
+
try {
|
|
578
|
+
built = { engine: new mod.Engine(this.#fonts) };
|
|
579
|
+
} catch (refused) {
|
|
580
|
+
built = { refused };
|
|
581
|
+
}
|
|
582
|
+
this.#engines.set(load, built);
|
|
583
|
+
if (this.#engines.size === this.#builds) this.#fonts = null;
|
|
561
584
|
}
|
|
562
|
-
|
|
585
|
+
if ('refused' in built) throw built.refused;
|
|
586
|
+
return { mod, engine: built.engine };
|
|
563
587
|
}
|
|
564
588
|
|
|
565
589
|
/**
|
|
@@ -658,6 +682,36 @@ export class Engine {
|
|
|
658
682
|
);
|
|
659
683
|
}
|
|
660
684
|
|
|
685
|
+
/**
|
|
686
|
+
* Run `fn` against `quill`'s build-memory clone, `quill` snapshotted before
|
|
687
|
+
* the first await as `#withClones` snapshots it.
|
|
688
|
+
* @param {string} method the caller's name, for the rejection message
|
|
689
|
+
* @param {Quill} quill
|
|
690
|
+
* @param {(ctx: { engine: any, quill: any }) => any} fn
|
|
691
|
+
*/
|
|
692
|
+
async #withQuill(method, quill, fn) {
|
|
693
|
+
const backendId = this.#backendOf(quill, method);
|
|
694
|
+
const quillTree = this.#quillClones.get(this.#descriptorFor(backendId).load)?.has(quill)
|
|
695
|
+
? null
|
|
696
|
+
: quill.toTree();
|
|
697
|
+
const { mod, engine } = await this.#resolveBackend(backendId);
|
|
698
|
+
try {
|
|
699
|
+
return fn({ engine, quill: this.#cachedQuillClone(mod, backendId, quill, quillTree) });
|
|
700
|
+
} catch (err) {
|
|
701
|
+
throw backendTrap(err);
|
|
702
|
+
}
|
|
703
|
+
}
|
|
704
|
+
|
|
705
|
+
/**
|
|
706
|
+
* @param {Quill} quill
|
|
707
|
+
* @returns {Promise<import('./runtime.d.ts').FontFace[]>}
|
|
708
|
+
*/
|
|
709
|
+
async fontFaces(quill) {
|
|
710
|
+
return this.#withQuill('engine.fontFaces(quill)', quill, ({ engine, quill: q }) =>
|
|
711
|
+
typeof engine.fontFaces === 'function' ? engine.fontFaces(q) : []
|
|
712
|
+
);
|
|
713
|
+
}
|
|
714
|
+
|
|
661
715
|
/**
|
|
662
716
|
* @param {Quill} quill
|
|
663
717
|
* @returns {Promise<void>}
|