Skip to main content

A simple Python package for OCR with searchable PDF generation using PaddleOCR

Project description

PaddleOCR Python Project

pdf-searchable-ocr

A simple and powerful Python package for Optical Character Recognition (OCR) with searchable PDF generation using PaddleOCR.

Features

  • 🔍 High-accuracy OCR using PaddleOCR
  • 📄 Searchable PDF generation with invisible text layers
  • 🎨 Bounding box visualization for OCR results
  • 🌍 Multi-language support (80+ languages)
  • GPU acceleration support
  • 🔧 Simple class-based API
  • 📦 Easy installation and usage

Installation

Using pip (recommended)

pip install pdf-searchable-ocr

Using uv (for development)

git clone <repository-url>
cd pdf-searchable-ocr
uv sync

Quick Start

Basic Usage

from py_ocr import OCRProcessor

# Initialize the OCR processor
ocr = OCRProcessor(lang='en', verbose=True)

# Process an image
ocr_result = ocr.process_image('path/to/your/image.jpg')

# Create a searchable PDF
pdf_path = ocr.create_searchable_pdf('path/to/your/image.jpg', ocr_result)

# Draw bounding boxes for visualization
boxed_image = ocr.draw_bounding_boxes('path/to/your/image.jpg', ocr_result)

print(f"Searchable PDF created: {pdf_path}")
print(f"Image with bounding boxes: {boxed_image}")

CLI Usage

The package also provides a command-line tool:

# Basic usage - creates searchable PDF only
pdf-searchable-ocr input.jpg

# Specify custom output PDF name
pdf-searchable-ocr input.jpg --output-pdf my_document.pdf

# Enable bounding box visualization
pdf-searchable-ocr input.jpg --bounding-boxes

# Full options with custom names
pdf-searchable-ocr invoice.jpg \
    --output-pdf invoice_searchable.pdf \
    --output-prefix invoice_processed \
    --bounding-boxes \
    --lang en

Complete Workflow

from py_ocr import OCRProcessor

# Initialize processor
ocr = OCRProcessor(lang='en', use_gpu=False, verbose=True)

# Process image with custom PDF name and bounding boxes enabled
results = ocr.process_and_generate_all(
    'invoice.jpg', 
    output_pdf='invoice_searchable.pdf',
    output_prefix='invoice_processed',
    bounding_boxes=True
)

if results['searchable_pdf']:
    print(f"✅ Searchable PDF: {results['searchable_pdf']}")
if results['boxed_image']:
    print(f"✅ Visualization: {results['boxed_image']}")

# Or use defaults (no bounding boxes)
results = ocr.process_and_generate_all('document.jpg')

Using Sample Images

from py_ocr import OCRProcessor

# Initialize processor
ocr = OCRProcessor()

# Download a sample image for testing
image_path = ocr.download_sample_image()

# Process with custom settings
results = ocr.process_and_generate_all(
    image_path,
    output_pdf='sample_searchable.pdf',
    output_prefix='sample',
    bounding_boxes=True  # Enable visualization
)

API Reference

OCRProcessor Class

__init__(lang='en', use_gpu=False, verbose=True, **kwargs)

Initialize the OCR processor.

Parameters:

  • lang (str): Language for OCR recognition (default: 'en')
  • use_gpu (bool): Whether to use GPU acceleration (default: False)
  • verbose (bool): Whether to print verbose output (default: True)
  • **kwargs: Additional arguments passed to PaddleOCR

process_image(image_path: str) -> Dict[str, Any]

Perform OCR on an image.

Parameters:

  • image_path (str): Path to the image file

Returns:

  • dict: OCR results containing texts, scores, and bounding boxes
  • None: If OCR failed

create_searchable_pdf(image_path: str, ocr_result: dict, output_pdf: str) -> str

Create a searchable PDF with invisible text layers.

Parameters:

  • image_path (str): Path to the source image
  • ocr_result (dict): OCR results from process_image()
  • output_pdf (str): Output PDF filename (default: "searchable_output.pdf")

Returns:

  • str: Path to the created PDF
  • None: If creation failed

draw_bounding_boxes(image_path: str, ocr_result: dict, output_image: str) -> str

Draw bounding boxes on the image to visualize OCR detection.

Parameters:

  • image_path (str): Path to the source image
  • ocr_result (dict): OCR results from process_image()
  • output_image (str): Output image filename (default: "image_with_boxes.jpg")

Returns:

  • str: Path to the image with bounding boxes
  • None: If creation failed

process_and_generate_all(image_path: str, output_pdf: str, output_prefix: str, bounding_boxes: bool) -> dict

Complete workflow: OCR + Searchable PDF + Optional Bounding Box Image.

Parameters:

  • image_path (str): Path to the input image
  • output_pdf (str): Output PDF filename (default: "searchable_output.pdf")
  • output_prefix (str): Prefix for output files (default: "output")
  • bounding_boxes (bool): Whether to generate bounding box visualization (default: False)

Returns:

  • dict: Dictionary containing paths to all generated files

Supported Languages

pdf-searchable-ocr supports 80+ languages through PaddleOCR. Some popular ones include:

  • en - English
  • ch - Chinese (Simplified)
  • french - French
  • german - German
  • korean - Korean
  • japan - Japanese
  • it - Italian
  • xi - Spanish
  • ru - Russian
  • ar - Arabic

For the complete list, see PaddleOCR documentation.

Advanced Configuration

Output Control

# Control output files and features
ocr = OCRProcessor(lang='en')

# Minimal processing - only searchable PDF
results = ocr.process_and_generate_all(
    'document.jpg',
    output_pdf='my_document.pdf',
    bounding_boxes=False  # Skip visualization
)

# Full processing with custom names
results = ocr.process_and_generate_all(
    'invoice.jpg',
    output_pdf='invoice_searchable.pdf',
    output_prefix='invoice_analysis',
    bounding_boxes=True  # Include visualization
)

# Generated files:
# - invoice_searchable.pdf (searchable PDF)
# - invoice_analysis_with_boxes.jpg (visualization)

GPU Acceleration

# Enable GPU acceleration (requires CUDA)
ocr = OCRProcessor(lang='en', use_gpu=True)

Custom PaddleOCR Settings

# Pass additional PaddleOCR parameters
ocr = OCRProcessor(
    lang='en',
    use_angle_cls=True,              # Enable angle classification
    use_textline_orientation=True,   # Enable text line orientation
    det_model_dir='custom/det/path', # Custom detection model
    rec_model_dir='custom/rec/path'  # Custom recognition model
)

Batch Processing

from py_ocr import OCRProcessor
import os

ocr = OCRProcessor(lang='en')

# Process multiple images
image_folder = 'path/to/images'
for filename in os.listdir(image_folder):
    if filename.lower().endswith(('.png', '.jpg', '.jpeg', '.bmp', '.tiff')):
        image_path = os.path.join(image_folder, filename)
        base_name = os.path.splitext(filename)[0]
        
        # Process with custom output names
        results = ocr.process_and_generate_all(
            image_path, 
            output_pdf=f"searchable_{base_name}.pdf",
            output_prefix=f"processed_{base_name}",
            bounding_boxes=True  # Generate visualizations
        )
        print(f"Processed: {filename}")

Output Examples

Console Output

🔧 Initializing OCR engine with language: en
✅ OCR engine initialized successfully
📁 Using existing sample image: sample_image.jpg
🔍 Processing image: sample_image.jpg
📊 Text blocks detected: 48 | Average confidence: 0.984
✅ Searchable PDF saved as: my_document.pdf
🎨 Drawing 48 bounding boxes on image...
✅ Image with bounding boxes saved as: output_with_boxes.jpg

Generated Files

When using bounding_boxes=True:

  • my_document.pdf - Searchable PDF with invisible text layers
  • output_with_boxes.jpg - Original image with colored bounding boxes

When using bounding_boxes=False (default):

  • my_document.pdf - Searchable PDF only (faster processing)

Requirements

  • Python >= 3.8
  • PaddleOCR >= 2.7.0
  • OpenCV >= 4.0
  • ReportLab >= 4.0
  • Pillow >= 8.0

Installation from Source

# Clone the repository
git clone <repository-url>
cd pdf-searchable-ocr

# Install with uv (recommended for development)
uv sync

# Or install with pip
pip install -e .

Development

Running Tests

uv run python -m pytest tests/

Code Formatting

uv run black py_ocr/
uv run isort py_ocr/

Type Checking

uv run mypy py_ocr/

Contributing

  1. Fork the repository
  2. Create a feature branch (git checkout -b feature/amazing-feature)
  3. Commit your changes (git commit -m 'Add amazing feature')
  4. Push to the branch (git push origin feature/amazing-feature)
  5. Open a Pull Request

License

This project is licensed under the MIT License - see the LICENSE file for details.

Acknowledgments

Changelog

v0.1.0

  • Initial release
  • Basic OCR functionality
  • Searchable PDF generation
  • Bounding box visualization
  • Multi-language support

Support

If you encounter any issues or have questions:

  1. Check the Issues page
  2. Create a new issue with detailed information
  3. Contact the maintainers

Roadmap

  • Web interface for easy usage
  • Batch processing CLI tool
  • Docker container
  • Additional output formats (Excel, Word)
  • OCR result caching
  • Performance optimizations

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

pdf_searchable_ocr-0.1.1.tar.gz (1.1 MB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

pdf_searchable_ocr-0.1.1-py3-none-any.whl (11.0 kB view details)

Uploaded Python 3

File details

Details for the file pdf_searchable_ocr-0.1.1.tar.gz.

File metadata

  • Download URL: pdf_searchable_ocr-0.1.1.tar.gz
  • Upload date:
  • Size: 1.1 MB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for pdf_searchable_ocr-0.1.1.tar.gz
Algorithm Hash digest
SHA256 103611c1e4f231d38883d888692baf99ef2654bc90e96bf04ee73f002ec11941
MD5 d3c62010d081655de4c1112536eee6eb
BLAKE2b-256 00ca3a1fded56e0e65e4f961e4d9b62715eabe3da7a93fb150495b039d8ecb04

See more details on using hashes here.

Provenance

The following attestation bundles were made for pdf_searchable_ocr-0.1.1.tar.gz:

Publisher: package-publish.yml on jasminmistry/pdf-searchable-ocr

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file pdf_searchable_ocr-0.1.1-py3-none-any.whl.

File metadata

File hashes

Hashes for pdf_searchable_ocr-0.1.1-py3-none-any.whl
Algorithm Hash digest
SHA256 5cb5b709155b89348590e444f8232fa429767ab94104528d97122da7a01753f1
MD5 030b392f2befd0fa71336ae8326a9016
BLAKE2b-256 0bf7294005d2fa843219f2f57fb19db6d520d6e413917caa2912f874441bb222

See more details on using hashes here.

Provenance

The following attestation bundles were made for pdf_searchable_ocr-0.1.1-py3-none-any.whl:

Publisher: package-publish.yml on jasminmistry/pdf-searchable-ocr

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page