C++環境において、画像処理ライブラリであるOpenCVと、オープンソースのOCRエンジンであるTesseractを組み合わせて、画像内の文字を抽出する方法を解説します。OpenCVで画像の前処理(ノイズ除去や二値化)を行い、その結果をTesseractに渡すことで、認識精度を向上させることができます。
1. 開発環境の構築
Windows環境では、パッケージマネージャーのvcpkgを使用すると、ライブラリの導入がスムーズです。以下のコマンドを使用して必要なライブラリをインストールします。
vcpkg install opencv
vcpkg install tesseract
また、文字認識には言語ごとの学習データ(.traineddata)が必要です。日本語(chi_sim)や英語(eng)のデータを、Tesseractのデータディレクトリ(tessdata)に配置してください。高精度な認識を求める場合は、LSTMエンジンに対応した「tessdata_best」の使用を推奨します。
2. OCR処理の実装コード
OpenCVで画像を読み込み、適応的二値化(Adaptive Thresholding)を施してTesseractに渡す基本的な実装例です。
#include <iostream>
#include <vector>
#include <opencv2/opencv.hpp>
#include <tesseract/baseapi.h>
#include <leptonica/allheaders.h>
int main() {
// 画像の読み込み
std::string path = "sample_image.jpg";
cv::Mat raw_img = cv::imread(path);
if (raw_img.empty()) {
std::cerr << "画像の読み込みに失敗しました。" << std::endl;
return -1;
}
// グレースケール変換と二値化処理
cv::Mat gray_img, binary_img;
cv::cvtColor(raw_img, gray_img, cv::COLOR_BGR2GRAY);
// 適応的二値化によるノイズ軽減
cv::adaptiveThreshold(gray_img, binary_img, 255,
cv::ADAPTIVE_THRESH_GAUSSIAN_C,
cv::THRESH_BINARY, 11, 2);
// デバッグ用表示
cv::imshow("Processed Image", binary_img);
// Tesseract APIの初期化
tesseract::TessBaseAPI* ocr_engine = new tesseract::TessBaseAPI();
// 日本語データを使用して初期化
if (ocr_engine->Init(NULL, "chi_sim")) {
std::cerr << "Tesseractの初期化に失敗しました。" << std::endl;
return -1;
}
// OpenCVのMatデータをTesseractにセット
ocr_engine->SetImage(binary_img.data, binary_img.cols, binary_img.rows, 1, binary_img.step);
// 文字認識の実行
char* result_text = ocr_engine->GetUTF8Text();
if (result_text) {
std::cout << "認識結果:\n" << result_text << std::endl;
delete[] result_text;
} else {
std::cout << "文字を検出できませんでした。" << std::endl;
}
// リソースの解放
ocr_engine->End();
cv::waitKey(0);
return 0;
}
3. CMakeプロジェクトの設定
vcpkgでインストールしたライブラリをプロジェクトにリンクするためのCMakeLists.txtの設定例です。
cmake_minimum_required(VERSION 3.10)
project(OcrProject CXX)
set(CMAKE_CXX_STANDARD 17)
# OpenCVの検索
find_package(OpenCV REQUIRED)
# Tesseractと依存ライブラリの検索
find_package(Tesseract REQUIRED)
find_package(Leptonica REQUIRED)
add_executable(ocr_app main.cpp)
target_include_directories(ocr_app PRIVATE ${OpenCV_INCLUDE_DIRS} ${Tesseract_INCLUDE_DIRS})
target_link_libraries(ocr_app PRIVATE ${OpenCV_LIBS} libtesseract leptonica)
4. 認識精度を調整するためのデバッグツール
二値化の閾値をリアルタイムに変更して、最適なパラメータを確認するためのコードです。トラックバーを使用して、文字が最も鮮明に見える設定を探ることができます。
#include <opencv2/opencv.hpp>
cv::Mat src_gray, result_img;
int threshold_limit = 128;
int const max_value = 255;
const char* win_name = "Threshold Debugger";
void update_threshold(int, void*) {
// 固定閾値による二値化
cv::threshold(src_gray, result_img, threshold_limit, max_value, cv::THRESH_BINARY);
cv::imshow(win_name, result_img);
}
int main() {
cv::Mat color_img = cv::imread("sample_image.jpg");
if (color_img.empty()) return -1;
cv::cvtColor(color_img, src_gray, cv::COLOR_BGR2GRAY);
cv::namedWindow(win_name);
// トラックバーの作成
cv::createTrackbar("Threshold", win_name, &threshold_limit, max_value, update_threshold);
update_threshold(0, 0);
cv::waitKey(0);
return 0;
}