kordoc 4.24.16 → 4.24.17

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 (133) hide show
  1. package/README.md +4 -4
  2. package/dist/{-ZKOPHIGY.js → -EM3WKYYH.js} +12 -12
  3. package/dist/{chunk-QJA3KGRP.js → chunk-2YCBFGMT.js} +2 -2
  4. package/dist/{chunk-NUQ5B2ZM.js → chunk-3W4ZOEL3.js} +3 -3
  5. package/dist/{chunk-X2SPQOI7.cjs → chunk-4JQO5D7Y.cjs} +261 -98
  6. package/dist/chunk-4JQO5D7Y.cjs.map +1 -0
  7. package/dist/{chunk-2UXGDAWQ.js → chunk-4LGYS5MV.js} +2 -2
  8. package/dist/{chunk-SR6DJBPM.cjs → chunk-6SITJI2W.cjs} +67 -29
  9. package/dist/chunk-6SITJI2W.cjs.map +1 -0
  10. package/dist/{chunk-DH564VPR.js → chunk-7X4BNPDR.js} +2 -2
  11. package/dist/{chunk-DH564VPR.js.map → chunk-7X4BNPDR.js.map} +1 -1
  12. package/dist/{chunk-NVOB6OHS.cjs → chunk-AYYPVST4.cjs} +2 -2
  13. package/dist/{chunk-NVOB6OHS.cjs.map → chunk-AYYPVST4.cjs.map} +1 -1
  14. package/dist/{chunk-FK7KGS5D.js → chunk-BX7VJQ4K.js} +2 -2
  15. package/dist/{chunk-S2VWNC2W.js → chunk-CQ2SQZU5.js} +3 -3
  16. package/dist/{chunk-6KELCESN.js → chunk-DG3BK3CA.js} +45 -7
  17. package/dist/chunk-DG3BK3CA.js.map +1 -0
  18. package/dist/{chunk-BHY2QAPM.js → chunk-DQDDQ7IH.js} +12 -12
  19. package/dist/{chunk-K3OLWLXH.js → chunk-FKAXXCRA.js} +4 -4
  20. package/dist/{chunk-K3OLWLXH.js.map → chunk-FKAXXCRA.js.map} +1 -1
  21. package/dist/{chunk-V5R3PJQH.js → chunk-HX556OPI.js} +2 -2
  22. package/dist/{chunk-GPZMU2CM.cjs → chunk-I4QRLAX7.cjs} +3 -3
  23. package/dist/{chunk-GPZMU2CM.cjs.map → chunk-I4QRLAX7.cjs.map} +1 -1
  24. package/dist/{chunk-JS5CL2ZI.js → chunk-ILPVBF4G.js} +179 -16
  25. package/dist/chunk-ILPVBF4G.js.map +1 -0
  26. package/dist/{chunk-BYMPPVT3.js → chunk-IQJKLIJV.js} +3 -3
  27. package/dist/chunk-IQJKLIJV.js.map +1 -0
  28. package/dist/{chunk-CCH6BUNI.cjs → chunk-ISHFQDFZ.cjs} +8 -8
  29. package/dist/{chunk-CCH6BUNI.cjs.map → chunk-ISHFQDFZ.cjs.map} +1 -1
  30. package/dist/{chunk-LPNWTWOQ.js → chunk-JLA752YE.js} +2 -2
  31. package/dist/{chunk-3TXAIEXL.js → chunk-KUTKDE4Z.js} +180 -17
  32. package/dist/chunk-KUTKDE4Z.js.map +1 -0
  33. package/dist/{chunk-UCEGWDWX.js → chunk-MHZLOPOO.js} +6 -6
  34. package/dist/{chunk-6PPVAQ2N.js → chunk-NIKO5MNS.js} +2 -2
  35. package/dist/{chunk-J5M5OW4S.js → chunk-O7YE4N45.js} +12 -3
  36. package/dist/chunk-O7YE4N45.js.map +1 -0
  37. package/dist/{chunk-GYVSGOQW.js → chunk-OOD7R4UR.js} +2 -2
  38. package/dist/{chunk-NS2F4DXC.cjs → chunk-PQR5Q2CN.cjs} +3 -3
  39. package/dist/{chunk-NS2F4DXC.cjs.map → chunk-PQR5Q2CN.cjs.map} +1 -1
  40. package/dist/{chunk-QOMLSZLM.js → chunk-QEOKQ5XD.js} +2 -2
  41. package/dist/{chunk-F3VIVCIF.js → chunk-SWEGYVUL.js} +2 -2
  42. package/dist/{chunk-TSCQDCAR.js → chunk-URA7A4PT.js} +2 -2
  43. package/dist/{chunk-VAMCM435.js → chunk-X2AVHAPM.js} +2 -2
  44. package/dist/{chunk-5Y7E5VTW.js → chunk-XNEITV3L.js} +2 -2
  45. package/dist/{chunk-6K2SYTNJ.js → chunk-Y43Y4KJC.js} +35 -5
  46. package/dist/chunk-Y43Y4KJC.js.map +1 -0
  47. package/dist/chunks-KB7TWL43.js +10 -0
  48. package/dist/cli.js +33 -33
  49. package/dist/cli.js.map +1 -1
  50. package/dist/{formula-KZWH4YUD.cjs → formula-AAVTR32F.cjs} +9 -9
  51. package/dist/{formula-KZWH4YUD.cjs.map → formula-AAVTR32F.cjs.map} +1 -1
  52. package/dist/{formula-4C7ADOLE.js → formula-BHBMDZLT.js} +4 -4
  53. package/dist/{formula-4Y7UWTEG.js → formula-XOF7RB5O.js} +3 -3
  54. package/dist/{image-ocr-AEX2L326.js → image-ocr-FUDCRQ77.js} +10 -10
  55. package/dist/{image-ocr-ASLUPAQG.js → image-ocr-GQFTBSR5.js} +6 -6
  56. package/dist/{image-ocr-GT3NILUJ.cjs → image-ocr-KRKCFP2H.cjs} +17 -17
  57. package/dist/{image-ocr-GT3NILUJ.cjs.map → image-ocr-KRKCFP2H.cjs.map} +1 -1
  58. package/dist/index.cjs +360 -360
  59. package/dist/index.d.cts +3 -2
  60. package/dist/index.d.ts +3 -2
  61. package/dist/index.js +6 -6
  62. package/dist/mcp.js +25 -25
  63. package/dist/mcp.js.map +1 -1
  64. package/dist/{model-bundle-2TXD77HN.js → model-bundle-636BXOZX.js} +5 -5
  65. package/dist/{models-WRJKLZA6.js → models-X7KSG5YH.js} +7 -5
  66. package/dist/{parse-worker-v2-C2GR62SO.js → parse-worker-v2-K4DOWRRE.js} +14 -14
  67. package/dist/parse-worker-v2-K4DOWRRE.js.map +1 -0
  68. package/dist/{parser-5R34V6PS.cjs → parser-JG5TDHTN.cjs} +159 -159
  69. package/dist/{parser-5R34V6PS.cjs.map → parser-JG5TDHTN.cjs.map} +1 -1
  70. package/dist/{parser-GFZILOKI.js → parser-TKVE62OM.js} +13 -13
  71. package/dist/{parser-LU7BIHXD.js → parser-ZS6ZYKFT.js} +9 -9
  72. package/dist/pdf-ocr-JJTEVY6C.cjs +35 -0
  73. package/dist/{pdf-ocr-QRBPEPOZ.cjs.map → pdf-ocr-JJTEVY6C.cjs.map} +1 -1
  74. package/dist/{pdf-ocr-VNK6UIS2.js → pdf-ocr-PJO3UIZQ.js} +10 -10
  75. package/dist/{pdf-ocr-U2ZRNQD4.js → pdf-ocr-R4BKOKOV.js} +6 -6
  76. package/dist/{profile-io-J3IWFBCM.js → profile-io-6DC7KBGZ.js} +3 -3
  77. package/dist/{rasterize-23MJWOUQ.js → rasterize-CXMAQVBK.js} +3 -3
  78. package/dist/{redact-doc-GGCEGT74.js → redact-doc-3GGPUJT7.js} +12 -12
  79. package/dist/{render-M2UAFQSI.js → render-BARUM5VX.js} +7 -7
  80. package/dist/seal-NR6HNFHD.js +10 -0
  81. package/dist/{setup-D7JWID23.js → setup-ZTF5QCXL.js} +3 -3
  82. package/dist/visual-H5Z72EB2.js +21 -0
  83. package/dist/{watch-E2XCUIA5.js → watch-WJWZLQDF.js} +13 -13
  84. package/package.json +1 -1
  85. package/dist/chunk-3TXAIEXL.js.map +0 -1
  86. package/dist/chunk-6K2SYTNJ.js.map +0 -1
  87. package/dist/chunk-6KELCESN.js.map +0 -1
  88. package/dist/chunk-BYMPPVT3.js.map +0 -1
  89. package/dist/chunk-J5M5OW4S.js.map +0 -1
  90. package/dist/chunk-JS5CL2ZI.js.map +0 -1
  91. package/dist/chunk-SR6DJBPM.cjs.map +0 -1
  92. package/dist/chunk-X2SPQOI7.cjs.map +0 -1
  93. package/dist/chunks-BHTYFFI2.js +0 -10
  94. package/dist/parse-worker-v2-C2GR62SO.js.map +0 -1
  95. package/dist/pdf-ocr-QRBPEPOZ.cjs +0 -35
  96. package/dist/seal-EHZTTMNE.js +0 -10
  97. package/dist/visual-2ZLXZ5NN.js +0 -21
  98. /package/dist/{-ZKOPHIGY.js.map → -EM3WKYYH.js.map} +0 -0
  99. /package/dist/{chunk-QJA3KGRP.js.map → chunk-2YCBFGMT.js.map} +0 -0
  100. /package/dist/{chunk-NUQ5B2ZM.js.map → chunk-3W4ZOEL3.js.map} +0 -0
  101. /package/dist/{chunk-2UXGDAWQ.js.map → chunk-4LGYS5MV.js.map} +0 -0
  102. /package/dist/{chunk-FK7KGS5D.js.map → chunk-BX7VJQ4K.js.map} +0 -0
  103. /package/dist/{chunk-S2VWNC2W.js.map → chunk-CQ2SQZU5.js.map} +0 -0
  104. /package/dist/{chunk-BHY2QAPM.js.map → chunk-DQDDQ7IH.js.map} +0 -0
  105. /package/dist/{chunk-V5R3PJQH.js.map → chunk-HX556OPI.js.map} +0 -0
  106. /package/dist/{chunk-LPNWTWOQ.js.map → chunk-JLA752YE.js.map} +0 -0
  107. /package/dist/{chunk-UCEGWDWX.js.map → chunk-MHZLOPOO.js.map} +0 -0
  108. /package/dist/{chunk-6PPVAQ2N.js.map → chunk-NIKO5MNS.js.map} +0 -0
  109. /package/dist/{chunk-GYVSGOQW.js.map → chunk-OOD7R4UR.js.map} +0 -0
  110. /package/dist/{chunk-QOMLSZLM.js.map → chunk-QEOKQ5XD.js.map} +0 -0
  111. /package/dist/{chunk-F3VIVCIF.js.map → chunk-SWEGYVUL.js.map} +0 -0
  112. /package/dist/{chunk-TSCQDCAR.js.map → chunk-URA7A4PT.js.map} +0 -0
  113. /package/dist/{chunk-VAMCM435.js.map → chunk-X2AVHAPM.js.map} +0 -0
  114. /package/dist/{chunk-5Y7E5VTW.js.map → chunk-XNEITV3L.js.map} +0 -0
  115. /package/dist/{chunks-BHTYFFI2.js.map → chunks-KB7TWL43.js.map} +0 -0
  116. /package/dist/{formula-4C7ADOLE.js.map → formula-BHBMDZLT.js.map} +0 -0
  117. /package/dist/{formula-4Y7UWTEG.js.map → formula-XOF7RB5O.js.map} +0 -0
  118. /package/dist/{image-ocr-AEX2L326.js.map → image-ocr-FUDCRQ77.js.map} +0 -0
  119. /package/dist/{image-ocr-ASLUPAQG.js.map → image-ocr-GQFTBSR5.js.map} +0 -0
  120. /package/dist/{model-bundle-2TXD77HN.js.map → model-bundle-636BXOZX.js.map} +0 -0
  121. /package/dist/{models-WRJKLZA6.js.map → models-X7KSG5YH.js.map} +0 -0
  122. /package/dist/{parser-GFZILOKI.js.map → parser-TKVE62OM.js.map} +0 -0
  123. /package/dist/{parser-LU7BIHXD.js.map → parser-ZS6ZYKFT.js.map} +0 -0
  124. /package/dist/{pdf-ocr-U2ZRNQD4.js.map → pdf-ocr-PJO3UIZQ.js.map} +0 -0
  125. /package/dist/{pdf-ocr-VNK6UIS2.js.map → pdf-ocr-R4BKOKOV.js.map} +0 -0
  126. /package/dist/{profile-io-J3IWFBCM.js.map → profile-io-6DC7KBGZ.js.map} +0 -0
  127. /package/dist/{rasterize-23MJWOUQ.js.map → rasterize-CXMAQVBK.js.map} +0 -0
  128. /package/dist/{redact-doc-GGCEGT74.js.map → redact-doc-3GGPUJT7.js.map} +0 -0
  129. /package/dist/{render-M2UAFQSI.js.map → render-BARUM5VX.js.map} +0 -0
  130. /package/dist/{seal-EHZTTMNE.js.map → seal-NR6HNFHD.js.map} +0 -0
  131. /package/dist/{setup-D7JWID23.js.map → setup-ZTF5QCXL.js.map} +0 -0
  132. /package/dist/{visual-2ZLXZ5NN.js.map → visual-H5Z72EB2.js.map} +0 -0
  133. /package/dist/{watch-E2XCUIA5.js.map → watch-WJWZLQDF.js.map} +0 -0
@@ -35,14 +35,15 @@ var _chunkTK3FDAEEcjs = require('./chunk-TK3FDAEE.cjs');
35
35
 
36
36
 
37
37
 
38
- var _chunkSR6DJBPMcjs = require('./chunk-SR6DJBPM.cjs');
39
38
 
39
+ var _chunk6SITJI2Wcjs = require('./chunk-6SITJI2W.cjs');
40
40
 
41
- var _chunkCCH6BUNIcjs = require('./chunk-CCH6BUNI.cjs');
42
41
 
42
+ var _chunkISHFQDFZcjs = require('./chunk-ISHFQDFZ.cjs');
43
43
 
44
44
 
45
- var _chunkNVOB6OHScjs = require('./chunk-NVOB6OHS.cjs');
45
+
46
+ var _chunkAYYPVST4cjs = require('./chunk-AYYPVST4.cjs');
46
47
 
47
48
  // src/ocr/ruling-lines.ts
48
49
  var INK_LUMA_MAX = 205;
@@ -389,8 +390,8 @@ var INKLESS_DELTA = 32;
389
390
  function restoreGlyphs(rgba, pageW, box, text, steps, stepPx, note = {}) {
390
391
  const chars = [...text];
391
392
  if (chars.length !== steps.length) return text;
392
- const gray = _chunkSR6DJBPMcjs.grayCrop.call(void 0, rgba, pageW, box);
393
- const c = { chars, cx: (i) => (steps[i] + 0.5) * stepPx, gray, w: box.w, h: box.h, ink: _chunkSR6DJBPMcjs.inkStats.call(void 0, gray) };
393
+ const gray = _chunk6SITJI2Wcjs.grayCrop.call(void 0, rgba, pageW, box);
394
+ const c = { chars, cx: (i) => (steps[i] + 0.5) * stepPx, gray, w: box.w, h: box.h, ink: _chunk6SITJI2Wcjs.inkStats.call(void 0, gray) };
394
395
  if (/[[\]]/.test(text)) brackets(c);
395
396
  if (text.includes("'")) cornerQuotes(c);
396
397
  if (/['"]/.test(text)) quotes(c);
@@ -401,13 +402,14 @@ function restoreGlyphs(rgba, pageW, box, text, steps, stepPx, note = {}) {
401
402
  gaps(c);
402
403
  if (chars.some((t) => t.includes("\u300C")) && chars.includes(",")) cornerCommas(c);
403
404
  note.ringLead = ring(c);
405
+ if (/[I|]/.test(text)) parallels(c);
404
406
  if (/[I1Ⅰ-Ⅲ|]|^\s*\./.test(text)) roman(c);
405
407
  return chars.join("");
406
408
  }
407
409
  function trimInklessEnds(rgba, pageW, box, text, steps, stepPx) {
408
410
  const chars = [...text], { w, h } = box;
409
411
  if (chars.length !== steps.length || steps.some((s) => (s + 0.5) * stepPx > w + stepPx)) return { text, steps };
410
- const gray = _chunkSR6DJBPMcjs.grayCrop.call(void 0, rgba, pageW, box);
412
+ const gray = _chunk6SITJI2Wcjs.grayCrop.call(void 0, rgba, pageW, box);
411
413
  const hist = new Uint32Array(256);
412
414
  for (const v of gray) hist[v]++;
413
415
  let bg = 0;
@@ -438,8 +440,8 @@ function cornerCommas({ chars, cx, gray, w, h, ink }) {
438
440
  continue;
439
441
  }
440
442
  if (open > 0) {
441
- const f = _chunkSR6DJBPMcjs.bracketFeatures.call(void 0, gray, w, h, ink, cx(i));
442
- if (f && _chunkSR6DJBPMcjs.bracketShape.call(void 0, f, true) === "\u300D") {
443
+ const f = _chunk6SITJI2Wcjs.bracketFeatures.call(void 0, gray, w, h, ink, cx(i));
444
+ if (f && _chunk6SITJI2Wcjs.bracketShape.call(void 0, f, true) === "\u300D") {
443
445
  chars[i] = "\u300D";
444
446
  open--;
445
447
  }
@@ -449,23 +451,34 @@ function cornerCommas({ chars, cx, gray, w, h, ink }) {
449
451
  function cornerQuotes({ chars, cx, gray, w, h, ink }) {
450
452
  for (let i = 0; i < chars.length; i++) {
451
453
  if (chars[i] !== "'" || !/^[가-힣]/.test(_nullishCoalesce(chars[i + 1], () => ( "")))) continue;
452
- const f = _chunkSR6DJBPMcjs.bracketFeatures.call(void 0, gray, w, h, ink, cx(i));
453
- if (!f || f.ch < f.charH * 0.45 || _chunkSR6DJBPMcjs.bracketShape.call(void 0, f, false) !== "\u300C") continue;
454
+ const f = _chunk6SITJI2Wcjs.bracketFeatures.call(void 0, gray, w, h, ink, cx(i));
455
+ if (!f || f.ch < f.charH * 0.45 || _chunk6SITJI2Wcjs.bracketShape.call(void 0, f, false) !== "\u300C") continue;
454
456
  const rest = chars.slice(i + 1), end = rest.findIndex((c) => c === "'" || c === "\u300D" || c === ",");
455
457
  const pair = end >= 0 && rest[end] !== "'" && (rest[end] === "\u300D" || (() => {
456
- const g = _chunkSR6DJBPMcjs.bracketFeatures.call(void 0, gray, w, h, ink, cx(i + 1 + end));
457
- return !!g && _chunkSR6DJBPMcjs.bracketShape.call(void 0, g, true) === "\u300D";
458
+ const g = _chunk6SITJI2Wcjs.bracketFeatures.call(void 0, gray, w, h, ink, cx(i + 1 + end));
459
+ return !!g && _chunk6SITJI2Wcjs.bracketShape.call(void 0, g, true) === "\u300D";
458
460
  })());
459
461
  if (pair) chars[i] = "\u300C";
460
462
  }
461
463
  }
462
464
  function brackets({ chars, cx, gray, w, h, ink }) {
465
+ const shape = chars.map((c, i) => {
466
+ if (c !== "[" && c !== "]") return null;
467
+ const f = _chunk6SITJI2Wcjs.bracketFeatures.call(void 0, gray, w, h, ink, cx(i));
468
+ return f && _chunk6SITJI2Wcjs.bracketShape.call(void 0, f, c === "]");
469
+ });
463
470
  for (let i = 0; i < chars.length; i++) {
464
- if (chars[i] !== "[" && chars[i] !== "]") continue;
465
- const f = _chunkSR6DJBPMcjs.bracketFeatures.call(void 0, gray, w, h, ink, cx(i));
466
- const shape = f && _chunkSR6DJBPMcjs.bracketShape.call(void 0, f, chars[i] === "]");
467
- if (shape) chars[i] = shape;
471
+ if (chars[i] !== "[") continue;
472
+ const j = chars.findIndex((c, k) => k > i && (c === "[" || c === "]"));
473
+ if (j < 0 || chars[j] !== "]") continue;
474
+ const a = shape[i], b = shape[j];
475
+ const opens = a === "\u3010" || a === "(" || a === "\u3014", closes = b === "\u3011" || b === ")" || b === "\u3015";
476
+ if ((opens || closes) && (!a || !b)) {
477
+ if (opens) shape[i] = null;
478
+ if (closes) shape[j] = null;
479
+ }
468
480
  }
481
+ for (let i = 0; i < chars.length; i++) if (shape[i]) chars[i] = shape[i];
469
482
  }
470
483
  function quotes({ chars, cx, gray, w, h, ink }) {
471
484
  const year = (i) => chars[i] === "'" && !/[\p{L}\p{N}]/u.test(_nullishCoalesce(chars[i - 1], () => ( ""))) && /^\d{2}(?!\d)/.test(chars.slice(i + 1, i + 4).join(""));
@@ -484,7 +497,7 @@ function quotes({ chars, cx, gray, w, h, ink }) {
484
497
  continue;
485
498
  }
486
499
  if (!year(i) && !single[kind]) continue;
487
- const r = _chunkSR6DJBPMcjs.quoteHead.call(void 0, gray, w, h, ink, cx(i));
500
+ const r = _chunk6SITJI2Wcjs.quoteHead.call(void 0, gray, w, h, ink, cx(i));
488
501
  if (r !== null && r >= 0.47) {
489
502
  chars[i] = kind === "'" ? "\u2018" : "\u201C";
490
503
  open[kind] = true;
@@ -495,7 +508,7 @@ function dashes({ chars, cx, gray, w, h, ink }) {
495
508
  const head = chars.findIndex((c) => c.trim()), letters = chars.some((c) => /[가-힣A-Za-z]/.test(c));
496
509
  for (let i = 0; i < chars.length; i++) {
497
510
  if (!/^[-\u2013\u2014]$/.test(chars[i])) continue;
498
- const r = _chunkSR6DJBPMcjs.dashRatio.call(void 0, gray, w, h, ink, cx(i));
511
+ const r = _chunk6SITJI2Wcjs.dashRatio.call(void 0, gray, w, h, ink, cx(i));
499
512
  if (r === null) continue;
500
513
  if (r < 0.65) chars[i] = "-";
501
514
  else if (r > 0.75 && i === head && letters) chars[i] = "\u2014";
@@ -504,7 +517,7 @@ function dashes({ chars, cx, gray, w, h, ink }) {
504
517
  function circled({ chars, cx, gray, w, h, ink }) {
505
518
  const at = chars.flatMap((c, i) => /^[1-9]$/.test(c) && !/\d/.test(_nullishCoalesce(chars[i - 1], () => ( ""))) && !/\d/.test(_nullishCoalesce(chars[i + 1], () => ( ""))) ? [i] : []);
506
519
  if (!at.length) return;
507
- const hit = _chunkSR6DJBPMcjs.circledAt.call(void 0, gray, w, h, ink, at.map(cx));
520
+ const hit = _chunk6SITJI2Wcjs.circledAt.call(void 0, gray, w, h, ink, at.map(cx));
508
521
  at.forEach((i, k) => {
509
522
  if (hit[k]) chars[i] = String.fromCharCode(9311 + Number(chars[i]));
510
523
  });
@@ -514,16 +527,16 @@ function stars({ chars, cx, gray, w, h, ink }) {
514
527
  if (chars[i] !== "*" || chars[i - 1] === "*") continue;
515
528
  let e = i;
516
529
  while (chars[e + 1] === "*") e++;
517
- const n = _chunkSR6DJBPMcjs.starRun.call(void 0, gray, w, h, ink, cx(i));
530
+ const n = _chunk6SITJI2Wcjs.starRun.call(void 0, gray, w, h, ink, cx(i));
518
531
  if (n > e - i + 1 && n <= 4) chars[e] += "*".repeat(n - (e - i + 1));
519
532
  i = e;
520
533
  }
521
534
  }
522
535
  function discs({ chars, cx, gray, w, h, ink }) {
523
- for (let i = 0; i < chars.length; i++) if (/^[\u00b7\u2022]$/.test(chars[i]) && _chunkSR6DJBPMcjs.discAt.call(void 0, gray, w, h, ink, cx(i))) chars[i] = "\u25CF";
536
+ for (let i = 0; i < chars.length; i++) if (/^[\u00b7\u2022]$/.test(chars[i]) && _chunk6SITJI2Wcjs.discAt.call(void 0, gray, w, h, ink, cx(i))) chars[i] = "\u25CF";
524
537
  }
525
538
  function gaps({ chars, cx, gray, w, h, ink }) {
526
- const { glyphs, bandH } = _chunkSR6DJBPMcjs.gapGlyphs.call(void 0, gray, w, h, ink);
539
+ const { glyphs, bandH } = _chunk6SITJI2Wcjs.gapGlyphs.call(void 0, gray, w, h, ink);
527
540
  if (!glyphs.length) return;
528
541
  const live = chars.map((c, i) => i).filter((i) => chars[i].trim());
529
542
  if (!live.length) return;
@@ -594,27 +607,47 @@ function ring({ chars, cx, gray, w, h, ink }) {
594
607
  const rest = chars.slice(k + 1).join("").trimStart();
595
608
  const live = chars.map((c, i) => i).filter((i) => chars[i].trim());
596
609
  if (live.length <= 3 && live.every((i) => /^[Oo]$/.test(chars[i]))) {
597
- if (_optionalChain([_chunkSR6DJBPMcjs.leadingBullet.call(void 0, gray, w, h, ink, cx(live[0])), 'optionalAccess', _5 => _5.mark]) === "\u25CE") return false;
598
- if (!live.every((i) => _chunkSR6DJBPMcjs.ringBullet.call(void 0, gray, w, h, ink, cx(i)) === "\u25CB")) return false;
610
+ if (_optionalChain([_chunk6SITJI2Wcjs.leadingBullet.call(void 0, gray, w, h, ink, cx(live[0])), 'optionalAccess', _5 => _5.mark]) === "\u25CE") return false;
611
+ if (!live.every((i) => _chunk6SITJI2Wcjs.ringBullet.call(void 0, gray, w, h, ink, cx(i)) === "\u25CB")) return false;
599
612
  for (const i of live) chars[i] = "\u25CB";
600
613
  return true;
601
614
  }
602
615
  if (/^[A-Z]{2,}/.test(rest) && /^[Oo0]$/.test(chars[k])) {
603
- if (_chunkSR6DJBPMcjs.ringBullet.call(void 0, gray, w, h, ink, cx(k)) !== "\u25CB") return false;
616
+ if (_chunk6SITJI2Wcjs.ringBullet.call(void 0, gray, w, h, ink, cx(k)) !== "\u25CB") return false;
604
617
  chars[k] = chars[k + 1] === " " ? "\u25CB" : "\u25CB ";
605
618
  return true;
606
619
  }
607
620
  if (!/^[(\[「【<]?\d*[가-힣]/.test(rest)) return false;
608
- const r = _chunkSR6DJBPMcjs.ringBullet.call(void 0, gray, w, h, ink, cx(k));
621
+ const r = _chunk6SITJI2Wcjs.ringBullet.call(void 0, gray, w, h, ink, cx(k));
609
622
  if (/^[Cc]$/.test(chars[k]) && r !== "\u25CB") return false;
610
623
  if (r) chars[k] = r;
611
624
  return r !== null;
612
625
  }
626
+ function parallels({ chars, cx, gray, w, h, ink }) {
627
+ for (let s = 0; s < chars.length; ) {
628
+ if (!/^[I|]$/.test(chars[s])) {
629
+ s++;
630
+ continue;
631
+ }
632
+ let e = s;
633
+ while (e + 1 < chars.length && /^[I|]$/.test(chars[e + 1])) e++;
634
+ if (e - s <= 1 && !/[A-Za-z]/.test((_nullishCoalesce(chars[s - 1], () => ( ""))) + (_nullishCoalesce(chars[e + 1], () => ( ""))))) {
635
+ let p = s - 1, q = e + 1;
636
+ while (p >= 0 && !chars[p].trim()) p--;
637
+ while (q < chars.length && !chars[q].trim()) q++;
638
+ if (_chunk6SITJI2Wcjs.slantedPair.call(void 0, gray, w, h, ink, p >= 0 ? cx(p) : -Infinity, q < chars.length ? cx(q) : Infinity)) {
639
+ chars[s] = "\u2225";
640
+ for (let k = s + 1; k <= e; k++) chars[k] = "";
641
+ }
642
+ }
643
+ s = e + 1;
644
+ }
645
+ }
613
646
  function roman({ chars, cx, gray, w, h, ink }) {
614
647
  const ROMAN = /^[IⅠ-Ⅲ]$/, LATIN = /[A-Za-z]$/;
615
648
  for (let i = 0; i < chars.length; i++) {
616
649
  if (chars[i] !== "1" || /[\dA-Za-z]$/.test(_nullishCoalesce(chars[i - 1], () => ( ""))) || /^[\dA-Za-z,]/.test(_nullishCoalesce(chars[i + 1], () => ( "")))) continue;
617
- if (_chunkSR6DJBPMcjs.serifOne.call(void 0, gray, w, h, ink, cx(i))) chars[i] = "\u2160";
650
+ if (_chunk6SITJI2Wcjs.serifOne.call(void 0, gray, w, h, ink, cx(i))) chars[i] = "\u2160";
618
651
  }
619
652
  for (let i = 0; i < chars.length; i++) {
620
653
  const hangul = /^[파피]$/.test(chars[i]);
@@ -624,13 +657,13 @@ function roman({ chars, cx, gray, w, h, ink }) {
624
657
  while (q < chars.length && !chars[q].trim()) q++;
625
658
  const glued = hangul ? chars[p] === "(" && chars[q] === "-" : /[가-힣]$/.test(_nullishCoalesce(chars[i - 1], () => ( ""))) || (_nullishCoalesce(chars[i + 1], () => ( ""))) === "." || chars[p] === "-" && chars[q] === "-";
626
659
  if (!glued) continue;
627
- const n = _chunkSR6DJBPMcjs.romanStems.call(void 0, gray, w, h, ink, p >= 0 ? cx(p) : -Infinity, q < chars.length ? cx(q) : Infinity, /[가-힣]$/.test(_nullishCoalesce(chars[p], () => ( ""))));
660
+ const n = _chunk6SITJI2Wcjs.romanStems.call(void 0, gray, w, h, ink, p >= 0 ? cx(p) : -Infinity, q < chars.length ? cx(q) : Infinity, /[가-힣]$/.test(_nullishCoalesce(chars[p], () => ( ""))));
628
661
  if (n) chars[i] = String.fromCharCode(8543 + n);
629
662
  }
630
663
  const inRoman = (i) => ROMAN.test(chars[i]) || chars[i] === "1" && (ROMAN.test(_nullishCoalesce(chars[i - 1], () => ( ""))) || ROMAN.test(_nullishCoalesce(chars[i + 1], () => ( ""))));
631
664
  const k = chars.findIndex((c) => c.trim());
632
665
  if (chars[k] === "." && chars.slice(k + 1).some((c) => /[가-힣A-Za-z0-9]/.test(c))) {
633
- const n = _chunkSR6DJBPMcjs.romanStems.call(void 0, gray, w, h, ink, -Infinity, cx(k));
666
+ const n = _chunk6SITJI2Wcjs.romanStems.call(void 0, gray, w, h, ink, -Infinity, cx(k));
634
667
  if (n) chars[k] = String.fromCharCode(8543 + n) + chars[k];
635
668
  }
636
669
  for (let s = 0; s < chars.length; ) {
@@ -648,7 +681,7 @@ function roman({ chars, cx, gray, w, h, ink }) {
648
681
  let p = s - 1, q = e;
649
682
  while (p >= 0 && !chars[p].trim()) p--;
650
683
  while (q < chars.length && !chars[q].trim()) q++;
651
- const n = _chunkSR6DJBPMcjs.romanStems.call(void 0, gray, w, h, ink, p >= 0 ? cx(p) : -Infinity, q < chars.length ? cx(q) : Infinity, /[가-힣]$/.test(_nullishCoalesce(chars[p], () => ( ""))));
684
+ const n = _chunk6SITJI2Wcjs.romanStems.call(void 0, gray, w, h, ink, p >= 0 ? cx(p) : -Infinity, q < chars.length ? cx(q) : Infinity, /[가-힣]$/.test(_nullishCoalesce(chars[p], () => ( ""))));
652
685
  const canon = n ? [["\u2160", "I"], ["\u2161", "II"], ["\u2162", "III"]][n - 1] : null;
653
686
  if (canon && !canon.includes(tok)) {
654
687
  chars[s] = canon[0];
@@ -910,6 +943,7 @@ var REC_BATCH_MAX_PIXELS = 48 * 16e3;
910
943
  var TALL_RATIO = 1.5;
911
944
  var ROTATE_RATIO = 3;
912
945
  var KEEP_MARGIN = 0.06;
946
+ var RETRY_SCORE = 0.9;
913
947
  var LEADER_MIN_DOTS = 4;
914
948
  var LEADER_CONTEXT = 0.5;
915
949
  var MIN_INK_RATIO = 0.01;
@@ -979,10 +1013,88 @@ function rowTailBoxes(rgba, width, items) {
979
1013
  const y0 = Math.min(...row.map((o) => o.y)), y1 = Math.max(...row.map((o) => o.y + o.h)), h = y1 - y0;
980
1014
  const x0 = last.x + last.w + 4, x1 = Math.floor(width * 0.95);
981
1015
  if (x1 - x0 < h) continue;
1016
+ const groups = [];
1017
+ for (let x = x0; x < x1; x++) {
1018
+ let top = -1, bot = -1;
1019
+ for (let y = y0; y < y1; y++) if (dark(x, y)) {
1020
+ if (top < 0) top = y;
1021
+ bot = y;
1022
+ }
1023
+ if (top < 0 || bot - top + 1 < h * 0.3) continue;
1024
+ const g = groups[groups.length - 1];
1025
+ if (!g || x - g.maxX > h) groups.push({ minX: x, maxX: x, minY: top, maxY: bot });
1026
+ else {
1027
+ g.maxX = x;
1028
+ g.minY = Math.min(g.minY, top);
1029
+ g.maxY = Math.max(g.maxY, bot);
1030
+ }
1031
+ }
1032
+ const height = Math.floor(rgba.length / 4 / width);
1033
+ const rule = (g) => {
1034
+ for (let x = g.minX; x <= g.maxX; x++) if (g.minY > 1 && dark(x, g.minY - 2) || g.maxY + 2 < height && dark(x, g.maxY + 2)) return true;
1035
+ return false;
1036
+ };
1037
+ const ink = groups.filter((g) => !rule(g));
1038
+ if (ink.length !== 1) continue;
1039
+ const { minX, maxX, minY, maxY } = ink[0];
1040
+ if (maxY - minY + 1 < h * 0.5 || maxX - minX + 1 > h * 4) continue;
1041
+ const pad = 4;
1042
+ out.push({ x: Math.max(0, minX - pad), y: Math.max(0, minY - pad), w: maxX - minX + 1 + 2 * pad, h: maxY - minY + 1 + 2 * pad });
1043
+ }
1044
+ return out;
1045
+ }
1046
+ function joinGapLeaders(rgba, width, items) {
1047
+ const gone = /* @__PURE__ */ new Set();
1048
+ const sameLine = (a, b) => Math.abs(a.y + a.h / 2 - (b.y + b.h / 2)) <= Math.max(a.h, b.h) / 2;
1049
+ const junk = (o) => /^[\s.:\u00b7\u2022\u2026]+$/u.test(o.text);
1050
+ for (const num of [...items].sort((a, b) => a.x - b.x)) {
1051
+ if (gone.has(num) || !/^[\s.:\u00b7\u2026]*\d{1,4}$/u.test(num.text)) continue;
1052
+ let left = null;
1053
+ for (const o of items) if (o !== num && !gone.has(o) && !junk(o) && sameLine(o, num) && o.x + o.w <= num.x + 2 && (!left || o.x + o.w > left.x + left.w)) left = o;
1054
+ if (!left || /\u2026/.test(left.text) || !/[가-힣A-Za-z]/.test(left.text)) continue;
1055
+ const h = Math.max(left.h, num.h), g0 = left.x + left.w, g1 = num.x;
1056
+ if (g1 - g0 < h * 3) continue;
1057
+ const pad = Math.round(h * 0.25), y = Math.max(0, Math.min(left.y, num.y) - pad), x = Math.max(0, Math.round(g0 - h));
1058
+ const box = { x, y, w: Math.min(width, Math.round(g1 + h)) - x, h: Math.min(Math.floor(rgba.length / 4 / width), Math.max(left.y + left.h, num.y + num.h) + pad) - y };
1059
+ const gray = _chunk6SITJI2Wcjs.grayCrop.call(void 0, rgba, width, box);
1060
+ const runs = _chunk6SITJI2Wcjs.leaderRuns.call(void 0, gray, box.w, box.h, _chunk6SITJI2Wcjs.inkStats.call(void 0, gray), LEADER_MIN_DOTS);
1061
+ const cover = runs.reduce((k, [a, b]) => k + Math.max(0, Math.min(b, g1 - box.x) - Math.max(a, g0 - box.x)), 0);
1062
+ if (cover < (g1 - g0) * 0.6) continue;
1063
+ for (const o of items) if (junk(o) && sameLine(o, num) && o.x >= g0 - 2 && o.x + o.w <= g1 + 2) gone.add(o);
1064
+ left.text = left.text.trimEnd() + " " + num.text.replace(/^[\s.:\u00b7\u2026]+/u, "");
1065
+ const x2 = Math.max(left.x + left.w, num.x + num.w), y2 = Math.max(left.y + left.h, num.y + num.h);
1066
+ left.y = Math.min(left.y, num.y);
1067
+ left.w = x2 - left.x;
1068
+ left.h = y2 - left.y;
1069
+ left.confidence = Math.min(left.confidence, num.confidence);
1070
+ gone.add(num);
1071
+ }
1072
+ return items.filter((it) => !gone.has(it));
1073
+ }
1074
+ function rowHeadBoxes(rgba, width, items) {
1075
+ const out = [];
1076
+ const dark = (x, y) => {
1077
+ const p = (y * width + x) * 4;
1078
+ return rgba[p] * 77 + rgba[p + 1] * 150 + rgba[p + 2] * 29 >> 8 < 160;
1079
+ };
1080
+ const inBox = (x, y) => items.some((b) => x >= b.x && x < b.x + b.w && y >= b.y && y < b.y + b.h);
1081
+ const height = Math.floor(rgba.length / 4 / width);
1082
+ const done = /* @__PURE__ */ new Set();
1083
+ for (const it of items) {
1084
+ if (done.has(it) || it.h < 12) continue;
1085
+ const row = items.filter((o) => Math.min(o.y + o.h, it.y + it.h) - Math.max(o.y, it.y) >= Math.min(o.h, it.h) * 0.6);
1086
+ for (const o of row) done.add(o);
1087
+ if (row.reduce((k, o) => k + (_nullishCoalesce(_optionalChain([o, 'access', _20 => _20.text, 'access', _21 => _21.match, 'call', _22 => _22(/[가-힣]/g), 'optionalAccess', _23 => _23.length]), () => ( 0))), 0) < 2) continue;
1088
+ const first = row.reduce((m, o) => o.x < m.x ? o : m);
1089
+ if (!/^[가-힣\d]/.test(first.text)) continue;
1090
+ const hs = row.map((o) => o.h).sort((a, b) => a - b), h = hs[hs.length >> 1];
1091
+ const y0 = Math.min(...row.map((o) => o.y)), y1 = Math.max(...row.map((o) => o.y + o.h));
1092
+ const x0 = Math.max(0, Math.round(first.x - 4 * h)), x1 = first.x - 2;
1093
+ if (x1 - x0 < h) continue;
982
1094
  let groups = 0, minX = -1, maxX = -1, minY = Infinity, maxY = -1;
983
1095
  for (let x = x0; x < x1; x++) {
984
1096
  let on = false;
985
- for (let y = y0; y < y1; y++) if (dark(x, y)) {
1097
+ for (let y = y0; y < y1; y++) if (dark(x, y) && !inBox(x, y)) {
986
1098
  on = true;
987
1099
  if (y < minY) minY = y;
988
1100
  if (y > maxY) maxY = y;
@@ -994,16 +1106,36 @@ function rowTailBoxes(rgba, width, items) {
994
1106
  }
995
1107
  maxX = x;
996
1108
  }
997
- if (groups !== 1 || maxY - minY + 1 < h * 0.5 || maxX - minX + 1 > h * 4) continue;
998
- const height = Math.floor(rgba.length / 4 / width);
1109
+ if (groups !== 1 || minX <= x0 || maxY - minY + 1 < h * 0.5 || maxX - minX + 1 > h * 3) continue;
999
1110
  let rule = false;
1000
- for (let x = minX; x <= maxX && !rule; x++) rule = minY > 1 && dark(x, minY - 2) || maxY + 2 < height && dark(x, maxY + 2);
1111
+ for (let x = minX; x <= maxX && !rule; x++) rule = minY > 1 && dark(x, minY - 2) && !inBox(x, minY - 2) || maxY + 2 < height && dark(x, maxY + 2) && !inBox(x, maxY + 2);
1001
1112
  if (rule) continue;
1002
- const pad = 4;
1113
+ const pad = Math.max(4, Math.round((maxY - minY + 1) * 0.3));
1003
1114
  out.push({ x: Math.max(0, minX - pad), y: Math.max(0, minY - pad), w: maxX - minX + 1 + 2 * pad, h: maxY - minY + 1 + 2 * pad });
1004
1115
  }
1005
1116
  return out;
1006
1117
  }
1118
+ function midBlankRow(gray, w, h, ink) {
1119
+ if (h < 24) return null;
1120
+ const isInk = (v) => ink.darkInk ? v <= ink.threshold : v > ink.threshold;
1121
+ const colInk = new Uint32Array(w);
1122
+ for (let y = 0; y < h; y++) for (let x = 0; x < w; x++) if (isInk(gray[y * w + x])) colInk[x]++;
1123
+ const blank = (y) => {
1124
+ let n = 0;
1125
+ for (let x = 0; x < w; x++) if (colInk[x] < h * 0.85 && isInk(gray[y * w + x])) n++;
1126
+ return n <= Math.max(1, w * 0.02);
1127
+ };
1128
+ let best = null;
1129
+ for (let y = Math.floor(h * 0.3); y < Math.ceil(h * 0.7); y++) {
1130
+ if (!blank(y)) continue;
1131
+ let a = y, b = y + 1;
1132
+ while (a > 0 && blank(a - 1)) a--;
1133
+ while (b < h && blank(b)) b++;
1134
+ if (!best || Math.abs((a + b) / 2 - h / 2) < Math.abs((best[0] + best[1]) / 2 - h / 2)) best = [a, b];
1135
+ y = b;
1136
+ }
1137
+ return best;
1138
+ }
1007
1139
  function placeholderSquares(rgba, width, height, items) {
1008
1140
  const dark = new Uint8Array(width * height);
1009
1141
  for (let p = 0, i = 0; p < dark.length; p++, i += 4) dark[p] = rgba[i] * 77 + rgba[i + 1] * 150 + rgba[i + 2] * 29 >> 8 < 128 ? 1 : 0;
@@ -1118,7 +1250,7 @@ function closingParens(rgba, width, items) {
1118
1250
  };
1119
1251
  for (const it of items) {
1120
1252
  const t = it.text.replace(/\s+$/, "");
1121
- if ((_nullishCoalesce(_optionalChain([t, 'access', _20 => _20.match, 'call', _21 => _21(/\(/g), 'optionalAccess', _22 => _22.length]), () => ( 0))) <= (_nullishCoalesce(_optionalChain([t, 'access', _23 => _23.match, 'call', _24 => _24(/\)/g), 'optionalAccess', _25 => _25.length]), () => ( 0))) || !/\([^()]*$/.test(t)) continue;
1253
+ if ((_nullishCoalesce(_optionalChain([t, 'access', _24 => _24.match, 'call', _25 => _25(/\(/g), 'optionalAccess', _26 => _26.length]), () => ( 0))) <= (_nullishCoalesce(_optionalChain([t, 'access', _27 => _27.match, 'call', _28 => _28(/\)/g), 'optionalAccess', _29 => _29.length]), () => ( 0))) || !/\([^()]*$/.test(t)) continue;
1122
1254
  const x0 = it.x + it.w + 2;
1123
1255
  const next = items.filter((o) => o !== it && o.x >= x0 && o.y < it.y + it.h && o.y + o.h > it.y).reduce((m, o) => Math.min(m, o.x), Infinity);
1124
1256
  let x1 = Math.min(width, next, x0 + it.h * 16);
@@ -1192,7 +1324,7 @@ var OcrEngine = class _OcrEngine {
1192
1324
  this.ort = parts.ort;
1193
1325
  this.sharp = parts.sharp;
1194
1326
  }
1195
- static async create(models = _chunkSR6DJBPMcjs.DEFAULT_OCR_MODELS) {
1327
+ static async create(models = _chunk6SITJI2Wcjs.DEFAULT_OCR_MODELS) {
1196
1328
  _chunkTK3FDAEEcjs.disableOrtTelemetry.call(void 0, );
1197
1329
  const [ortMod, sharpModRaw] = await Promise.all([
1198
1330
  tryImport("onnxruntime-node", () => Promise.resolve().then(() => _interopRequireWildcard(require("onnxruntime-node")))),
@@ -1212,16 +1344,16 @@ var OcrEngine = class _OcrEngine {
1212
1344
  const local = (s) => "spec" in s ? Promise.resolve(null) : verifiedBytes(s);
1213
1345
  const [detBytes, recBytes, dictBytes] = await Promise.all([local(models.det), local(models.rec), local(models.dict)]);
1214
1346
  const session = (s, bytes) => bytes ? ortMod.InferenceSession.create(bytes, sessionOpts).catch(() => {
1215
- throw new (0, _chunkNVOB6OHScjs.KordocError)(`OCR \uBAA8\uB378\uC744 \uC5F4\uC9C0 \uBABB\uD588\uC2B5\uB2C8\uB2E4: ${_path.basename.call(void 0, _chunkSR6DJBPMcjs.ocrSourcePath.call(void 0, s))} \u2014 ONNX \uBAA8\uB378\uC774 \uC544\uB2C8\uAC70\uB098 \uC190\uC0C1\uB410\uC2B5\uB2C8\uB2E4`);
1216
- }) : ortMod.InferenceSession.create(_chunkSR6DJBPMcjs.ocrSourcePath.call(void 0, s), sessionOpts);
1347
+ throw new (0, _chunkAYYPVST4cjs.KordocError)(`OCR \uBAA8\uB378\uC744 \uC5F4\uC9C0 \uBABB\uD588\uC2B5\uB2C8\uB2E4: ${_path.basename.call(void 0, _chunk6SITJI2Wcjs.ocrSourcePath.call(void 0, s))} \u2014 ONNX \uBAA8\uB378\uC774 \uC544\uB2C8\uAC70\uB098 \uC190\uC0C1\uB410\uC2B5\uB2C8\uB2E4`);
1348
+ }) : ortMod.InferenceSession.create(_chunk6SITJI2Wcjs.ocrSourcePath.call(void 0, s), sessionOpts);
1217
1349
  const [det, rec, dictYml] = await Promise.all([
1218
1350
  session(models.det, detBytes),
1219
1351
  session(models.rec, recBytes),
1220
- dictBytes ? new TextDecoder().decode(dictBytes) : _promises.readFile.call(void 0, _chunkSR6DJBPMcjs.ocrSourcePath.call(void 0, models.dict), "utf-8")
1352
+ dictBytes ? new TextDecoder().decode(dictBytes) : _promises.readFile.call(void 0, _chunk6SITJI2Wcjs.ocrSourcePath.call(void 0, models.dict), "utf-8")
1221
1353
  ]);
1222
- const dict = _chunkSR6DJBPMcjs.parseCharacterDict.call(void 0, dictYml);
1354
+ const dict = _chunk6SITJI2Wcjs.parseCharacterDict.call(void 0, dictYml);
1223
1355
  if (dict.length === 0) {
1224
- throw "spec" in models.dict ? new Error("OCR \uC0AC\uC804 \uD30C\uC2F1 \uC2E4\uD328 \u2014 \uBAA8\uB378 \uCE90\uC2DC\uB97C \uC0AD\uC81C \uD6C4 \uC7AC\uB2E4\uC6B4\uB85C\uB4DC\uD558\uC138\uC694") : new (0, _chunkNVOB6OHScjs.KordocError)(`OCR \uC0AC\uC804 \uD30C\uC2F1 \uC2E4\uD328 \u2014 ${_path.basename.call(void 0, models.dict.file.path)} \uC5D0 PostProcess.character_dict \uBAA9\uB85D\uC774 \uC5C6\uC2B5\uB2C8\uB2E4`);
1356
+ throw "spec" in models.dict ? new Error("OCR \uC0AC\uC804 \uD30C\uC2F1 \uC2E4\uD328 \u2014 \uBAA8\uB378 \uCE90\uC2DC\uB97C \uC0AD\uC81C \uD6C4 \uC7AC\uB2E4\uC6B4\uB85C\uB4DC\uD558\uC138\uC694") : new (0, _chunkAYYPVST4cjs.KordocError)(`OCR \uC0AC\uC804 \uD30C\uC2F1 \uC2E4\uD328 \u2014 ${_path.basename.call(void 0, models.dict.file.path)} \uC5D0 PostProcess.character_dict \uBAA9\uB85D\uC774 \uC5C6\uC2B5\uB2C8\uB2E4`);
1225
1357
  }
1226
1358
  return new _OcrEngine({ det, rec, dict, ort: ortMod, sharp: sharpMod });
1227
1359
  }
@@ -1253,10 +1385,10 @@ var OcrEngine = class _OcrEngine {
1253
1385
  if (it.x - x < it.h * 0.8) return;
1254
1386
  if (items.some((o) => o !== it && o.x < it.x && o.x + o.w > x && o.y < it.y + it.h && o.y + o.h > it.y)) return;
1255
1387
  const box = { x, y: it.y, w: it.x + it.w - x, h: it.h };
1256
- const g = _chunkSR6DJBPMcjs.grayCrop.call(void 0, rgba, width, box);
1257
- const b = _chunkSR6DJBPMcjs.leadingBullet.call(void 0, g, box.w, box.h, _chunkSR6DJBPMcjs.inkStats.call(void 0, g), it.x - x, 1.05);
1258
- if (_optionalChain([b, 'optionalAccess', _26 => _26.mark]) !== "\u25A1" || b.covers) return;
1259
- const ink = _chunkSR6DJBPMcjs.inkStats.call(void 0, g), on = (v) => ink.darkInk ? v <= ink.threshold : v > ink.threshold;
1388
+ const g = _chunk6SITJI2Wcjs.grayCrop.call(void 0, rgba, width, box);
1389
+ const b = _chunk6SITJI2Wcjs.leadingBullet.call(void 0, g, box.w, box.h, _chunk6SITJI2Wcjs.inkStats.call(void 0, g), it.x - x, 1.05);
1390
+ if (_optionalChain([b, 'optionalAccess', _30 => _30.mark]) !== "\u25A1" || b.covers) return;
1391
+ const ink = _chunk6SITJI2Wcjs.inkStats.call(void 0, g), on = (v) => ink.darkInk ? v <= ink.threshold : v > ink.threshold;
1260
1392
  let left = 0;
1261
1393
  while (left < it.x - x && !Array.from({ length: box.h }, (_, y) => g[y * box.w + left]).some(on)) left++;
1262
1394
  it.text = "\u25A1 " + it.text;
@@ -1273,12 +1405,12 @@ var OcrEngine = class _OcrEngine {
1273
1405
  const joins = [];
1274
1406
  let group = 0;
1275
1407
  for (const b of boxes) {
1276
- const gray = _chunkSR6DJBPMcjs.grayCrop.call(void 0, rgba, width, b);
1277
- const ink = _chunkSR6DJBPMcjs.inkStats.call(void 0, gray);
1408
+ const gray = _chunk6SITJI2Wcjs.grayCrop.call(void 0, rgba, width, b);
1409
+ const ink = _chunk6SITJI2Wcjs.inkStats.call(void 0, gray);
1278
1410
  if (tuning.minInkContrast > 0 && ink.contrast < tuning.minInkContrast) continue;
1279
1411
  if (tuning.minInkContrast > 0 && ink.inkRatio < MIN_INK_RATIO) continue;
1280
1412
  if (tuning.splitTall && b.h >= b.w * TALL_RATIO) {
1281
- const bands = _chunkSR6DJBPMcjs.splitRowBands.call(void 0, gray, b.w, b.h, ink, 0.45);
1413
+ const bands = _chunk6SITJI2Wcjs.splitRowBands.call(void 0, gray, b.w, b.h, ink, 0.45);
1282
1414
  if (bands.length >= 2) {
1283
1415
  for (const sub of bandBoxes(b, bands, height)) jobs.push({ box: sub, rot: 0, group: group++ });
1284
1416
  continue;
@@ -1289,9 +1421,9 @@ var OcrEngine = class _OcrEngine {
1289
1421
  continue;
1290
1422
  }
1291
1423
  }
1292
- const trim = tuning.trimEdges ? _chunkSR6DJBPMcjs.edgeTrim.call(void 0, gray, b.w, b.h, ink) : null;
1424
+ const trim = tuning.trimEdges ? _chunk6SITJI2Wcjs.edgeTrim.call(void 0, gray, b.w, b.h, ink) : null;
1293
1425
  const keep = trim ? { ...trim, bg: median(gray) } : void 0;
1294
- const leaders = tuning.splitLeaders ? _chunkSR6DJBPMcjs.leaderRuns.call(void 0, gray, b.w, b.h, ink, LEADER_MIN_DOTS) : [];
1426
+ const leaders = tuning.splitLeaders ? _chunk6SITJI2Wcjs.leaderRuns.call(void 0, gray, b.w, b.h, ink, LEADER_MIN_DOTS) : [];
1295
1427
  if (leaders.length) {
1296
1428
  const join = joins.length;
1297
1429
  joins.push({ box: b, parts: [], trailDots: false });
@@ -1300,7 +1432,7 @@ var OcrEngine = class _OcrEngine {
1300
1432
  const bare = { x: b.x + x0, y: b.y, w: a - x0, h: b.h };
1301
1433
  const end = c > a ? Math.min(c, a + Math.round(b.h * LEADER_CONTEXT)) : a;
1302
1434
  x0 = c;
1303
- if (bare.w >= DET_MIN_SIZE && _chunkSR6DJBPMcjs.inkStats.call(void 0, _chunkSR6DJBPMcjs.grayCrop.call(void 0, rgba, width, bare)).contrast >= Math.max(1, tuning.minInkContrast)) {
1435
+ if (bare.w >= DET_MIN_SIZE && _chunk6SITJI2Wcjs.inkStats.call(void 0, _chunk6SITJI2Wcjs.grayCrop.call(void 0, rgba, width, bare)).contrast >= Math.max(1, tuning.minInkContrast)) {
1304
1436
  jobs.push({ box: { ...bare, w: end - (bare.x - b.x) }, rot: 0, group: group++, join, dotsBefore: dots, trimDots: end > a });
1305
1437
  dots = false;
1306
1438
  }
@@ -1329,6 +1461,7 @@ var OcrEngine = class _OcrEngine {
1329
1461
  if (r.text.replace(/\s/g, "") === "\xB7" + b && /^[가-힣]/.test(b)) best.set(job.group, { ...cur, text: "\xB7" + cur.text, steps: [r.steps[0], ...cur.steps] });
1330
1462
  });
1331
1463
  let items = [];
1464
+ const retry = [];
1332
1465
  for (const r of best.values()) {
1333
1466
  const { job, confidence, stepPx } = r;
1334
1467
  const { text: read, steps } = tuning.postprocess && job.rot === 0 ? trimInklessEnds(rgba, width, job.box, r.text, r.steps, stepPx) : r;
@@ -1337,47 +1470,51 @@ var OcrEngine = class _OcrEngine {
1337
1470
  let text = tuning.postprocess ? restoreSymbols(raw.trim(), note.ringLead) : raw;
1338
1471
  if (!text.trim()) continue;
1339
1472
  if (tuning.postprocess && job.rot === 0 && text !== "/" && /^[(:;/)]+$/.test(text) && text.includes("/")) {
1340
- const g = _chunkSR6DJBPMcjs.grayCrop.call(void 0, rgba, width, job.box);
1341
- if (_chunkSR6DJBPMcjs.tallInkCount.call(void 0, g, job.box.w, job.box.h, _chunkSR6DJBPMcjs.inkStats.call(void 0, g)) === 1) text = "/";
1473
+ const g = _chunk6SITJI2Wcjs.grayCrop.call(void 0, rgba, width, job.box);
1474
+ if (_chunk6SITJI2Wcjs.tallInkCount.call(void 0, g, job.box.w, job.box.h, _chunk6SITJI2Wcjs.inkStats.call(void 0, g)) === 1) text = "/";
1342
1475
  }
1476
+ let ringByShape = false;
1343
1477
  if (tuning.postprocess && job.rot === 0 && !/^[◎●▪□■▣❐❏○ㅇ◆◇◈]/.test(text)) {
1344
1478
  const chars = [...read], k = chars.findIndex((c) => c.trim());
1345
1479
  if (k >= 0 && steps.length === chars.length) {
1346
- const g = _chunkSR6DJBPMcjs.grayCrop.call(void 0, rgba, width, job.box);
1347
- const b = _chunkSR6DJBPMcjs.leadingBullet.call(void 0, g, job.box.w, job.box.h, _chunkSR6DJBPMcjs.inkStats.call(void 0, g), (steps[k] + 0.5) * stepPx);
1480
+ const g = _chunk6SITJI2Wcjs.grayCrop.call(void 0, rgba, width, job.box);
1481
+ const b = _chunk6SITJI2Wcjs.leadingBullet.call(void 0, g, job.box.w, job.box.h, _chunk6SITJI2Wcjs.inkStats.call(void 0, g), (steps[k] + 0.5) * stepPx);
1348
1482
  const body = (_nullishCoalesce(text.match(/[가-힣]/g), () => ( []))).length >= 4;
1349
1483
  const miss = /^[Oo0•·ㆍ∙‧○]/.test(text);
1350
- if (_optionalChain([b, 'optionalAccess', _27 => _27.mark]) === "\u25CE" && b.covers && /^[Oo0○]/.test(text)) text = b.mark + " " + text.slice(1).trimStart();
1351
- else if (_optionalChain([b, 'optionalAccess', _28 => _28.mark]) === "\u25A1" || _optionalChain([b, 'optionalAccess', _29 => _29.mark]) === "\u25A3") {
1484
+ if (_optionalChain([b, 'optionalAccess', _31 => _31.mark]) === "\u25CE" && b.covers && /^[Oo0○©]/.test(text)) {
1485
+ text = b.mark + " " + text.slice(1).trimStart();
1486
+ ringByShape = true;
1487
+ } else if (_optionalChain([b, 'optionalAccess', _32 => _32.mark]) === "\u25A1" || _optionalChain([b, 'optionalAccess', _33 => _33.mark]) === "\u25A3") {
1352
1488
  if (!b.covers && body) text = b.mark + " " + text;
1353
- } else if (_optionalChain([b, 'optionalAccess', _30 => _30.mark]) === "\u25C6" || _optionalChain([b, 'optionalAccess', _31 => _31.mark]) === "\u25C7" || _optionalChain([b, 'optionalAccess', _32 => _32.mark]) === "\u25C8") {
1489
+ } else if (_optionalChain([b, 'optionalAccess', _34 => _34.mark]) === "\u25C6" || _optionalChain([b, 'optionalAccess', _35 => _35.mark]) === "\u25C7" || _optionalChain([b, 'optionalAccess', _36 => _36.mark]) === "\u25C8") {
1354
1490
  if (b.covers ? /^[\p{S}\p{P}]/u.test(text) : body) text = b.covers ? b.mark + " " + text.slice(1).trimStart() : b.mark + " " + text;
1355
- } else if (_optionalChain([b, 'optionalAccess', _33 => _33.mark]) === "\u2023") {
1491
+ } else if (_optionalChain([b, 'optionalAccess', _37 => _37.mark]) === "\u2023") {
1356
1492
  if (b.covers ? text.startsWith("\u2192") : body) text = b.covers ? b.mark + " " + text.slice(1).trimStart() : b.mark + " " + text;
1357
- } else if (_optionalChain([b, 'optionalAccess', _34 => _34.mark]) === "\u2750" || _optionalChain([b, 'optionalAccess', _35 => _35.mark]) === "\u274F") {
1493
+ } else if (_optionalChain([b, 'optionalAccess', _38 => _38.mark]) === "\u2750" || _optionalChain([b, 'optionalAccess', _39 => _39.mark]) === "\u274F") {
1358
1494
  if (b.covers ? /^[ㅁ口]/.test(text) : body) text = b.covers ? b.mark + text.slice(1) : b.mark + " " + text;
1359
1495
  } else if (b && b.mark !== "\u25CE" && body) text = b.covers ? miss ? b.mark + " " + text.slice(1).trimStart() : text : b.mark + " " + text;
1360
- else if (!b && body && /^[가-힣]/.test(chars[k]) && _chunkSR6DJBPMcjs.leadingRing.call(void 0, g, job.box.w, job.box.h, _chunkSR6DJBPMcjs.inkStats.call(void 0, g), (steps[k] + 0.5) * stepPx)) text = "\u25CB " + text;
1496
+ else if (!b && body && /^[가-힣]/.test(chars[k]) && _chunk6SITJI2Wcjs.leadingRing.call(void 0, g, job.box.w, job.box.h, _chunk6SITJI2Wcjs.inkStats.call(void 0, g), (steps[k] + 0.5) * stepPx)) text = "\u25CB " + text;
1361
1497
  }
1362
1498
  }
1363
1499
  if (tuning.postprocess && /^\d/.test(text) && job.rot === 0) {
1364
- const g = _chunkSR6DJBPMcjs.grayCrop.call(void 0, rgba, width, job.box);
1365
- const tri = _chunkSR6DJBPMcjs.leadingTriangle.call(void 0, g, job.box.w, job.box.h, _chunkSR6DJBPMcjs.inkStats.call(void 0, g));
1500
+ const g = _chunk6SITJI2Wcjs.grayCrop.call(void 0, rgba, width, job.box);
1501
+ const tri = _chunk6SITJI2Wcjs.leadingTriangle.call(void 0, g, job.box.w, job.box.h, _chunk6SITJI2Wcjs.inkStats.call(void 0, g));
1366
1502
  if (tri) text = tri + text;
1367
1503
  }
1368
1504
  if (tuning.postprocess && text === "\u2192" && job.rot === 0 && job.join === void 0) {
1369
- const g = _chunkSR6DJBPMcjs.grayCrop.call(void 0, rgba, width, job.box);
1370
- text = _nullishCoalesce(_chunkSR6DJBPMcjs.arrowGlyph.call(void 0, g, job.box.w, job.box.h, _chunkSR6DJBPMcjs.inkStats.call(void 0, g)), () => ( text));
1505
+ const g = _chunk6SITJI2Wcjs.grayCrop.call(void 0, rgba, width, job.box);
1506
+ text = _nullishCoalesce(_chunk6SITJI2Wcjs.arrowGlyph.call(void 0, g, job.box.w, job.box.h, _chunk6SITJI2Wcjs.inkStats.call(void 0, g)), () => ( text));
1371
1507
  }
1372
1508
  if (job.footer) {
1373
1509
  if (!/^[-\u2013\u2014]?\s*(?:\d{1,4}|[ivxIVXⅰ-ⅹⅠ-Ⅹ]{1,4})\s*[-\u2013\u2014]?$/.test(text.trim())) continue;
1374
1510
  text = text.replace(/[\u2013\u2014]/g, "-");
1375
1511
  }
1376
1512
  if (tuning.postprocess && isDotFragment(text)) continue;
1377
- if (confidence < tuning.textScore) {
1513
+ if (confidence < tuning.textScore && !(ringByShape && text.trim() === "\u25CE")) {
1514
+ if (tuning.postprocess && job.rot === 0 && job.join === void 0 && !job.footer) retry.push(job.box);
1378
1515
  if (stats) {
1379
1516
  stats.droppedLowConf++;
1380
- _optionalChain([stats, 'access', _36 => _36.dropped, 'optionalAccess', _37 => _37.push, 'call', _38 => _38({ text, ...this.itemBox(rgba, width, job.box, tuning), confidence })]);
1517
+ _optionalChain([stats, 'access', _40 => _40.dropped, 'optionalAccess', _41 => _41.push, 'call', _42 => _42({ text, ...this.itemBox(rgba, width, job.box, tuning), confidence })]);
1381
1518
  }
1382
1519
  continue;
1383
1520
  }
@@ -1387,9 +1524,26 @@ var OcrEngine = class _OcrEngine {
1387
1524
  continue;
1388
1525
  }
1389
1526
  const item = { text, ...this.itemBox(rgba, width, job.box, tuning), confidence };
1390
- if (job.rot === 0) _chunkSR6DJBPMcjs.rememberOcrTextGaps.call(void 0, item, _chunkSR6DJBPMcjs.findOcrTextGaps.call(void 0, rgba, width, job.box, read, text, steps, stepPx));
1527
+ if (job.rot === 0) _chunk6SITJI2Wcjs.rememberOcrTextGaps.call(void 0, item, _chunk6SITJI2Wcjs.findOcrTextGaps.call(void 0, rgba, width, job.box, read, text, steps, stepPx));
1391
1528
  items.push(item);
1392
1529
  }
1530
+ if (retry.length) {
1531
+ const subs = [];
1532
+ for (const b of retry) {
1533
+ const gray = _chunk6SITJI2Wcjs.grayCrop.call(void 0, rgba, width, b);
1534
+ const cut = midBlankRow(gray, b.w, b.h, _chunk6SITJI2Wcjs.inkStats.call(void 0, gray));
1535
+ if (cut && b.w >= 3 * Math.max(cut[0], b.h - cut[1])) subs.push({ ...b, h: cut[0] }, { ...b, y: b.y + cut[1], h: b.h - cut[1] });
1536
+ }
1537
+ const overlap = (a, o) => Math.max(0, Math.min(a.x + a.w, o.x + o.w) - Math.max(a.x, o.x)) * Math.max(0, Math.min(a.y + a.h, o.y + o.h) - Math.max(a.y, o.y));
1538
+ for (let k = subs.length - 1; k >= 0; k--) if (subs[k].h < 8 || items.some((o) => overlap(subs[k], o) * 2 > subs[k].w * subs[k].h)) subs.splice(k, 1);
1539
+ const res = subs.length ? await this.recognizeJobs(rgba, width, subs.map((box, k) => ({ box, rot: 0, group: k })), tuning.recBatch) : [];
1540
+ subs.forEach((box, k) => {
1541
+ const r = res[k];
1542
+ if (!r || r.confidence < RETRY_SCORE) return;
1543
+ const text = restoreSymbols(restoreGlyphs(rgba, width, box, r.text, r.steps, r.stepPx).trim());
1544
+ if ((_nullishCoalesce(text.match(/[\p{L}\p{N}]/gu), () => ( []))).length >= 2) items.push({ text, ...this.itemBox(rgba, width, box, tuning), confidence: r.confidence });
1545
+ });
1546
+ }
1393
1547
  const leaderEnds = /* @__PURE__ */ new Map();
1394
1548
  for (const j of joins) {
1395
1549
  if (!j.parts.length) continue;
@@ -1419,11 +1573,20 @@ var OcrEngine = class _OcrEngine {
1419
1573
  if (tails.length) {
1420
1574
  const res = await this.recognizeJobs(rgba, width, tails.map((box, k) => ({ box, rot: 0, group: k })), tuning.recBatch);
1421
1575
  tails.forEach((box, k) => {
1422
- const t = _nullishCoalesce(_optionalChain([res, 'access', _39 => _39[k], 'optionalAccess', _40 => _40.text, 'access', _41 => _41.trim, 'call', _42 => _42()]), () => ( ""));
1423
- if (/^\d{1,4}$/.test(t) && (_nullishCoalesce(_optionalChain([res, 'access', _43 => _43[k], 'optionalAccess', _44 => _44.confidence]), () => ( 0))) >= tuning.textScore) items.push({ text: t, ...this.itemBox(rgba, width, box, tuning), confidence: res[k].confidence });
1576
+ const t = _nullishCoalesce(_optionalChain([res, 'access', _43 => _43[k], 'optionalAccess', _44 => _44.text, 'access', _45 => _45.trim, 'call', _46 => _46()]), () => ( ""));
1577
+ if (/^\d{1,4}$/.test(t) && (_nullishCoalesce(_optionalChain([res, 'access', _47 => _47[k], 'optionalAccess', _48 => _48.confidence]), () => ( 0))) >= tuning.textScore) items.push({ text: t, ...this.itemBox(rgba, width, box, tuning), confidence: res[k].confidence });
1578
+ });
1579
+ }
1580
+ const heads = rowHeadBoxes(rgba, width, items);
1581
+ if (heads.length) {
1582
+ const res = await this.recognizeJobs(rgba, width, heads.map((box, k) => ({ box, rot: 0, group: k })), tuning.recBatch);
1583
+ heads.forEach((box, k) => {
1584
+ const t = _nullishCoalesce(_optionalChain([res, 'access', _49 => _49[k], 'optionalAccess', _50 => _50.text, 'access', _51 => _51.trim, 'call', _52 => _52()]), () => ( ""));
1585
+ if (/^(?:[IVXⅠ-Ⅻ]{1,4}|\d{1,2})\s?\.$/.test(t) && (_nullishCoalesce(_optionalChain([res, 'access', _53 => _53[k], 'optionalAccess', _54 => _54.confidence]), () => ( 0))) >= tuning.textScore) items.push({ text: t, ...this.itemBox(rgba, width, box, tuning), confidence: res[k].confidence });
1424
1586
  });
1425
1587
  }
1426
1588
  }
1589
+ if (tuning.postprocess) items = joinGapLeaders(rgba, width, items);
1427
1590
  if (tuning.postprocess) restoreBulletItems(items);
1428
1591
  items.sort((a, b) => a.y - b.y || a.x - b.x);
1429
1592
  return items;
@@ -1431,8 +1594,8 @@ var OcrEngine = class _OcrEngine {
1431
1594
  /** 결과 좌표 — det 박스 그대로 또는 박스 안 잉크 외곽 (tightBoxes) */
1432
1595
  itemBox(rgba, width, b, tuning) {
1433
1596
  if (!tuning.tightBoxes) return b;
1434
- const gray = _chunkSR6DJBPMcjs.grayCrop.call(void 0, rgba, width, b);
1435
- const t = _chunkSR6DJBPMcjs.inkBounds.call(void 0, gray, b.w, b.h, _chunkSR6DJBPMcjs.inkStats.call(void 0, gray));
1597
+ const gray = _chunk6SITJI2Wcjs.grayCrop.call(void 0, rgba, width, b);
1598
+ const t = _chunk6SITJI2Wcjs.inkBounds.call(void 0, gray, b.w, b.h, _chunk6SITJI2Wcjs.inkStats.call(void 0, gray));
1436
1599
  return { x: b.x + t.x0, y: b.y + t.y0, w: t.x1 - t.x0, h: t.y1 - t.y0 };
1437
1600
  }
1438
1601
  // ─── det ─────────────────────────────────────────────
@@ -1505,7 +1668,7 @@ var OcrEngine = class _OcrEngine {
1505
1668
  const out = await this.rec.run({ [this.rec.inputNames[0]]: tensor });
1506
1669
  const logits = out[this.rec.outputNames[0]];
1507
1670
  const [, T, C] = logits.dims;
1508
- if (C !== this.dict.length + 2) throw new (0, _chunkNVOB6OHScjs.KordocError)(`OCR rec \uCD9C\uB825 \uD074\uB798\uC2A4 ${C}\uAC1C\uAC00 \uC0AC\uC804 ${this.dict.length}\uC790 + 2 \uC640 \uB2E4\uB985\uB2C8\uB2E4 \u2014 \uBAA8\uB378\uC5D0 \uB9DE\uB294 \uC0AC\uC804(ocrRecDict)\uC744 \uC9C0\uC815\uD558\uC138\uC694`);
1671
+ if (C !== this.dict.length + 2) throw new (0, _chunkAYYPVST4cjs.KordocError)(`OCR rec \uCD9C\uB825 \uD074\uB798\uC2A4 ${C}\uAC1C\uAC00 \uC0AC\uC804 ${this.dict.length}\uC790 + 2 \uC640 \uB2E4\uB985\uB2C8\uB2E4 \u2014 \uBAA8\uB378\uC5D0 \uB9DE\uB294 \uC0AC\uC804(ocrRecDict)\uC744 \uC9C0\uC815\uD558\uC138\uC694`);
1509
1672
  const data = logits.data;
1510
1673
  idx.forEach((ci, k) => {
1511
1674
  const r = ctcDecode(data.subarray(k * T * C, (k + 1) * T * C), T, C, this.dict);
@@ -1515,9 +1678,9 @@ var OcrEngine = class _OcrEngine {
1515
1678
  const chars = r ? [...r.text] : [];
1516
1679
  if (r && job.rot === 0 && chars.length === r.steps.length && r.steps.some((t) => t > last) && !r.text.includes("(cid:")) {
1517
1680
  const tallCh = (c) => !/[\s.,:;\u00b7\u2026'"\u2018-\u201d`\-_~]/.test(c);
1518
- const g = _chunkSR6DJBPMcjs.grayCrop.call(void 0, rgba, pageW, job.box);
1681
+ const g = _chunk6SITJI2Wcjs.grayCrop.call(void 0, rgba, pageW, job.box);
1519
1682
  const inside = chars.filter((c, i) => r.steps[i] <= last && tallCh(c)).length;
1520
- let budget = inside <= 2 ? _chunkSR6DJBPMcjs.tallInkCount.call(void 0, g, job.box.w, job.box.h, _chunkSR6DJBPMcjs.inkStats.call(void 0, g)) - inside : Infinity;
1683
+ let budget = inside <= 2 ? _chunk6SITJI2Wcjs.tallInkCount.call(void 0, g, job.box.w, job.box.h, _chunk6SITJI2Wcjs.inkStats.call(void 0, g)) - inside : Infinity;
1521
1684
  const keep = chars.map((c, i) => r.steps[i] <= last || !tallCh(c) || budget-- > 0);
1522
1685
  if (!keep.every(Boolean)) kept = { ...r, text: chars.filter((_, i) => keep[i]).join(""), steps: r.steps.filter((_, i) => keep[i]) };
1523
1686
  }
@@ -1628,13 +1791,13 @@ async function tryImport(name, loader) {
1628
1791
  return await loader();
1629
1792
  } catch (e) {
1630
1793
  throw new Error(
1631
- `\uB0B4\uC7A5 OCR \uC744 \uC0AC\uC6A9\uD558\uB824\uBA74 optional dependency '${name}' \uC774 \uD544\uC694\uD569\uB2C8\uB2E4. \`npm install ${name}\` \uD6C4 \uB2E4\uC2DC \uC2E4\uD589\uD558\uC138\uC694.${_chunkNVOB6OHScjs.OPTIONAL_DEP_INSTALL_HINT} \uC6D0\uC778: ${e.message}`
1794
+ `\uB0B4\uC7A5 OCR \uC744 \uC0AC\uC6A9\uD558\uB824\uBA74 optional dependency '${name}' \uC774 \uD544\uC694\uD569\uB2C8\uB2E4. \`npm install ${name}\` \uD6C4 \uB2E4\uC2DC \uC2E4\uD589\uD558\uC138\uC694.${_chunkAYYPVST4cjs.OPTIONAL_DEP_INSTALL_HINT} \uC6D0\uC778: ${e.message}`
1632
1795
  );
1633
1796
  }
1634
1797
  }
1635
1798
  async function verifiedBytes(s) {
1636
1799
  const name = _path.basename.call(void 0, s.file.path);
1637
- const fail = (why2) => new (0, _chunkNVOB6OHScjs.KordocError)(`OCR \uBAA8\uB378 \uD30C\uC77C\uC744 \uC77D\uC9C0 \uBABB\uD588\uC2B5\uB2C8\uB2E4: ${name} (${why2})`);
1800
+ const fail = (why2) => new (0, _chunkAYYPVST4cjs.KordocError)(`OCR \uBAA8\uB378 \uD30C\uC77C\uC744 \uC77D\uC9C0 \uBABB\uD588\uC2B5\uB2C8\uB2E4: ${name} (${why2})`);
1638
1801
  const why = (e) => {
1639
1802
  const code = e.code;
1640
1803
  return code === "ENOENT" ? "\uD30C\uC77C\uC774 \uC5C6\uC74C" : code === "EACCES" || code === "EPERM" ? "\uAD8C\uD55C \uC5C6\uC74C" : "\uC77D\uAE30 \uC2E4\uD328";
@@ -1655,13 +1818,13 @@ async function verifiedBytes(s) {
1655
1818
  }
1656
1819
  const actual = _crypto.createHash.call(void 0, "sha256").update(bytes).digest("hex");
1657
1820
  if (actual !== s.file.sha256) {
1658
- throw new (0, _chunkNVOB6OHScjs.KordocError)(`OCR \uBAA8\uB378 SHA256 mismatch: ${_path.basename.call(void 0, s.file.path)} \u2014 expected ${s.file.sha256}, got ${actual} (\uB85C\uB4DC \uAC70\uBD80)`);
1821
+ throw new (0, _chunkAYYPVST4cjs.KordocError)(`OCR \uBAA8\uB378 SHA256 mismatch: ${_path.basename.call(void 0, s.file.path)} \u2014 expected ${s.file.sha256}, got ${actual} (\uB85C\uB4DC \uAC70\uBD80)`);
1659
1822
  }
1660
1823
  return bytes;
1661
1824
  }
1662
1825
  var engines = /* @__PURE__ */ new Map();
1663
- function getOcrEngine(models = _chunkSR6DJBPMcjs.DEFAULT_OCR_MODELS) {
1664
- const key = _chunkSR6DJBPMcjs.ocrSelectionKey.call(void 0, models);
1826
+ function getOcrEngine(models = _chunk6SITJI2Wcjs.DEFAULT_OCR_MODELS) {
1827
+ const key = _chunk6SITJI2Wcjs.ocrSelectionKey.call(void 0, models);
1665
1828
  let p = engines.get(key);
1666
1829
  if (!p) {
1667
1830
  p = OcrEngine.create(models).catch((err) => {
@@ -1764,13 +1927,13 @@ function rotateRgba(rgba, width, height, deg) {
1764
1927
  var OCR_RENDER_SCALE = 3;
1765
1928
  var MAX_OCR_PIXELS = 24e6;
1766
1929
  var PAGE_TIMEOUT_MS = 12e4;
1767
- var DEFAULT_BUILTIN_OCR = Object.freeze({ models: _chunkSR6DJBPMcjs.DEFAULT_OCR_MODELS, tuning: DEFAULT_OCR_TUNING });
1930
+ var DEFAULT_BUILTIN_OCR = Object.freeze({ models: _chunk6SITJI2Wcjs.DEFAULT_OCR_MODELS, tuning: DEFAULT_OCR_TUNING });
1768
1931
  function builtinOcrConfig(o) {
1769
1932
  if (!o || o.ocrDet === void 0 && o.ocrDetLongSide === void 0 && o.ocrRec === void 0 && o.ocrRecDict === void 0 && !o.ocrLines) return DEFAULT_BUILTIN_OCR;
1770
- const bad = _chunkCCH6BUNIcjs.validateOcrOptions.call(void 0, o);
1771
- if (bad) throw new (0, _chunkNVOB6OHScjs.KordocError)(bad);
1933
+ const bad = _chunkISHFQDFZcjs.validateOcrOptions.call(void 0, o);
1934
+ if (bad) throw new (0, _chunkAYYPVST4cjs.KordocError)(bad);
1772
1935
  return {
1773
- models: _chunkSR6DJBPMcjs.resolveOcrModels.call(void 0, o),
1936
+ models: _chunk6SITJI2Wcjs.resolveOcrModels.call(void 0, o),
1774
1937
  tuning: o.ocrDetLongSide === void 0 ? DEFAULT_OCR_TUNING : { ...DEFAULT_OCR_TUNING, detLongSide: o.ocrDetLongSide },
1775
1938
  lines: o.ocrLines === "all" ? "all" : o.ocrLines ? "kept" : void 0
1776
1939
  };
@@ -1804,7 +1967,7 @@ async function runPdfOcr(buffer, targets, mode, warnings, onProgress, detectTabl
1804
1967
  "@hyzyla/pdfium",
1805
1968
  () => Promise.resolve().then(() => _interopRequireWildcard(require("@hyzyla/pdfium")))
1806
1969
  );
1807
- if (mode === "builtin") await _chunkSR6DJBPMcjs.ensureOcrModelsFor.call(void 0, config.models, reportModelDownload);
1970
+ if (mode === "builtin") await _chunk6SITJI2Wcjs.ensureOcrModelsFor.call(void 0, config.models, reportModelDownload);
1808
1971
  const engine = mode === "builtin" ? await getOcrEngine(config.models) : null;
1809
1972
  const pdfium = await pdfiumMod.PDFiumLibrary.init();
1810
1973
  const doc = await pdfium.loadDocument(new Uint8Array(buffer));
@@ -1813,15 +1976,15 @@ async function runPdfOcr(buffer, targets, mode, warnings, onProgress, detectTabl
1813
1976
  const count = doc.getPageCount();
1814
1977
  for (const pageNo of [...targets].filter((p) => p >= 1 && p <= count).sort((a, b) => a - b)) {
1815
1978
  const page = doc.getPage(pageNo - 1);
1816
- _optionalChain([onProgress, 'optionalCall', _45 => _45(++done, targets.size)]);
1979
+ _optionalChain([onProgress, 'optionalCall', _55 => _55(++done, targets.size)]);
1817
1980
  try {
1818
1981
  const { blocks, lines } = await withTimeout(
1819
- ocrOnePage(page, pageNo, mode, engine, warnings, detectTables, _optionalChain([vectorOps, 'optionalAccess', _46 => _46.get, 'call', _47 => _47(pageNo)]), _optionalChain([imageRegions, 'optionalAccess', _48 => _48.get, 'call', _49 => _49(pageNo)]), config),
1982
+ ocrOnePage(page, pageNo, mode, engine, warnings, detectTables, _optionalChain([vectorOps, 'optionalAccess', _56 => _56.get, 'call', _57 => _57(pageNo)]), _optionalChain([imageRegions, 'optionalAccess', _58 => _58.get, 'call', _59 => _59(pageNo)]), config),
1820
1983
  PAGE_TIMEOUT_MS,
1821
1984
  `OCR \uD398\uC774\uC9C0 ${pageNo} \uD0C0\uC784\uC544\uC6C3 (${PAGE_TIMEOUT_MS / 1e3}\uCD08)`
1822
1985
  );
1823
1986
  result.set(pageNo, blocks);
1824
- if (lines) _optionalChain([linesOut, 'optionalAccess', _50 => _50.set, 'call', _51 => _51(pageNo, lines)]);
1987
+ if (lines) _optionalChain([linesOut, 'optionalAccess', _60 => _60.set, 'call', _61 => _61(pageNo, lines)]);
1825
1988
  } catch (e) {
1826
1989
  warnings.push({
1827
1990
  page: pageNo,
@@ -1886,7 +2049,7 @@ async function ocrOnePage(page, pageNo, mode, engine, warnings, detectTables, ve
1886
2049
  const regionBlocks = regions.flatMap((r, k) => {
1887
2050
  let own = items.filter((it) => inside(it, r));
1888
2051
  const near = reads[k];
1889
- if (_optionalChain([near, 'optionalAccess', _52 => _52.length]) && meanConfidence(near) > meanConfidence(own)) {
2052
+ if (_optionalChain([near, 'optionalAccess', _62 => _62.length]) && meanConfidence(near) > meanConfidence(own)) {
1890
2053
  own = near;
1891
2054
  reread.add(k);
1892
2055
  }
@@ -1894,9 +2057,9 @@ async function ocrOnePage(page, pageNo, mode, engine, warnings, detectTables, ve
1894
2057
  for (const it of own) used.add(it);
1895
2058
  const blocks = ocrItemsToBlocks(own, pageNo, pdfW, pdfH, scale, ruling && rulingToPdfLines(ruling, scale, pdfH), detectTables, void 0, true);
1896
2059
  const x1 = r.x1 * scale - 2, x2 = r.x2 * scale + 2, y1 = (pdfH - r.y2) * scale - 2, y2 = (pdfH - r.y1) * scale + 2;
1897
- const columnRules = _nullishCoalesce(_optionalChain([ruling, 'optionalAccess', _53 => _53.verticals, 'access', _54 => _54.filter, 'call', _55 => _55((s) => Math.min(s.x1, s.x2) >= x1 && Math.max(s.x1, s.x2) <= x2 && Math.min(s.y1, s.y2) >= y1 && Math.max(s.y1, s.y2) <= y2), 'access', _56 => _56.length]), () => ( 0));
2060
+ const columnRules = _nullishCoalesce(_optionalChain([ruling, 'optionalAccess', _63 => _63.verticals, 'access', _64 => _64.filter, 'call', _65 => _65((s) => Math.min(s.x1, s.x2) >= x1 && Math.max(s.x1, s.x2) <= x2 && Math.min(s.y1, s.y2) >= y1 && Math.max(s.y1, s.y2) <= y2), 'access', _66 => _66.length]), () => ( 0));
1898
2061
  if (columnRules < 2) {
1899
- for (const b of blocks) if (b.type === "table") _chunkSR6DJBPMcjs.UNRULED_REGION_TABLES.add(b);
2062
+ for (const b of blocks) if (b.type === "table") _chunk6SITJI2Wcjs.UNRULED_REGION_TABLES.add(b);
1900
2063
  }
1901
2064
  return blocks;
1902
2065
  });
@@ -1955,7 +2118,7 @@ async function closerReads(rgba, rw, rh, pdfH, hi, regions, engine, tuning = REG
1955
2118
  const items = await engine.recognizePage(crop, cw, ch, void 0, tuning);
1956
2119
  out.push(items.map((it) => {
1957
2120
  const placed = { ...it, x: (it.x + x0) / 2, y: (it.y + y0) / 2, w: it.w / 2, h: it.h / 2 };
1958
- _chunkSR6DJBPMcjs.copyOcrTextGaps.call(void 0, it, placed, 0.5, x0 / 2);
2121
+ _chunk6SITJI2Wcjs.copyOcrTextGaps.call(void 0, it, placed, 0.5, x0 / 2);
1959
2122
  return placed;
1960
2123
  }));
1961
2124
  }
@@ -1963,7 +2126,7 @@ async function closerReads(rgba, rw, rh, pdfH, hi, regions, engine, tuning = REG
1963
2126
  }
1964
2127
  var proseBox = (b) => {
1965
2128
  const t = b.text.replace(/\s/g, "");
1966
- return b.w >= b.h * 7 && (_nullishCoalesce(_optionalChain([t, 'access', _57 => _57.match, 'call', _58 => _58(/\d/g), 'optionalAccess', _59 => _59.length]), () => ( 0))) < t.length * 0.3;
2129
+ return b.w >= b.h * 7 && (_nullishCoalesce(_optionalChain([t, 'access', _67 => _67.match, 'call', _68 => _68(/\d/g), 'optionalAccess', _69 => _69.length]), () => ( 0))) < t.length * 0.3;
1967
2130
  };
1968
2131
  function groupOcrLines(items, figureRegion = false) {
1969
2132
  const order = items.map((_, i) => i).sort((a, b) => items[a].y + items[a].h / 2 - (items[b].y + items[b].h / 2));
@@ -2035,17 +2198,17 @@ function ocrItemsToBlocks(items, pageNumber, pdfW, pdfH, scale, extraLines, dete
2035
2198
  isHidden: false,
2036
2199
  ...xs[i].space ? { hasSpaceBefore: true } : {}
2037
2200
  };
2038
- _chunkSR6DJBPMcjs.copyOcrTextGaps.call(void 0, it, normalized, 1 / scale);
2201
+ _chunk6SITJI2Wcjs.copyOcrTextGaps.call(void 0, it, normalized, 1 / scale);
2039
2202
  return normalized;
2040
2203
  });
2041
- return _chunkSR6DJBPMcjs.extractPageBlocksWithLines.call(void 0, norm, pageNumber, opList, pdfW, pdfH, extraLines, detectTables);
2204
+ return _chunk6SITJI2Wcjs.extractPageBlocksWithLines.call(void 0, norm, pageNumber, opList, pdfW, pdfH, extraLines, detectTables);
2042
2205
  }
2043
2206
  async function tryImport2(name, loader) {
2044
2207
  try {
2045
2208
  return await loader();
2046
2209
  } catch (e) {
2047
2210
  throw new Error(
2048
- `OCR \uC744 \uC0AC\uC6A9\uD558\uB824\uBA74 optional dependency '${name}' \uC774 \uD544\uC694\uD569\uB2C8\uB2E4. \`npm install ${name}\` \uD6C4 \uB2E4\uC2DC \uC2E4\uD589\uD558\uC138\uC694.${_chunkNVOB6OHScjs.OPTIONAL_DEP_INSTALL_HINT} \uC6D0\uC778: ${e.message}`
2211
+ `OCR \uC744 \uC0AC\uC6A9\uD558\uB824\uBA74 optional dependency '${name}' \uC774 \uD544\uC694\uD569\uB2C8\uB2E4. \`npm install ${name}\` \uD6C4 \uB2E4\uC2DC \uC2E4\uD589\uD558\uC138\uC694.${_chunkAYYPVST4cjs.OPTIONAL_DEP_INSTALL_HINT} \uC6D0\uC778: ${e.message}`
2049
2212
  );
2050
2213
  }
2051
2214
  }
@@ -2093,4 +2256,4 @@ function bgraToRgba(bgra) {
2093
2256
 
2094
2257
 
2095
2258
  exports.getOcrEngine = getOcrEngine; exports.detectRulingLines = detectRulingLines; exports.rulingToPdfLines = rulingToPdfLines; exports.deskewPage = deskewPage; exports.MAX_OCR_PIXELS = MAX_OCR_PIXELS; exports.DEFAULT_BUILTIN_OCR = DEFAULT_BUILTIN_OCR; exports.builtinOcrConfig = builtinOcrConfig; exports.reportModelDownload = reportModelDownload; exports.toOcrLine = toOcrLine; exports.pageLines = pageLines; exports.cellEdgeVerticals = cellEdgeVerticals; exports.cellEdgeHorizontals = cellEdgeHorizontals; exports.runPdfOcr = runPdfOcr; exports.ocrOnePage = ocrOnePage; exports.groupOcrLines = groupOcrLines; exports.ocrItemsToBlocks = ocrItemsToBlocks;
2096
- //# sourceMappingURL=chunk-X2SPQOI7.cjs.map
2259
+ //# sourceMappingURL=chunk-4JQO5D7Y.cjs.map