@laminapdf/wasm 0.2.0-alpha.3 → 0.2.0-alpha.4

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.
@@ -32,7 +32,7 @@ export interface ProgressJs {
32
32
  */
33
33
  total?: number;
34
34
  /**
35
- * The phase (`parse`, `layout`, `extract`, `render`, `write`, `sign`).
35
+ * The phase (`parse`, `layout`, `extract`, `render`, `write`, `sign`, `model`).
36
36
  */
37
37
  phase: string;
38
38
  }
@@ -891,7 +891,8 @@ export class WasmPageBuilder {
891
891
  [Symbol.dispose](): void;
892
892
  /**
893
893
  * Opens an artifact until the matching `endTag`: `kind` is `layout`, `page`, `pagination`
894
- * or `background`.
894
+ * or `background`, or a pagination artifact that says what it is: `header` (attached to the
895
+ * top edge), `footer` (the bottom) or `watermark`.
895
896
  *
896
897
  * # Errors
897
898
  * `invalid-argument` for another kind.
@@ -674,7 +674,8 @@ export class WasmPageBuilder {
674
674
  }
675
675
  /**
676
676
  * Opens an artifact until the matching `endTag`: `kind` is `layout`, `page`, `pagination`
677
- * or `background`.
677
+ * or `background`, or a pagination artifact that says what it is: `header` (attached to the
678
+ * top edge), `footer` (the bottom) or `watermark`.
678
679
  *
679
680
  * # Errors
680
681
  * `invalid-argument` for another kind.
Binary file
@@ -50,11 +50,35 @@ export interface ProgressJs {
50
50
  */
51
51
  total?: number;
52
52
  /**
53
- * The phase (`parse`, `layout`, `extract`, `render`, `write`, `sign`).
53
+ * The phase (`parse`, `layout`, `extract`, `render`, `write`, `sign`, `model`).
54
54
  */
55
55
  phase: string;
56
56
  }
57
57
 
58
+ /**
59
+ * A kid of a structure element: an element, or marked content on a page.
60
+ */
61
+ export type StructureKidJs = ({ type: "node" } & StructureNodeJs) | { type: "content"; page: number; mcid: number };
62
+
63
+ /**
64
+ * A layout region, its box `[x, y, width, height]` in top-left points (ADR 0027), as the
65
+ * output's boxes are.
66
+ */
67
+ export interface RegionInit {
68
+ /**
69
+ * What it is.
70
+ */
71
+ label: RegionLabelName;
72
+ /**
73
+ * `[x, y, width, height]`.
74
+ */
75
+ bbox: [number, number, number, number];
76
+ /**
77
+ * The model's confidence, 0 to 1.
78
+ */
79
+ score: number;
80
+ }
81
+
58
82
  /**
59
83
  * A list of ops with its schema version ([ADR 0006] §6): `{ "v": 1, "ops": [ … ] }`, used
60
84
  * for saved op logs, batch processing and sync messages. Unknown fields are rejected, and so
@@ -76,11 +100,114 @@ export interface OpLog {
76
100
  ops: Op[];
77
101
  }
78
102
 
103
+ /**
104
+ * A model result the job waits for.
105
+ */
106
+ export interface ModelRequestJs {
107
+ /**
108
+ * `layout` (regions) or `ocr` (words).
109
+ */
110
+ kind: string;
111
+ /**
112
+ * The 0-based page to render.
113
+ */
114
+ page: number;
115
+ /**
116
+ * The resolution to render it at.
117
+ */
118
+ dpi: number;
119
+ /**
120
+ * OCR's languages (BCP 47); empty for the engine's default.
121
+ */
122
+ langs: string[];
123
+ }
124
+
125
+ /**
126
+ * A model the host runs, as the output's `generator.models` names it.
127
+ */
128
+ export interface ModelInfoInit {
129
+ /**
130
+ * Its name.
131
+ */
132
+ name: string;
133
+ /**
134
+ * Its version or revision.
135
+ */
136
+ version: string;
137
+ /**
138
+ * Its weights' SHA-256, lowercase hex.
139
+ */
140
+ sha256: string;
141
+ /**
142
+ * Its weights' SPDX licence.
143
+ */
144
+ licence: string;
145
+ }
146
+
147
+ /**
148
+ * A page and how to show it.
149
+ */
150
+ export interface TargetJs {
151
+ /**
152
+ * The page's 0-based index.
153
+ */
154
+ page: number;
155
+ /**
156
+ * How to show it, in page space.
157
+ */
158
+ view: TargetViewJs;
159
+ }
160
+
79
161
  /**
80
162
  * A page-label numbering style.
81
163
  */
82
164
  export type LabelStyleInit = "decimal" | "upperRoman" | "lowerRoman" | "upperLetters" | "lowerLetters";
83
165
 
166
+ /**
167
+ * A region's kind.
168
+ */
169
+ export type RegionLabelName = "text" | "title" | "section-header" | "list-item" | "table" | "picture" | "caption" | "footnote" | "formula" | "page-header" | "page-footer" | "other";
170
+
171
+ /**
172
+ * A step's progress, and the model result the job waits for, if any.
173
+ */
174
+ export interface ExtractProgressJs {
175
+ /**
176
+ * Pages done.
177
+ */
178
+ done: number;
179
+ /**
180
+ * Pages asked for.
181
+ */
182
+ total?: number;
183
+ /**
184
+ * `extract`, or `model` while a request is open.
185
+ */
186
+ phase: string;
187
+ /**
188
+ * The result the job waits for: hand it to `provide`.
189
+ */
190
+ request?: ModelRequestJs;
191
+ }
192
+
193
+ /**
194
+ * An OCR word, its box as a region's.
195
+ */
196
+ export interface WordInit {
197
+ /**
198
+ * Its text.
199
+ */
200
+ text: string;
201
+ /**
202
+ * `[x, y, width, height]`.
203
+ */
204
+ bbox: [number, number, number, number];
205
+ /**
206
+ * The engine's confidence, 0 to 1.
207
+ */
208
+ confidence: number;
209
+ }
210
+
84
211
  /**
85
212
  * An attached file's options.
86
213
  */
@@ -181,6 +308,11 @@ export interface SetInfo {
181
308
  */
182
309
  export type FitInit = { type: "page" } | { type: "width"; top?: number } | { type: "height"; left?: number } | { type: "xyz"; left?: number; top?: number; zoom?: number } | { type: "rect"; x: number; y: number; width: number; height: number } | { type: "bounds" };
183
310
 
311
+ /**
312
+ * How a target shows its page, in page space; an unset coordinate is left out.
313
+ */
314
+ export type TargetViewJs = { kind: "at"; x?: number; y?: number; zoom?: number } | { kind: "fit" } | { kind: "fit-width"; y?: number } | { kind: "fit-height"; x?: number } | { kind: "fit-rect"; x0: number; y0: number; x1: number; y1: number };
315
+
184
316
  /**
185
317
  * How a viewer lays pages out.
186
318
  */
@@ -237,6 +369,32 @@ export interface ViewerPreferencesInit {
237
369
  */
238
370
  export type RenumberJs = "keep" | "compact";
239
371
 
372
+ /**
373
+ * One element of the structure tree (`laminapdf::StructureNode`; its strings are document text).
374
+ */
375
+ export interface StructureNodeJs {
376
+ /**
377
+ * Its standard structure type (`H1`, `P`, `LI`, `Figure` …), through the `/RoleMap`.
378
+ */
379
+ kind: string;
380
+ /**
381
+ * `/Alt`: alternate text.
382
+ */
383
+ alt?: string;
384
+ /**
385
+ * `/Lang`: the language of its content.
386
+ */
387
+ lang?: string;
388
+ /**
389
+ * `/ActualText`: the text its content stands for.
390
+ */
391
+ actualText?: string;
392
+ /**
393
+ * Its kids, in reading order.
394
+ */
395
+ kids: StructureKidJs[];
396
+ }
397
+
240
398
  /**
241
399
  * One outline item and its children.
242
400
  */
@@ -271,6 +429,28 @@ export interface OutlineEntryInit {
271
429
  italic?: boolean;
272
430
  }
273
431
 
432
+ /**
433
+ * One outline item.
434
+ */
435
+ export interface OutlineNodeJs {
436
+ /**
437
+ * Its title (document text).
438
+ */
439
+ title: string;
440
+ /**
441
+ * Whether it opens with its children shown.
442
+ */
443
+ open: boolean;
444
+ /**
445
+ * Where it goes, when its destination names a page of this document.
446
+ */
447
+ target?: TargetJs;
448
+ /**
449
+ * Its children, in order.
450
+ */
451
+ children: OutlineNodeJs[];
452
+ }
453
+
274
454
  /**
275
455
  * One page's facts (`laminapdf::PageInfo`).
276
456
  */
@@ -402,6 +582,10 @@ export interface ExtractInit {
402
582
  * How chunks are cut (`chunks`, and `json` to include them).
403
583
  */
404
584
  chunk?: ChunkInit;
585
+ /**
586
+ * Models the host runs (`extractJob` only): the job asks for their results.
587
+ */
588
+ models?: ModelsInit;
405
589
  }
406
590
 
407
591
  /**
@@ -609,6 +793,28 @@ export interface MetadataInit {
609
793
  */
610
794
  export type ModificationClass = "metadata" | "formFill" | "annotation" | "signature" | "pageStructure" | "content" | "document";
611
795
 
796
+ /**
797
+ * The models the host runs for an extraction job.
798
+ */
799
+ export interface ModelsInit {
800
+ /**
801
+ * A layout model: every page's regions are asked for.
802
+ */
803
+ layout?: ModelInfoInit;
804
+ /**
805
+ * An OCR engine: pages with no visible text are asked for.
806
+ */
807
+ ocr?: ModelInfoInit;
808
+ /**
809
+ * The resolution pages are asked for at; 150 by default.
810
+ */
811
+ dpi?: number;
812
+ /**
813
+ * OCR's languages (BCP 47).
814
+ */
815
+ langs?: string[];
816
+ }
817
+
612
818
  /**
613
819
  * The pages an edit touched.
614
820
  */
@@ -634,6 +840,11 @@ export type SaveModeJs = "auto" | "incremental" | "fullRewrite";
634
840
  */
635
841
  export type ExtractFormat = "markdown" | "json" | "text" | "chunks";
636
842
 
843
+ /**
844
+ * What `provide` takes.
845
+ */
846
+ export type ModelResultInit = { kind: "layout"; regions: RegionInit[] } | { kind: "ocr"; words: WordInit[] };
847
+
637
848
  /**
638
849
  * What a save wrote (`laminapdf::SaveReport`).
639
850
  */
@@ -873,6 +1084,16 @@ export class WasmDocument {
873
1084
  * error (nothing is applied).
874
1085
  */
875
1086
  apply(ops: Op[]): EditedJs;
1087
+ /**
1088
+ * An extraction stepped a page at a time, whose models the host runs: each step returns
1089
+ * its progress, with the result it waits for under `request` (render that page at `dpi`,
1090
+ * run the model, hand the result to `provide`), and once every page is done, the output in
1091
+ * `options.format` (the extract and text modules).
1092
+ *
1093
+ * # Errors
1094
+ * As `extract`, for the options and the pages asked for.
1095
+ */
1096
+ extractJob(options: ExtractInit): WasmExtractJob;
876
1097
  /**
877
1098
  * The document's text for retrieval and LLMs, as one string: Markdown, plain text, the
878
1099
  * `laminapdf.extract/1` JSON, or the chunks as a JSON array (the extract and text modules).
@@ -893,6 +1114,21 @@ export class WasmDocument {
893
1114
  * Reading errors.
894
1115
  */
895
1116
  info(): DocumentInfoJs;
1117
+ /**
1118
+ * Whether the document says it is tagged (`/MarkInfo /Marked true`; the extract and text modules).
1119
+ *
1120
+ * # Errors
1121
+ * Reading errors.
1122
+ */
1123
+ isTagged(): boolean;
1124
+ /**
1125
+ * The named destination `name`, or `undefined` when the document has none by that name or
1126
+ * it names no page here (the extract and text modules).
1127
+ *
1128
+ * # Errors
1129
+ * `data-pending` and the reading errors.
1130
+ */
1131
+ namedDestination(name: string): TargetJs | undefined;
896
1132
  /**
897
1133
  * Opens a document from its bytes.
898
1134
  *
@@ -910,6 +1146,14 @@ export class WasmDocument {
910
1146
  * As `openBytes`, and `data-pending`.
911
1147
  */
912
1148
  static openSource(source: WasmSparseSource, options: OpenOptionsInit | undefined): WasmDocument;
1149
+ /**
1150
+ * The outline's top-level items, each with its children; empty without an outline (the
1151
+ * extract and text modules).
1152
+ *
1153
+ * # Errors
1154
+ * `data-pending` and the reading errors.
1155
+ */
1156
+ outline(): OutlineNodeJs[];
913
1157
  /**
914
1158
  * A handle on the page with `id` (`p12.0`).
915
1159
  *
@@ -973,6 +1217,14 @@ export class WasmDocument {
973
1217
  * The save's errors (`would-invalidate-signatures`, `requires-rewrite`, …).
974
1218
  */
975
1219
  save(options: SaveOptionsInit | undefined): { bytes: Uint8Array<ArrayBuffer>; report: SaveReportJs };
1220
+ /**
1221
+ * The structure tree's top-level elements in reading order, or `undefined` without one (the
1222
+ * extract and text modules, beside `WasmPage.text`, whose runs it links by MCID).
1223
+ *
1224
+ * # Errors
1225
+ * Reading errors.
1226
+ */
1227
+ structureTree(): StructureNodeJs[] | undefined;
976
1228
  /**
977
1229
  * Undoes the newest transaction; `undefined` when there is nothing to undo.
978
1230
  *
@@ -986,6 +1238,38 @@ export class WasmDocument {
986
1238
  warnings(): WasmWarningCursor;
987
1239
  }
988
1240
 
1241
+ /**
1242
+ * An extraction in progress, from `WasmDocument.extractJob`; it holds its document weakly.
1243
+ */
1244
+ export class WasmExtractJob {
1245
+ private constructor();
1246
+ free(): void;
1247
+ [Symbol.dispose](): void;
1248
+ /**
1249
+ * Stops the job: its next step fails with `cancelled`.
1250
+ */
1251
+ cancel(): void;
1252
+ /**
1253
+ * Hands the job the result of its open request: `{ kind: "layout", regions }` or
1254
+ * `{ kind: "ocr", words }`, boxes as `[x, y, width, height]` in top-left points.
1255
+ *
1256
+ * # Errors
1257
+ * `model-result-unexpected` when nothing was asked for or `result` is the other kind;
1258
+ * `invalid-argument` / `unknown-option` for a malformed result.
1259
+ */
1260
+ provide(result: ModelResultInit): void;
1261
+ /**
1262
+ * Extracts up to `budget` pages: `{ state: "progress", done, total, phase, request? }` or
1263
+ * `{ state: "done", output }`, the output in the job's format. While `request` is set, a
1264
+ * step does nothing until `provide` answers it.
1265
+ *
1266
+ * # Errors
1267
+ * `cancelled`, `document-changed`, `job-finished`, `disposed` when the document is freed,
1268
+ * and the reading errors.
1269
+ */
1270
+ step(budget: number): ({ state: "progress" } & ExtractProgressJs) | { state: "done"; output: string };
1271
+ }
1272
+
989
1273
  /**
990
1274
  * An image to draw (decoded or passed through once, shared by every use).
991
1275
  */
@@ -1071,7 +1355,8 @@ export class WasmPageBuilder {
1071
1355
  [Symbol.dispose](): void;
1072
1356
  /**
1073
1357
  * Opens an artifact until the matching `endTag`: `kind` is `layout`, `page`, `pagination`
1074
- * or `background`.
1358
+ * or `background`, or a pagination artifact that says what it is: `header` (attached to the
1359
+ * top edge), `footer` (the bottom) or `watermark`.
1075
1360
  *
1076
1361
  * # Errors
1077
1362
  * `invalid-argument` for another kind.
@@ -1340,6 +1625,7 @@ export interface InitOutput {
1340
1625
  readonly memory: WebAssembly.Memory;
1341
1626
  readonly __wbg_wasmbuilder_free: (a: number, b: number) => void;
1342
1627
  readonly __wbg_wasmdocument_free: (a: number, b: number) => void;
1628
+ readonly __wbg_wasmextractjob_free: (a: number, b: number) => void;
1343
1629
  readonly __wbg_wasmimage_free: (a: number, b: number) => void;
1344
1630
  readonly __wbg_wasmpage_free: (a: number, b: number) => void;
1345
1631
  readonly __wbg_wasmpagebuilder_free: (a: number, b: number) => void;
@@ -1362,10 +1648,14 @@ export interface InitOutput {
1362
1648
  readonly wasmdocument_apply: (a: number, b: any) => [number, number, number];
1363
1649
  readonly wasmdocument_applyLog: (a: number, b: number, c: number) => [number, number, number];
1364
1650
  readonly wasmdocument_extract: (a: number, b: any) => [number, number, number, number];
1651
+ readonly wasmdocument_extractJob: (a: number, b: any) => [number, number, number];
1365
1652
  readonly wasmdocument_hasUnsavedChanges: (a: number) => number;
1366
1653
  readonly wasmdocument_info: (a: number) => [number, number, number];
1654
+ readonly wasmdocument_isTagged: (a: number) => [number, number, number];
1655
+ readonly wasmdocument_namedDestination: (a: number, b: number, c: number) => [number, number, number];
1367
1656
  readonly wasmdocument_openBytes: (a: number, b: number, c: any) => [number, number, number];
1368
1657
  readonly wasmdocument_openSource: (a: number, b: any) => [number, number, number];
1658
+ readonly wasmdocument_outline: (a: number) => [number, number, number];
1369
1659
  readonly wasmdocument_page: (a: number, b: number) => [number, number, number];
1370
1660
  readonly wasmdocument_pageById: (a: number, b: number, c: number) => [number, number, number];
1371
1661
  readonly wasmdocument_pageCount: (a: number) => [number, number, number];
@@ -1375,8 +1665,12 @@ export interface InitOutput {
1375
1665
  readonly wasmdocument_redo: (a: number) => [number, number, number];
1376
1666
  readonly wasmdocument_save: (a: number, b: any) => [number, number, number];
1377
1667
  readonly wasmdocument_saveJob: (a: number, b: any) => [number, number, number];
1668
+ readonly wasmdocument_structureTree: (a: number) => [number, number, number];
1378
1669
  readonly wasmdocument_undo: (a: number) => [number, number, number];
1379
1670
  readonly wasmdocument_warnings: (a: number) => number;
1671
+ readonly wasmextractjob_cancel: (a: number) => void;
1672
+ readonly wasmextractjob_provide: (a: number, b: any) => [number, number];
1673
+ readonly wasmextractjob_step: (a: number, b: number) => [number, number, number];
1380
1674
  readonly wasmimage_height: (a: number) => number;
1381
1675
  readonly wasmimage_jpeg: (a: number, b: number) => [number, number, number];
1382
1676
  readonly wasmimage_png: (a: number, b: number) => [number, number, number];
@@ -240,6 +240,25 @@ export class WasmDocument {
240
240
  }
241
241
  return takeFromExternrefTable0(ret[0]);
242
242
  }
243
+ /**
244
+ * An extraction stepped a page at a time, whose models the host runs: each step returns
245
+ * its progress, with the result it waits for under `request` (render that page at `dpi`,
246
+ * run the model, hand the result to `provide`), and once every page is done, the output in
247
+ * `options.format` (the extract and text modules).
248
+ *
249
+ * # Errors
250
+ * As `extract`, for the options and the pages asked for.
251
+ * @param {ExtractInit} options
252
+ * @returns {WasmExtractJob}
253
+ */
254
+ extractJob(options) {
255
+ let ret;
256
+ ret = wasm.wasmdocument_extractJob(this.__wbg_ptr, options);
257
+ if (ret[2]) {
258
+ throw takeFromExternrefTable0(ret[1]);
259
+ }
260
+ return WasmExtractJob.__wrap(ret[0]);
261
+ }
243
262
  /**
244
263
  * The document's text for retrieval and LLMs, as one string: Markdown, plain text, the
245
264
  * `laminapdf.extract/1` JSON, or the chunks as a JSON array (the extract and text modules).
@@ -293,6 +312,40 @@ export class WasmDocument {
293
312
  }
294
313
  return takeFromExternrefTable0(ret[0]);
295
314
  }
315
+ /**
316
+ * Whether the document says it is tagged (`/MarkInfo /Marked true`; the extract and text modules).
317
+ *
318
+ * # Errors
319
+ * Reading errors.
320
+ * @returns {boolean}
321
+ */
322
+ isTagged() {
323
+ let ret;
324
+ ret = wasm.wasmdocument_isTagged(this.__wbg_ptr);
325
+ if (ret[2]) {
326
+ throw takeFromExternrefTable0(ret[1]);
327
+ }
328
+ return ret[0] !== 0;
329
+ }
330
+ /**
331
+ * The named destination `name`, or `undefined` when the document has none by that name or
332
+ * it names no page here (the extract and text modules).
333
+ *
334
+ * # Errors
335
+ * `data-pending` and the reading errors.
336
+ * @param {string} name
337
+ * @returns {TargetJs | undefined}
338
+ */
339
+ namedDestination(name) {
340
+ const ptr0 = passStringToWasm0(name, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
341
+ const len0 = WASM_VECTOR_LEN;
342
+ let ret;
343
+ ret = wasm.wasmdocument_namedDestination(this.__wbg_ptr, ptr0, len0);
344
+ if (ret[2]) {
345
+ throw takeFromExternrefTable0(ret[1]);
346
+ }
347
+ return takeFromExternrefTable0(ret[0]);
348
+ }
296
349
  /**
297
350
  * Opens a document from its bytes.
298
351
  *
@@ -333,6 +386,22 @@ export class WasmDocument {
333
386
  }
334
387
  return WasmDocument.__wrap(ret[0]);
335
388
  }
389
+ /**
390
+ * The outline's top-level items, each with its children; empty without an outline (the
391
+ * extract and text modules).
392
+ *
393
+ * # Errors
394
+ * `data-pending` and the reading errors.
395
+ * @returns {OutlineNodeJs[]}
396
+ */
397
+ outline() {
398
+ let ret;
399
+ ret = wasm.wasmdocument_outline(this.__wbg_ptr);
400
+ if (ret[2]) {
401
+ throw takeFromExternrefTable0(ret[1]);
402
+ }
403
+ return takeFromExternrefTable0(ret[0]);
404
+ }
336
405
  /**
337
406
  * A handle on the page with `id` (`p12.0`).
338
407
  *
@@ -476,6 +545,22 @@ export class WasmDocument {
476
545
  }
477
546
  return takeFromExternrefTable0(ret[0]);
478
547
  }
548
+ /**
549
+ * The structure tree's top-level elements in reading order, or `undefined` without one (the
550
+ * extract and text modules, beside `WasmPage.text`, whose runs it links by MCID).
551
+ *
552
+ * # Errors
553
+ * Reading errors.
554
+ * @returns {StructureNodeJs[] | undefined}
555
+ */
556
+ structureTree() {
557
+ let ret;
558
+ ret = wasm.wasmdocument_structureTree(this.__wbg_ptr);
559
+ if (ret[2]) {
560
+ throw takeFromExternrefTable0(ret[1]);
561
+ }
562
+ return takeFromExternrefTable0(ret[0]);
563
+ }
479
564
  /**
480
565
  * Undoes the newest transaction; `undefined` when there is nothing to undo.
481
566
  *
@@ -503,6 +588,73 @@ export class WasmDocument {
503
588
  }
504
589
  if (Symbol.dispose) WasmDocument.prototype[Symbol.dispose] = WasmDocument.prototype.free;
505
590
 
591
+ /**
592
+ * An extraction in progress, from `WasmDocument.extractJob`; it holds its document weakly.
593
+ */
594
+ export class WasmExtractJob {
595
+ static __wrap(ptr) {
596
+ const obj = Object.create(WasmExtractJob.prototype);
597
+ obj.__wbg_ptr = ptr;
598
+ Object.defineProperty(obj, '__wbg_inst', { value: __wbg_instance_id, writable: true });
599
+
600
+ WasmExtractJobFinalization.register(obj, { ptr, instance: __wbg_instance_id }, obj);
601
+ return obj;
602
+ }
603
+ __destroy_into_raw() {
604
+ const ptr = this.__wbg_ptr;
605
+ this.__wbg_ptr = 0;
606
+ WasmExtractJobFinalization.unregister(this);
607
+ return ptr;
608
+ }
609
+ free() {
610
+ const ptr = this.__destroy_into_raw();
611
+ wasm.__wbg_wasmextractjob_free(ptr, 0);
612
+
613
+ }
614
+ /**
615
+ * Stops the job: its next step fails with `cancelled`.
616
+ */
617
+ cancel() {
618
+ wasm.wasmextractjob_cancel(this.__wbg_ptr);
619
+ }
620
+ /**
621
+ * Hands the job the result of its open request: `{ kind: "layout", regions }` or
622
+ * `{ kind: "ocr", words }`, boxes as `[x, y, width, height]` in top-left points.
623
+ *
624
+ * # Errors
625
+ * `model-result-unexpected` when nothing was asked for or `result` is the other kind;
626
+ * `invalid-argument` / `unknown-option` for a malformed result.
627
+ * @param {ModelResultInit} result
628
+ */
629
+ provide(result) {
630
+ let ret;
631
+ ret = wasm.wasmextractjob_provide(this.__wbg_ptr, result);
632
+ if (ret[1]) {
633
+ throw takeFromExternrefTable0(ret[0]);
634
+ }
635
+ }
636
+ /**
637
+ * Extracts up to `budget` pages: `{ state: "progress", done, total, phase, request? }` or
638
+ * `{ state: "done", output }`, the output in the job's format. While `request` is set, a
639
+ * step does nothing until `provide` answers it.
640
+ *
641
+ * # Errors
642
+ * `cancelled`, `document-changed`, `job-finished`, `disposed` when the document is freed,
643
+ * and the reading errors.
644
+ * @param {number} budget
645
+ * @returns {({ state: "progress" } & ExtractProgressJs) | { state: "done"; output: string }}
646
+ */
647
+ step(budget) {
648
+ let ret;
649
+ ret = wasm.wasmextractjob_step(this.__wbg_ptr, budget);
650
+ if (ret[2]) {
651
+ throw takeFromExternrefTable0(ret[1]);
652
+ }
653
+ return takeFromExternrefTable0(ret[0]);
654
+ }
655
+ }
656
+ if (Symbol.dispose) WasmExtractJob.prototype[Symbol.dispose] = WasmExtractJob.prototype.free;
657
+
506
658
  /**
507
659
  * An image to draw (decoded or passed through once, shared by every use).
508
660
  */
@@ -721,7 +873,8 @@ export class WasmPageBuilder {
721
873
  }
722
874
  /**
723
875
  * Opens an artifact until the matching `endTag`: `kind` is `layout`, `page`, `pagination`
724
- * or `background`.
876
+ * or `background`, or a pagination artifact that says what it is: `header` (attached to the
877
+ * top edge), `footer` (the bottom) or `watermark`.
725
878
  *
726
879
  * # Errors
727
880
  * `invalid-argument` for another kind.
@@ -1488,6 +1641,11 @@ const WasmDocumentFinalization = (typeof FinalizationRegistry === 'undefined')
1488
1641
  : new FinalizationRegistry(({ ptr, instance }) => {
1489
1642
  if (instance === __wbg_instance_id) wasm.__wbg_wasmdocument_free(ptr, 1);
1490
1643
  });
1644
+ const WasmExtractJobFinalization = (typeof FinalizationRegistry === 'undefined')
1645
+ ? { register: () => {}, unregister: () => {} }
1646
+ : new FinalizationRegistry(({ ptr, instance }) => {
1647
+ if (instance === __wbg_instance_id) wasm.__wbg_wasmextractjob_free(ptr, 1);
1648
+ });
1491
1649
  const WasmImageFinalization = (typeof FinalizationRegistry === 'undefined')
1492
1650
  ? { register: () => {}, unregister: () => {} }
1493
1651
  : new FinalizationRegistry(({ ptr, instance }) => {
Binary file
Binary file
@@ -55,11 +55,35 @@ export interface ProgressJs {
55
55
  */
56
56
  total?: number;
57
57
  /**
58
- * The phase (`parse`, `layout`, `extract`, `render`, `write`, `sign`).
58
+ * The phase (`parse`, `layout`, `extract`, `render`, `write`, `sign`, `model`).
59
59
  */
60
60
  phase: string;
61
61
  }
62
62
 
63
+ /**
64
+ * A kid of a structure element: an element, or marked content on a page.
65
+ */
66
+ export type StructureKidJs = ({ type: "node" } & StructureNodeJs) | { type: "content"; page: number; mcid: number };
67
+
68
+ /**
69
+ * A layout region, its box `[x, y, width, height]` in top-left points (ADR 0027), as the
70
+ * output's boxes are.
71
+ */
72
+ export interface RegionInit {
73
+ /**
74
+ * What it is.
75
+ */
76
+ label: RegionLabelName;
77
+ /**
78
+ * `[x, y, width, height]`.
79
+ */
80
+ bbox: [number, number, number, number];
81
+ /**
82
+ * The model's confidence, 0 to 1.
83
+ */
84
+ score: number;
85
+ }
86
+
63
87
  /**
64
88
  * A link over drawn text.
65
89
  */
@@ -95,6 +119,64 @@ export interface OpLog {
95
119
  ops: Op[];
96
120
  }
97
121
 
122
+ /**
123
+ * A model result the job waits for.
124
+ */
125
+ export interface ModelRequestJs {
126
+ /**
127
+ * `layout` (regions) or `ocr` (words).
128
+ */
129
+ kind: string;
130
+ /**
131
+ * The 0-based page to render.
132
+ */
133
+ page: number;
134
+ /**
135
+ * The resolution to render it at.
136
+ */
137
+ dpi: number;
138
+ /**
139
+ * OCR's languages (BCP 47); empty for the engine's default.
140
+ */
141
+ langs: string[];
142
+ }
143
+
144
+ /**
145
+ * A model the host runs, as the output's `generator.models` names it.
146
+ */
147
+ export interface ModelInfoInit {
148
+ /**
149
+ * Its name.
150
+ */
151
+ name: string;
152
+ /**
153
+ * Its version or revision.
154
+ */
155
+ version: string;
156
+ /**
157
+ * Its weights' SHA-256, lowercase hex.
158
+ */
159
+ sha256: string;
160
+ /**
161
+ * Its weights' SPDX licence.
162
+ */
163
+ licence: string;
164
+ }
165
+
166
+ /**
167
+ * A page and how to show it.
168
+ */
169
+ export interface TargetJs {
170
+ /**
171
+ * The page's 0-based index.
172
+ */
173
+ page: number;
174
+ /**
175
+ * How to show it, in page space.
176
+ */
177
+ view: TargetViewJs;
178
+ }
179
+
98
180
  /**
99
181
  * A page-label numbering style.
100
182
  */
@@ -122,11 +204,56 @@ export interface RectJs {
122
204
  height: number;
123
205
  }
124
206
 
207
+ /**
208
+ * A region's kind.
209
+ */
210
+ export type RegionLabelName = "text" | "title" | "section-header" | "list-item" | "table" | "picture" | "caption" | "footnote" | "formula" | "page-header" | "page-footer" | "other";
211
+
212
+ /**
213
+ * A step's progress, and the model result the job waits for, if any.
214
+ */
215
+ export interface ExtractProgressJs {
216
+ /**
217
+ * Pages done.
218
+ */
219
+ done: number;
220
+ /**
221
+ * Pages asked for.
222
+ */
223
+ total?: number;
224
+ /**
225
+ * `extract`, or `model` while a request is open.
226
+ */
227
+ phase: string;
228
+ /**
229
+ * The result the job waits for: hand it to `provide`.
230
+ */
231
+ request?: ModelRequestJs;
232
+ }
233
+
125
234
  /**
126
235
  * Alignment of a text box's lines.
127
236
  */
128
237
  export type AlignInit = "start" | "end" | "left" | "right" | "center";
129
238
 
239
+ /**
240
+ * An OCR word, its box as a region's.
241
+ */
242
+ export interface WordInit {
243
+ /**
244
+ * Its text.
245
+ */
246
+ text: string;
247
+ /**
248
+ * `[x, y, width, height]`.
249
+ */
250
+ bbox: [number, number, number, number];
251
+ /**
252
+ * The engine's confidence, 0 to 1.
253
+ */
254
+ confidence: number;
255
+ }
256
+
130
257
  /**
131
258
  * An attached file's options.
132
259
  */
@@ -257,6 +384,11 @@ export interface TextOptionsInit {
257
384
  direction?: DirectionInit;
258
385
  }
259
386
 
387
+ /**
388
+ * How a target shows its page, in page space; an unset coordinate is left out.
389
+ */
390
+ export type TargetViewJs = { kind: "at"; x?: number; y?: number; zoom?: number } | { kind: "fit" } | { kind: "fit-width"; y?: number } | { kind: "fit-height"; x?: number } | { kind: "fit-rect"; x0: number; y0: number; x1: number; y1: number };
391
+
260
392
  /**
261
393
  * How a text box laid its text out.
262
394
  */
@@ -266,9 +398,15 @@ export interface TextLayoutJs {
266
398
  */
267
399
  lines: LineBoxJs[];
268
400
  /**
269
- * Where the text that didn't fit starts (UTF-16 offset), if any.
401
+ * Where the text that didn't fit starts (UTF-16 offset), if any; `0` when no line fitted.
270
402
  */
271
403
  overflow?: number;
404
+ /**
405
+ * Where the next element can start: the bottom of the last drawn line that draws
406
+ * something, before the surface's transform. Left out when no line does (nothing, only
407
+ * white space and control characters, or a box too short).
408
+ */
409
+ bottom?: number;
272
410
  }
273
411
 
274
412
  /**
@@ -354,6 +492,32 @@ export interface LineBoxJs {
354
492
  baseline: number;
355
493
  }
356
494
 
495
+ /**
496
+ * One element of the structure tree (`laminapdf::StructureNode`; its strings are document text).
497
+ */
498
+ export interface StructureNodeJs {
499
+ /**
500
+ * Its standard structure type (`H1`, `P`, `LI`, `Figure` …), through the `/RoleMap`.
501
+ */
502
+ kind: string;
503
+ /**
504
+ * `/Alt`: alternate text.
505
+ */
506
+ alt?: string;
507
+ /**
508
+ * `/Lang`: the language of its content.
509
+ */
510
+ lang?: string;
511
+ /**
512
+ * `/ActualText`: the text its content stands for.
513
+ */
514
+ actualText?: string;
515
+ /**
516
+ * Its kids, in reading order.
517
+ */
518
+ kids: StructureKidJs[];
519
+ }
520
+
357
521
  /**
358
522
  * One outline item and its children.
359
523
  */
@@ -388,6 +552,28 @@ export interface OutlineEntryInit {
388
552
  italic?: boolean;
389
553
  }
390
554
 
555
+ /**
556
+ * One outline item.
557
+ */
558
+ export interface OutlineNodeJs {
559
+ /**
560
+ * Its title (document text).
561
+ */
562
+ title: string;
563
+ /**
564
+ * Whether it opens with its children shown.
565
+ */
566
+ open: boolean;
567
+ /**
568
+ * Where it goes, when its destination names a page of this document.
569
+ */
570
+ target?: TargetJs;
571
+ /**
572
+ * Its children, in order.
573
+ */
574
+ children: OutlineNodeJs[];
575
+ }
576
+
391
577
  /**
392
578
  * One page's facts (`laminapdf::PageInfo`).
393
579
  */
@@ -519,6 +705,10 @@ export interface ExtractInit {
519
705
  * How chunks are cut (`chunks`, and `json` to include them).
520
706
  */
521
707
  chunk?: ChunkInit;
708
+ /**
709
+ * Models the host runs (`extractJob` only): the job asks for their results.
710
+ */
711
+ models?: ModelsInit;
522
712
  }
523
713
 
524
714
  /**
@@ -766,6 +956,28 @@ export interface MetadataInit {
766
956
  */
767
957
  export type ModificationClass = "metadata" | "formFill" | "annotation" | "signature" | "pageStructure" | "content" | "document";
768
958
 
959
+ /**
960
+ * The models the host runs for an extraction job.
961
+ */
962
+ export interface ModelsInit {
963
+ /**
964
+ * A layout model: every page's regions are asked for.
965
+ */
966
+ layout?: ModelInfoInit;
967
+ /**
968
+ * An OCR engine: pages with no visible text are asked for.
969
+ */
970
+ ocr?: ModelInfoInit;
971
+ /**
972
+ * The resolution pages are asked for at; 150 by default.
973
+ */
974
+ dpi?: number;
975
+ /**
976
+ * OCR's languages (BCP 47).
977
+ */
978
+ langs?: string[];
979
+ }
980
+
769
981
  /**
770
982
  * The pages an edit touched.
771
983
  */
@@ -791,6 +1003,11 @@ export type SaveModeJs = "auto" | "incremental" | "fullRewrite";
791
1003
  */
792
1004
  export type ExtractFormat = "markdown" | "json" | "text" | "chunks";
793
1005
 
1006
+ /**
1007
+ * What `provide` takes.
1008
+ */
1009
+ export type ModelResultInit = { kind: "layout"; regions: RegionInit[] } | { kind: "ocr"; words: WordInit[] };
1010
+
794
1011
  /**
795
1012
  * What a run measures.
796
1013
  */
@@ -807,6 +1024,12 @@ export interface TextRunJs {
807
1024
  * Its lines (a run breaks only at line breaks in the text).
808
1025
  */
809
1026
  lines: number;
1027
+ /**
1028
+ * Where the next element can start: the bottom of the descent below its last line that
1029
+ * draws something, before the surface's transform. Left out when nothing is drawn (empty
1030
+ * text, or only white space and control characters); invisible text counts.
1031
+ */
1032
+ bottom?: number;
810
1033
  }
811
1034
 
812
1035
  /**
@@ -1069,6 +1292,16 @@ export class WasmDocument {
1069
1292
  * error (nothing is applied).
1070
1293
  */
1071
1294
  apply(ops: Op[]): EditedJs;
1295
+ /**
1296
+ * An extraction stepped a page at a time, whose models the host runs: each step returns
1297
+ * its progress, with the result it waits for under `request` (render that page at `dpi`,
1298
+ * run the model, hand the result to `provide`), and once every page is done, the output in
1299
+ * `options.format` (the extract and text modules).
1300
+ *
1301
+ * # Errors
1302
+ * As `extract`, for the options and the pages asked for.
1303
+ */
1304
+ extractJob(options: ExtractInit): WasmExtractJob;
1072
1305
  /**
1073
1306
  * The document's text for retrieval and LLMs, as one string: Markdown, plain text, the
1074
1307
  * `laminapdf.extract/1` JSON, or the chunks as a JSON array (the extract and text modules).
@@ -1089,6 +1322,21 @@ export class WasmDocument {
1089
1322
  * Reading errors.
1090
1323
  */
1091
1324
  info(): DocumentInfoJs;
1325
+ /**
1326
+ * Whether the document says it is tagged (`/MarkInfo /Marked true`; the extract and text modules).
1327
+ *
1328
+ * # Errors
1329
+ * Reading errors.
1330
+ */
1331
+ isTagged(): boolean;
1332
+ /**
1333
+ * The named destination `name`, or `undefined` when the document has none by that name or
1334
+ * it names no page here (the extract and text modules).
1335
+ *
1336
+ * # Errors
1337
+ * `data-pending` and the reading errors.
1338
+ */
1339
+ namedDestination(name: string): TargetJs | undefined;
1092
1340
  /**
1093
1341
  * Opens a document from its bytes.
1094
1342
  *
@@ -1106,6 +1354,14 @@ export class WasmDocument {
1106
1354
  * As `openBytes`, and `data-pending`.
1107
1355
  */
1108
1356
  static openSource(source: WasmSparseSource, options: OpenOptionsInit | undefined): WasmDocument;
1357
+ /**
1358
+ * The outline's top-level items, each with its children; empty without an outline (the
1359
+ * extract and text modules).
1360
+ *
1361
+ * # Errors
1362
+ * `data-pending` and the reading errors.
1363
+ */
1364
+ outline(): OutlineNodeJs[];
1109
1365
  /**
1110
1366
  * A handle on the page with `id` (`p12.0`).
1111
1367
  *
@@ -1169,6 +1425,14 @@ export class WasmDocument {
1169
1425
  * The save's errors (`would-invalidate-signatures`, `requires-rewrite`, …).
1170
1426
  */
1171
1427
  save(options: SaveOptionsInit | undefined): { bytes: Uint8Array<ArrayBuffer>; report: SaveReportJs };
1428
+ /**
1429
+ * The structure tree's top-level elements in reading order, or `undefined` without one (the
1430
+ * extract and text modules, beside `WasmPage.text`, whose runs it links by MCID).
1431
+ *
1432
+ * # Errors
1433
+ * Reading errors.
1434
+ */
1435
+ structureTree(): StructureNodeJs[] | undefined;
1172
1436
  /**
1173
1437
  * Undoes the newest transaction; `undefined` when there is nothing to undo.
1174
1438
  *
@@ -1182,6 +1446,38 @@ export class WasmDocument {
1182
1446
  warnings(): WasmWarningCursor;
1183
1447
  }
1184
1448
 
1449
+ /**
1450
+ * An extraction in progress, from `WasmDocument.extractJob`; it holds its document weakly.
1451
+ */
1452
+ export class WasmExtractJob {
1453
+ private constructor();
1454
+ free(): void;
1455
+ [Symbol.dispose](): void;
1456
+ /**
1457
+ * Stops the job: its next step fails with `cancelled`.
1458
+ */
1459
+ cancel(): void;
1460
+ /**
1461
+ * Hands the job the result of its open request: `{ kind: "layout", regions }` or
1462
+ * `{ kind: "ocr", words }`, boxes as `[x, y, width, height]` in top-left points.
1463
+ *
1464
+ * # Errors
1465
+ * `model-result-unexpected` when nothing was asked for or `result` is the other kind;
1466
+ * `invalid-argument` / `unknown-option` for a malformed result.
1467
+ */
1468
+ provide(result: ModelResultInit): void;
1469
+ /**
1470
+ * Extracts up to `budget` pages: `{ state: "progress", done, total, phase, request? }` or
1471
+ * `{ state: "done", output }`, the output in the job's format. While `request` is set, a
1472
+ * step does nothing until `provide` answers it.
1473
+ *
1474
+ * # Errors
1475
+ * `cancelled`, `document-changed`, `job-finished`, `disposed` when the document is freed,
1476
+ * and the reading errors.
1477
+ */
1478
+ step(budget: number): ({ state: "progress" } & ExtractProgressJs) | { state: "done"; output: string };
1479
+ }
1480
+
1185
1481
  /**
1186
1482
  * A font registered with a [`WasmBuilder`].
1187
1483
  */
@@ -1288,7 +1584,8 @@ export class WasmPageBuilder {
1288
1584
  [Symbol.dispose](): void;
1289
1585
  /**
1290
1586
  * Opens an artifact until the matching `endTag`: `kind` is `layout`, `page`, `pagination`
1291
- * or `background`.
1587
+ * or `background`, or a pagination artifact that says what it is: `header` (attached to the
1588
+ * top edge), `footer` (the bottom) or `watermark`.
1292
1589
  *
1293
1590
  * # Errors
1294
1591
  * `invalid-argument` for another kind.
@@ -1574,6 +1871,7 @@ export interface InitOutput {
1574
1871
  readonly memory: WebAssembly.Memory;
1575
1872
  readonly __wbg_wasmbuilder_free: (a: number, b: number) => void;
1576
1873
  readonly __wbg_wasmdocument_free: (a: number, b: number) => void;
1874
+ readonly __wbg_wasmextractjob_free: (a: number, b: number) => void;
1577
1875
  readonly __wbg_wasmfont_free: (a: number, b: number) => void;
1578
1876
  readonly __wbg_wasmimage_free: (a: number, b: number) => void;
1579
1877
  readonly __wbg_wasmpage_free: (a: number, b: number) => void;
@@ -1599,10 +1897,14 @@ export interface InitOutput {
1599
1897
  readonly wasmdocument_apply: (a: number, b: any) => [number, number, number];
1600
1898
  readonly wasmdocument_applyLog: (a: number, b: number, c: number) => [number, number, number];
1601
1899
  readonly wasmdocument_extract: (a: number, b: any) => [number, number, number, number];
1900
+ readonly wasmdocument_extractJob: (a: number, b: any) => [number, number, number];
1602
1901
  readonly wasmdocument_hasUnsavedChanges: (a: number) => number;
1603
1902
  readonly wasmdocument_info: (a: number) => [number, number, number];
1903
+ readonly wasmdocument_isTagged: (a: number) => [number, number, number];
1904
+ readonly wasmdocument_namedDestination: (a: number, b: number, c: number) => [number, number, number];
1604
1905
  readonly wasmdocument_openBytes: (a: number, b: number, c: any) => [number, number, number];
1605
1906
  readonly wasmdocument_openSource: (a: number, b: any) => [number, number, number];
1907
+ readonly wasmdocument_outline: (a: number) => [number, number, number];
1606
1908
  readonly wasmdocument_page: (a: number, b: number) => [number, number, number];
1607
1909
  readonly wasmdocument_pageById: (a: number, b: number, c: number) => [number, number, number];
1608
1910
  readonly wasmdocument_pageCount: (a: number) => [number, number, number];
@@ -1612,8 +1914,12 @@ export interface InitOutput {
1612
1914
  readonly wasmdocument_redo: (a: number) => [number, number, number];
1613
1915
  readonly wasmdocument_save: (a: number, b: any) => [number, number, number];
1614
1916
  readonly wasmdocument_saveJob: (a: number, b: any) => [number, number, number];
1917
+ readonly wasmdocument_structureTree: (a: number) => [number, number, number];
1615
1918
  readonly wasmdocument_undo: (a: number) => [number, number, number];
1616
1919
  readonly wasmdocument_warnings: (a: number) => number;
1920
+ readonly wasmextractjob_cancel: (a: number) => void;
1921
+ readonly wasmextractjob_provide: (a: number, b: any) => [number, number];
1922
+ readonly wasmextractjob_step: (a: number, b: number) => [number, number, number];
1617
1923
  readonly wasmfont_family: (a: number) => [number, number];
1618
1924
  readonly wasmfont_isStandard: (a: number) => number;
1619
1925
  readonly wasmfont_postscriptName: (a: number) => [number, number];
@@ -278,6 +278,25 @@ export class WasmDocument {
278
278
  }
279
279
  return takeFromExternrefTable0(ret[0]);
280
280
  }
281
+ /**
282
+ * An extraction stepped a page at a time, whose models the host runs: each step returns
283
+ * its progress, with the result it waits for under `request` (render that page at `dpi`,
284
+ * run the model, hand the result to `provide`), and once every page is done, the output in
285
+ * `options.format` (the extract and text modules).
286
+ *
287
+ * # Errors
288
+ * As `extract`, for the options and the pages asked for.
289
+ * @param {ExtractInit} options
290
+ * @returns {WasmExtractJob}
291
+ */
292
+ extractJob(options) {
293
+ let ret;
294
+ ret = wasm.wasmdocument_extractJob(this.__wbg_ptr, options);
295
+ if (ret[2]) {
296
+ throw takeFromExternrefTable0(ret[1]);
297
+ }
298
+ return WasmExtractJob.__wrap(ret[0]);
299
+ }
281
300
  /**
282
301
  * The document's text for retrieval and LLMs, as one string: Markdown, plain text, the
283
302
  * `laminapdf.extract/1` JSON, or the chunks as a JSON array (the extract and text modules).
@@ -331,6 +350,40 @@ export class WasmDocument {
331
350
  }
332
351
  return takeFromExternrefTable0(ret[0]);
333
352
  }
353
+ /**
354
+ * Whether the document says it is tagged (`/MarkInfo /Marked true`; the extract and text modules).
355
+ *
356
+ * # Errors
357
+ * Reading errors.
358
+ * @returns {boolean}
359
+ */
360
+ isTagged() {
361
+ let ret;
362
+ ret = wasm.wasmdocument_isTagged(this.__wbg_ptr);
363
+ if (ret[2]) {
364
+ throw takeFromExternrefTable0(ret[1]);
365
+ }
366
+ return ret[0] !== 0;
367
+ }
368
+ /**
369
+ * The named destination `name`, or `undefined` when the document has none by that name or
370
+ * it names no page here (the extract and text modules).
371
+ *
372
+ * # Errors
373
+ * `data-pending` and the reading errors.
374
+ * @param {string} name
375
+ * @returns {TargetJs | undefined}
376
+ */
377
+ namedDestination(name) {
378
+ const ptr0 = passStringToWasm0(name, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
379
+ const len0 = WASM_VECTOR_LEN;
380
+ let ret;
381
+ ret = wasm.wasmdocument_namedDestination(this.__wbg_ptr, ptr0, len0);
382
+ if (ret[2]) {
383
+ throw takeFromExternrefTable0(ret[1]);
384
+ }
385
+ return takeFromExternrefTable0(ret[0]);
386
+ }
334
387
  /**
335
388
  * Opens a document from its bytes.
336
389
  *
@@ -371,6 +424,22 @@ export class WasmDocument {
371
424
  }
372
425
  return WasmDocument.__wrap(ret[0]);
373
426
  }
427
+ /**
428
+ * The outline's top-level items, each with its children; empty without an outline (the
429
+ * extract and text modules).
430
+ *
431
+ * # Errors
432
+ * `data-pending` and the reading errors.
433
+ * @returns {OutlineNodeJs[]}
434
+ */
435
+ outline() {
436
+ let ret;
437
+ ret = wasm.wasmdocument_outline(this.__wbg_ptr);
438
+ if (ret[2]) {
439
+ throw takeFromExternrefTable0(ret[1]);
440
+ }
441
+ return takeFromExternrefTable0(ret[0]);
442
+ }
374
443
  /**
375
444
  * A handle on the page with `id` (`p12.0`).
376
445
  *
@@ -514,6 +583,22 @@ export class WasmDocument {
514
583
  }
515
584
  return takeFromExternrefTable0(ret[0]);
516
585
  }
586
+ /**
587
+ * The structure tree's top-level elements in reading order, or `undefined` without one (the
588
+ * extract and text modules, beside `WasmPage.text`, whose runs it links by MCID).
589
+ *
590
+ * # Errors
591
+ * Reading errors.
592
+ * @returns {StructureNodeJs[] | undefined}
593
+ */
594
+ structureTree() {
595
+ let ret;
596
+ ret = wasm.wasmdocument_structureTree(this.__wbg_ptr);
597
+ if (ret[2]) {
598
+ throw takeFromExternrefTable0(ret[1]);
599
+ }
600
+ return takeFromExternrefTable0(ret[0]);
601
+ }
517
602
  /**
518
603
  * Undoes the newest transaction; `undefined` when there is nothing to undo.
519
604
  *
@@ -541,6 +626,73 @@ export class WasmDocument {
541
626
  }
542
627
  if (Symbol.dispose) WasmDocument.prototype[Symbol.dispose] = WasmDocument.prototype.free;
543
628
 
629
+ /**
630
+ * An extraction in progress, from `WasmDocument.extractJob`; it holds its document weakly.
631
+ */
632
+ export class WasmExtractJob {
633
+ static __wrap(ptr) {
634
+ const obj = Object.create(WasmExtractJob.prototype);
635
+ obj.__wbg_ptr = ptr;
636
+ Object.defineProperty(obj, '__wbg_inst', { value: __wbg_instance_id, writable: true });
637
+
638
+ WasmExtractJobFinalization.register(obj, { ptr, instance: __wbg_instance_id }, obj);
639
+ return obj;
640
+ }
641
+ __destroy_into_raw() {
642
+ const ptr = this.__wbg_ptr;
643
+ this.__wbg_ptr = 0;
644
+ WasmExtractJobFinalization.unregister(this);
645
+ return ptr;
646
+ }
647
+ free() {
648
+ const ptr = this.__destroy_into_raw();
649
+ wasm.__wbg_wasmextractjob_free(ptr, 0);
650
+
651
+ }
652
+ /**
653
+ * Stops the job: its next step fails with `cancelled`.
654
+ */
655
+ cancel() {
656
+ wasm.wasmextractjob_cancel(this.__wbg_ptr);
657
+ }
658
+ /**
659
+ * Hands the job the result of its open request: `{ kind: "layout", regions }` or
660
+ * `{ kind: "ocr", words }`, boxes as `[x, y, width, height]` in top-left points.
661
+ *
662
+ * # Errors
663
+ * `model-result-unexpected` when nothing was asked for or `result` is the other kind;
664
+ * `invalid-argument` / `unknown-option` for a malformed result.
665
+ * @param {ModelResultInit} result
666
+ */
667
+ provide(result) {
668
+ let ret;
669
+ ret = wasm.wasmextractjob_provide(this.__wbg_ptr, result);
670
+ if (ret[1]) {
671
+ throw takeFromExternrefTable0(ret[0]);
672
+ }
673
+ }
674
+ /**
675
+ * Extracts up to `budget` pages: `{ state: "progress", done, total, phase, request? }` or
676
+ * `{ state: "done", output }`, the output in the job's format. While `request` is set, a
677
+ * step does nothing until `provide` answers it.
678
+ *
679
+ * # Errors
680
+ * `cancelled`, `document-changed`, `job-finished`, `disposed` when the document is freed,
681
+ * and the reading errors.
682
+ * @param {number} budget
683
+ * @returns {({ state: "progress" } & ExtractProgressJs) | { state: "done"; output: string }}
684
+ */
685
+ step(budget) {
686
+ let ret;
687
+ ret = wasm.wasmextractjob_step(this.__wbg_ptr, budget);
688
+ if (ret[2]) {
689
+ throw takeFromExternrefTable0(ret[1]);
690
+ }
691
+ return takeFromExternrefTable0(ret[0]);
692
+ }
693
+ }
694
+ if (Symbol.dispose) WasmExtractJob.prototype[Symbol.dispose] = WasmExtractJob.prototype.free;
695
+
544
696
  /**
545
697
  * A font registered with a [`WasmBuilder`].
546
698
  */
@@ -828,7 +980,8 @@ export class WasmPageBuilder {
828
980
  }
829
981
  /**
830
982
  * Opens an artifact until the matching `endTag`: `kind` is `layout`, `page`, `pagination`
831
- * or `background`.
983
+ * or `background`, or a pagination artifact that says what it is: `header` (attached to the
984
+ * top edge), `footer` (the bottom) or `watermark`.
832
985
  *
833
986
  * # Errors
834
987
  * `invalid-argument` for another kind.
@@ -1648,6 +1801,11 @@ const WasmDocumentFinalization = (typeof FinalizationRegistry === 'undefined')
1648
1801
  : new FinalizationRegistry(({ ptr, instance }) => {
1649
1802
  if (instance === __wbg_instance_id) wasm.__wbg_wasmdocument_free(ptr, 1);
1650
1803
  });
1804
+ const WasmExtractJobFinalization = (typeof FinalizationRegistry === 'undefined')
1805
+ ? { register: () => {}, unregister: () => {} }
1806
+ : new FinalizationRegistry(({ ptr, instance }) => {
1807
+ if (instance === __wbg_instance_id) wasm.__wbg_wasmextractjob_free(ptr, 1);
1808
+ });
1651
1809
  const WasmFontFinalization = (typeof FinalizationRegistry === 'undefined')
1652
1810
  ? { register: () => {}, unregister: () => {} }
1653
1811
  : new FinalizationRegistry(({ ptr, instance }) => {
Binary file
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@laminapdf/wasm",
3
- "version": "0.2.0-alpha.3",
3
+ "version": "0.2.0-alpha.4",
4
4
  "description": "Lamina PDF's WebAssembly modules and their wasm-bindgen glue: lamina_pdf_base (open, read, edit, save, vector and image pages), lamina_pdf_text (all of base plus fonts and text) and lamina_pdf_extract (all of base plus text extraction); and lamina_pdf_render_hayro, laminapdf-render's hayro adapter, which @laminapdf/render-hayro wraps. Generated into dist/ by `cargo xtask wasm`; @laminapdf/sdk is the API to use.",
5
5
  "license": "MIT OR Apache-2.0",
6
6
  "homepage": "https://laminapdf.com",