Адаптеры Tesseract OCR
HPDFTesseractRecognition предоставляет опциональные движки Windows, реализующие IHPDFOCREngine для текстовых слоёв OCR с поддержкой поиска
Фабрика нативной DLL
function HPDFCreateTesseractDLLOCREngine(const LibraryPath,
TessDataDirectory, Language: string): IHPDFOCREngine; overload;
function HPDFCreateTesseractDLLOCREngine(const LibraryPath,
TessDataDirectory, Language: string;
const Options: THPDFTesseractOptions): IHPDFOCREngine; overload;
Подготовьте существующую DLL Tesseract с C API, совместимым с Tesseract 5, каталог tessdata и ASCII-идентификатор языка или комбинацию вроде eng, chi_sim или chi_sim+eng
Архитектура библиотеки должна совпадать с приложением: приложение Win32 загружает 32-битную DLL, а приложение Win64 — 64-битную
Держите нужные зависимые DLL рядом с выбранной библиотекой или в стандартных каталогах загрузчика Windows; адаптер загружает явно указанный путь к библиотеке, не меняя текущий каталог и пути поиска процесса
Фабрика проверяет каждый запрошенный файл .traineddata, загружает библиотеку и разрешает требуемые экспорты перед возвратом; неверные пути, модели или опции, отсутствующие экспорты, несовпадение архитектуры и недоступные зависимости выбрасывают исключение
Ни OCR-рантайм, ни модели не поставляются в комплекте и не скачиваются автоматически
Обе фабрики доступны в пакете Windows FPC/Lazarus, а также в сборках Delphi и C++Builder; пересоберите Lib/FPC/HotPDFLaz.lpk под целевую архитектуру, прежде чем использовать HPDFTesseractRecognition
Нативный FPC-адаптер читает текущее сырое изображение LCL, включая пиксели, записанные через scanline, и сохраняет Unicode-слова независимо от системной ANSI-кодовой страницы
Опции
THPDFTesseractOptions = record
PageSegMode: THPDFTesseractPageSegMode;
EngineMode: THPDFTesseractEngineMode;
TimeoutMilliseconds: Cardinal;
MaxPixels: Integer;
class function Default: THPDFTesseractOptions; static;
end;
Вызовите THPDFTesseractOptions.Default до переопределения полей; та же запись настраивает и фабрику нативной DLL, и локальную CLI-перегрузку с опциями
| Поле | По умолчанию | Значение |
|---|---|---|
PageSegMode | tpsAuto | Автоматическая сегментация страницы без определения ориентации |
EngineMode | temDefault | Режим движка, поддерживаемый выбранными языковыми моделями |
TimeoutMilliseconds | 60000 | Дедлайн запроса от 1 до 3,600,000 миллисекунд; DLL сотрудничает с отменой, а CLI-воркер по таймауту завершается |
MaxPixels | 16777216 | Бюджет входных пикселей, настраивается от 1 до 67,108,864 пикселей |
THPDFTesseractPageSegMode = (
tpsOSDOnly, tpsAutoOSD, tpsAutoOnly, tpsAuto, tpsSingleColumn,
tpsSingleBlockVertical, tpsSingleBlock, tpsSingleLine, tpsSingleWord,
tpsCircleWord, tpsSingleCharacter, tpsSparseText, tpsSparseTextOSD,
tpsRawLine);
THPDFTesseractEngineMode = (
temLegacyOnly, temLSTMOnly, temLegacyAndLSTM, temDefault);
tpsOSDOnly и tpsAutoOnly не распознают слова и отвергаются адаптером; tpsAutoOSD и tpsSparseTextOSD дополнительно требуют osd.traineddata
tpsSingleLine — для одной текстовой строки, tpsSingleBlock — для однородного блока, tpsSparseText — для разрозненного текста; эти режимы не исправляют перспективу скана и не дают общей гарантии разметки
temLSTMOnly требует LSTM-моделей, а legacy-режимы — соответствующих компонентов legacy-моделей; неподдерживаемые комбинации падают при нативной инициализации
Пример PDF с поддержкой поиска
PDF должен быть уже загружен, а DLL, зависимости и языковые модели — установлены по показанным путям
uses SysUtils, HPDFDoc, HPDFTesseractRecognition;
procedure AddNativeOCRText(PDF: THotPDF);
var
Engine: IHPDFOCREngine;
NativeOptions: THPDFTesseractOptions;
LayerOptions: THPDFOCRTextLayerOptions;
Info: THPDFOCRTextLayerInfo;
begin
NativeOptions := THPDFTesseractOptions.Default;
NativeOptions.EngineMode := temLSTMOnly;
NativeOptions.PageSegMode := tpsAuto;
Engine := HPDFCreateTesseractDLLOCREngine(
'C:\OCR\libtesseract-5.dll', 'C:\OCR\tessdata',
'chi_sim+eng', NativeOptions);
LayerOptions := THPDFOCRTextLayerOptions.Default;
if not PDF.ApplyLoadedOCRTextLayer([0], Engine, LayerOptions, Info) then
raise Exception.Create(string(Info.Diagnostic));
end;
Результаты и владение
Адаптер копирует одолженный bitmap в буфер градаций серого с порядком строк сверху вниз, передаёт DPI запроса и распознаёт через нативный экземпляр API, локальный для запроса
Слова сохраняют нативный порядок чтения, провалидированный Unicode-текст UTF-8, пиксельные границы от левого верхнего угла и уверенность, перемасштабированную из диапазона 0–100 в 0–1; дополнительные символы расходуют по две единицы UTF-16
Доступные базовые линии слов передаются дальше с обоими концами; когда базовой линии нет, действует обычный геометрический fallback текстового слоя
При преимущественно вертикальной базовой линии нативный адаптер использует ширину рамки слова как TextHeightPixels; горизонтальные базовые линии используют высоту рамки, включая обращённые направления чтения, поэтому длина вертикального слова не превращается в его размер шрифта
Это оценка по доминирующей оси: выровненные по осям рамка слова и базовая линия сами по себе не позволяют восстановить точную высоту текста при произвольных углах наклона
Пустая страница завершается успешно с пустым массивом слов; повреждённый UTF-8, встроенные управляющие символы, невалидная геометрия или уверенность, исчерпанные бюджеты слов или текста, отмена и сбои распознавания возвращают False, очищают все частичные слова и заполняют диагностику
Каждый запрос освобождает свой итератор, выделенные нативные строки, монитор и экземпляр API; освобождение адаптера выгружает его ссылку на библиотеку
Лимиты и отмена
Каждое входное измерение должно быть не больше 32,767 пикселей и укладываться в MaxPixels; распознанный текст должен умещаться в бюджет MaxTextCodeUnits запроса и лимит адаптера в 1,048,576 единиц UTF-16, а число слов — в MaxWords
Адаптер проверяет отмену и прошедшее время при конвертации bitmap и обходе результатов, а во время распознавания передаёт нативный монитор с оставшимся дедлайном и callback отмены
Нативная отмена кооперативная: монитор Tesseract покрывает распознавание слов и не прерывает каждый шаг инициализации или анализа разметки; такие вызовы могут завершиться раньше, чем будет сообщена запрошенная отмена или истёкший дедлайн
Бюджеты пикселей и вывода не накладывают жёсткого лимита на память моделей или распознавания нативной библиотеки; если приложению нужен отдельно завершаемый воркер, используйте процессный адаптер
ApplyLoadedOCRTextLayer валидирует все результаты и атомарно публикует каждую выбранную страницу, поэтому сбой адаптера оставляет загруженный документ неизменным
DLL-адаптер отвергает невалидный UTF-8, обрезает декодированный текст слов и отбраковывает оставшиеся управляющие символы C0, DEL и C1 до возврата результатов, так что искажённый текст приводит запрос к сбою, а не молча выпадает из PDF-текстового слоя
Фабрика локального CLI
function HPDFCreateTesseractOCREngine(const ExecutablePath,
TessDataDirectory, Language: string;
TimeoutMilliseconds: Cardinal = 60000): IHPDFOCREngine; overload;
function HPDFCreateTesseractOCREngine(const ExecutablePath,
TessDataDirectory, Language: string;
const Options: THPDFTesseractOptions): IHPDFOCREngine; overload;
Перегрузка с опциями передаёт PageSegMode как --psm и EngineMode как --oem, использует настроенный таймаут и проверяет MaxPixels до сохранения одолженного bitmap или запуска воркера
Существующая перегрузка с таймаутом сохраняет автоматическую сегментацию страницы и режим движка, выбранный исполняемым файлом, без нового лимита пикселей адаптера; когда нужен явный лимит входа, используйте перегрузку с опциями
Обе перегрузки сохраняют запрошенный DPI, TSV-вывод, ограниченные наследуемые дескрипторы, опрос отмены и завершение воркера при сбое; CLI не имеет нативной информации о базовых линиях, ограничивает TSV-вывод 64 MiB, а вывод файла диагностики — 1 MiB
Неверные режимы сегментации, режимы движка, таймауты и лимиты пикселей выбрасывают EArgumentException при создании настроенного движка; доступность моделей, включая osd.traineddata для режимов ориентации, и совместимость модели и движка проверяет исполняемый файл во время распознавания
var
CLIOptions: THPDFTesseractOptions;
Engine: IHPDFOCREngine;
begin
CLIOptions := THPDFTesseractOptions.Default;
CLIOptions.PageSegMode := tpsSingleLine;
CLIOptions.EngineMode := temLSTMOnly;
CLIOptions.MaxPixels := 8000000;
Engine := HPDFCreateTesseractOCREngine(
'C:\OCR\tesseract.exe', 'C:\OCR\tessdata', 'eng', CLIOptions);
end;
Используйте tpsSingleWord для отдельного слова, tpsSparseText для разрозненного текста или tpsSingleBlockVertical с подходящей моделью вертикального текста для одного вертикального блока; фабрика не обрезает страницы и не подбирает модели автоматически
CLI-адаптер строго валидирует UTF-8, отклоняет байты NUL и управляющие символы C0/C1 внутри распознанных слов и очищает все результаты, если за корректным словом следует искажённый вывод
CLI-пример, параметры рендеринга, группировку в optional content и ограничения соответствия смотрите в разделе Текстовые слои OCR с поддержкой поиска