scanlayer
Scanned image → searchable PDF

Turn any scan or
phone photo into a
searchable document.

scanlayer runs a scanned image or photograph through OCR and produces a PDF with an invisible, selectable text layer over the original page, or exports the raw OCR result as text, JSON, TSV, or hOCR. One CLI, one Python library, no cloud service, runs on Windows, macOS, and Linux.

MIT licensed Python 3.9+ CLI + library, same engine Win / macOS / Linux
How a page moves through the pipeline
01

Preprocess

EXIF fix, deskew, denoise, illumination correction, blank-page check.

02

OCR

Tesseract across several page segmentation modes, best-confidence pass wins.

03

Reading order

Geometric multi-column reconstruction, independent of Tesseract's own block numbering.

04

Output

Searchable PDF, or a raw txt / json / tsv / hocr export.

Quick start

The exact same conversion, run two ways. Everything the CLI flag does maps one-to-one onto a keyword argument, see Examples for the two put side by side across every feature.

bash
# standard install (adds the `scanlayer` command)
pip install scanlayer
scanlayer invoice.jpg -o invoice.pdf

# or run from a source checkout with no install, e.g. to contribute
pip install -r requirements.txt
python -m scanlayer invoice.jpg -o invoice.pdf
pythonquickstart.py
import scanlayer

result = scanlayer.convert("invoice.jpg", "invoice.pdf")
print(result.words_count, result.mean_confidence)
Requires Tesseract scanlayer wraps Tesseract OCR, which is installed separately from the Python package. See Installation for the one-line install command per OS, and how scanlayer locates the binary automatically.

Two interfaces, one engine

Every capability is available from the scanlayer command and from import scanlayer: the CLI is a thin wrapper over the exact same convert() pipeline.

Four export formats besides PDF

Skip the PDF entirely and get txt, json, tsv, or hocr straight from the OCR pass with --format.

Real multi-column reading order

Two-column reports and letters are reconstructed geometrically, not read column-by-line the way raw Tesseract output is.

Batch, merge, and native PDF input

Convert a folder of mixed images and PDFs in one call, or merge several pages into a single multi-page searchable PDF.

One configuration surface

configure(), a JSON/YAML profile, or CLI flags, using the same keys, documented precedence, unknown keys rejected loudly.

A debug overlay for every run

--debug-image draws every detected word, color-coded by confidence, so a bad OCR result is diagnosable in seconds.

Which page do I want?

SituationWhat to reach for
Convert one scanned invoice to a searchable PDFconvert() / scanlayer file.jpg -o file.pdf
Convert a folder of scans, some might failconvert_batch() / scanlayer *.jpg -o ./out/
Combine several photographed pages into one PDFconvert_merge() / --merge
You only need the text, not a PDFoutput_format="txt" / --format txt
OCR looks wrong and you don't know why--debug-image
Embedding scanlayer in a packaged desktop appBundling Tesseract

Contents of this repository

PathWhat's in it
scanlayer/The library + CLI source.
README.mdInstall instructions and a five-minute quick start.
CONTRIBUTING.mdHow to set up a dev environment and submit a change.
LICENSE.mdMIT.