@exige/web-scanner-sdk 0.2.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (57) hide show
  1. package/README.md +330 -0
  2. package/dist/assets/document-worker.js +2 -0
  3. package/dist/assets/document-worker.js.map +1 -0
  4. package/dist/assets/ort-wasm-simd-threaded.jsep.mjs +108 -0
  5. package/dist/assets/ort-wasm-simd-threaded.jsep.wasm +0 -0
  6. package/dist/assets/ort.min.js +2937 -0
  7. package/dist/assets/ort.min.js.map +1 -0
  8. package/dist/assets/tesseract/eng.traineddata.LICENSE +201 -0
  9. package/dist/assets/tesseract/eng.traineddata.NOTICE +9 -0
  10. package/dist/assets/tesseract/eng.traineddata.gz +0 -0
  11. package/dist/assets/tesseract/tesseract-core-lstm.wasm.js +191 -0
  12. package/dist/assets/tesseract/tesseract-core-relaxedsimd-lstm.wasm.js +191 -0
  13. package/dist/assets/tesseract/tesseract-core-simd-lstm.wasm.js +191 -0
  14. package/dist/assets/tesseract/tesseract.js-core.LICENSE +202 -0
  15. package/dist/assets/tesseract/tesseract.js.LICENSE +201 -0
  16. package/dist/assets/tesseract/worker.min.js +3 -0
  17. package/dist/assets/tesseract/worker.min.js.LICENSE.txt +12 -0
  18. package/dist/assets-manifest.json +11 -0
  19. package/dist/components/ModelDownloadRing.d.ts +4 -0
  20. package/dist/components/scanner-camera-overlay.css +2 -0
  21. package/dist/finder-DFueuWuS.js +1225 -0
  22. package/dist/finder-DFueuWuS.js.map +1 -0
  23. package/dist/index.d.ts +24 -0
  24. package/dist/live-overlay-geometry.d.ts +11 -0
  25. package/dist/react/context.d.ts +2 -0
  26. package/dist/react/hooks.d.ts +3 -0
  27. package/dist/react/parts.d.ts +16 -0
  28. package/dist/react/scanner-context.d.ts +5 -0
  29. package/dist/react/types.d.ts +113 -0
  30. package/dist/react.d.ts +4 -0
  31. package/dist/react.js +594 -0
  32. package/dist/react.js.map +1 -0
  33. package/dist/scanner-sdk.js +1001 -0
  34. package/dist/scanner-sdk.js.map +1 -0
  35. package/dist/sdk/camera.d.ts +150 -0
  36. package/dist/sdk/display-quad.d.ts +23 -0
  37. package/dist/sdk/errors.d.ts +14 -0
  38. package/dist/sdk/face-model.d.ts +22 -0
  39. package/dist/sdk/field-model.d.ts +29 -0
  40. package/dist/sdk/finder-simulator.d.ts +17 -0
  41. package/dist/sdk/finder.d.ts +174 -0
  42. package/dist/sdk/frame-geometry.d.ts +6 -0
  43. package/dist/sdk/image.d.ts +18 -0
  44. package/dist/sdk/license-codec.d.ts +2 -0
  45. package/dist/sdk/license-public-key.d.ts +9 -0
  46. package/dist/sdk/license-runtime.d.ts +2 -0
  47. package/dist/sdk/license.d.ts +84 -0
  48. package/dist/sdk/lighting.d.ts +22 -0
  49. package/dist/sdk/model-download.d.ts +25 -0
  50. package/dist/sdk/ocr-runtime.d.ts +27 -0
  51. package/dist/sdk/ocr.d.ts +104 -0
  52. package/dist/sdk/ort-runtime.d.ts +23 -0
  53. package/dist/sdk/programmatic-redaction.d.ts +151 -0
  54. package/dist/sdk/redact.d.ts +17 -0
  55. package/dist/sdk/scan.d.ts +61 -0
  56. package/dist/sdk/types.d.ts +80 -0
  57. package/package.json +93 -0
@@ -0,0 +1,1225 @@
1
+ //#region src/sdk/errors.ts
2
+ var e = class extends Error {
3
+ code;
4
+ constructor(e, t) {
5
+ super(t), this.name = "ScannerError", this.code = e;
6
+ }
7
+ };
8
+ function t() {
9
+ return new e("canvas", "Canvas 2D is unavailable in this browser.");
10
+ }
11
+ //#endregion
12
+ //#region src/sdk/license-codec.ts
13
+ function n(e) {
14
+ let t = e.replaceAll("-", "+").replaceAll("_", "/"), n = t + "=".repeat((4 - t.length % 4) % 4), r = atob(n), i = new Uint8Array(r.length);
15
+ for (let e = 0; e < r.length; e += 1) i[e] = r.charCodeAt(e);
16
+ return i;
17
+ }
18
+ //#endregion
19
+ //#region src/sdk/license-public-key.ts
20
+ var r = "uFpA_UXGk-1AjjG31cFP6cqXOQX0w2TnuR7Bl-msZ6I";
21
+ //#endregion
22
+ //#region src/sdk/license-runtime.ts
23
+ function i() {
24
+ return n(r);
25
+ }
26
+ //#endregion
27
+ //#region src/sdk/license.ts
28
+ var a = [
29
+ "localhost",
30
+ "127.0.0.1",
31
+ "exige-scanner-sdk.vercel.app",
32
+ "exige-park-app.ngrok.io",
33
+ "*.exige.io"
34
+ ], o = class extends Error {
35
+ code;
36
+ constructor(e, t) {
37
+ super(t), this.name = "LicenseError", this.code = e;
38
+ }
39
+ }, s, c;
40
+ function l(e) {
41
+ return e.trim().toLowerCase().replace(/\.$/u, "");
42
+ }
43
+ function u() {
44
+ let e = globalThis.location?.hostname;
45
+ if (typeof e == "string") return l(e) || void 0;
46
+ }
47
+ function d() {
48
+ return Math.floor(Date.now() / 1e3);
49
+ }
50
+ function f(e, t) {
51
+ let n = l(t);
52
+ if (n.startsWith("*.")) {
53
+ let t = n.slice(2);
54
+ return !t.includes(".") || t.startsWith(".") || t.includes("*") ? !1 : e === t || e.endsWith(`.${t}`);
55
+ }
56
+ return e === n;
57
+ }
58
+ function p(e) {
59
+ let t = l(e);
60
+ return !t || t.includes("*") ? !1 : a.some((e) => f(t, e));
61
+ }
62
+ function m(e) {
63
+ return {
64
+ customerId: "dev",
65
+ domains: [e],
66
+ exp: 4102444800,
67
+ features: {
68
+ scan: !0,
69
+ ocr: !0,
70
+ redaction: !0,
71
+ vehicles: !0,
72
+ torch: !0
73
+ }
74
+ };
75
+ }
76
+ function h(e) {
77
+ return {
78
+ customerId: e.customerId,
79
+ domains: [...e.domains],
80
+ exp: e.exp,
81
+ features: { ...e.features }
82
+ };
83
+ }
84
+ function g(e = "This license key is not a signed payload.") {
85
+ return new o("malformed", e);
86
+ }
87
+ function _(e) {
88
+ if (!e || typeof e != "object" || Array.isArray(e)) throw g();
89
+ let t = e;
90
+ if (typeof t.customerId != "string" || t.customerId.trim() === "" || t.customerId.length > 200) throw g("This license key is missing a customer id.");
91
+ if (!Array.isArray(t.domains) || t.domains.some((e) => typeof e != "string")) throw g("This license key is missing a domain list.");
92
+ if (typeof t.exp != "number" || !Number.isSafeInteger(t.exp) || t.exp <= 0) throw g("This license key is missing a Unix expiry.");
93
+ if (!t.features || typeof t.features != "object" || Array.isArray(t.features)) throw g("This license key is missing feature flags.");
94
+ let n = t.features, r = [...new Set(t.domains.map((e) => l(e)).filter(Boolean))].sort();
95
+ return {
96
+ customerId: t.customerId.trim(),
97
+ domains: r,
98
+ exp: t.exp,
99
+ features: {
100
+ scan: n.scan === !0,
101
+ ocr: n.ocr === !0,
102
+ redaction: n.redaction === !0,
103
+ vehicles: n.vehicles === !0,
104
+ torch: n.torch === !0
105
+ }
106
+ };
107
+ }
108
+ async function v(e, t) {
109
+ let r = e.trim().split(".");
110
+ if (r.length !== 2 || !r[0] || !r[1]) throw g();
111
+ let i, a;
112
+ try {
113
+ i = n(r[0]), a = n(r[1]);
114
+ } catch {
115
+ throw g();
116
+ }
117
+ let s, c = !1;
118
+ try {
119
+ s = await crypto.subtle.importKey("raw", t.publicKey, { name: "Ed25519" }, !1, ["verify"]), c = await crypto.subtle.verify("Ed25519", s, a, i);
120
+ } catch {
121
+ c = !1;
122
+ }
123
+ if (!c) throw new o("invalid-signature", "This license key signature does not match the SDK public key.");
124
+ let u;
125
+ try {
126
+ u = JSON.parse(new TextDecoder().decode(i));
127
+ } catch {
128
+ throw g();
129
+ }
130
+ let d = _(u);
131
+ if (d.exp <= t.now) throw new o("expired", "This license key has expired.");
132
+ let f = l(t.hostname);
133
+ if (!f || !d.domains.includes(f)) throw new o("domain", `This license key is not valid for ${f || "this host"}.`);
134
+ return d;
135
+ }
136
+ async function y(e) {
137
+ let t = u();
138
+ if (!t) throw new o("domain", "The license check requires a browser hostname.");
139
+ let n = await v(e, {
140
+ publicKey: i(),
141
+ hostname: t,
142
+ now: d()
143
+ });
144
+ return s = e.trim(), c = n, h(n);
145
+ }
146
+ function b() {
147
+ let e = u();
148
+ return c && e && c.domains.includes(e) && c.exp > d() ? h(c) : !s && e && p(e) ? h(m(e)) : null;
149
+ }
150
+ async function x(e) {
151
+ let t = u();
152
+ if (!t) throw new o("domain", "The license check requires a browser hostname.");
153
+ if (!s) {
154
+ if (p(t)) return h(m(t));
155
+ throw new o("missing", "A license key is required. Call setLicenseKey() before using the scanner SDK.");
156
+ }
157
+ let n = await v(s, {
158
+ publicKey: i(),
159
+ hostname: t,
160
+ now: d()
161
+ });
162
+ if (c = n, !n.features[e]) throw new o("feature", `This license key does not include the ${e} feature.`);
163
+ return h(n);
164
+ }
165
+ //#endregion
166
+ //#region src/sdk/model-download.ts
167
+ var S = /* @__PURE__ */ new Map(), C = /* @__PURE__ */ new Set(), w = /* @__PURE__ */ new Map(), T = /* @__PURE__ */ new Map();
168
+ function E(e) {
169
+ let t = Number(e.headers.get("content-length"));
170
+ return Number.isFinite(t) && t > 0 ? t : null;
171
+ }
172
+ function ee() {
173
+ if (S.size === 0) return {
174
+ downloading: !1,
175
+ loaded: 0,
176
+ total: null
177
+ };
178
+ let e = 0, t = 0, n = !0;
179
+ for (let r of S.values()) e += r.loaded, r.total == null ? n = !1 : t += r.total;
180
+ return {
181
+ downloading: !0,
182
+ loaded: e,
183
+ total: n ? t : null
184
+ };
185
+ }
186
+ function D() {
187
+ let e = ee();
188
+ for (let t of C) t(e);
189
+ }
190
+ function O(e, t) {
191
+ t.done ? S.delete(e) : S.set(e, {
192
+ loaded: t.loaded,
193
+ total: t.total
194
+ }), D();
195
+ }
196
+ async function te(e, t) {
197
+ let n = E(e);
198
+ if (!e.body) {
199
+ let r = await e.arrayBuffer();
200
+ return t?.({
201
+ loaded: r.byteLength,
202
+ total: n ?? r.byteLength
203
+ }), r;
204
+ }
205
+ let r = e.body.getReader(), i = [], a = 0;
206
+ for (;;) {
207
+ let { done: e, value: o } = await r.read();
208
+ if (e) break;
209
+ o?.byteLength && (i.push(o), a += o.byteLength, t?.({
210
+ loaded: a,
211
+ total: n
212
+ }));
213
+ }
214
+ let o = new Uint8Array(a), s = 0;
215
+ for (let e of i) o.set(e, s), s += e.byteLength;
216
+ return a === 0 && t?.({
217
+ loaded: 0,
218
+ total: n
219
+ }), o.buffer;
220
+ }
221
+ async function ne(t, n) {
222
+ let r = w.get(t);
223
+ if (r) return r.slice(0);
224
+ let i = T.get(t);
225
+ if (i) return i.then((e) => e.slice(0));
226
+ let a = (async () => {
227
+ O(t, {
228
+ loaded: 0,
229
+ total: null
230
+ });
231
+ let r = await fetch(t, { cache: n?.cache });
232
+ if (!r.ok) throw new e("model-http", `Model request failed with HTTP ${r.status}.`);
233
+ return te(r, (e) => O(t, e));
234
+ })();
235
+ T.set(t, a);
236
+ try {
237
+ let e = await a;
238
+ return w.set(t, e), e.slice(0);
239
+ } finally {
240
+ T.delete(t), S.has(t) && (S.delete(t), D());
241
+ }
242
+ }
243
+ //#endregion
244
+ //#region src/sdk/ort-runtime.ts
245
+ var re = new URL("./assets/ort-wasm-simd-threaded.jsep.wasm", import.meta.url), ie = new URL("./assets/ort-wasm-simd-threaded.jsep.mjs", import.meta.url);
246
+ function k() {
247
+ return {
248
+ wasm: re.href,
249
+ mjs: ie.href
250
+ };
251
+ }
252
+ function ae(e) {
253
+ return typeof e == "string" ? e.trim() || k() : e?.wasm.trim() && e.mjs.trim() ? {
254
+ wasm: e.wasm.trim(),
255
+ mjs: e.mjs.trim()
256
+ } : k();
257
+ }
258
+ //#endregion
259
+ //#region src/sdk/image.ts
260
+ function oe(e, t, n) {
261
+ let r = n ? Math.min(1, n / Math.max(e, t)) : 1;
262
+ return {
263
+ width: Math.max(1, Math.round(e * r)),
264
+ height: Math.max(1, Math.round(t * r))
265
+ };
266
+ }
267
+ async function se(e) {
268
+ let t = URL.createObjectURL(e);
269
+ try {
270
+ let e = new Image();
271
+ return e.src = t, await e.decode(), e;
272
+ } finally {
273
+ URL.revokeObjectURL(t);
274
+ }
275
+ }
276
+ async function A(e, n = {}) {
277
+ if (e instanceof HTMLCanvasElement && n.cloneCanvas === !1 && !n.maxDimension) return e;
278
+ let r = document.createElement("canvas"), i = r.getContext("2d", { willReadFrequently: !0 });
279
+ if (!i) throw t();
280
+ if (e instanceof Blob) {
281
+ if ("createImageBitmap" in window) try {
282
+ let t = await createImageBitmap(e), a = oe(t.width, t.height, n.maxDimension);
283
+ return r.width = a.width, r.height = a.height, i.drawImage(t, 0, 0, a.width, a.height), t.close(), r;
284
+ } catch {}
285
+ e = await se(e);
286
+ }
287
+ let a = e instanceof HTMLImageElement ? e.naturalWidth : e.width, o = e instanceof HTMLImageElement ? e.naturalHeight : e.height;
288
+ if (!a || !o) throw Error("The image has no readable dimensions.");
289
+ let s = oe(a, o, n.maxDimension);
290
+ return r.width = s.width, r.height = s.height, i.drawImage(e, 0, 0, s.width, s.height), r;
291
+ }
292
+ function ce(e, t = "image/png", n = .92) {
293
+ return new Promise((r, i) => e.toBlob((e) => e ? r(e) : i(/* @__PURE__ */ Error("Could not encode the image.")), t, n));
294
+ }
295
+ function le(e, t, n) {
296
+ let r = Math.max(0, Math.min(t, e.x)), i = Math.max(0, Math.min(n, e.y));
297
+ return {
298
+ x: r,
299
+ y: i,
300
+ width: Math.max(0, Math.min(t - r, e.width)),
301
+ height: Math.max(0, Math.min(n - i, e.height))
302
+ };
303
+ }
304
+ //#endregion
305
+ //#region src/sdk/scan.ts
306
+ var ue = "https://exige-scanner-sdk.vercel.app/models/docaligner-lcnet100-f4117b78.onnx";
307
+ function j(e) {
308
+ return e?.trim() || "https://exige-scanner-sdk.vercel.app/models/docaligner-lcnet100-f4117b78.onnx";
309
+ }
310
+ var de = 3, M, fe = 0, N = /* @__PURE__ */ new Map();
311
+ function P(e, t) {
312
+ return Math.hypot(e.x - t.x, e.y - t.y);
313
+ }
314
+ function F(e) {
315
+ return {
316
+ ...e,
317
+ edges: {
318
+ top: {
319
+ start: e.topLeft,
320
+ end: e.topRight
321
+ },
322
+ right: {
323
+ start: e.topRight,
324
+ end: e.bottomRight
325
+ },
326
+ bottom: {
327
+ start: e.bottomRight,
328
+ end: e.bottomLeft
329
+ },
330
+ left: {
331
+ start: e.bottomLeft,
332
+ end: e.topLeft
333
+ }
334
+ }
335
+ };
336
+ }
337
+ function pe(e, t) {
338
+ let n = (e) => ({
339
+ x: e.x / t,
340
+ y: e.y / t
341
+ });
342
+ return {
343
+ topLeft: n(e.topLeft),
344
+ topRight: n(e.topRight),
345
+ bottomRight: n(e.bottomRight),
346
+ bottomLeft: n(e.bottomLeft)
347
+ };
348
+ }
349
+ function I() {
350
+ return typeof navigator > "u" ? !1 : navigator.maxTouchPoints > 0 || navigator.hardwareConcurrency <= 4 || typeof matchMedia == "function" && matchMedia("(pointer: coarse)").matches;
351
+ }
352
+ function me(t, n, r, i) {
353
+ return new Promise((a, o) => {
354
+ M || (M = new Worker(new URL("./assets/document-worker.js", import.meta.url), { type: "module" }), M.onmessage = (t) => {
355
+ if (t.data.download?.url) {
356
+ O(t.data.download.url, t.data.download);
357
+ return;
358
+ }
359
+ let n = N.get(t.data.id);
360
+ n && (N.delete(t.data.id), t.data.error ? n.reject(t.data.errorCode ? new e(t.data.errorCode, t.data.error) : Error(t.data.error)) : t.data.result ? n.resolve(t.data.result) : n.reject(/* @__PURE__ */ Error("The document worker returned no result.")));
361
+ }, M.onerror = () => {
362
+ let t = new e("worker", "The document worker could not start.");
363
+ for (let e of N.values()) e.reject(t);
364
+ N.clear(), M?.terminate(), M = void 0;
365
+ });
366
+ let s = ++fe;
367
+ N.set(s, {
368
+ resolve: a,
369
+ reject: o
370
+ });
371
+ let c = t.slice().buffer;
372
+ M.postMessage({
373
+ id: s,
374
+ pixels: c,
375
+ width: n,
376
+ height: r,
377
+ modelUrl: j(i.modelUrl),
378
+ heatmapThreshold: i.heatmapThreshold,
379
+ cacheModel: i.cacheModel,
380
+ ortWasmPaths: ae(i.ortWasmPaths)
381
+ }, [c]);
382
+ });
383
+ }
384
+ async function L(n, r) {
385
+ let { width: i, height: a } = n, o = r.minDimension ?? 360;
386
+ if (Math.min(i, a) < o) return {
387
+ status: "low-quality",
388
+ confidence: 0,
389
+ message: `Use an image at least ${o}px on its shortest side.`,
390
+ sourceWidth: i,
391
+ sourceHeight: a
392
+ };
393
+ let s = I() ? 560 : 900, c = Math.min(1, (r.maxAnalysisDimension ?? s) / Math.max(i, a)), l = document.createElement("canvas");
394
+ l.width = Math.max(1, Math.round(i * c)), l.height = Math.max(1, Math.round(a * c));
395
+ let u = l.getContext("2d", { willReadFrequently: !0 });
396
+ if (!u) throw t();
397
+ u.drawImage(n, 0, 0, l.width, l.height);
398
+ let d = u.getImageData(0, 0, l.width, l.height).data, f;
399
+ if (r.useWorker !== !1 && typeof Worker < "u") try {
400
+ f = await me(d, l.width, l.height, r);
401
+ } catch (t) {
402
+ if (t instanceof e && (t.code === "worker" || t.code === "model-http")) throw t;
403
+ f = {
404
+ sharpness: 20,
405
+ detector: "ml",
406
+ modelStatus: "failed",
407
+ modelError: t instanceof Error ? t.message : "Document worker failed."
408
+ };
409
+ }
410
+ else f = {
411
+ sharpness: 20,
412
+ detector: "ml",
413
+ modelStatus: "failed",
414
+ modelError: "ML detection requires a Web Worker."
415
+ };
416
+ let { sharpness: p, candidate: m, detector: h, modelStatus: g, modelProvider: _, modelError: v, inferenceMs: y } = f, b = {
417
+ detector: h,
418
+ modelStatus: g,
419
+ modelProvider: _,
420
+ modelError: v,
421
+ inferenceMs: y
422
+ };
423
+ if (p < de) return {
424
+ status: "low-quality",
425
+ confidence: Math.min(.3, p / 18),
426
+ message: "The image is too soft or dark to resolve four document edges.",
427
+ sourceWidth: i,
428
+ sourceHeight: a,
429
+ ...b
430
+ };
431
+ if (!m) return {
432
+ status: "no-document",
433
+ confidence: 0,
434
+ message: "No document corners found. Place all four edges on a contrasting surface.",
435
+ sourceWidth: i,
436
+ sourceHeight: a,
437
+ ...b
438
+ };
439
+ let x = pe(m.corners, c), S = F(x), C = r.minConfidence ?? .58;
440
+ return m.confidence < C ? {
441
+ status: "low-confidence",
442
+ quad: S,
443
+ corners: x,
444
+ confidence: m.confidence,
445
+ message: "Four possible corners were found, but the geometry is not reliable enough to crop.",
446
+ sourceWidth: i,
447
+ sourceHeight: a,
448
+ ...b
449
+ } : {
450
+ status: "success",
451
+ quad: S,
452
+ corners: x,
453
+ confidence: m.confidence,
454
+ message: "Four document edges detected.",
455
+ sourceWidth: i,
456
+ sourceHeight: a,
457
+ ...b
458
+ };
459
+ }
460
+ function he(e, t) {
461
+ let n = Math.max(1, Math.round(Math.max(P(e.topLeft, e.topRight), P(e.bottomLeft, e.bottomRight)))), r = Math.max(1, Math.round(Math.max(P(e.topLeft, e.bottomLeft), P(e.topRight, e.bottomRight)))), i = Math.min(1, t / Math.max(n, r));
462
+ return {
463
+ width: Math.max(1, Math.round(n * i)),
464
+ height: Math.max(1, Math.round(r * i))
465
+ };
466
+ }
467
+ function R(e, n, r) {
468
+ let { width: i, height: a } = he(n, r), o = e.getContext("2d", { willReadFrequently: !0 });
469
+ if (!o) throw t();
470
+ let s = o.getImageData(0, 0, e.width, e.height), c = document.createElement("canvas");
471
+ c.width = i, c.height = a;
472
+ let l = c.getContext("2d");
473
+ if (!l) throw t();
474
+ let u = l.createImageData(i, a), { topLeft: d, topRight: f, bottomRight: p, bottomLeft: m } = n, h = f.x - p.x, g = m.x - p.x, _ = f.y - p.y, v = m.y - p.y, y = d.x - f.x + p.x - m.x, b = d.y - f.y + p.y - m.y, x = h * v - g * _, S = Math.abs(x) < 1e-4 ? 0 : (y * v - g * b) / x, C = Math.abs(x) < 1e-4 ? 0 : (h * b - y * _) / x, w = f.x - d.x + S * f.x, T = m.x - d.x + C * m.x, E = f.y - d.y + S * f.y, ee = m.y - d.y + C * m.y;
475
+ for (let t = 0; t < a; t += 1) {
476
+ let n = t / Math.max(1, a - 1);
477
+ for (let r = 0; r < i; r += 1) {
478
+ let a = r / Math.max(1, i - 1), o = S * a + C * n + 1, c = Math.max(0, Math.min(e.width - 1, Math.round((w * a + T * n + d.x) / o))), l = (Math.max(0, Math.min(e.height - 1, Math.round((E * a + ee * n + d.y) / o))) * e.width + c) * 4, f = (t * i + r) * 4;
479
+ u.data[f] = s.data[l], u.data[f + 1] = s.data[l + 1], u.data[f + 2] = s.data[l + 2], u.data[f + 3] = s.data[l + 3];
480
+ }
481
+ }
482
+ return l.putImageData(u, 0, 0), c;
483
+ }
484
+ async function z(e, t = {}) {
485
+ return await x("scan"), L(await A(e, { cloneCanvas: !1 }), t);
486
+ }
487
+ async function ge(e, t, n = {}) {
488
+ await x("scan");
489
+ let r = await A(e, { cloneCanvas: !1 }), i = n.maxOutputDimension ?? (I() ? 2048 : 4096);
490
+ return {
491
+ status: "success",
492
+ corners: t,
493
+ quad: F(t),
494
+ confidence: 1,
495
+ message: "Captured with the document edges shown in the finder.",
496
+ sourceWidth: r.width,
497
+ sourceHeight: r.height,
498
+ canvas: R(r, t, i)
499
+ };
500
+ }
501
+ async function _e(e, t = {}) {
502
+ await x("scan");
503
+ let n = await A(e, { cloneCanvas: !1 }), r = await L(n, t);
504
+ if (r.status !== "success" || !r.corners) return r;
505
+ let i = t.maxOutputDimension ?? (I() ? 2048 : 4096);
506
+ return {
507
+ ...r,
508
+ canvas: R(n, r.corners, i),
509
+ message: "Four document edges detected and perspective-corrected."
510
+ };
511
+ }
512
+ //#endregion
513
+ //#region src/sdk/camera.ts
514
+ function B(e, t) {
515
+ let { engine: n } = t;
516
+ return [
517
+ `${e}:`,
518
+ ` engine: ${n.engine}/${n.browser}${n.iosWebKit ? " ios-webkit" : ""}`,
519
+ ` ua: ${n.userAgent}`,
520
+ ` video: ${t.videoWidth}x${t.videoHeight} readyState=${t.readyState}${t.paused ? " paused" : ""}${t.rendered ? "" : " hidden"}${t.connected ? "" : " disconnected"}`,
521
+ ` track: ${t.trackReadyState}${t.trackEnabled ? "" : " disabled"}${t.trackMuted ? " muted" : ""}`,
522
+ ` liveLuma: ${t.liveLuminance.toFixed(1)}`,
523
+ ` mirrorLuma: ${t.mirrorLuminance.toFixed(1)}`,
524
+ ` mirrorAgeMs: ${Number.isFinite(t.mirrorAgeMs) ? Math.round(t.mirrorAgeMs) : "none"}`,
525
+ ` hasImageCapture: ${t.hasImageCapture} (never used)`,
526
+ ` torch: ${t.torch.mode} supported=${t.torch.supported} on=${t.torch.on}`
527
+ ].join("\n");
528
+ }
529
+ function ve(e) {
530
+ let t = ["Exige scanner capture report", `time: ${e.capturedAt ?? (/* @__PURE__ */ new Date()).toISOString()}`];
531
+ if (e.error && t.push(`error: ${e.error}`), e.captureMethod && t.push(`method: ${e.captureMethod}`), e.luminance !== void 0 && t.push(`luminance: ${e.luminance.toFixed(1)}`), e.fallbackReason && t.push(`fallback: ${e.fallbackReason}`), e.shutter && t.push(B("shutter", e.shutter)), e.live && t.push(B("live", e.live)), e.finder) {
532
+ let n = e.finder;
533
+ t.push([
534
+ "finder:",
535
+ ` state: ${n.state ?? "unknown"}`,
536
+ ` confidence: ${n.confidence === void 0 ? "—" : n.confidence.toFixed(3)}`,
537
+ ` stable: ${n.stableFrames ?? "—"}/${n.requiredStableFrames ?? "—"}`,
538
+ ` detector: ${n.detector ?? "—"} ${n.modelStatus ?? ""}`.trim(),
539
+ ` source: ${n.sourceWidth ?? "—"}x${n.sourceHeight ?? "—"}`
540
+ ].join("\n"));
541
+ }
542
+ return `${t.join("\n")}\n`;
543
+ }
544
+ function V(e = typeof navigator > "u" ? "" : navigator.userAgent, t = typeof navigator > "u" ? 0 : navigator.maxTouchPoints) {
545
+ let n = /CriOS|Chrome/i.test(e) ? "chrome" : /EdgiOS|Edg/i.test(e) ? "edge" : /FxiOS|Firefox/i.test(e) ? "firefox" : /Safari/i.test(e) ? "safari" : "unknown", r = /iPhone|iPad|iPod/i.test(e) || /Macintosh/i.test(e) && t > 1, i = /CriOS|EdgiOS|FxiOS|OPiOS|Mercury/i.test(e), a = r || i;
546
+ return {
547
+ engine: a || /AppleWebKit/i.test(e) && !/Chrome|Chromium|Edg/i.test(e) ? "webkit" : /Chrome|Chromium|Edg/i.test(e) ? "blink" : /Gecko\//i.test(e) ? "gecko" : "unknown",
548
+ browser: n,
549
+ iosWebKit: a,
550
+ userAgent: e
551
+ };
552
+ }
553
+ var ye = 10, H = class {
554
+ on = !1;
555
+ darkCount = 0;
556
+ brightCount = 0;
557
+ turnOnLuminance;
558
+ turnOffLuminance;
559
+ darkSamples;
560
+ brightSamples;
561
+ constructor(e = {}) {
562
+ this.turnOnLuminance = e.turnOnLuminance ?? 62, this.turnOffLuminance = e.turnOffLuminance ?? 155, this.darkSamples = e.darkSamples ?? 3, this.brightSamples = e.brightSamples ?? 8;
563
+ }
564
+ update(e) {
565
+ if (!Number.isFinite(e) || e <= 10) {
566
+ this.darkCount = 0, this.brightCount = 0;
567
+ return;
568
+ }
569
+ if (!this.on) return this.brightCount = 0, this.darkCount = e <= this.turnOnLuminance ? this.darkCount + 1 : 0, this.darkCount < this.darkSamples ? void 0 : (this.darkCount = 0, this.on = !0, !0);
570
+ if (this.darkCount = 0, this.brightCount = e >= this.turnOffLuminance ? this.brightCount + 1 : 0, !(this.brightCount < this.brightSamples)) return this.brightCount = 0, this.on = !1, !1;
571
+ }
572
+ getState() {
573
+ return this.on;
574
+ }
575
+ };
576
+ function U(e, t) {
577
+ return t ? e === "alwaysOn" || e === "alwaysOff" ? {
578
+ mode: e,
579
+ supported: !0,
580
+ on: e === "alwaysOn",
581
+ visible: !1,
582
+ mutable: !1,
583
+ automatic: !1
584
+ } : {
585
+ mode: e,
586
+ supported: !0,
587
+ on: e === "defaultOn",
588
+ visible: !0,
589
+ mutable: e !== "auto",
590
+ automatic: e === "auto"
591
+ } : {
592
+ mode: e,
593
+ supported: !1,
594
+ on: !1,
595
+ visible: !1,
596
+ mutable: !1,
597
+ automatic: e === "auto"
598
+ };
599
+ }
600
+ function W(e) {
601
+ let t = Math.floor(e.length / 4);
602
+ if (!t) return 0;
603
+ let n = 0;
604
+ for (let r = 0; r < t * 4; r += 4) n += e[r] * .299 + e[r + 1] * .587 + e[r + 2] * .114;
605
+ return n / t;
606
+ }
607
+ function be(e, t = 10) {
608
+ if (e.length < 4) return !0;
609
+ let n = Math.floor(e.length / 4), r = 0;
610
+ for (let i = 0; i < n * 4; i += 4) e[i] * .299 + e[i + 1] * .587 + e[i + 2] * .114 > t * 2 && (r += 1);
611
+ return W(e) <= t && r / n < .01;
612
+ }
613
+ function G(e, t, n) {
614
+ if (!t || !n) return 0;
615
+ let r = document.createElement("canvas");
616
+ r.width = Math.min(32, t), r.height = Math.min(32, n);
617
+ let i = r.getContext("2d", { willReadFrequently: !0 });
618
+ return i ? (i.drawImage(e, 0, 0, r.width, r.height), W(i.getImageData(0, 0, r.width, r.height).data)) : 0;
619
+ }
620
+ function xe(e) {
621
+ return G(e, e.width, e.height);
622
+ }
623
+ function Se(e, t = 120) {
624
+ let n = document.createElement("canvas"), r = n.getContext("2d"), i = typeof e.requestVideoFrameCallback == "function", a = !0, o = 0, s = 0, c = 0, l = 0, u = 0, d = () => {
625
+ a && (o = i ? e.requestVideoFrameCallback(f) : requestAnimationFrame(f));
626
+ };
627
+ function f() {
628
+ if (!a) return;
629
+ let { videoWidth: i, videoHeight: o } = e, f = performance.now();
630
+ r && i && o && f - s >= t && (s = f, l = G(e, i, o), l > 10 && ((n.width !== i || n.height !== o) && (n.width = i, n.height = o), r.drawImage(e, 0, 0, i, o), u = l, c = f)), d();
631
+ }
632
+ return d(), {
633
+ stop() {
634
+ a = !1, i ? e.cancelVideoFrameCallback?.(o) : cancelAnimationFrame(o);
635
+ },
636
+ getFrame: () => c ? n : void 0,
637
+ getLiveLuminance: () => l,
638
+ getMirrorLuminance: () => u,
639
+ getMirrorAgeMs: () => c ? performance.now() - c : Infinity
640
+ };
641
+ }
642
+ function Ce(e) {
643
+ let t = document.createElement("canvas");
644
+ return t.width = e.width, t.height = e.height, t.getContext("2d")?.drawImage(e, 0, 0), t;
645
+ }
646
+ function K(e = {}) {
647
+ let t = { ideal: e.idealWidth ?? 3840 }, n = { ideal: e.idealHeight ?? 2160 };
648
+ return e.maxWidth && (t.max = e.maxWidth), e.maxHeight && (n.max = e.maxHeight), {
649
+ audio: !1,
650
+ video: {
651
+ facingMode: { ideal: e.facingMode ?? "environment" },
652
+ width: t,
653
+ height: n,
654
+ frameRate: {
655
+ ideal: e.maxFrameRate ?? 30,
656
+ max: e.maxFrameRate ?? 30
657
+ }
658
+ }
659
+ };
660
+ }
661
+ function q(e, n) {
662
+ if (!e.videoWidth || !e.videoHeight) throw Error("The camera is not ready to capture a frame.");
663
+ let r = n ? Math.min(1, n / Math.max(e.videoWidth, e.videoHeight)) : 1, i = document.createElement("canvas");
664
+ i.width = Math.max(1, Math.round(e.videoWidth * r)), i.height = Math.max(1, Math.round(e.videoHeight * r));
665
+ let a = i.getContext("2d");
666
+ if (!a) throw t();
667
+ return a.drawImage(e, 0, 0, i.width, i.height), i;
668
+ }
669
+ function we(e) {
670
+ return e.idealWidth || e.idealHeight || e.maxWidth || e.maxHeight ? [K(e)] : [
671
+ K({
672
+ ...e,
673
+ idealWidth: 3840,
674
+ idealHeight: 2160
675
+ }),
676
+ K({
677
+ ...e,
678
+ idealWidth: 2560,
679
+ idealHeight: 1440
680
+ }),
681
+ K({
682
+ ...e,
683
+ idealWidth: 1920,
684
+ idealHeight: 1080
685
+ })
686
+ ];
687
+ }
688
+ async function Te(t, n = {}) {
689
+ await x("scan");
690
+ let r = n.torch ?? "alwaysOff";
691
+ if (r !== "alwaysOff" && await x("torch"), !window.isSecureContext && location.hostname !== "localhost") throw new e("secure-context", "Camera access requires HTTPS.");
692
+ if (!navigator.mediaDevices?.getUserMedia) throw Error("Live camera access is unavailable. Use the native camera picker instead.");
693
+ t.muted = !0, t.autoplay = !0, t.playsInline = !0, t.setAttribute("playsinline", "");
694
+ let i, a;
695
+ for (let e of we(n)) try {
696
+ i = await navigator.mediaDevices.getUserMedia(e);
697
+ break;
698
+ } catch (e) {
699
+ if (a = e, !(e instanceof DOMException) || e.name !== "OverconstrainedError") throw e;
700
+ }
701
+ if (!i) throw a ?? /* @__PURE__ */ Error("No rear camera resolution is available.");
702
+ t.srcObject = i, await t.play();
703
+ let o = i.getVideoTracks()[0];
704
+ if (!o) {
705
+ for (let e of i.getTracks()) e.stop();
706
+ throw Error("The camera did not provide a video track.");
707
+ }
708
+ let s = Se(t), c = "ImageCapture" in globalThis, l = U(r, (typeof o.getCapabilities == "function" ? o.getCapabilities() : void 0)?.torch === !0), u = !1, d = async (e) => {
709
+ if (!l.supported || o.readyState !== "live") return !1;
710
+ try {
711
+ return await o.applyConstraints({ advanced: [{ torch: e }] }), l = {
712
+ ...l,
713
+ on: e
714
+ }, !0;
715
+ } catch {
716
+ return l = {
717
+ ...l,
718
+ supported: !1,
719
+ on: !1,
720
+ visible: !1,
721
+ mutable: !1
722
+ }, !1;
723
+ }
724
+ };
725
+ l.on && await d(!0);
726
+ let f = r === "auto" && l.supported ? new H() : void 0, p = f ? window.setInterval(() => {
727
+ if (u || !l.supported) return;
728
+ let e = f.update(s.getLiveLuminance());
729
+ e !== void 0 && e !== l.on && (u = !0, d(e).finally(() => {
730
+ u = !1;
731
+ }));
732
+ }, 350) : 0, m = () => {
733
+ let e = t.getBoundingClientRect();
734
+ return {
735
+ videoWidth: t.videoWidth,
736
+ videoHeight: t.videoHeight,
737
+ readyState: t.readyState,
738
+ paused: t.paused,
739
+ connected: t.isConnected,
740
+ rendered: e.width > 0 && e.height > 0,
741
+ trackReadyState: o.readyState ?? "missing",
742
+ trackEnabled: o.enabled,
743
+ trackMuted: o.muted,
744
+ liveLuminance: s.getLiveLuminance(),
745
+ mirrorLuminance: s.getMirrorLuminance(),
746
+ mirrorAgeMs: s.getMirrorAgeMs(),
747
+ hasImageCapture: c,
748
+ torchMode: l.mode,
749
+ torchSupported: l.supported,
750
+ torchOn: l.on,
751
+ torch: { ...l },
752
+ engine: V()
753
+ };
754
+ };
755
+ return {
756
+ stream: i,
757
+ get torchMode() {
758
+ return l.mode;
759
+ },
760
+ get torchSupported() {
761
+ return l.supported;
762
+ },
763
+ get torchOn() {
764
+ return l.on;
765
+ },
766
+ capture: (e) => q(t, e),
767
+ async capturePhoto() {
768
+ let e, n = 0;
769
+ try {
770
+ e = q(t), n = xe(e);
771
+ } catch {
772
+ e = void 0;
773
+ }
774
+ let r = s.getFrame(), i = e && n > 10 ? e : void 0, a = i ?? (r ? Ce(r) : void 0);
775
+ if (!a) throw Error("The camera preview produced no visible pixels. Keep the scanner on screen, wait for the preview, and retake.");
776
+ return {
777
+ frame: a,
778
+ method: i ? "video-frame" : "live-mirror",
779
+ settings: o.getSettings(),
780
+ fallbackReason: i ? void 0 : "video-frame-empty",
781
+ luminance: i ? n : s.getMirrorLuminance(),
782
+ diagnostics: m()
783
+ };
784
+ },
785
+ getSettings: () => o.getSettings(),
786
+ getDiagnostics: m,
787
+ getTorchStatus: () => ({ ...l }),
788
+ async setTorch(e) {
789
+ return l.mutable ? d(e) : !1;
790
+ },
791
+ stop() {
792
+ p && window.clearInterval(p), s.stop();
793
+ for (let e of i.getTracks()) e.stop();
794
+ t.srcObject === i && (t.srcObject = null);
795
+ }
796
+ };
797
+ }
798
+ //#endregion
799
+ //#region src/sdk/lighting.ts
800
+ function Ee(e, t) {
801
+ if (!e.length) return 0;
802
+ let n = [...e].sort((e, t) => e - t);
803
+ return n[Math.min(n.length - 1, Math.floor(n.length * t))];
804
+ }
805
+ function J(e, t, n, r = 12) {
806
+ if (!t || !n || e.length < t * n) return {
807
+ strong: !1,
808
+ strength: 0,
809
+ darkness: 0,
810
+ areaRatio: 0
811
+ };
812
+ let i = Math.min(r, t), a = Math.min(r, n), o = [];
813
+ for (let r = 0; r < a; r += 1) {
814
+ let s = Math.floor(r * n / a), c = Math.max(s + 1, Math.floor((r + 1) * n / a));
815
+ for (let n = 0; n < i; n += 1) {
816
+ let r = Math.floor(n * t / i), a = Math.max(r + 1, Math.floor((n + 1) * t / i)), l = 0, u = 0, d = 0;
817
+ for (let n = s; n < c; n += 1) for (let i = r; i < a; i += 1) {
818
+ let r = e[n * t + i];
819
+ l += r, u += r * r, d += 1;
820
+ }
821
+ let f = l / d;
822
+ o.push({
823
+ mean: f,
824
+ deviation: Math.sqrt(Math.max(0, u / d - f * f))
825
+ });
826
+ }
827
+ }
828
+ let s = Ee(o.map((e) => e.mean), .8), c = o.map((e) => s - e.mean >= 24 && e.mean >= 35), l = new Uint8Array(o.length), u = [];
829
+ for (let e = 0; e < o.length; e += 1) {
830
+ if (!c[e] || l[e]) continue;
831
+ let t = [], n = [e];
832
+ for (l[e] = 1; n.length;) {
833
+ let e = n.shift();
834
+ t.push(e);
835
+ let r = Math.floor(e / i), o = e % i;
836
+ for (let [e, t] of [
837
+ [o - 1, r],
838
+ [o + 1, r],
839
+ [o, r - 1],
840
+ [o, r + 1]
841
+ ]) {
842
+ if (e < 0 || e >= i || t < 0 || t >= a) continue;
843
+ let r = t * i + e;
844
+ c[r] && !l[r] && (l[r] = 1, n.push(r));
845
+ }
846
+ }
847
+ u.push(t);
848
+ }
849
+ let d = {
850
+ strong: !1,
851
+ strength: 0,
852
+ darkness: 0,
853
+ areaRatio: 0
854
+ };
855
+ for (let e of u) {
856
+ let t = e.length / o.length;
857
+ if (t < .06 || t > .75) continue;
858
+ let n = e.reduce((e, t) => e + s - o[t].mean, 0) / e.length, r = e.filter((e) => o[e].deviation >= 9).length / e.length;
859
+ if (r < .08 && n < 42) continue;
860
+ let c = e.map((e) => e % i), l = e.map((e) => Math.floor(e / i)), u = Math.min(...c), f = Math.max(...c), p = Math.min(...l), m = Math.max(...l), h = Math.max(0, u - 1) / i, g = Math.max(0, p - 1) / a, _ = Math.min(i, f + 1 + 1) / i, v = Math.min(a, m + 1 + 1) / a, y = n * Math.sqrt(t) * (.75 + Math.min(.25, r));
861
+ y > d.strength && (d = {
862
+ strong: y >= 10,
863
+ strength: y,
864
+ darkness: n,
865
+ areaRatio: t,
866
+ region: {
867
+ x: h,
868
+ y: g,
869
+ width: _ - h,
870
+ height: v - g
871
+ }
872
+ });
873
+ }
874
+ return d;
875
+ }
876
+ function De(e, t, n, r = Math.max(12, Math.round(Math.max(t, n) / 32))) {
877
+ let i = t + 1, a = new Uint32Array((t + 1) * (n + 1));
878
+ for (let r = 1; r <= n; r += 1) {
879
+ let n = 0;
880
+ for (let o = 1; o <= t; o += 1) n += e[(r - 1) * t + o - 1], a[r * i + o] = a[(r - 1) * i + o] + n;
881
+ }
882
+ let o = new Uint8Array(e.length);
883
+ for (let s = 0; s < n; s += 1) {
884
+ let c = Math.max(0, s - r), l = Math.min(n, s + r + 1);
885
+ for (let n = 0; n < t; n += 1) {
886
+ let u = Math.max(0, n - r), d = Math.min(t, n + r + 1), f = (d - u) * (l - c), p = (a[l * i + d] - a[c * i + d] - a[l * i + u] + a[c * i + u]) / f;
887
+ o[s * t + n] = Math.max(0, Math.min(255, Math.round(e[s * t + n] * 235 / Math.max(24, p))));
888
+ }
889
+ }
890
+ return o;
891
+ }
892
+ function Oe(e, t, n) {
893
+ let r = [
894
+ e.topLeft,
895
+ e.topRight,
896
+ e.bottomRight,
897
+ e.bottomLeft
898
+ ], i = Math.max(0, Math.min(...r.map((e) => e.x))), a = Math.max(0, Math.min(...r.map((e) => e.y))), o = Math.min(t, Math.max(...r.map((e) => e.x))), s = Math.min(n, Math.max(...r.map((e) => e.y)));
899
+ return {
900
+ left: i,
901
+ top: a,
902
+ width: o - i,
903
+ height: s - a
904
+ };
905
+ }
906
+ function ke(e, t) {
907
+ let n = Oe(t, e.width, e.height);
908
+ if (n.width <= 0 || n.height <= 0) return {
909
+ strong: !1,
910
+ strength: 0,
911
+ darkness: 0,
912
+ areaRatio: 0
913
+ };
914
+ let r = document.createElement("canvas");
915
+ r.width = 60, r.height = 60;
916
+ let i = r.getContext("2d", { willReadFrequently: !0 });
917
+ if (!i) return {
918
+ strong: !1,
919
+ strength: 0,
920
+ darkness: 0,
921
+ areaRatio: 0
922
+ };
923
+ i.drawImage(e, n.left, n.top, n.width, n.height, 0, 0, r.width, r.height);
924
+ let a = i.getImageData(0, 0, r.width, r.height).data, o = new Uint8Array(r.width * r.height);
925
+ for (let e = 0, t = 0; e < o.length; e += 1, t += 4) o[e] = Math.round(a[t] * .299 + a[t + 1] * .587 + a[t + 2] * .114);
926
+ return J(o, r.width, r.height);
927
+ }
928
+ //#endregion
929
+ //#region src/sdk/finder.ts
930
+ function Ae(e, t) {
931
+ return t.castShadow && (e.reason === "hold-still" || e.reason === "ready") ? t.hint ?? e.hint : e.hint;
932
+ }
933
+ async function je(e, t) {
934
+ let n = await e();
935
+ return t(), n;
936
+ }
937
+ function Y(e) {
938
+ return e === "alwaysOn" || e === "only" ? {
939
+ visible: !1,
940
+ checked: !0,
941
+ mutable: !1
942
+ } : e === "alwaysOff" ? {
943
+ visible: !1,
944
+ checked: !1,
945
+ mutable: !1
946
+ } : {
947
+ visible: !0,
948
+ checked: e === "defaultOn",
949
+ mutable: !0
950
+ };
951
+ }
952
+ function X(e) {
953
+ return [
954
+ e.topLeft,
955
+ e.topRight,
956
+ e.bottomRight,
957
+ e.bottomLeft
958
+ ];
959
+ }
960
+ function Me(e) {
961
+ let t = 0;
962
+ for (let n = 0; n < e.length; n += 1) {
963
+ let r = e[n], i = e[(n + 1) % e.length];
964
+ t += r.x * i.y - i.x * r.y;
965
+ }
966
+ return Math.abs(t) / 2;
967
+ }
968
+ function Z(e, t) {
969
+ return Math.hypot(e.x - t.x, e.y - t.y);
970
+ }
971
+ var Q = {
972
+ widthFill: 0,
973
+ heightFill: 0,
974
+ limitingFill: 0,
975
+ areaFill: 0,
976
+ aspectRatio: 1
977
+ };
978
+ function Ne(e, t, n) {
979
+ let r = X(e), i = r.map(({ x: e }) => e), a = r.map(({ y: e }) => e), o = (Math.max(...i) - Math.min(...i)) / Math.max(1, t), s = (Math.max(...a) - Math.min(...a)) / Math.max(1, n), [c, l, u, d] = r, f = Math.max(Z(c, l), Z(d, u)), p = Math.max(Z(c, d), Z(l, u));
980
+ return {
981
+ widthFill: o,
982
+ heightFill: s,
983
+ limitingFill: Math.max(o, s),
984
+ areaFill: Me(r) / Math.max(1, t * n),
985
+ aspectRatio: Math.max(f, p) / Math.max(1, Math.min(f, p))
986
+ };
987
+ }
988
+ function Pe(e, t, n, r = {}) {
989
+ let i = t ? r.exitFillRatio ?? .64 : r.minFillRatio ?? .72, a = r.highAspectRatio ?? 2.2;
990
+ if (e.aspectRatio < a) return i;
991
+ let o = t ? r.highAspectExitFillRatio : r.highAspectFillRatio;
992
+ return Math.min(o ?? i + .08, 1 - n * 2);
993
+ }
994
+ function Fe(e, t, n = {}) {
995
+ let r = n.confidenceThreshold ?? .72;
996
+ if (e.status !== "success" || !e.quad || e.confidence < r || !e.sourceWidth || !e.sourceHeight) return {
997
+ hint: "Place the document in the frame",
998
+ reason: "place-document",
999
+ fillRatio: 0,
1000
+ fill: Q,
1001
+ readyForAutoCapture: !1
1002
+ };
1003
+ let i = X(e.quad), a = Ne(e.quad, e.sourceWidth, e.sourceHeight), o = a.limitingFill, s = t.previouslyReady ? n.exitEdgeMarginRatio ?? .005 : n.edgeMarginRatio ?? .015, c = e.sourceWidth * s, l = e.sourceHeight * s;
1004
+ if (i.some(({ x: t, y: n }) => t <= c || t >= e.sourceWidth - c || n <= l || n >= e.sourceHeight - l)) return {
1005
+ hint: "Move farther away",
1006
+ reason: "move-farther-away",
1007
+ fillRatio: o,
1008
+ fill: a,
1009
+ readyForAutoCapture: !1
1010
+ };
1011
+ let [u, d, f, p] = i, m = Z(u, d), h = Z(d, f), g = Z(f, p), _ = Z(p, u);
1012
+ return Math.min(Math.min(m, g) / Math.max(1, Math.max(m, g)), Math.min(_, h) / Math.max(1, Math.max(_, h))) < (t.previouslyReady ? n.exitMinPerspectiveRatio ?? .4 : n.minPerspectiveRatio ?? .48) ? {
1013
+ hint: "Hold the camera straight",
1014
+ reason: "straighten-camera",
1015
+ fillRatio: o,
1016
+ fill: a,
1017
+ readyForAutoCapture: !1
1018
+ } : o < Pe(a, t.previouslyReady === !0, s, n) ? {
1019
+ hint: "Move closer",
1020
+ reason: "move-closer",
1021
+ fillRatio: o,
1022
+ fill: a,
1023
+ readyForAutoCapture: !1
1024
+ } : {
1025
+ hint: "Hold still",
1026
+ reason: t.ready ? "ready" : "hold-still",
1027
+ fillRatio: o,
1028
+ fill: a,
1029
+ readyForAutoCapture: t.ready
1030
+ };
1031
+ }
1032
+ var $ = class {
1033
+ previous;
1034
+ count = 0;
1035
+ ready = !1;
1036
+ options;
1037
+ constructor(e) {
1038
+ this.options = e;
1039
+ }
1040
+ reset() {
1041
+ this.previous = void 0, this.count = 0, this.ready = !1;
1042
+ }
1043
+ update(e) {
1044
+ if (e.status !== "success" || !e.quad || e.confidence < this.options.confidenceThreshold) return this.reset(), {
1045
+ stableFrames: 0,
1046
+ ready: !1,
1047
+ movement: Infinity
1048
+ };
1049
+ let t = Math.hypot(e.sourceWidth, e.sourceHeight), n = this.previous ? Math.max(...X(e.quad).map((e, n) => {
1050
+ let r = X(this.previous)[n];
1051
+ return Math.hypot(e.x - r.x, e.y - r.y) / Math.max(1, t);
1052
+ })) : Infinity, r = this.options.exitCornerTolerance ?? Math.max(this.options.cornerTolerance, .036);
1053
+ return this.ready && this.previous && n <= r ? this.count = Math.max(this.options.stableFrames, this.count + 1) : (this.ready = !1, this.count = this.previous && n <= this.options.cornerTolerance ? this.count + 1 : 1, this.count >= this.options.stableFrames && (this.ready = !0)), this.previous = e.quad, {
1054
+ stableFrames: this.count,
1055
+ ready: this.ready,
1056
+ movement: n
1057
+ };
1058
+ }
1059
+ };
1060
+ function Ie(e, n) {
1061
+ let r = Math.min(1, n / Math.max(e.width, e.height)), i = document.createElement("canvas");
1062
+ i.width = Math.max(1, Math.round(e.width * r)), i.height = Math.max(1, Math.round(e.height * r));
1063
+ let a = i.getContext("2d");
1064
+ if (!a) throw t();
1065
+ return a.drawImage(e, 0, 0, i.width, i.height), i;
1066
+ }
1067
+ function Le() {
1068
+ let e = window.AudioContext ?? window.webkitAudioContext;
1069
+ if (!e) return;
1070
+ let t = new e(), n = Math.round(t.sampleRate * .09), r = t.createBuffer(1, n, t.sampleRate), i = r.getChannelData(0);
1071
+ for (let e = 0; e < n; e += 1) {
1072
+ let n = Math.exp(-e / (t.sampleRate * .018));
1073
+ i[e] = (Math.random() * 2 - 1) * n;
1074
+ }
1075
+ let a = t.createBufferSource(), o = t.createBiquadFilter(), s = t.createGain();
1076
+ o.type = "bandpass", o.frequency.value = 1400, s.gain.value = .42, a.buffer = r, a.connect(o).connect(s).connect(t.destination), a.start(), a.onended = () => void t.close();
1077
+ }
1078
+ async function Re(e) {
1079
+ let t = document.createElement("video");
1080
+ return t.muted = !0, t.autoplay = !0, t.playsInline = !0, t.srcObject = e, await t.play(), t;
1081
+ }
1082
+ async function ze(t) {
1083
+ await x("scan");
1084
+ let n = Y(t.autoCapture), r = new $({
1085
+ stableFrames: t.stableFrames ?? 4,
1086
+ confidenceThreshold: t.confidenceThreshold ?? .72,
1087
+ cornerTolerance: t.cornerTolerance ?? .024,
1088
+ exitCornerTolerance: t.exitCornerTolerance ?? .036
1089
+ }), i = t.maxFrameDimension ?? 1600, a = t.intervalMs ?? 140, o = {
1090
+ minDimension: 220,
1091
+ maxAnalysisDimension: 520,
1092
+ ...t.detection
1093
+ }, s = typeof MediaStream < "u" && t.source instanceof MediaStream ? await Re(t.source) : t.source, c = !0, l = !1, u = !1, d = 0, f, p = {
1094
+ state: "detecting",
1095
+ confidence: 0,
1096
+ guidance: {
1097
+ hint: "Place the document in the frame",
1098
+ reason: "place-document",
1099
+ fillRatio: 0,
1100
+ fill: Q,
1101
+ readyForAutoCapture: !1
1102
+ },
1103
+ lighting: {
1104
+ castShadow: !1,
1105
+ strength: 0
1106
+ },
1107
+ stableFrames: 0,
1108
+ requiredStableFrames: t.stableFrames ?? 4,
1109
+ autoCapture: { ...n }
1110
+ }, m = () => s instanceof HTMLCanvasElement ? Ie(s, i) : q(s, i), h = (e) => {
1111
+ p = e, t.onStatus?.(e);
1112
+ }, g = () => {
1113
+ c = !1, window.clearTimeout(d), s instanceof HTMLVideoElement && s !== t.source && (s.srcObject = null);
1114
+ }, _ = async (e = "manual") => {
1115
+ if (l) throw Error("A finder capture is already in progress.");
1116
+ l = !0;
1117
+ let n;
1118
+ try {
1119
+ n = await je(t.captureFrame ?? m, () => {
1120
+ h({
1121
+ ...p,
1122
+ state: "captured"
1123
+ }), t.playShutterSound !== !1 && Le(), g();
1124
+ });
1125
+ } catch (e) {
1126
+ throw l = !1, e instanceof Error ? e : /* @__PURE__ */ Error("The camera frame could not be captured.");
1127
+ }
1128
+ let r = {
1129
+ frame: n,
1130
+ detection: f,
1131
+ reason: e
1132
+ };
1133
+ return await t.onCapture?.(r), r;
1134
+ }, v = async () => {
1135
+ if (c && !l) {
1136
+ try {
1137
+ let e = m(), i = await z(e, o);
1138
+ f = i;
1139
+ let a = i.quad ? ke(e, i.quad) : {
1140
+ strong: !1,
1141
+ strength: 0
1142
+ }, s = a.strong ? {
1143
+ castShadow: !0,
1144
+ strength: a.strength,
1145
+ hint: "Tilt to move the shadow off the page"
1146
+ } : {
1147
+ castShadow: !1,
1148
+ strength: a.strength
1149
+ }, c = r.update(i), l = Fe(i, {
1150
+ ...c,
1151
+ previouslyReady: u
1152
+ }, {
1153
+ confidenceThreshold: t.confidenceThreshold ?? .72,
1154
+ ...t.guidance
1155
+ });
1156
+ u = l.readyForAutoCapture;
1157
+ let d = i.status !== "success" || l.reason === "place-document" ? "seeking" : l.readyForAutoCapture ? "ready" : "unstable";
1158
+ if (h({
1159
+ state: d,
1160
+ confidence: i.confidence,
1161
+ quad: i.quad,
1162
+ guidance: l,
1163
+ lighting: s,
1164
+ stableFrames: c.stableFrames,
1165
+ requiredStableFrames: p.requiredStableFrames,
1166
+ autoCapture: { ...n },
1167
+ sourceWidth: i.sourceWidth,
1168
+ sourceHeight: i.sourceHeight,
1169
+ detector: i.detector,
1170
+ modelStatus: i.modelStatus,
1171
+ modelProvider: i.modelProvider,
1172
+ modelError: i.modelError,
1173
+ inferenceMs: i.inferenceMs
1174
+ }), l.readyForAutoCapture && n.checked) try {
1175
+ await _("auto");
1176
+ return;
1177
+ } catch (e) {
1178
+ r.reset(), u = !1, t.onCaptureError?.(e instanceof Error ? e : /* @__PURE__ */ Error("Automatic capture failed."));
1179
+ }
1180
+ } catch (t) {
1181
+ r.reset(), u = !1;
1182
+ let i = t instanceof e ? {
1183
+ detector: "ml",
1184
+ modelStatus: "failed",
1185
+ modelError: t.message
1186
+ } : {};
1187
+ h({
1188
+ state: "seeking",
1189
+ confidence: 0,
1190
+ guidance: {
1191
+ hint: "Place the document in the frame",
1192
+ reason: "place-document",
1193
+ fillRatio: 0,
1194
+ fill: Q,
1195
+ readyForAutoCapture: !1
1196
+ },
1197
+ lighting: {
1198
+ castShadow: !1,
1199
+ strength: 0
1200
+ },
1201
+ stableFrames: 0,
1202
+ requiredStableFrames: p.requiredStableFrames,
1203
+ autoCapture: { ...n },
1204
+ ...i
1205
+ });
1206
+ }
1207
+ c && (d = window.setTimeout(() => void v(), a));
1208
+ }
1209
+ };
1210
+ return t.onStatus?.(p), v(), {
1211
+ stop: g,
1212
+ capture: () => _("manual"),
1213
+ setAutoCapture(e) {
1214
+ return !n.mutable || l ? !1 : (n.checked = e, h({
1215
+ ...p,
1216
+ autoCapture: { ...n }
1217
+ }), !0);
1218
+ },
1219
+ getStatus: () => p
1220
+ };
1221
+ }
1222
+ //#endregion
1223
+ export { o as A, j as C, A as D, le as E, t as F, b as M, y as N, ne as O, e as P, z as S, ce as T, K as _, Fe as a, ue as b, J as c, ye as d, q as f, W as g, be as h, Ne as i, x as j, a as k, De as l, ve as m, Y as n, Ae as o, V as p, Pe as r, ze as s, $ as t, H as u, Te as v, _e as w, ge as x, U as y };
1224
+
1225
+ //# sourceMappingURL=finder-DFueuWuS.js.map