kordoc 4.18.3 → 4.18.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/{-WOKB25R2.js → -DDAVBMHD.js} +11 -11
- package/dist/{chunk-BGOR5GCF.js → chunk-274ZPMHK.js} +2 -2
- package/dist/{chunk-2ZBLQVAS.cjs → chunk-3WLZOJIE.cjs} +6 -6
- package/dist/chunk-3WLZOJIE.cjs.map +1 -0
- package/dist/{chunk-SHRRD2TD.cjs → chunk-3XSP7V5P.cjs} +2 -2
- package/dist/chunk-3XSP7V5P.cjs.map +1 -0
- package/dist/{chunk-6GLTGOP6.js → chunk-4IBY5LTJ.js} +2 -2
- package/dist/chunk-6H25SXDI.js +11 -0
- package/dist/chunk-6H25SXDI.js.map +1 -0
- package/dist/{chunk-CAN5P6N6.js → chunk-7GR2GCJF.js} +2 -2
- package/dist/{chunk-HZV52V2X.cjs → chunk-AVIZ55NQ.cjs} +3 -3
- package/dist/chunk-AVIZ55NQ.cjs.map +1 -0
- package/dist/chunk-DC6CTQTK.js +9 -0
- package/dist/chunk-DC6CTQTK.js.map +1 -0
- package/dist/{chunk-NES5U4JK.js → chunk-DUV7Y6IQ.js} +3 -3
- package/dist/{chunk-WN5YLP7H.cjs → chunk-E2644XCO.cjs} +693 -187
- package/dist/chunk-E2644XCO.cjs.map +1 -0
- package/dist/{chunk-3FZGL3IL.js → chunk-ELOPDQES.js} +2 -2
- package/dist/{chunk-2I2RTJJ5.js → chunk-F2GDLA45.js} +25 -35
- package/dist/chunk-F2GDLA45.js.map +1 -0
- package/dist/{chunk-VGDTONTB.js → chunk-F5YVCJVF.js} +2 -2
- package/dist/chunk-GS7T56RP.cjs.map +1 -1
- package/dist/{chunk-RDBTOE5X.js → chunk-HRJJDNRD.js} +2 -2
- package/dist/{chunk-KSJ7GKNQ.js → chunk-IAXGGQGD.js} +2 -2
- package/dist/{chunk-IXX3WHIE.js → chunk-IBQCK4F3.js} +7 -3
- package/dist/chunk-IBQCK4F3.js.map +1 -0
- package/dist/chunk-J55UQC5H.cjs.map +1 -1
- package/dist/{chunk-J2A46VCA.js → chunk-KUUSP6OS.js} +576 -70
- package/dist/chunk-KUUSP6OS.js.map +1 -0
- package/dist/{chunk-RSDUH4XF.js → chunk-LGF2IO66.js} +2 -2
- package/dist/{chunk-BJ6RYYXV.js → chunk-MXA6YW2W.js} +577 -71
- package/dist/chunk-MXA6YW2W.js.map +1 -0
- package/dist/{chunk-ZD5WNQNC.cjs → chunk-OIUSF2VA.cjs} +16 -12
- package/dist/chunk-OIUSF2VA.cjs.map +1 -0
- package/dist/{chunk-AZQWESRH.js → chunk-QVCHFCT2.js} +2 -2
- package/dist/{chunk-W7P4GPOV.js → chunk-RCI7LY4N.js} +8 -4
- package/dist/chunk-RCI7LY4N.js.map +1 -0
- package/dist/{chunk-V4BKT65D.cjs → chunk-SVNBZEL6.cjs} +3 -3
- package/dist/chunk-SVNBZEL6.cjs.map +1 -0
- package/dist/{chunk-OOX2GZZ4.js → chunk-T2BJPT6D.js} +3 -3
- package/dist/{chunk-OOX2GZZ4.js.map → chunk-T2BJPT6D.js.map} +1 -1
- package/dist/chunk-TK3FDAEE.cjs +9 -0
- package/dist/chunk-TK3FDAEE.cjs.map +1 -0
- package/dist/{chunk-UVUKT3IQ.js → chunk-TMJVD6FW.js} +2 -2
- package/dist/{chunk-ZN3LHNJG.js → chunk-V5X4LLVM.js} +28 -27
- package/dist/chunk-V5X4LLVM.js.map +1 -0
- package/dist/{chunk-W3RADOLO.js → chunk-VTVK2JMI.js} +2 -2
- package/dist/{chunk-PSJLB3SZ.js → chunk-XG4SYOZL.js} +2 -2
- package/dist/{chunk-RRURZDEK.js → chunk-YCY2R4FM.js} +2 -2
- package/dist/{chunk-5X7XWYR2.js → chunk-Z2PPDQK2.js} +2 -2
- package/dist/chunks-5QTTAT5T.js +10 -0
- package/dist/cli.js +154 -115
- package/dist/cli.js.map +1 -1
- package/dist/{formula-QZAOKPBX.js → formula-7ZOZ5QJ6.js} +8 -4
- package/dist/{formula-QZAOKPBX.js.map → formula-7ZOZ5QJ6.js.map} +1 -1
- package/dist/{formula-GPCOJJXN.js → formula-HQFZEXFF.js} +7 -3
- package/dist/{formula-GPCOJJXN.js.map → formula-HQFZEXFF.js.map} +1 -1
- package/dist/{formula-BQ5RW5XD.cjs → formula-YYJQBKEN.cjs} +13 -9
- package/dist/formula-YYJQBKEN.cjs.map +1 -0
- package/dist/{image-ocr-POCME5I4.js → image-ocr-4BGX2EJJ.js} +7 -6
- package/dist/{image-ocr-POCME5I4.js.map → image-ocr-4BGX2EJJ.js.map} +1 -1
- package/dist/{image-ocr-VKIUBLBX.cjs → image-ocr-CC26Q5KG.cjs} +16 -15
- package/dist/image-ocr-CC26Q5KG.cjs.map +1 -0
- package/dist/{image-ocr-TWNNVTZS.js → image-ocr-RK3HJVCI.js} +10 -9
- package/dist/{image-ocr-TWNNVTZS.js.map → image-ocr-RK3HJVCI.js.map} +1 -1
- package/dist/index.cjs +338 -347
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +42 -51
- package/dist/index.js.map +1 -1
- package/dist/mcp.js +22 -22
- package/dist/{model-bundle-THYUL7GG.js → model-bundle-VHRXG63R.js} +5 -5
- package/dist/{models-U22N4RXX.js → models-G3WA24SY.js} +5 -5
- package/dist/page-range-QHHFTL7X.cjs.map +1 -1
- package/dist/{parser-JOMFOZLH.cjs → parser-BGORCLIU.cjs} +449 -244
- package/dist/parser-BGORCLIU.cjs.map +1 -0
- package/dist/{parser-SCXRLOW7.js → parser-GFDGAVLV.js} +242 -37
- package/dist/parser-GFDGAVLV.js.map +1 -0
- package/dist/{parser-NKP2NCSV.js → parser-SOWTUOMK.js} +245 -40
- package/dist/parser-SOWTUOMK.js.map +1 -0
- package/dist/pdf-ocr-7IOOVR2I.js +20 -0
- package/dist/pdf-ocr-EJ2HNZN6.cjs +17 -0
- package/dist/pdf-ocr-EJ2HNZN6.cjs.map +1 -0
- package/dist/pdf-ocr-RACAZU3N.js +16 -0
- package/dist/{profile-io-UI3TZBYH.js → profile-io-Q2T47RVH.js} +3 -3
- package/dist/{rasterize-XMBV5H2I.js → rasterize-OAVMUTE6.js} +3 -3
- package/dist/{redact-doc-7ZZMHDBO.js → redact-doc-ECFOVR4X.js} +11 -11
- package/dist/{render-SWRTUDAV.js → render-NSKWZVTD.js} +7 -7
- package/dist/seal-A4MG7MPQ.js +10 -0
- package/dist/{setup-43JJEEU7.js → setup-REH2KZP2.js} +3 -3
- package/dist/visual-B56WQAGW.js +20 -0
- package/dist/{watch-NRATQ472.js → watch-JXDUZYBY.js} +12 -12
- package/package.json +1 -1
- package/dist/chunk-2I2RTJJ5.js.map +0 -1
- package/dist/chunk-2ZBLQVAS.cjs.map +0 -1
- package/dist/chunk-BJ6RYYXV.js.map +0 -1
- package/dist/chunk-HZV52V2X.cjs.map +0 -1
- package/dist/chunk-IXX3WHIE.js.map +0 -1
- package/dist/chunk-J2A46VCA.js.map +0 -1
- package/dist/chunk-SHRRD2TD.cjs.map +0 -1
- package/dist/chunk-V4BKT65D.cjs.map +0 -1
- package/dist/chunk-W7P4GPOV.js.map +0 -1
- package/dist/chunk-WN5YLP7H.cjs.map +0 -1
- package/dist/chunk-ZD5WNQNC.cjs.map +0 -1
- package/dist/chunk-ZN3LHNJG.js.map +0 -1
- package/dist/chunks-OQDRDICD.js +0 -10
- package/dist/formula-BQ5RW5XD.cjs.map +0 -1
- package/dist/image-ocr-VKIUBLBX.cjs.map +0 -1
- package/dist/parser-JOMFOZLH.cjs.map +0 -1
- package/dist/parser-NKP2NCSV.js.map +0 -1
- package/dist/parser-SCXRLOW7.js.map +0 -1
- package/dist/pdf-ocr-NF4AY5MI.cjs +0 -16
- package/dist/pdf-ocr-NF4AY5MI.cjs.map +0 -1
- package/dist/pdf-ocr-OLII3WAG.js +0 -15
- package/dist/pdf-ocr-VJL7ON2Q.js +0 -19
- package/dist/seal-UKKJZHKE.js +0 -10
- package/dist/visual-D2563HCJ.js +0 -20
- /package/dist/{-WOKB25R2.js.map → -DDAVBMHD.js.map} +0 -0
- /package/dist/{chunk-BGOR5GCF.js.map → chunk-274ZPMHK.js.map} +0 -0
- /package/dist/{chunk-6GLTGOP6.js.map → chunk-4IBY5LTJ.js.map} +0 -0
- /package/dist/{chunk-CAN5P6N6.js.map → chunk-7GR2GCJF.js.map} +0 -0
- /package/dist/{chunk-NES5U4JK.js.map → chunk-DUV7Y6IQ.js.map} +0 -0
- /package/dist/{chunk-3FZGL3IL.js.map → chunk-ELOPDQES.js.map} +0 -0
- /package/dist/{chunk-VGDTONTB.js.map → chunk-F5YVCJVF.js.map} +0 -0
- /package/dist/{chunk-RDBTOE5X.js.map → chunk-HRJJDNRD.js.map} +0 -0
- /package/dist/{chunk-KSJ7GKNQ.js.map → chunk-IAXGGQGD.js.map} +0 -0
- /package/dist/{chunk-RSDUH4XF.js.map → chunk-LGF2IO66.js.map} +0 -0
- /package/dist/{chunk-AZQWESRH.js.map → chunk-QVCHFCT2.js.map} +0 -0
- /package/dist/{chunk-UVUKT3IQ.js.map → chunk-TMJVD6FW.js.map} +0 -0
- /package/dist/{chunk-W3RADOLO.js.map → chunk-VTVK2JMI.js.map} +0 -0
- /package/dist/{chunk-PSJLB3SZ.js.map → chunk-XG4SYOZL.js.map} +0 -0
- /package/dist/{chunk-RRURZDEK.js.map → chunk-YCY2R4FM.js.map} +0 -0
- /package/dist/{chunk-5X7XWYR2.js.map → chunk-Z2PPDQK2.js.map} +0 -0
- /package/dist/{chunks-OQDRDICD.js.map → chunks-5QTTAT5T.js.map} +0 -0
- /package/dist/{model-bundle-THYUL7GG.js.map → model-bundle-VHRXG63R.js.map} +0 -0
- /package/dist/{models-U22N4RXX.js.map → models-G3WA24SY.js.map} +0 -0
- /package/dist/{pdf-ocr-OLII3WAG.js.map → pdf-ocr-7IOOVR2I.js.map} +0 -0
- /package/dist/{pdf-ocr-VJL7ON2Q.js.map → pdf-ocr-RACAZU3N.js.map} +0 -0
- /package/dist/{profile-io-UI3TZBYH.js.map → profile-io-Q2T47RVH.js.map} +0 -0
- /package/dist/{rasterize-XMBV5H2I.js.map → rasterize-OAVMUTE6.js.map} +0 -0
- /package/dist/{redact-doc-7ZZMHDBO.js.map → redact-doc-ECFOVR4X.js.map} +0 -0
- /package/dist/{render-SWRTUDAV.js.map → render-NSKWZVTD.js.map} +0 -0
- /package/dist/{seal-UKKJZHKE.js.map → seal-A4MG7MPQ.js.map} +0 -0
- /package/dist/{setup-43JJEEU7.js.map → setup-REH2KZP2.js.map} +0 -0
- /package/dist/{visual-D2563HCJ.js.map → visual-B56WQAGW.js.map} +0 -0
- /package/dist/{watch-NRATQ472.js.map → watch-JXDUZYBY.js.map} +0 -0
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import {
|
|
2
2
|
blocksToPages,
|
|
3
3
|
encodePng
|
|
4
|
-
} from "./chunk-
|
|
4
|
+
} from "./chunk-274ZPMHK.js";
|
|
5
5
|
import {
|
|
6
6
|
hasRequestedPagesAfter,
|
|
7
7
|
parsePageRange
|
|
@@ -12,6 +12,8 @@ import {
|
|
|
12
12
|
CONT_PARTS,
|
|
13
13
|
EMPTY_PARTS,
|
|
14
14
|
FILLER_CELLS,
|
|
15
|
+
FRAME_READING_UNITS,
|
|
16
|
+
FRAME_TITLE_BLOCKS,
|
|
15
17
|
IMAGE_CELLS,
|
|
16
18
|
NO_EDGES,
|
|
17
19
|
PART_COLXS,
|
|
@@ -22,6 +24,7 @@ import {
|
|
|
22
24
|
TOC_BLOCKS,
|
|
23
25
|
WrapLexicon,
|
|
24
26
|
collapseEvenSpacing,
|
|
27
|
+
computeBBox,
|
|
25
28
|
computeMedianFontSizeFromFreq,
|
|
26
29
|
detectDocumentStyleHeadings,
|
|
27
30
|
detectHeadings,
|
|
@@ -29,26 +32,32 @@ import {
|
|
|
29
32
|
detectMarkerHeadings,
|
|
30
33
|
detectPageLeadHeadings,
|
|
31
34
|
detectRepeatedPageLabels,
|
|
35
|
+
detectRightArrowRegions,
|
|
32
36
|
detectSiblingStyleHeadings,
|
|
33
37
|
detectTableCaptions,
|
|
34
38
|
detectTypographyHeadings,
|
|
39
|
+
dominantStyle,
|
|
35
40
|
extractImageRegions,
|
|
36
41
|
extractLines,
|
|
37
42
|
extractPageBlocksWithLines,
|
|
38
43
|
filterHiddenText,
|
|
44
|
+
groupByY,
|
|
39
45
|
joinCellEdges,
|
|
40
46
|
joinPageBreakWraps,
|
|
41
47
|
latinSoftWrap,
|
|
48
|
+
mergeLineSimple,
|
|
42
49
|
mergeStackedHeadingLines,
|
|
43
50
|
normalizeItems,
|
|
44
51
|
ocrModelsCached,
|
|
52
|
+
recordFrameReadingUnit,
|
|
45
53
|
refineDocumentStyleHeadings,
|
|
46
54
|
removeHeaderFooterBlocks,
|
|
47
55
|
removeSideTabs,
|
|
56
|
+
restoreImageBullets,
|
|
48
57
|
startsNewItem,
|
|
49
58
|
trimTrailingEmptyTableCols,
|
|
50
59
|
wrapJoiner
|
|
51
|
-
} from "./chunk-
|
|
60
|
+
} from "./chunk-MXA6YW2W.js";
|
|
52
61
|
import {
|
|
53
62
|
CELL_EDGES,
|
|
54
63
|
CONTENT_CELLS,
|
|
@@ -58,12 +67,12 @@ import {
|
|
|
58
67
|
escapeLiteralTags,
|
|
59
68
|
stripScriptTags,
|
|
60
69
|
unframeLayoutTables
|
|
61
|
-
} from "./chunk-
|
|
62
|
-
import "./chunk-
|
|
70
|
+
} from "./chunk-XG4SYOZL.js";
|
|
71
|
+
import "./chunk-ELOPDQES.js";
|
|
63
72
|
import {
|
|
64
73
|
KordocError,
|
|
65
74
|
sanitizeHref
|
|
66
|
-
} from "./chunk-
|
|
75
|
+
} from "./chunk-7GR2GCJF.js";
|
|
67
76
|
|
|
68
77
|
// src/pdf/ocr-region-merge.ts
|
|
69
78
|
function mergeOcrImageRegions(blocks, page, regions, ocrBlocks) {
|
|
@@ -76,8 +85,10 @@ function mergeOcrImageRegions(blocks, page, regions, ocrBlocks) {
|
|
|
76
85
|
const overlapH = Math.max(0, Math.min(b.y + b.height, region.y2) - Math.max(b.y, region.y1));
|
|
77
86
|
return overlapW * overlapH >= b.width * b.height * 0.8;
|
|
78
87
|
});
|
|
88
|
+
const labels = candidates.filter((b) => b.type === "paragraph" && b.bbox.height <= 24 && (b.text?.match(/[\p{L}\p{N}]/gu)?.length ?? 0) >= 2);
|
|
89
|
+
const axisFragments = rotatedAxisFragments(candidates);
|
|
79
90
|
const accepted = candidates.filter((b) => {
|
|
80
|
-
if (b.type === "paragraph") return (b.text?.match(/[\p{L}\p{N}]/gu)?.length ?? 0) >= 2;
|
|
91
|
+
if (b.type === "paragraph") return (b.text?.match(/[\p{L}\p{N}]/gu)?.length ?? 0) >= 2 || !axisFragments.has(b) && supportedDiagramLabel(b, labels, region);
|
|
81
92
|
const t = b.table;
|
|
82
93
|
if (b.type !== "table" || !t) return false;
|
|
83
94
|
if (t.rows === 1 && t.cols === 1) {
|
|
@@ -88,29 +99,89 @@ function mergeOcrImageRegions(blocks, page, regions, ocrBlocks) {
|
|
|
88
99
|
return t.rows >= 2 && t.cols >= 2 && headerLabels >= t.cols * 0.75 && t.cells.slice(1).some((row) => row.filter((c) => c.text.trim()).length >= 2);
|
|
89
100
|
});
|
|
90
101
|
const selected = candidates.flatMap((b) => accepted.includes(b) ? [b] : b.type === "table" && b.table ? rowParagraphs(b).filter((p) => /[\p{L}\p{N}]{2}/u.test(p.text ?? "")) : []);
|
|
91
|
-
|
|
102
|
+
const hasOriginal = (block) => blocks.some((existing) => {
|
|
92
103
|
const b = block.bbox;
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
});
|
|
107
|
-
const
|
|
108
|
-
|
|
109
|
-
|
|
104
|
+
if (existing.pageNumber !== page || !existing.bbox || existing.type === "image") return false;
|
|
105
|
+
const e = existing.bbox;
|
|
106
|
+
const x = Math.max(0, Math.min(e.x + e.width, b.x + b.width) - Math.max(e.x, b.x));
|
|
107
|
+
const y = Math.max(0, Math.min(e.y + e.height, b.y + b.height) - Math.max(e.y, b.y));
|
|
108
|
+
return x * y > b.width * b.height * 0.2;
|
|
109
|
+
});
|
|
110
|
+
const selectedSet = new Set(selected), seen = /* @__PURE__ */ new Set();
|
|
111
|
+
for (const block of selected) {
|
|
112
|
+
if (seen.has(block)) continue;
|
|
113
|
+
const frame = FRAME_READING_UNITS.get(block);
|
|
114
|
+
const source = frame?.blocks.every((member) => selectedSet.has(member)) ? frame.blocks : [block];
|
|
115
|
+
source.forEach((member) => seen.add(member));
|
|
116
|
+
const available = source.filter((member) => !hasOriginal(member));
|
|
117
|
+
const units = frame && available.length === source.length && source === frame.blocks ? [{ blocks: available, bbox: frame.bbox, atomic: true }] : available.map((member) => ({ blocks: [member], bbox: member.bbox, atomic: false }));
|
|
118
|
+
for (const unit of units) {
|
|
119
|
+
const b = unit.bbox;
|
|
120
|
+
const index = blocks.findIndex((existing) => {
|
|
121
|
+
const e = FRAME_READING_UNITS.get(existing)?.bbox ?? existing.bbox;
|
|
122
|
+
if (existing.pageNumber !== page || !e) return false;
|
|
123
|
+
const beside = e.y < region.y2 && e.y + e.height > region.y1 && e.x >= region.x2 - 1;
|
|
124
|
+
return e.y < b.y || beside;
|
|
125
|
+
});
|
|
126
|
+
const placed = unit.blocks.map((member) => member.type === "paragraph" ? { ...member, style: void 0 } : member);
|
|
127
|
+
if (unit.atomic) recordFrameReadingUnit(placed, unit.bbox);
|
|
128
|
+
blocks.splice(index < 0 ? blocks.length : index, 0, ...placed);
|
|
129
|
+
added += placed.length;
|
|
130
|
+
}
|
|
110
131
|
}
|
|
111
132
|
}
|
|
112
133
|
return added;
|
|
113
134
|
}
|
|
135
|
+
function supportedDiagramLabel(block, labels, region) {
|
|
136
|
+
const b = block.bbox, text = block.text?.trim() ?? "";
|
|
137
|
+
if (!b || !/^[\p{L}\p{N}]$/u.test(text) || b.height < 4 || b.width < 1 || b.width > b.height * 2 || b.x < region.x1 || b.y < region.y1 || b.x + b.width > region.x2 || b.y + b.height > region.y2 || b.width * b.height > (region.x2 - region.x1) * (region.y2 - region.y1) * 5e-3 || labels.length < 3 || !labels.some((l) => /\p{L}{3}/u.test(l.text ?? "")) || labels.filter((l) => !/\p{L}/u.test(l.text ?? "") && (l.text?.match(/\p{N}/gu)?.length ?? 0) >= 2).length < 2) return false;
|
|
138
|
+
let above = false, below = false;
|
|
139
|
+
for (const label of labels) {
|
|
140
|
+
const a = label.bbox, em = Math.max(b.height, a.height);
|
|
141
|
+
if (b.x + b.width < a.x - em * 2 || b.x > a.x + a.width + em * 2) continue;
|
|
142
|
+
const upperGap = a.y - (b.y + b.height), lowerGap = b.y - (a.y + a.height);
|
|
143
|
+
if (upperGap >= 0 && upperGap <= em * 4) above = true;
|
|
144
|
+
if (lowerGap >= 0 && lowerGap <= em * 4) below = true;
|
|
145
|
+
}
|
|
146
|
+
return above && below;
|
|
147
|
+
}
|
|
148
|
+
function rotatedAxisFragments(candidates) {
|
|
149
|
+
const paragraphs = candidates.filter((b) => b.type === "paragraph" && b.bbox.height <= 24);
|
|
150
|
+
const axes = [];
|
|
151
|
+
for (const block of paragraphs) {
|
|
152
|
+
const b = block.bbox, text = block.text?.trim() ?? "";
|
|
153
|
+
if (!/^[\d\s.,%+−-]+$/u.test(text) || !/\d/u.test(text) || b.width > b.height * 6) continue;
|
|
154
|
+
const axis = axes.find((a) => Math.abs(a[0].bbox.x + a[0].bbox.width - b.x - b.width) <= Math.max(a[0].bbox.height, b.height) * 0.5);
|
|
155
|
+
if (axis) axis.push(block);
|
|
156
|
+
else axes.push([block]);
|
|
157
|
+
}
|
|
158
|
+
const fragments = /* @__PURE__ */ new Set();
|
|
159
|
+
const aligned = (a, b) => {
|
|
160
|
+
const x = a.bbox, y = b.bbox, tolerance = Math.max(x.height, y.height) * 0.5;
|
|
161
|
+
return Math.abs(x.x - y.x) <= tolerance || Math.abs(x.x + x.width - y.x - y.width) <= tolerance;
|
|
162
|
+
};
|
|
163
|
+
for (const axis of axes) {
|
|
164
|
+
if (axis.length < 3) continue;
|
|
165
|
+
const bottom = Math.min(...axis.map((a) => a.bbox.y)), top = Math.max(...axis.map((a) => a.bbox.y + a.bbox.height));
|
|
166
|
+
const em = Math.max(...axis.map((a) => a.bbox.height)), right = axis[0].bbox.x + axis[0].bbox.width;
|
|
167
|
+
if (top - bottom < em * 6) continue;
|
|
168
|
+
const left = paragraphs.filter((block) => {
|
|
169
|
+
const b = block.bbox, text = block.text?.trim() ?? "";
|
|
170
|
+
return /\p{Script=Latin}/u.test(text) && (text.match(/[\p{L}\p{N}]/gu)?.length ?? 0) <= 3 && b.width <= b.height * 3 && b.x + b.width >= right - em * 6 && b.x + b.width <= right - Math.max(em, b.height) && b.y >= bottom && b.y + b.height <= top;
|
|
171
|
+
});
|
|
172
|
+
const stack = left.filter((a) => left.some((b) => {
|
|
173
|
+
if (a === b || !aligned(a, b)) return false;
|
|
174
|
+
const x = a.bbox, y = b.bbox, gap = Math.max(x.y, y.y) - Math.min(x.y + x.height, y.y + y.height);
|
|
175
|
+
return gap >= -Math.min(x.height, y.height) * 0.5 && gap <= Math.max(x.height, y.height);
|
|
176
|
+
}));
|
|
177
|
+
if (stack.length < 2) continue;
|
|
178
|
+
for (const block of paragraphs) {
|
|
179
|
+
const b = block.bbox;
|
|
180
|
+
if (b.y >= bottom && b.y + b.height <= top && b.x + b.width >= right - em * 6 && b.x + b.width <= right - Math.max(em, b.height) && /^[\p{L}\p{N}]$/u.test(block.text?.trim() ?? "") && stack.some((s) => aligned(s, block))) fragments.add(block);
|
|
181
|
+
}
|
|
182
|
+
}
|
|
183
|
+
return fragments;
|
|
184
|
+
}
|
|
114
185
|
function rowParagraphs(block) {
|
|
115
186
|
const t = block.table, b = block.bbox;
|
|
116
187
|
const h = b.height / t.rows;
|
|
@@ -1120,7 +1191,7 @@ function sameHeadShape(a, b) {
|
|
|
1120
1191
|
let tall = false;
|
|
1121
1192
|
for (let c = 0; c < a.length; c++) {
|
|
1122
1193
|
if (a[c].colSpan !== b[c].colSpan || a[c].rowSpan !== b[c].rowSpan) return false;
|
|
1123
|
-
if (a[c].rowSpan >= 2 && a[c].text.trim()) tall = true;
|
|
1194
|
+
if (a[c].rowSpan >= 2 && a[c].text.trim() && b[c].text.trim()) tall = true;
|
|
1124
1195
|
}
|
|
1125
1196
|
return tall;
|
|
1126
1197
|
}
|
|
@@ -1157,9 +1228,10 @@ function mergeCrossPageTables(blocks, pageHeights, lex) {
|
|
|
1157
1228
|
if (px && cx && !shiftedSame(px, cx, !CLIP_TABLES.has(prev.table) && !CLIP_TABLES.has(curr.table))) continue;
|
|
1158
1229
|
if (!rowTextsEqual(prev.table.cells[0], curr.table.cells[0]) && sameHeadShape(prev.table.cells[0], curr.table.cells[0])) continue;
|
|
1159
1230
|
let currCells = curr.table.cells;
|
|
1160
|
-
|
|
1161
|
-
|
|
1162
|
-
|
|
1231
|
+
const headRows = repeatedHeaderRows(prev.table, curr.table);
|
|
1232
|
+
if (headRows < 0) continue;
|
|
1233
|
+
if (headRows) currCells = currCells.slice(headRows);
|
|
1234
|
+
if (currCells.length) continueRowSpans(prev.table.cells, currCells);
|
|
1163
1235
|
if (currCells.length === 0) {
|
|
1164
1236
|
blocks.splice(j, 1);
|
|
1165
1237
|
continue;
|
|
@@ -1361,6 +1433,45 @@ function chainHead(blocks, i, pageHeights) {
|
|
|
1361
1433
|
}
|
|
1362
1434
|
return k;
|
|
1363
1435
|
}
|
|
1436
|
+
var ROW_CONTINUATIONS = /* @__PURE__ */ new WeakMap();
|
|
1437
|
+
function continueRowSpans(prevCells, currCells) {
|
|
1438
|
+
const first = currCells[0];
|
|
1439
|
+
const last = prevCells.length;
|
|
1440
|
+
for (let c = 0; c < first.length; c++) {
|
|
1441
|
+
const cell = first[c];
|
|
1442
|
+
if (hasContent(cell) || (cell.rowSpan || 1) < 2) continue;
|
|
1443
|
+
let anchor;
|
|
1444
|
+
for (let r = last - 1; r >= 0 && !anchor; r--) {
|
|
1445
|
+
const a = prevCells[r]?.[c];
|
|
1446
|
+
if (a && r + (a.rowSpan || 1) === last && (a.colSpan || 1) === (cell.colSpan || 1) && (hasContent(a) || a.rowSpan >= 2)) anchor = a;
|
|
1447
|
+
}
|
|
1448
|
+
if (!anchor) continue;
|
|
1449
|
+
if (!hasContent(anchor)) {
|
|
1450
|
+
ROW_CONTINUATIONS.set(anchor, cell);
|
|
1451
|
+
continue;
|
|
1452
|
+
}
|
|
1453
|
+
for (let part = cell; part; ) {
|
|
1454
|
+
const next = ROW_CONTINUATIONS.get(part);
|
|
1455
|
+
anchor.rowSpan = (anchor.rowSpan || 1) + part.rowSpan;
|
|
1456
|
+
part.rowSpan = 1;
|
|
1457
|
+
part.colSpan = 1;
|
|
1458
|
+
ROW_CONTINUATIONS.delete(part);
|
|
1459
|
+
part = next;
|
|
1460
|
+
}
|
|
1461
|
+
}
|
|
1462
|
+
}
|
|
1463
|
+
function repeatedHeaderRows(prev, curr) {
|
|
1464
|
+
if (!rowTextsEqual(prev.cells[0], curr.cells[0])) return 0;
|
|
1465
|
+
const pa = anchorsOf(prev), ca = anchorsOf(curr);
|
|
1466
|
+
let depth = 1;
|
|
1467
|
+
for (let r = 0; r < depth && r < prev.rows; r++) {
|
|
1468
|
+
for (const a of pa) if (a.r === r) depth = Math.max(depth, r + a.rs);
|
|
1469
|
+
}
|
|
1470
|
+
if (depth >= curr.rows || depth > prev.rows) return -1;
|
|
1471
|
+
const p = pa.filter((a) => a.r < depth), d = ca.filter((a) => a.r < depth);
|
|
1472
|
+
const norm = (text) => flowText(text).replace(/\s+/g, "");
|
|
1473
|
+
return p.length === d.length && p.every((a, i) => a.r === d[i].r && a.c === d[i].c && a.rs === d[i].rs && a.cs === d[i].cs && norm(a.cell.text) === norm(d[i].cell.text)) ? depth : -1;
|
|
1474
|
+
}
|
|
1364
1475
|
function rowTextsEqual(a, b) {
|
|
1365
1476
|
if (a.length !== b.length) return false;
|
|
1366
1477
|
const norm = (t) => flowText(t).replace(/\s+/g, "");
|
|
@@ -1455,6 +1566,34 @@ function fillNestedContinuation(blocks, at) {
|
|
|
1455
1566
|
blocks.splice(at, 1);
|
|
1456
1567
|
}
|
|
1457
1568
|
|
|
1569
|
+
// src/pdf/selection-context.ts
|
|
1570
|
+
function selectionContextPages(selected, pageCount) {
|
|
1571
|
+
const out = /* @__PURE__ */ new Set();
|
|
1572
|
+
for (const page of selected) {
|
|
1573
|
+
for (let distance = 1; distance <= 4; distance++) {
|
|
1574
|
+
for (const neighbor of [page - distance, page + distance]) {
|
|
1575
|
+
if (neighbor < 1 || neighbor > pageCount || selected.has(neighbor)) continue;
|
|
1576
|
+
out.add(neighbor);
|
|
1577
|
+
}
|
|
1578
|
+
}
|
|
1579
|
+
}
|
|
1580
|
+
return [...out].sort((a, b) => a - b);
|
|
1581
|
+
}
|
|
1582
|
+
function marginContextBlocks(raw, page, view) {
|
|
1583
|
+
const [x1, y1, x2, y2] = view;
|
|
1584
|
+
const width = x2 - x1, height = y2 - y1;
|
|
1585
|
+
const items = filterHiddenText(normalizeItems(raw), width, height, x1, y1).visible;
|
|
1586
|
+
for (const item of items) {
|
|
1587
|
+
item.x -= x1;
|
|
1588
|
+
item.y -= y1;
|
|
1589
|
+
}
|
|
1590
|
+
return groupByY(items).flatMap((line) => {
|
|
1591
|
+
const bbox = computeBBox(line, page);
|
|
1592
|
+
if (bbox.y + bbox.height < height * 0.88 && bbox.y > height * 0.12) return [];
|
|
1593
|
+
return [{ type: "paragraph", text: mergeLineSimple(line), pageNumber: page, bbox, style: dominantStyle(line) }];
|
|
1594
|
+
});
|
|
1595
|
+
}
|
|
1596
|
+
|
|
1458
1597
|
// src/pdf/symbol-fonts.ts
|
|
1459
1598
|
var WINANSI_REVERSE = {
|
|
1460
1599
|
8364: 128,
|
|
@@ -1762,6 +1901,9 @@ var NAMED = {
|
|
|
1762
1901
|
quotedblright: "\u201D",
|
|
1763
1902
|
quotesingle: "'",
|
|
1764
1903
|
quotedbl: '"',
|
|
1904
|
+
bullet: "\u2022",
|
|
1905
|
+
openbullet: "\u25E6",
|
|
1906
|
+
whitebullet: "\u25E6",
|
|
1765
1907
|
question: "?",
|
|
1766
1908
|
exclam: "!",
|
|
1767
1909
|
percent: "%",
|
|
@@ -1778,7 +1920,9 @@ function glyphNameText(name) {
|
|
|
1778
1920
|
let out = "";
|
|
1779
1921
|
for (const part of base.split("_")) {
|
|
1780
1922
|
const uni = /^uni([0-9A-F]{4})$/.exec(part) ?? /^u([0-9A-F]{4,6})$/.exec(part);
|
|
1781
|
-
const
|
|
1923
|
+
const code = uni ? parseInt(uni[1], 16) : void 0;
|
|
1924
|
+
if (code !== void 0 && (code > 1114111 || code >= 55296 && code <= 57343)) return void 0;
|
|
1925
|
+
const ch = /^[A-Za-z]$/.test(part) ? part : NAMED[part] ?? (code !== void 0 ? String.fromCodePoint(code) : void 0);
|
|
1782
1926
|
if (ch === void 0) return void 0;
|
|
1783
1927
|
out += ch;
|
|
1784
1928
|
}
|
|
@@ -2464,6 +2608,35 @@ function demoteNonHeadingRoles(blocks, pageHeights, faceNames) {
|
|
|
2464
2608
|
}
|
|
2465
2609
|
}
|
|
2466
2610
|
}
|
|
2611
|
+
const citedProse = /* @__PURE__ */ new Set();
|
|
2612
|
+
const numberedProse = /* @__PURE__ */ new Set();
|
|
2613
|
+
for (const page of byPage.values()) {
|
|
2614
|
+
const numbered = page.filter((b) => (b.type === "heading" || b.type === "paragraph") && /^[①-⑮]\s*/.test(b.text?.trim() ?? "") && b.bbox && b.style?.fontName && b.style.fontSize && !/Bold|Black|Heavy|Semibold/i.test(faceNames?.get(b.style.fontName) ?? ""));
|
|
2615
|
+
let chain = [];
|
|
2616
|
+
const finish = () => {
|
|
2617
|
+
if (chain.length < 3 || !chain.some((b) => (b.text?.length ?? 0) >= 40 && b.bbox.height >= b.style.fontSize * 2.4)) return;
|
|
2618
|
+
for (const b of chain) numberedProse.add(b);
|
|
2619
|
+
const first = chain[0], size = first.style.fontSize;
|
|
2620
|
+
for (const b of page) if (/^[○●•◦]\s/.test(b.text?.trim() ?? "") && b.style?.fontName === first.style?.fontName && b.style?.fontSize === size && b.bbox && Math.abs(b.bbox.x - first.bbox.x) <= size * 0.5 && (b.text?.length ?? 0) >= 15) numberedProse.add(b);
|
|
2621
|
+
};
|
|
2622
|
+
for (const b of numbered) {
|
|
2623
|
+
const prev = chain.at(-1), size = b.style.fontSize;
|
|
2624
|
+
if (!prev || b.text.trim().charCodeAt(0) !== prev.text.trim().charCodeAt(0) + 1 || b.style.fontName !== prev.style.fontName || size !== prev.style.fontSize || Math.abs(b.bbox.x - prev.bbox.x) > size * 0.5 || prev.bbox.y - (b.bbox.y + b.bbox.height) > size * 8) {
|
|
2625
|
+
finish();
|
|
2626
|
+
chain = [];
|
|
2627
|
+
}
|
|
2628
|
+
chain.push(b);
|
|
2629
|
+
}
|
|
2630
|
+
finish();
|
|
2631
|
+
}
|
|
2632
|
+
for (let i = 0; i + 1 < blocks.length; i++) {
|
|
2633
|
+
const prose = blocks[i], reference = blocks[i + 1];
|
|
2634
|
+
const a = prose.bbox, b = reference.bbox, size = prose.style?.fontSize ?? 0;
|
|
2635
|
+
const source = reference.text?.replace(/<[^>]+>/g, "").trim() ?? "";
|
|
2636
|
+
if (prose.type !== "heading" && prose.type !== "paragraph" && prose.type !== "list" || reference.type !== "heading" && reference.type !== "paragraph" || (prose.text?.length ?? 0) < 40 || !a || !b || size <= 0 || a.height < size * 2.4 || prose.pageNumber !== reference.pageNumber || prose.style?.fontName !== reference.style?.fontName || prose.style?.fontSize !== reference.style?.fontSize || Math.abs(a.x - b.x) > size && !(/^[○●•◦]\s/.test(prose.text ?? "") && b.x >= a.x && b.x - a.x <= size * 2) || a.y - (b.y + b.height) < 0 || a.y - (b.y + b.height) > size || !/^[((].*(?:제\s*\d+\s*조|(?:Article|Section)\s+\d+).*[))]$/i.test(source)) continue;
|
|
2637
|
+
citedProse.add(prose);
|
|
2638
|
+
citedProse.add(reference);
|
|
2639
|
+
}
|
|
2467
2640
|
for (let i = 0; i < blocks.length; i++) {
|
|
2468
2641
|
const block = blocks[i];
|
|
2469
2642
|
if (block.type !== "heading" || !block.text) continue;
|
|
@@ -2511,7 +2684,7 @@ function demoteNonHeadingRoles(blocks, pageHeights, faceNames) {
|
|
|
2511
2684
|
const byline = /Italic|Oblique/i.test(face) && !/Bold|Black|Heavy|Semibold/i.test(face) && !!bodyFace && size <= Number(bodySize) + 0.5 && blocks[i - 1]?.type === "heading" && blocks[i - 1].pageNumber === block.pageNumber;
|
|
2512
2685
|
const ocrFragment = block.style?.fontName === "ocr" && (/^[.,;:…·•-]/.test(text) || text.includes("\u2026") || (text.match(/\p{L}/gu)?.length ?? 0) < 2 || text.split(/\s+/).length > 7);
|
|
2513
2686
|
const crowdedOcr = block.style?.fontName === "ocr" && !!box && [prev, next].every((o) => o?.type === "paragraph" && o.pageNumber === block.pageNumber && o.style?.fontName === "ocr" && !!o.bbox && (o.text?.length ?? 0) >= 15 && Math.abs(o.bbox.x - box.x) <= size * 0.25 && Math.min(o.bbox.y + o.bbox.height, box.y + box.height) - Math.max(o.bbox.y, box.y) >= o.bbox.height * 0.2) && prev.bbox.y > box.y && next.bbox.y < box.y;
|
|
2514
|
-
if (ocrFragment || crowdedOcr || tocEntry || proseStyle || kicker || byline || tiny || !/\p{L}/u.test(text) && !chapterNumber || /^[a-z]/.test(text) || CAPTION.test(text) || EQUATION_NUMBER.test(block.text) || DISPLAY_MATH.test(text) || // 닫는 괄호가 여는 괄호보다 많으면 앞 줄에서 이어진 문장 조각이다 ("Fact-checking) and is used …") — "1)"·"가)" 앞머리 번호는 빼고 센다
|
|
2687
|
+
if (numberedProse.has(block) || citedProse.has(block) || ocrFragment || crowdedOcr || tocEntry || proseStyle || kicker || byline || tiny || !/\p{L}/u.test(text) && !chapterNumber || /^[a-z]/.test(text) || CAPTION.test(text) || EQUATION_NUMBER.test(block.text) || DISPLAY_MATH.test(text) || // 닫는 괄호가 여는 괄호보다 많으면 앞 줄에서 이어진 문장 조각이다 ("Fact-checking) and is used …") — "1)"·"가)" 앞머리 번호는 빼고 센다
|
|
2515
2688
|
unbalancedClose(text.replace(/^\s*[\dA-Za-z가-힣ⅰ-ⅹ]{1,3}\)\s*/, "")) || isRunningHead(block, page, pageHeights.get(block.pageNumber ?? 0))) {
|
|
2516
2689
|
block.type = "paragraph";
|
|
2517
2690
|
block.level = void 0;
|
|
@@ -2552,6 +2725,11 @@ function splitSingleCellTables(blocks) {
|
|
|
2552
2725
|
const out = [];
|
|
2553
2726
|
for (const b of blocks) {
|
|
2554
2727
|
const t = b.type === "table" ? b.table : void 0;
|
|
2728
|
+
const title = t && FRAME_TITLE_BLOCKS.get(t);
|
|
2729
|
+
if (title) {
|
|
2730
|
+
out.push({ ...title, text: `${t.cells[0][0].text.trim()} ${t.cells[0][2].text.trim()}` });
|
|
2731
|
+
continue;
|
|
2732
|
+
}
|
|
2555
2733
|
const only = t && t.rows === 1 && t.cols === 1 && t.cells[0]?.[0]?.blocks?.length === 1 ? t.cells[0][0].blocks[0] : void 0;
|
|
2556
2734
|
const squash = (s) => s.replace(/\s/g, "");
|
|
2557
2735
|
const inner = only && (!squash(t.cells[0][0].text) || only.type === "table" && squash(t.cells[0][0].text) === squash(only.table.cells.flat().map((c) => c.text).join(""))) ? only : void 0;
|
|
@@ -2561,12 +2739,16 @@ function splitSingleCellTables(blocks) {
|
|
|
2561
2739
|
continue;
|
|
2562
2740
|
}
|
|
2563
2741
|
const cell = t && t.rows === 1 && t.cols === 1 ? t.cells[0]?.[0] : void 0;
|
|
2564
|
-
if (!cell
|
|
2742
|
+
if (!cell) {
|
|
2565
2743
|
out.push(b);
|
|
2566
2744
|
continue;
|
|
2567
2745
|
}
|
|
2568
2746
|
const lines = (cell.text ?? "").split(/\n/).map((l) => l.trim()).filter(Boolean);
|
|
2569
2747
|
if (t?.caption?.trim()) out.push({ type: "paragraph", text: t.caption.trim(), pageNumber: b.pageNumber, bbox: b.bbox });
|
|
2748
|
+
if (cell.blocks?.length) {
|
|
2749
|
+
out.push(...splitSingleCellTables(cell.blocks));
|
|
2750
|
+
continue;
|
|
2751
|
+
}
|
|
2570
2752
|
for (const text of lines) out.push({ type: "paragraph", text, pageNumber: b.pageNumber, bbox: b.bbox });
|
|
2571
2753
|
}
|
|
2572
2754
|
return out;
|
|
@@ -2691,7 +2873,7 @@ function mergeLinkRuns(markdown) {
|
|
|
2691
2873
|
|
|
2692
2874
|
// src/pdf/formula-ocr.ts
|
|
2693
2875
|
async function applyFormulaOcr(buffer, blocks, pageFilter, effectivePageCount, warnings, _onProgress) {
|
|
2694
|
-
const formulaMod = await import("./formula-
|
|
2876
|
+
const formulaMod = await import("./formula-HQFZEXFF.js");
|
|
2695
2877
|
const { FormulaPipeline, ensureFormulaModels } = formulaMod;
|
|
2696
2878
|
await ensureFormulaModels((p) => {
|
|
2697
2879
|
if (p.phase === "download" && p.total) {
|
|
@@ -2914,12 +3096,29 @@ async function parsePdfDocument(buffer, options) {
|
|
|
2914
3096
|
const uncoveredImageRegions = /* @__PURE__ */ new Map();
|
|
2915
3097
|
const largeImageRegions = /* @__PURE__ */ new Set();
|
|
2916
3098
|
const imageState = createPdfImageState();
|
|
3099
|
+
const imageBulletShapes = /* @__PURE__ */ new Map();
|
|
3100
|
+
const imageArrowDirections = /* @__PURE__ */ new Map();
|
|
2917
3101
|
const extractedImages = [];
|
|
2918
3102
|
const pageImageBlocks = /* @__PURE__ */ new Map();
|
|
2919
3103
|
const carry = {};
|
|
2920
3104
|
const vectorPageOps = /* @__PURE__ */ new Map();
|
|
2921
3105
|
const wrapLexicon = new WrapLexicon();
|
|
2922
3106
|
const noteMarks = /* @__PURE__ */ new Map();
|
|
3107
|
+
const headerContext = [];
|
|
3108
|
+
if (pageFilter && options?.removeHeaderFooter !== false && pageFilter.size < effectivePageCount) {
|
|
3109
|
+
for (const number of selectionContextPages(pageFilter, effectivePageCount)) {
|
|
3110
|
+
let contextPage;
|
|
3111
|
+
try {
|
|
3112
|
+
contextPage = await doc.getPage(number);
|
|
3113
|
+
const content = await contextPage.getTextContent();
|
|
3114
|
+
pageHeights.set(number, contextPage.view[3] - contextPage.view[1]);
|
|
3115
|
+
headerContext.push(...marginContextBlocks(content.items, number, contextPage.view));
|
|
3116
|
+
} catch {
|
|
3117
|
+
} finally {
|
|
3118
|
+
contextPage?.cleanup();
|
|
3119
|
+
}
|
|
3120
|
+
}
|
|
3121
|
+
}
|
|
2923
3122
|
let parsedPages = 0;
|
|
2924
3123
|
for (let i = 1; i <= effectivePageCount; i++) {
|
|
2925
3124
|
if (pageFilter && !pageFilter.has(i)) continue;
|
|
@@ -2973,6 +3172,7 @@ async function parsePdfDocument(buffer, options) {
|
|
|
2973
3172
|
} : rawOps;
|
|
2974
3173
|
remapSymbolFontItems(visible, (loadedName) => fontObj(loadedName)?.name);
|
|
2975
3174
|
remapControlGlyphs(visible, differencesOf);
|
|
3175
|
+
await restoreImageBullets(visible, page, opList.fnArray, opList.argsArray, imageBulletShapes);
|
|
2976
3176
|
const faces = /* @__PURE__ */ new Map();
|
|
2977
3177
|
for (const it of visible) {
|
|
2978
3178
|
if (!it.fontName) continue;
|
|
@@ -3019,7 +3219,8 @@ async function parsePdfDocument(buffer, options) {
|
|
|
3019
3219
|
if (marks.length) noteMarks.set(i, { marks, seps: footnoteSeparators(extractLines(opList.fnArray, opList.argsArray).horizontals, pageW, pageH) });
|
|
3020
3220
|
const stamp = marginStamp(visible);
|
|
3021
3221
|
const flow = stamp.length ? visible.filter((it) => !stamp.includes(it)) : visible;
|
|
3022
|
-
const
|
|
3222
|
+
const rightArrows = options?.tables !== false ? await detectRightArrowRegions(page, opList.fnArray, opList.argsArray, imageArrowDirections) : [];
|
|
3223
|
+
const pageBlocks = orderTwoUpPage(extractPageBlocksWithLines(flow, i, opList, pageW, pageH, void 0, options?.tables !== false, carry, wrapLexicon, rightArrows), pageW, pageH);
|
|
3023
3224
|
if (stamp.length) pageBlocks.unshift({ type: "paragraph", text: [...stamp].sort((a, b) => a.y - b.y).map((it) => it.text).join(" "), pageNumber: i });
|
|
3024
3225
|
for (const b of pageBlocks) blocks.push(b);
|
|
3025
3226
|
try {
|
|
@@ -3075,7 +3276,7 @@ async function parsePdfDocument(buffer, options) {
|
|
|
3075
3276
|
}
|
|
3076
3277
|
if (targets.size > 0) {
|
|
3077
3278
|
try {
|
|
3078
|
-
const { runPdfOcr } = await import("./pdf-ocr-
|
|
3279
|
+
const { runPdfOcr } = await import("./pdf-ocr-RACAZU3N.js");
|
|
3079
3280
|
const mode = typeof options?.ocr === "function" ? options.ocr : "builtin";
|
|
3080
3281
|
const regionPages = new Map([...ocrRegions].filter(([p]) => options?.ocr !== "force" && !isImageBased && !pageQuality.find((q) => q.page === p)?.needsOcr));
|
|
3081
3282
|
const ocrPageBlocks = await runPdfOcr(ocrBuffer, targets, mode, warnings, options?.onProgress, options?.tables !== false, vectorPageOps, regionPages);
|
|
@@ -3142,8 +3343,8 @@ async function parsePdfDocument(buffer, options) {
|
|
|
3142
3343
|
warnings.push({ page, message: `${count}\uAC1C \uC774\uBBF8\uC9C0 \uC601\uC5ED\uC5D0 \uCD94\uCD9C \uAC00\uB2A5\uD55C \uD14D\uC2A4\uD2B8 \uC5C6\uC74C (\uADF8\uB9BC/\uCC28\uD2B8/\uB3C4\uC7A5 \uB0B4\uC6A9 \uB204\uB77D \uAC00\uB2A5 \u2014 \uADF8\uB9BC \uC18D \uAE00\uC740 ocr: true / CLI --ocr \uB85C \uC77D\uC2B5\uB2C8\uB2E4)`, code: "SKIPPED_IMAGE" });
|
|
3143
3344
|
}
|
|
3144
3345
|
}
|
|
3145
|
-
if (options?.removeHeaderFooter !== false && parsedPageCount >= 3) {
|
|
3146
|
-
const removed = removeHeaderFooterBlocks(blocks, pageHeights, warnings, noteMarks);
|
|
3346
|
+
if (options?.removeHeaderFooter !== false && (parsedPageCount >= 3 || headerContext.length)) {
|
|
3347
|
+
const removed = removeHeaderFooterBlocks(blocks, pageHeights, warnings, noteMarks, false, headerContext);
|
|
3147
3348
|
for (let ri = removed.length - 1; ri >= 0; ri--) {
|
|
3148
3349
|
blocks.splice(removed[ri], 1);
|
|
3149
3350
|
}
|
|
@@ -3191,6 +3392,10 @@ async function parsePdfDocument(buffer, options) {
|
|
|
3191
3392
|
const outline = blocks.filter((b) => b.type === "heading" && b.level && b.text).map((b) => ({ level: b.level, text: b.text, pageNumber: b.pageNumber }));
|
|
3192
3393
|
sanitizeBlockControlChars(blocks);
|
|
3193
3394
|
let outBlocks = splitSingleCellTables(blocks);
|
|
3395
|
+
if (options?.layoutTables !== "keep") {
|
|
3396
|
+
blocks.length = 0;
|
|
3397
|
+
for (const block of outBlocks) blocks.push(block);
|
|
3398
|
+
}
|
|
3194
3399
|
outBlocks = inlineFootnotes(outBlocks, noteMarks);
|
|
3195
3400
|
outBlocks = relocateEndnotes(outBlocks);
|
|
3196
3401
|
if (options?.removeHeaderFooter !== false) outBlocks = outBlocks.filter((b) => {
|
|
@@ -3307,4 +3512,4 @@ export {
|
|
|
3307
3512
|
parsePdfDocument,
|
|
3308
3513
|
removeHeaderFooterBlocks
|
|
3309
3514
|
};
|
|
3310
|
-
//# sourceMappingURL=parser-
|
|
3515
|
+
//# sourceMappingURL=parser-GFDGAVLV.js.map
|