From 8ce837c8cac771a0ca670dafb427407761bfb7ea Mon Sep 17 00:00:00 2001 From: gb <741021719@qq.com> Date: Wed, 28 Sep 2022 20:00:03 +0800 Subject: [PATCH] =?UTF-8?q?=E8=B0=83=E6=95=B4=E8=AE=BE=E5=A4=87=E6=98=BE?= =?UTF-8?q?=E7=A4=BA=E5=90=8D=E7=A7=B0=EF=BC=9B=E5=BA=94=E7=94=A8=E6=96=B0?= =?UTF-8?q?=E7=9A=84=E7=81=B0=E5=BA=A6=E8=BD=AC=E9=BB=91=E7=99=BD=E5=9B=BE?= =?UTF-8?q?=E5=83=8F=E7=AE=97=E6=B3=95=EF=BC=88=E4=BD=8D=E5=BA=8F=E8=BF=98?= =?UTF-8?q?=E9=9C=80=E8=A6=81=E8=B0=83=E6=95=B4=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- hgdriver/hgdev/char_const.h | 38 ++- hgdriver/hgdev/hg_scanner.cpp | 6 +- hgdriver/hgdev/image_process.cpp | 504 +++++++++++++++++------------ hgdriver/hgdev/image_process.h | 3 +- hgdriver/hgdev/scanner_manager.cpp | 18 +- 5 files changed, 330 insertions(+), 239 deletions(-) diff --git a/hgdriver/hgdev/char_const.h b/hgdriver/hgdev/char_const.h index b8f4298..d3a16df 100644 --- a/hgdriver/hgdev/char_const.h +++ b/hgdriver/hgdev/char_const.h @@ -117,33 +117,43 @@ // 设备名称 // #define SCANNER_NAME_HG_G100 "华高扫描仪—G100" -#define SCANNER_NAME_HG_G100 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G100" +// #define SCANNER_NAME_HG_G100 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G100" // #define SCANNER_NAME_HG_G200 "华高扫描仪—G200" -#define SCANNER_NAME_HG_G200 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G200" +// #define SCANNER_NAME_HG_G200 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G200" // #define SCANNER_NAME_HG_G300 "华高扫描仪—G300" -#define SCANNER_NAME_HG_G300 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G300" +// #define SCANNER_NAME_HG_G300 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G300" // #define SCANNER_NAME_HG_G400 "华高扫描仪—G400" -#define SCANNER_NAME_HG_G400 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G400" +// #define SCANNER_NAME_HG_G400 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G400" // #define SCANNER_NAME_HG_G139 "华高扫描仪—G139" -#define SCANNER_NAME_HG_G139 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G139" +// #define SCANNER_NAME_HG_G139 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G139" // #define SCANNER_NAME_HG_G239 "华高扫描仪—G239" -#define SCANNER_NAME_HG_G239 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G239" +// #define SCANNER_NAME_HG_G239 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G239" // #define SCANNER_NAME_HG_G339 "华高扫描仪—G339" -#define SCANNER_NAME_HG_G339 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G339" +// #define SCANNER_NAME_HG_G339 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G339" // #define SCANNER_NAME_HG_G439 "华高扫描仪—G439" -#define SCANNER_NAME_HG_G439 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G439" -// #define SCANNER_NAME_HG_G402 "华高扫描仪—G402" -#define SCANNER_NAME_HG_G402 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G402" +// #define SCANNER_NAME_HG_G439 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G439" +// #define SCANNER_NAME_HG_G402 "华高扫描仪—G402" +// #define SCANNER_NAME_HG_G402 "\345\215\216\351\253\230\346\211\253\346\217\217\344\273\252\342\200\224G402" + +#define SCANNER_NAME_HG_G100 "HUAGOSCAN G100" +#define SCANNER_NAME_HG_G200 "HUAGOSCAN G200" +#define SCANNER_NAME_HG_G300 "HUAGOSCAN G300" +#define SCANNER_NAME_HG_G400 "HUAGOSCAN G400" // #define SCANNER_NAME_LSC_G42S "立思辰扫描仪—G42S" -#define SCANNER_NAME_LSC_G42S "\347\253\213\346\200\235\350\276\260\346\211\253\346\217\217\344\273\252\342\200\224G42S" +// #define SCANNER_NAME_LSC_G42S "\347\253\213\346\200\235\350\276\260\346\211\253\346\217\217\344\273\252\342\200\224G42S" // #define SCANNER_NAME_LSC_G52S "立思辰扫描仪—G52S" -#define SCANNER_NAME_LSC_G52S "\347\253\213\346\200\235\350\276\260\346\211\253\346\217\217\344\273\252\342\200\224G52S" +// #define SCANNER_NAME_LSC_G52S "\347\253\213\346\200\235\350\276\260\346\211\253\346\217\217\344\273\252\342\200\224G52S" // #define SCANNER_NAME_LSC_G62S "立思辰扫描仪—G62S" -#define SCANNER_NAME_LSC_G62S "\347\253\213\346\200\235\350\276\260\346\211\253\346\217\217\344\273\252\342\200\224G62S" +// #define SCANNER_NAME_LSC_G62S "\347\253\213\346\200\235\350\276\260\346\211\253\346\217\217\344\273\252\342\200\224G62S" // #define SCANNER_NAME_LSC_G73S "立思辰扫描仪—G73S" -#define SCANNER_NAME_LSC_G73S "\347\253\213\346\200\235\350\276\260\346\211\253\346\217\217\344\273\252\342\200\224G73S" +// #define SCANNER_NAME_LSC_G73S "\347\253\213\346\200\235\350\276\260\346\211\253\346\217\217\344\273\252\342\200\224G73S" +#define SCANNER_NAME_LSC_G42S "LANXUMSCAN G42S" +#define SCANNER_NAME_LSC_G52S "LANXUMSCAN G52S" +#define SCANNER_NAME_LSC_G62S "LANXUMSCAN G62S" +#define SCANNER_NAME_LSC_G73S "LANXUMSCAN G73S" + // #define SCANNER_NAME_HW_7000 "汉王扫描仪—HW7000" // #define SCANNER_NAME_HW_7000 "\346\261\211\347\216\213\346\211\253\346\217\217\344\273\252\342\200\224HW7000" // #define SCANNER_NAME_HW_7002 "汉王扫描仪—HW7002" diff --git a/hgdriver/hgdev/hg_scanner.cpp b/hgdriver/hgdev/hg_scanner.cpp index b363395..39b851b 100644 --- a/hgdriver/hgdev/hg_scanner.cpp +++ b/hgdriver/hgdev/hg_scanner.cpp @@ -14,7 +14,7 @@ static int ui_default_callback(scanner_handle, int, void*, unsigned int*, void*) { return 0; } -static std::string bmp_821(unsigned char* bits/*bits data*/, int w, int h, int* lbytes, bool line_align_4, int threashold, bool reverse) +static std::string bmp_821(unsigned char* bits/*bits data*/, int w, int h, int* lbytes/*in/out 行字节*/, bool line_align_4/*是否行对齐4字节*/, int threashold/*黑白像素阈值*/, bool reverse/*是否反色输出*/) { static unsigned int g_bmp8_pallete[] = { 0x00000000, 0x00800000, 0x00008000, 0x00808000, 0x00000080, 0x00800080, 0x00008080, 0x00c0c0c0, 0x00c0dcc0, 0x00a6caf0, 0x00402000, 0x00602000, 0x00802000, 0x00a02000, 0x00c02000, 0x00e02000 @@ -2317,7 +2317,11 @@ int hg_scanner::save_final_image(hg_imgproc::LPIMGHEAD head, void* buf) if (img_conf_.pixtype == 0 || (is_1bit && is_multiout)) { int old = head->line_bytes; + /*/ bw = bmp_821((unsigned char*)buf, head->width, head->height, &head->line_bytes, async_io_, bw_threshold_, is_white_0_); + /*/ + bw = hg_imgproc::bmp8_2_1bit((unsigned char*)buf, head->width, head->height, head->line_bytes, bw_threshold_, is_white_0_, async_io_); + head->line_bytes = bw.length() / head->height;////////*////////// buf = &bw[0]; head->channels = head->bits = 1; head->total_bytes = head->line_bytes * head->height; diff --git a/hgdriver/hgdev/image_process.cpp b/hgdriver/hgdev/image_process.cpp index 7dc889b..0e791bd 100644 --- a/hgdriver/hgdev/image_process.cpp +++ b/hgdriver/hgdev/image_process.cpp @@ -60,6 +60,10 @@ extern "C" #include "hg_ipc.h" #include "../ImageProcess/G4Tiff.h" +#include +#define CV_MAT_DEPTH_SET(flags, depth) (((flags) & ~(CV_MAT_DEPTH_MASK)) | (depth & CV_MAT_DEPTH_MASK)) + + using namespace std; #define GET_BYTE(a) ((a) & 0x0ff) #define MAKE_INT(a, b, c, d) (GET_BYTE(a) | (GET_BYTE(b) << 8) | (GET_BYTE(c) << 16) | (GET_BYTE(d) << 24)) @@ -458,7 +462,10 @@ namespace hg_imgproc mat = output.apply(mats[i]); for(size_t j = 0;j < mat.size();j++) { - mats_.push_back(mat[j]); + //if (out_type != MULTI_COLOR_AND_GRAY && i == mats.size() - 1) + // mats_.push_back(convert_8bit_2_1bit(mat[j], 127, false, false)); + //else + mats_.push_back(mat[j]); // std::string filename = "multi_out("+std::to_string(num++)+").jpg"; // cv::imwrite(filename,mat[j]); } @@ -700,249 +707,283 @@ namespace hg_imgproc //#endif return ret; } - //除网? - int textureRemove() - { - int ret = SCANNER_ERR_OK; - std::vector mats(mats_); - mats_.clear(); - - CImageApplyTextureRemoval Removal; - - Removal.apply(mats,img_conf_.is_duplex); - mats_ = mats; - - return ret; - } - //锐化 - int sharpenType() - { - int ret = SCANNER_ERR_OK; - std::vector mats(mats_); - mats_.clear(); - - CImageApplyFilter::FilterMode sharpenType = (CImageApplyFilter::FilterMode)img_conf_.sharpen; - CImageApplyFilter Filte(sharpenType); - for (size_t i = 0; i < mats.size(); ++i) + //除网? + int textureRemove() { - Filte.apply(mats[i],img_conf_.is_duplex); - mats_.push_back(mats[i]); - } - return ret; - } - //黑白降噪 - int nosieDetach() - { - int ret = SCANNER_ERR_OK; - std::vector mats(mats_); - mats_.clear(); - - CImageApplyDetachNoise Noise(img_conf_.detachnoise.detachnoise); - for (size_t i = 0; i < mats.size(); ++i) - { - Noise.apply(mats[i],img_conf_.is_duplex); - mats_.push_back(mats[i]); - } - return ret; - - } - //错误扩散 - int errorextention() - { - int ret = SCANNER_ERR_OK; - std::vector mats(mats_); - mats_.clear(); - - CImageApplyBWBinaray::ThresholdType thrtype; - if(img_conf_.errorExtention) - thrtype = CImageApplyBWBinaray::ThresholdType::ERROR_DIFFUSION; - else - thrtype = CImageApplyBWBinaray::ThresholdType::THRESH_BINARY; - - CImageApplyBWBinaray BWBinaray(thrtype); - for (size_t i = 0; i < mats.size(); ++i) - { - BWBinaray.apply(mats[i],img_conf_.is_duplex); - mats_.push_back(mats[i]); - } - return ret; - } - - int discardBlank() - { - int ret = SCANNER_ERR_OK; - std::vector mats(mats_); - mats_.clear(); - - double threshold = 40; - int edge = 150; - - CImageApplyDiscardBlank(threshold,edge,img_conf_.discardblank_percent); - - for (size_t i = 0; i < mats.size(); ++i) - { - bool b = CImageApplyDiscardBlank::apply(mats[i]); - - if (b) - mats[i].release(); - else - mats_.push_back(mats[i]); - } - return ret; - } - //答题卡出? - int answerSheetFilterRed() - { - int ret = SCANNER_ERR_OK; + int ret = SCANNER_ERR_OK; std::vector mats(mats_); mats_.clear(); - CImageApplyHSVCorrect correct((CImageApplyHSVCorrect::Red_Removal)); + CImageApplyTextureRemoval Removal; + + Removal.apply(mats,img_conf_.is_duplex); + mats_ = mats; + + return ret; + } + //锐化 + int sharpenType() + { + int ret = SCANNER_ERR_OK; + std::vector mats(mats_); + mats_.clear(); + + CImageApplyFilter::FilterMode sharpenType = (CImageApplyFilter::FilterMode)img_conf_.sharpen; + CImageApplyFilter Filte(sharpenType); for (size_t i = 0; i < mats.size(); ++i) { - correct.apply(mats[i],img_conf_.is_duplex); + Filte.apply(mats[i],img_conf_.is_duplex); mats_.push_back(mats[i]); } return ret; - } - //对折 - int fold() - { - int ret = SCANNER_ERR_OK; + } + //黑白降噪 + int nosieDetach() + { + int ret = SCANNER_ERR_OK; std::vector mats(mats_); mats_.clear(); - CImageApplyConcatenation fold(CImageApplyConcatenation::horizontal); - fold.apply(mats,img_conf_.is_duplex); - mats_= mats; + CImageApplyDetachNoise Noise(img_conf_.detachnoise.detachnoise); + for (size_t i = 0; i < mats.size(); ++i) + { + Noise.apply(mats[i],img_conf_.is_duplex); + mats_.push_back(mats[i]); + } + return ret; - return ret; - } - - //画质 - int quality(int dpi_dst) - { - int ret = SCANNER_ERR_OK; + } + //错误扩散 + int errorextention() + { + int ret = SCANNER_ERR_OK; std::vector mats(mats_); mats_.clear(); - //mats_.resize(mats.size()); - float xy = (float)dpi_dst/200.0; + + CImageApplyBWBinaray::ThresholdType thrtype; + if(img_conf_.errorExtention) + thrtype = CImageApplyBWBinaray::ThresholdType::ERROR_DIFFUSION; + else + thrtype = CImageApplyBWBinaray::ThresholdType::THRESH_BINARY; + + CImageApplyBWBinaray BWBinaray(thrtype); + for (size_t i = 0; i < mats.size(); ++i) + { + BWBinaray.apply(mats[i],img_conf_.is_duplex); + mats_.push_back(mats[i]); + } + return ret; + } + + int discardBlank() + { + int ret = SCANNER_ERR_OK; + std::vector mats(mats_); + mats_.clear(); + + double threshold = 40; + int edge = 150; + + CImageApplyDiscardBlank(threshold,edge,img_conf_.discardblank_percent); for (size_t i = 0; i < mats.size(); ++i) { - cv::Mat out; - cv::resize(mats[i],out, cv::Size(),xy,xy); - mats_.push_back(out); + bool b = CImageApplyDiscardBlank::apply(mats[i]); + + if (b) + mats[i].release(); + else + mats_.push_back(mats[i]); } - return SCANNER_ERR_OK; - } -#ifdef _WIN32 - -#endif -#define test - int ocr_auto_txtdirect() - { - std::vector mats(mats_); - mats_.clear(); - - int pDirect = -1, - ret = SCANNER_ERR_OK; - void* pHanld = NULL; - - typedef int (* SDKInitialize)(void** ppstOcrHandle); - typedef void(* SDKExit)(void* pstOcrHandle); - typedef int (* SDKGetFileDirectImage)(BYTE* pbImage, int nWidth, int nHeight, TColorType nColorType, void* pstHandle, int* pDirect); - - SDKInitialize ocrinit = NULL; - SDKGetFileDirectImage ocrgetdirectimage = NULL; - SDKExit ocrexit = NULL; - -#ifndef WIN32 - #ifdef OEM_HANWANG - string libname = "libhwdriver.so"; - #elif defined(OEM_LISICHENG) - string libname = "liblscdriver.so"; - #else - string libname = "libhgdriver.so"; - #endif - - string scanner_path = hg_log::get_module_full_path(libname.c_str()); - - if(scanner_path.empty()) - { - return SCANNER_ERR_OUT_OF_RANGE; + return ret; } - scanner_path = scanner_path.substr(0,scanner_path.size() - libname.size()); - scanner_path+="libhwocrdetect.so"; - printf("hwlib path:%s\r\n",scanner_path.c_str()); - - if(access(scanner_path.c_str(),F_OK) != 0) + //答题卡出? + int answerSheetFilterRed() { - return SCANNER_ERR_OUT_OF_RANGE; - } -#endif -#if ((!defined x86_64) && (!defined WIN32)) -//linux x86_64 暂时没有OCR三方 + int ret = SCANNER_ERR_OK; + std::vector mats(mats_); + mats_.clear(); - void *hanlde = dlopen(scanner_path.c_str(),RTLD_LAZY); - if(!hanlde) + CImageApplyHSVCorrect correct((CImageApplyHSVCorrect::Red_Removal)); + for (size_t i = 0; i < mats.size(); ++i) + { + correct.apply(mats[i],img_conf_.is_duplex); + mats_.push_back(mats[i]); + } + return ret; + } + //对折 + int fold() { - return SCANNER_ERR_OUT_OF_RANGE; - } - ocrinit = (SDKInitialize)dlsym(hanlde , "HWOCR_SDKInitialize"); - ocrgetdirectimage = (SDKGetFileDirectImage)dlsym(hanlde , "HWOCR_GetFileDirectImage"); - ocrexit= (SDKExit)dlsym(hanlde , "HWOCR_SDKExit"); + int ret = SCANNER_ERR_OK; + std::vector mats(mats_); + mats_.clear(); -#else - #ifdef _WIN32 - HINSTANCE handle = LoadLibrary(L"hanwangOCRdetect.dll"); - if (handle) + CImageApplyConcatenation fold(CImageApplyConcatenation::horizontal); + fold.apply(mats,img_conf_.is_duplex); + mats_= mats; + + return ret; + } + + //画质 + int quality(int dpi_dst) + { + int ret = SCANNER_ERR_OK; + std::vector mats(mats_); + mats_.clear(); + //mats_.resize(mats.size()); + float xy = (float)dpi_dst/200.0; + + for (size_t i = 0; i < mats.size(); ++i) + { + cv::Mat out; + cv::resize(mats[i],out, cv::Size(),xy,xy); + mats_.push_back(out); + } + return SCANNER_ERR_OK; + } + #ifdef _WIN32 + + #endif + #define test + int ocr_auto_txtdirect() + { + std::vector mats(mats_); + mats_.clear(); + + int pDirect = -1, + ret = SCANNER_ERR_OK; + void* pHanld = NULL; + + typedef int (* SDKInitialize)(void** ppstOcrHandle); + typedef void(* SDKExit)(void* pstOcrHandle); + typedef int (* SDKGetFileDirectImage)(BYTE* pbImage, int nWidth, int nHeight, TColorType nColorType, void* pstHandle, int* pDirect); + + SDKInitialize ocrinit = NULL; + SDKGetFileDirectImage ocrgetdirectimage = NULL; + SDKExit ocrexit = NULL; + + #ifndef WIN32 + #ifdef OEM_HANWANG + string libname = "libhwdriver.so"; + #elif defined(OEM_LISICHENG) + string libname = "liblscdriver.so"; + #else + string libname = "libhgdriver.so"; + #endif + + string scanner_path = hg_log::get_module_full_path(libname.c_str()); + + if(scanner_path.empty()) { - ocrinit = (SDKInitialize)GetProcAddress(handle, "HWOCR_SDKInitialize"); - ocrgetdirectimage = (SDKGetFileDirectImage)GetProcAddress(handle, "HWOCR_GetFileDirectImage"); - ocrexit = (SDKExit)GetProcAddress(handle, "HWOCR_SDKExit"); + return SCANNER_ERR_OUT_OF_RANGE; } - #endif // WIN32 //暂时保留文本方向旋转 -#endif - int r = ocrinit(&pHanld); - for (size_t i = 0; i < mats.size(); i++) + scanner_path = scanner_path.substr(0,scanner_path.size() - libname.size()); + scanner_path+="libhwocrdetect.so"; + printf("hwlib path:%s\r\n",scanner_path.c_str()); + + if(access(scanner_path.c_str(),F_OK) != 0) { - r = ocrgetdirectimage(const_cast(mats[i].data), mats[i].cols, mats[i].rows, mats[i].channels() == 1 ? TColorType::EGray256 : TColorType::EColor16M, pHanld, &pDirect); + return SCANNER_ERR_OUT_OF_RANGE; + } + #endif + #if ((!defined x86_64) && (!defined WIN32)) + //linux x86_64 暂时没有OCR三方 - if (pDirect == 1) - pDirect = 3; - else if (pDirect == 3) - pDirect = 1; + void *hanlde = dlopen(scanner_path.c_str(),RTLD_LAZY); + if(!hanlde) + { + return SCANNER_ERR_OUT_OF_RANGE; + } + ocrinit = (SDKInitialize)dlsym(hanlde , "HWOCR_SDKInitialize"); + ocrgetdirectimage = (SDKGetFileDirectImage)dlsym(hanlde , "HWOCR_GetFileDirectImage"); + ocrexit= (SDKExit)dlsym(hanlde , "HWOCR_SDKExit"); - CImageApplyRotation(CImageApplyRotation::RotationType(pDirect)).apply(mats[i], false); + #else + #ifdef _WIN32 + HINSTANCE handle = LoadLibrary(L"hanwangOCRdetect.dll"); + if (handle) + { + ocrinit = (SDKInitialize)GetProcAddress(handle, "HWOCR_SDKInitialize"); + ocrgetdirectimage = (SDKGetFileDirectImage)GetProcAddress(handle, "HWOCR_GetFileDirectImage"); + ocrexit = (SDKExit)GetProcAddress(handle, "HWOCR_SDKExit"); + } + #endif // WIN32 //暂时保留文本方向旋转 + #endif + int r = ocrinit(&pHanld); + for (size_t i = 0; i < mats.size(); i++) + { + r = ocrgetdirectimage(const_cast(mats[i].data), mats[i].cols, mats[i].rows, mats[i].channels() == 1 ? TColorType::EGray256 : TColorType::EColor16M, pHanld, &pDirect); + + if (pDirect == 1) + pDirect = 3; + else if (pDirect == 3) + pDirect = 1; + + CImageApplyRotation(CImageApplyRotation::RotationType(pDirect)).apply(mats[i], false); + mats_.push_back(mats[i]); + } + ocrexit(pHanld); + #if ((!defined x86_64) && (!defined WIN32)) + dlclose(hanlde); + #else + + #endif + return ret; + } + int size_detection() + { + int ret = SCANNER_ERR_OK; + std::vector mats(mats_); + mats_.clear(); + CImageApplySizeDetection paper(img_conf_.papertype); + for (size_t i = 0; i < mats.size(); ++i) + { + ret = paper.apply(mats[i]); mats_.push_back(mats[i]); } - ocrexit(pHanld); -#if ((!defined x86_64) && (!defined WIN32)) - dlclose(hanlde); -#else - -#endif - return ret; - } - int size_detection() - { - int ret = SCANNER_ERR_OK; - std::vector mats(mats_); - mats_.clear(); - CImageApplySizeDetection paper(img_conf_.papertype); - for (size_t i = 0; i < mats.size(); ++i) - { - ret = paper.apply(mats[i]); - mats_.push_back(mats[i]); - } - if(ret == 1) - { - return SCANNER_ERR_DEVICE_SIZE_CHECK; - } - return SCANNER_ERR_OK; + if(ret == 1) + { + return SCANNER_ERR_DEVICE_SIZE_CHECK; + } + return SCANNER_ERR_OK; - } + } + + /// + /// 8λͼת1λͼ + /// + /// 8bitͼ + /// ֵĬ127 + /// trueΪɫ01֮Ȼ + /// trueΪֽڶ + /// 1λͼ + static cv::Mat convert_8bit_2_1bit(const cv::Mat& image, uchar threshold, bool reverse, bool align) + { + if (image.channels() != 1) + return cv::Mat(); + + int cols = align ? (((image.cols + 7) / 8 + 3) / 4 * 4) : ((image.cols + 7) / 8); + int rows = image.rows; + + uchar tableData[256]; + memset(tableData, reverse ? 0 : 1, 256); + memset(tableData, reverse ? 1 : 0, threshold); + + cv::Mat dst = cv::Mat::zeros(rows, cols, (int)CV_8UC1); + uchar* ptr_src, * ptr_dst; + for (size_t y = 0; y < rows; y++) + { + ptr_dst = dst.ptr(y); + ptr_src = const_cast(image.ptr(y)); + for (size_t x = 0; x < image.cols; x++) + ptr_dst[x / 8] += tableData[ptr_src[x]] << (x % 8); + } + + return dst; + } + // final public: int final(void) @@ -1195,8 +1236,6 @@ namespace hg_imgproc } // seperate utilites ... -#include -#define CV_MAT_DEPTH_SET(flags, depth) (((flags) & ~(CV_MAT_DEPTH_MASK)) | (depth & CV_MAT_DEPTH_MASK)) static cv::Mat from_bmp_file_bits(const BITMAPINFOHEADER& bih, unsigned char* data, bool line_reverse, bool bw_reverse) { cv::Mat m; @@ -1470,6 +1509,43 @@ namespace hg_imgproc return 0; } + + static unsigned char reverse_bit(unsigned char v) + { + unsigned char r = 0; + + for (int i = 0; i < 8; ++i) + { + r <<= 1; + r |= v & 1; + v >>= 1; + } + + return r; + } + std::string bmp8_2_1bit(const unsigned char* data, int w, int h, int line_len, int threshold, bool reverse, bool align) + { + cv::Mat m; + unsigned char* dst = NULL; + + m.create(h, w, CV_8UC1); + dst = m.ptr();// +w * (h - 1); + for (int i = 0; i < h; ++i) + { + memcpy(dst, data, w); + dst += w; + data += line_len; + } + + cv::Mat bw = imgproc::convert_8bit_2_1bit(m, threshold, reverse, align); + //std::string ret(""); + + dst = bw.ptr(); + for (int i = 0; i < bw.total(); ++i) + dst[i] = reverse_bit(dst[i]); + + return std::string((char*)bw.ptr(), bw.total()); + } } diff --git a/hgdriver/hgdev/image_process.h b/hgdriver/hgdev/image_process.h index 2fcf92e..158b6db 100644 --- a/hgdriver/hgdev/image_process.h +++ b/hgdriver/hgdev/image_process.h @@ -212,8 +212,9 @@ namespace hg_imgproc int get_final_data(HIMGPRC himg, LPIMGHEAD pimh, std::vector* buf, int index); void release(HIMGPRC himg); - // seperate utilites ... int convert_image_file(SANE_ImageFormatConvert* conv); int save_2_bmp_file(const char* bmp_file, LPIMGHEAD head, void* buf, int resolution); + + std::string bmp8_2_1bit(const unsigned char* data, int w, int h, int line_len, int threshold, bool reverse, bool align); } diff --git a/hgdriver/hgdev/scanner_manager.cpp b/hgdriver/hgdev/scanner_manager.cpp index 1fb1d98..9b0f4da 100644 --- a/hgdriver/hgdev/scanner_manager.cpp +++ b/hgdriver/hgdev/scanner_manager.cpp @@ -33,13 +33,13 @@ g_supporting_devices[] = { #ifdef OEM_LISICHENG {0x31c9, 0x8200, SCANNER_NAME_LSC_G42S, "G42x0F", "", &hg_scanner_mgr::create_scanner_g300} , {0x31c9, 0x8420, SCANNER_NAME_LSC_G42S, "G426xF", "", &hg_scanner_mgr::create_scanner_g300} + , {0x31c9, 0x8429, SCANNER_NAME_LSC_G42S, "G42x0F", "", &hg_scanner_mgr::create_scanner_empty} , {0x31c9, 0x8520, SCANNER_NAME_LSC_G52S, "G52x0F", "", &hg_scanner_mgr::create_scanner_g400} + , {0x31c9, 0x8529, SCANNER_NAME_LSC_G52S, "G52x0F", "", &hg_scanner_mgr::create_scanner_g239} , {0x31c9, 0x8620, SCANNER_NAME_LSC_G62S, "G6290U", "", &hg_scanner_mgr::create_scanner_g100} , {0x31c9, 0x8629, SCANNER_NAME_LSC_G62S, "G6290U", "", &hg_scanner_mgr::create_scanner_g239} , {0x31c9, 0x8730, SCANNER_NAME_LSC_G73S, "G73x0U", "", &hg_scanner_mgr::create_scanner_g100} , {0x31c9, 0x8739, SCANNER_NAME_LSC_G73S, "G73x0U", "", &hg_scanner_mgr::create_scanner_g239} - , {0x31c9, 0x8529, SCANNER_NAME_LSC_G52S, "G52x0F", "", &hg_scanner_mgr::create_scanner_g239} - , {0x31c9, 0x8429, SCANNER_NAME_LSC_G42S, "G42x0F", "", &hg_scanner_mgr::create_scanner_empty} #elif defined(OEM_HANWANG) {0x2903, 0x1000, SCANNER_NAME_HW_1000, SCANNER_NAME_HW_1000, "",& hg_scanner_mgr::create_scanner_g300} // "HW-1060A" @@ -51,16 +51,16 @@ g_supporting_devices[] = { , {0x2903, 0x9000, SCANNER_NAME_HW_9000, SCANNER_NAME_HW_9000, "", &hg_scanner_mgr::create_scanner_g239} // "HW-9110E" #else {0x3072, 0x100, SCANNER_NAME_HG_G100, "GScanO200", "", &hg_scanner_mgr::create_scanner_g100} + , {0x3072, 0x139, SCANNER_NAME_HG_G100, "GScanO1003399", "", &hg_scanner_mgr::create_scanner_g239} , {0x3072, 0x200, SCANNER_NAME_HG_G200, "GScanO200", "", &hg_scanner_mgr::create_scanner_g100} + , {0x3072, 0x239, SCANNER_NAME_HG_G200, "GScanO1003399", "", &hg_scanner_mgr::create_scanner_g239} , {0x3072, 0x300, SCANNER_NAME_HG_G300, "GScanO400", "", &hg_scanner_mgr::create_scanner_g300} - , {0x3072, 0x400, SCANNER_NAME_HG_G400, "GScanO400", "", &hg_scanner_mgr::create_scanner_g400} - , {0x3072, 0x139, SCANNER_NAME_HG_G139, "GScanO1003399", "", &hg_scanner_mgr::create_scanner_g239} - , {0x3072, 0x239, SCANNER_NAME_HG_G239, "GScanO1003399", "", &hg_scanner_mgr::create_scanner_g239} - , {0x3072, 0x339, SCANNER_NAME_HG_G339, "GScanO1003399", "", &hg_scanner_mgr::create_scanner_empty} - , {0x3072, 0x439, SCANNER_NAME_HG_G439, "GScanO1003399", "", &hg_scanner_mgr::create_scanner_g239} - , {0x064B, 0x7823, SCANNER_NAME_HG_G200, "GScanO200", "", &hg_scanner_mgr::create_scanner_empty} , {0x3072, 0x302, SCANNER_NAME_HG_G300, "GScanO400", "", &hg_scanner_mgr::create_scanner_g302} - , {0x3072, 0x402, SCANNER_NAME_HG_G402, "GScanO4003399", "", &hg_scanner_mgr::create_scanner_g402} + , {0x3072, 0x339, SCANNER_NAME_HG_G300, "GScanO1003399", "", &hg_scanner_mgr::create_scanner_empty} + , {0x3072, 0x400, SCANNER_NAME_HG_G400, "GScanO400", "", &hg_scanner_mgr::create_scanner_g400} + , {0x3072, 0x402, SCANNER_NAME_HG_G400, "GScanO4003399", "", &hg_scanner_mgr::create_scanner_g402} + , {0x3072, 0x439, SCANNER_NAME_HG_G400, "GScanO1003399", "", &hg_scanner_mgr::create_scanner_g239} + , {0x064B, 0x7823,SCANNER_NAME_HG_G200, "GScanO200", "", &hg_scanner_mgr::create_scanner_empty} #endif }; static std::string g_vendor = COMPANY_NAME;