#include "ImageApplyRotation.h" #define USE_TESSERCAT //#define USE_HANWANG //#define HG_GPDF_API_BUILD #include "hg_ocr.h" CImageApplyRotation::CImageApplyRotation(RotationType rotation, bool isBackTransposed, int dpi, const char* tessdataPath) : m_rotation(rotation) , m_backTranspose(isBackTransposed) , m_dpi(dpi) , osd(nullptr) { if (rotation == RotationType::AutoTextOrientation) { #ifdef USE_TESSERCAT osd = new HG_OCR(); std::string strpath(tessdataPath); reinterpret_cast(osd)->init(strpath.c_str(), HG_OCR::PSM_TYPE::Orientation); #endif } } CImageApplyRotation::~CImageApplyRotation() { #ifdef USE_TESSERCAT if (osd) delete reinterpret_cast(osd); #endif } void CImageApplyRotation::apply(cv::Mat& pDib, int side) { m_angleResult = 0; if (pDib.empty()) { return; } if (m_rotation == RotationType::AutoTextOrientation) //�Զ��ı�����ʶ�� { #ifdef USE_HANWANG cv::Mat temp; if (m_dpi != 200) { double scale = 200 / static_cast(m_dpi); int new_w = static_cast(pDib.cols * scale) / 4 * 4; int new_h = pDib.rows * scale; cv::resize(pDib, temp, cv::Size(new_w, new_h)); } else temp = pDib(cv::Rect(0, 0, pDib.cols / 4 * 4, pDib.rows)).clone(); if (temp.channels() == 3) cv::cvtColor(temp, temp, cv::COLOR_BGR2GRAY); cv::threshold(temp, temp, 180, 255, cv::THRESH_OTSU); int orientation = HG_OCR::orientation(temp.data, temp.cols, temp.rows, temp.channels()); switch (orientation) { case 90: cv::transpose(pDib, pDib); cv::flip(pDib, pDib, 0); break; case 180: cv::flip(pDib, pDib, 0); cv::flip(pDib, pDib, 1); break; case 270: cv::transpose(pDib, pDib); cv::flip(pDib, pDib, 1); break; default: break; } #endif #ifdef USE_TESSERCAT if (osd) { cv::Mat temp; if (m_dpi != 200) { double scale = 200 / static_cast(m_dpi); int new_w = (static_cast(pDib.cols * scale) + 3) / 4 * 4; int new_h = pDib.rows * scale; cv::resize(pDib, temp, cv::Size(new_w, new_h)); } else temp = pDib(cv::Rect(0, 0, pDib.cols / 4 * 4, pDib.rows)).clone(); HG_OCR* ptr_osd = reinterpret_cast(osd); int ori = -1; int direction = -1; int order = -1; float angle = -1; ptr_osd->getOrientation(temp.data, temp.cols, temp.rows, temp.channels(), temp.step1(), ori, direction, order, angle); switch (ori) { case 1: cv::transpose(pDib, pDib); cv::flip(pDib, pDib, 0); m_angleResult = 90; break; case 2: cv::flip(pDib, pDib, 0); cv::flip(pDib, pDib, 1); m_angleResult = 180; break; case 3: cv::transpose(pDib, pDib); cv::flip(pDib, pDib, 1); m_angleResult = 270; break; default: m_angleResult = 0; break; } } #endif } else if (m_backTranspose && side == 1) //������ת180 { if (m_rotation != RotationType::Rotate_180) //��ת180�� { if (m_rotation == RotationType::Rotate_90_clockwise || m_rotation == RotationType::Rotate_90_anti_clockwise) //90�� -90�� { transpose(pDib, pDib); flip(pDib, pDib, m_rotation == RotationType::Rotate_90_clockwise ? 0 : 1); m_angleResult = m_rotation == RotationType::Rotate_90_clockwise ? 270 : 90; } else { flip(pDib, pDib, 0); flip(pDib, pDib, 1); m_angleResult = 180; } } } else //zh { if (m_rotation == RotationType::Rotate_90_clockwise || m_rotation == RotationType::Rotate_90_anti_clockwise) //90�� -90�� { transpose(pDib, pDib); flip(pDib, pDib, m_rotation == RotationType::Rotate_90_clockwise ? 1 : 0); m_angleResult = m_rotation == RotationType::Rotate_90_clockwise ? 90 : 270; } else if (m_rotation == RotationType::Rotate_180) { flip(pDib, pDib, 0); flip(pDib, pDib, 1); m_angleResult = 180; } } } void CImageApplyRotation::apply(std::vector& mats, bool isTwoSide) { (void)isTwoSide; m_angleResults.clear(); int i = 0; for (cv::Mat& var : mats) { if (!var.empty()) { apply(var, i); m_angleResults.push_back(m_angleResult); i++; } } }