change image process thread pool

This commit is contained in:
gb 2023-05-11 17:19:00 +08:00
parent d56e482a7a
commit eec4604ee3
13 changed files with 341 additions and 420 deletions

View File

@ -17,7 +17,7 @@
static const std::string loggername = "imageusbhandler"; static const std::string loggername = "imageusbhandler";
ImageUsbHandler::ImageUsbHandler(std::shared_ptr<UsbImageProcQueue> images) ImageUsbHandler::ImageUsbHandler(std::shared_ptr<UsbImageProcQueue> images)
: pool(1), encodepools(6),pushpool(1) : pool(1), encodepools(/*6*/1),pushpool(1)
{ {
LOG_INIT(); LOG_INIT();
this->images = images; this->images = images;
@ -37,13 +37,13 @@ static int num = 0;
void ImageUsbHandler::add_image(void *data, int width, int height, int type, int scannnum,unsigned int fpgaversion) void ImageUsbHandler::add_image(void *data, int width, int height, int type, int scannnum,unsigned int fpgaversion)
{ {
printf("ImageUsbHandler::add_image %d(%d * %d), fpgaversion = %d, HRatio = %f, VRatio = %f\n", scannnum, width, height, fpgaversion, H_ratio, V_ratio); printf("ImageUsbHandler::add_image %d(%d * %d), fpgaversion = %d, HRatio = %f, VRatio = %f\n", scannnum, width, height, fpgaversion, H_ratio, V_ratio);
#ifdef ASYNC_EP
if(images->push_raw(data, width, height, type == CV_8UC1 ? COLOR_CHANNEL_GRAY : COLOR_CHANNEL_RGB, scannnum, fpgaversion, 0)) if(images->push_raw(data, width, height, type == CV_8UC1 ? COLOR_CHANNEL_GRAY : COLOR_CHANNEL_RGB, scannnum, fpgaversion, 0))
{ {
return; return;
} }
#endif
images->push(nullptr, false); // notify ONE paper passed
std::string ext = ".jpg"; std::string ext = ".jpg";
{ {
@ -129,6 +129,10 @@ void ImageUsbHandler::add_image(void *data, int width, int height, int type, int
// if((H_ratio != 1.0f) || (V_ratio != 1.0f)) // if((H_ratio != 1.0f) || (V_ratio != 1.0f))
// cv::resize(saveMat,saveMat,cv::Size(),H_ratio,V_ratio); // cv::resize(saveMat,saveMat,cv::Size(),H_ratio,V_ratio);
// test sequence ...
// if(scannnum % 1) std::this_thread::sleep_for(std::chrono::milliseconds(500));
encode_data.Put(saveMat); encode_data.Put(saveMat);
encodeimgs.push(encodepools.enqueue([this,width,height,type]() -> std::vector<MemoryPtr> encodeimgs.push(encodepools.enqueue([this,width,height,type]() -> std::vector<MemoryPtr>
@ -293,7 +297,9 @@ void ImageUsbHandler::Set_ratio(u32 h_ratio,u32 v_ratio)
bool ImageUsbHandler::done() bool ImageUsbHandler::done()
{ {
#ifdef ASYNC_EP
return images->is_image_processing_over(); return images->is_image_processing_over();
#endif
std::lock_guard<std::mutex> guard(mtx); std::lock_guard<std::mutex> guard(mtx);
if(results.size() >= 1){ if(results.size() >= 1){

View File

@ -90,7 +90,7 @@ Scanner::Scanner(std::shared_ptr<ICapturer> capturer, std::shared_ptr<MotorBoard
LOG_TRACE("callback SIZE ERROR\n"); LOG_TRACE("callback SIZE ERROR\n");
} }
mb_error_code = code; mb_error_code = code;
printf("---------------mb_error_code value = %d ---------------\n", error_code); printf("---------------mb_error_code value = %d (%d)---------------\n", error_code, error_code);
if (code != 0) if (code != 0)
{ {
HGIntInfo errType = {.From = MtBoard, .Code = code}; HGIntInfo errType = {.From = MtBoard, .Code = code};
@ -117,12 +117,13 @@ Scanner::Scanner(std::shared_ptr<ICapturer> capturer, std::shared_ptr<MotorBoard
}; };
auto mb_coveropen_call = [&](bool isopen) auto mb_coveropen_call = [&](bool isopen)
{ {
HGIntInfo errType = {.From = MtBoard, .Code = 5 - isopen};
if (imagehandler.get())
imagehandler->add_scanevent(errType);
if (isopen) if (isopen)
{ {
LOG_TRACE("cover opened \n"); LOG_TRACE("cover opened \n");
HGIntInfo errType = {.From = MtBoard, .Code = 4};
if (imagehandler.get())
imagehandler->add_scanevent(errType);
done_scan = 1; done_scan = 1;
} }
else else
@ -574,9 +575,10 @@ void Scanner::runScan()
else else
autosizescan(); autosizescan();
savescannerinfo(scannerinfo); savescannerinfo(scannerinfo);
imagehandler->add_scanevent({.From = STOPSCAN, mb_error_code}); imagehandler->add_scanevent({.From = STOPSCAN, .Code = mb_error_code});
while (!imagehandler->done()) while (!imagehandler->done())
this_thread::sleep_for(chrono::milliseconds(10)); this_thread::sleep_for(chrono::milliseconds(10));
printf("\nscan finished.\n");
done_scan = 0; done_scan = 0;
if (wake.get()) if (wake.get())
@ -699,20 +701,20 @@ bool Scanner::pickpaper()
while (imagehandler->is_limit()) while (imagehandler->is_limit())
std::this_thread::sleep_for(std::chrono::milliseconds(10)); std::this_thread::sleep_for(std::chrono::milliseconds(10));
} }
// unsigned int reg2v; unsigned int reg2v;
// mb->read(0x02, reg2v); mb->read(0x02, reg2v);
// if (reg2v & 0x00010000) if (reg2v & 0x00010000)
// { //有纸 { //有纸
printf("\n+++++++++pick paper "); printf("\n+++++++++pick paper ");
mb->pick_paper(); mb->pick_paper();
startcapimage(true); startcapimage(true);
return true; return true;
// } }
// else else
// { {
// printf("\n+++++++++pick paper no paper"); printf("\n+++++++++pick paper no paper");
// return false; return false;
// } }
} }
void Scanner::set_motorboardcallback(MotorBoardGlue glue) void Scanner::set_motorboardcallback(MotorBoardGlue glue)

View File

@ -7,7 +7,7 @@
// configuration text // configuration text
// //
static std::string g_cis_cfg("{\"montage\":{\"cat\":\"cis\",\"group\":\"CIS\",\"title\":\"\\u56fe\\u50cf\\u62fc\\u63a5\",\"desc\":\"\\u5c06CIS\\u91c7\\u96c6\\u7684\\u539f\\u59cb\\u6570\\u636e\\u6062\\u590d\\u4e3a\\u6b63\\u5e38\\u7684\\u56fe\\u50cf\",\"ver\":1,\"pos\":10,\"type\":\"bool\",\"unit\":\"none\",\"affect\":0,\"readonly\":false,\"visible\":false,\"enabled\":true,\"size\":4,\"cur\":true,\"default\":true},\"cis-color-correct\":{\"cat\":\"CIS\",\"group\":\"CIS\",\"title\":\"\\u5149\\u5b66\\u989c\\u8272\\u6821\\u6b63\",\"desc\":\"\\u5bf9CIS\\u7684\\u539f\\u56fe\\u989c\\u8272\\u8fdb\\u884c\\u6821\\u6b63\",\"ver\":1,\"pos\":20,\"type\":\"bool\",\"unit\":\"none\",\"affect\":0,\"readonly\":false,\"visible\":false,\"enabled\":true,\"size\":4,\"cur\":true,\"default\":true},\"reinstate\":{\"cat\":\"CIS\",\"group\":\"CIS\",\"title\":\"\\u786c\\u4ef6\\u590d\\u539f\",\"desc\":\"\\u6d88\\u9664CIS\\u786c\\u4ef6\\u62c9\\u4f38\\u56e0\\u7d20\\uff0c\\u6062\\u590d\\u56fe\\u7247\\u521d\\u59cb\\u72b6\\u6001\",\"ver\":1,\"pos\":30,\"type\":\"bool\",\"unit\":\"none\",\"affect\":0,\"readonly\":false,\"visible\":false,\"enabled\":true,\"size\":4,\"cur\":true,\"default\":true},\"fb-split\":{\"cat\":\"CIS\",\"group\":\"CIS\",\"title\":\"\\u62c6\\u5206\\u6b63\\u53cd\\u9762\",\"desc\":\"\\u5c06\\u6b63\\u53cd\\u9762\\u5408\\u6210\\u7684\\u4e00\\u5f20\\u56fe\\u7247\\u62c6\\u5206\\u6210\\u6b63\\u9762\\u548c\\u53cd\\u9762\\u56fe\\u7247\",\"ver\":1,\"pos\":40,\"type\":\"bool\",\"unit\":\"none\",\"affect\":2,\"readonly\":false,\"visible\":false,\"enabled\":true,\"size\":4,\"cur\":true,\"default\":true},\"page\":{\"cat\":\"CIS\",\"group\":\"base\",\"title\":\"\\u9875\\u9762\",\"desc\":\"\\u83b7\\u53d6\\u7eb8\\u5f20\\u6307\\u5b9a\\u9762\\u7684\\u56fe\\u7247\",\"ver\":1,\"pos\":50,\"type\":\"string\",\"unit\":\"none\",\"affect\":2,\"readonly\":false,\"visible\":true,\"enabled\":true,\"size\":30,\"cur\":\"\\u53cc\\u9762\",\"default\":\"\\u53cc\\u9762\",\"range\":[\"\\u6b63\\u9762\",\"\\u80cc\\u9762\",\"\\u53cc\\u9762\"],\"depend_or\":[\"fb-split==true\"]},\"is-exchange\":{\"cat\":\"CIS\",\"group\":\"base\",\"title\":\"\\u4ea4\\u6362\\u6b63\\u53cd\\u9762\",\"desc\":\"\\u4ea4\\u6362\\u6bcf\\u5f20\\u6587\\u7a3f\\u7684\\u6b63\\u53cd\\u9762\\u51fa\\u56fe\\u987a\\u5e8f\",\"ver\":1,\"pos\":60,\"type\":\"bool\",\"unit\":\"none\",\"affect\":0,\"readonly\":false,\"visible\":true,\"enabled\":true,\"size\":4,\"cur\":false,\"default\":false,\"depend_and\":[\"fb-split==true\",\"page==\\u53cc\\u9762\"]}}"); static std::string g_cis_cfg("{\"montage\":{\"cat\":\"cis\",\"group\":\"CIS\",\"title\":\"\\u56fe\\u50cf\\u62fc\\u63a5\",\"desc\":\"\\u5c06CIS\\u91c7\\u96c6\\u7684\\u539f\\u59cb\\u6570\\u636e\\u6062\\u590d\\u4e3a\\u6b63\\u5e38\\u7684\\u56fe\\u50cf\",\"ver\":1,\"pos\":10,\"type\":\"bool\",\"unit\":\"none\",\"affect\":0,\"readonly\":false,\"visible\":false,\"enabled\":true,\"size\":4,\"cur\":true,\"default\":true},\"cis-color-correct\":{\"cat\":\"CIS\",\"group\":\"CIS\",\"title\":\"\\u5149\\u5b66\\u989c\\u8272\\u6821\\u6b63\",\"desc\":\"\\u5bf9CIS\\u7684\\u539f\\u56fe\\u989c\\u8272\\u8fdb\\u884c\\u6821\\u6b63\",\"ver\":1,\"pos\":20,\"type\":\"bool\",\"unit\":\"none\",\"affect\":0,\"readonly\":false,\"visible\":false,\"enabled\":true,\"size\":4,\"cur\":true,\"default\":true},\"reinstate\":{\"cat\":\"CIS\",\"group\":\"CIS\",\"title\":\"\\u786c\\u4ef6\\u590d\\u539f\",\"desc\":\"\\u6d88\\u9664CIS\\u786c\\u4ef6\\u62c9\\u4f38\\u56e0\\u7d20\\uff0c\\u6062\\u590d\\u56fe\\u7247\\u521d\\u59cb\\u72b6\\u6001\",\"ver\":1,\"pos\":30,\"type\":\"bool\",\"unit\":\"none\",\"affect\":0,\"readonly\":false,\"visible\":false,\"enabled\":true,\"size\":4,\"cur\":true,\"default\":true},\"fb-split\":{\"cat\":\"CIS\",\"group\":\"CIS\",\"title\":\"\\u62c6\\u5206\\u6b63\\u53cd\\u9762\",\"desc\":\"\\u5c06\\u6b63\\u53cd\\u9762\\u5408\\u6210\\u7684\\u4e00\\u5f20\\u56fe\\u7247\\u62c6\\u5206\\u6210\\u6b63\\u9762\\u548c\\u53cd\\u9762\\u56fe\\u7247\",\"ver\":1,\"pos\":40,\"type\":\"bool\",\"unit\":\"none\",\"affect\":2,\"readonly\":false,\"visible\":false,\"enabled\":true,\"size\":4,\"cur\":true,\"default\":true},\"page\":{\"cat\":\"CIS\",\"group\":\"base\",\"title\":\"\\u9875\\u9762\",\"desc\":\"\\u83b7\\u53d6\\u7eb8\\u5f20\\u6307\\u5b9a\\u9762\\u7684\\u56fe\\u7247\",\"ver\":1,\"pos\":50,\"type\":\"string\",\"unit\":\"none\",\"affect\":2,\"readonly\":false,\"visible\":true,\"enabled\":true,\"size\":30,\"cur\":\"\\u53cc\\u9762\",\"default\":\"\\u53cc\\u9762\",\"range\":[\"\\u6b63\\u9762\",\"\\u80cc\\u9762\",\"\\u53cc\\u9762\"],\"depend_or\":[\"fb-split==true\"]},\"is-exchange\":{\"cat\":\"CIS\",\"group\":\"base\",\"title\":\"\\u4ea4\\u6362\\u6b63\\u53cd\\u9762\",\"desc\":\"\\u4ea4\\u6362\\u6bcf\\u5f20\\u6587\\u7a3f\\u7684\\u6b63\\u53cd\\u9762\\u51fa\\u56fe\\u987a\\u5e8f\",\"ver\":1,\"pos\":60,\"type\":\"bool\",\"unit\":\"none\",\"affect\":0,\"readonly\":false,\"visible\":true,\"enabled\":true,\"size\":4,\"cur\":false,\"default\":false,\"depend_and\":[\"fb-split==true\",\"page==\\u53cc\\u9762\"]},\"is-rotate-bkg-180\":{\"cat\":\"CIS\",\"group\":\"base\",\"title\":\"\\u80cc\\u9762\\u65cb\\u8f6c180\\u00b0\",\"desc\":\"\\u80cc\\u9762\\u626b\\u63cf\\u7684\\u56fe\\u50cf\\u65cb\\u8f6c180\\u00b0\",\"ver\":1,\"pos\":70,\"type\":\"bool\",\"unit\":\"none\",\"affect\":0,\"readonly\":false,\"visible\":true,\"enabled\":true,\"size\":4,\"cur\":false,\"default\":false,\"depend_and\":[\"fb-split==true\",\"page!=\\u6b63\\u9762\"]}}");
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
@ -106,7 +106,7 @@ cis_pre_do::cis_pre_do(std::function<img_one_paper* (img_one_paper*)> montage
, std::function<SPLIT_PROTO> split) , std::function<SPLIT_PROTO> split)
: montage_(montage), split_(split) : montage_(montage), split_(split)
, cfg_(g_cis_cfg), is_montage_(true), is_split_(true), page_(PAGE_DUPLEX), cis_dpi_(200) , cfg_(g_cis_cfg), is_montage_(true), is_split_(true), page_(PAGE_DUPLEX), cis_dpi_(200)
, reinstate_(true), photo_mode_(false), is_correct_(true), is_exchg_(false) , reinstate_(true), photo_mode_(false), is_correct_(true), is_exchg_(false), is_bkg_rot_180_(false)
{ {
if (!montage_) if (!montage_)
montage_ = cis_montager; montage_ = cis_montager;
@ -186,6 +186,15 @@ void cis_pre_do::init_value(void)
is_exchg_ = false; is_exchg_ = false;
child->release(); child->release();
} }
if (jsn->get_value("is-rotate-bkg-180", child) && child)
{
bool enable = false;
child->get_value("enabled", enable);
if (!child->get_value("cur", is_bkg_rot_180_))
is_bkg_rot_180_ = false;
is_bkg_rot_180_ &= enable;
child->release();
}
jsn->release(); jsn->release();
} }
} }
@ -313,7 +322,7 @@ img_one_paper* cis_pre_do::execute(img_one_paper* img)
{ {
for(auto& v: img->images_queue()) for(auto& v: img->images_queue())
{ {
correctColor(v.img, v.head.resolution_x, v.img.channels() == 3 ? 1 : 0, !photo_mode_); correctColor(v.img, v.head.resolution_x, v.img.channels() == 3 ? 1 : 0, !photo_mode_);
} }
} }
@ -345,6 +354,17 @@ img_one_paper* cis_pre_do::execute(img_one_paper* img)
} }
} }
} }
if(!is_bkg_rot_180_)
{
for(auto& v: img->images_queue())
{
if(v.head.pos.paper_side == PAPER_SIDE_BACK)
{
cv::flip(v.img, v.img, 0);
cv::flip(v.img, v.img, 1);
}
}
}
} }
return img; return img;

View File

@ -14,8 +14,8 @@ class gb_json;
// "montage": { // "montage": {
// "cat": "cis", // "cat": "cis",
// "group": "CIS", // "group": "CIS",
// "title": "图像拼接", // "title": "\u56fe\u50cf\u62fc\u63a5",
// "desc": "将CIS采集的原始数据恢复为正常的图像", // "desc": "\u5c06CIS\u91c7\u96c6\u7684\u539f\u59cb\u6570\u636e\u6062\u590d\u4e3a\u6b63\u5e38\u7684\u56fe\u50cf",
// "ver": 1, // "ver": 1,
// "pos": 10, // "pos": 10,
// "type": "bool", // "type": "bool",
@ -31,8 +31,8 @@ class gb_json;
// "cis-color-correct": { // "cis-color-correct": {
// "cat": "CIS", // "cat": "CIS",
// "group": "CIS", // "group": "CIS",
// "title": "光学颜色校正", // "title": "\u5149\u5b66\u989c\u8272\u6821\u6b63",
// "desc": "对CIS的原图颜色进行校正", // "desc": "\u5bf9CIS\u7684\u539f\u56fe\u989c\u8272\u8fdb\u884c\u6821\u6b63",
// "ver": 1, // "ver": 1,
// "pos": 20, // "pos": 20,
// "type": "bool", // "type": "bool",
@ -48,8 +48,8 @@ class gb_json;
// "reinstate": { // "reinstate": {
// "cat": "CIS", // "cat": "CIS",
// "group": "CIS", // "group": "CIS",
// "title": "硬件复原", // "title": "\u786c\u4ef6\u590d\u539f",
// "desc": "消除CIS硬件拉伸因素恢复图片初始状态", // "desc": "\u6d88\u9664CIS\u786c\u4ef6\u62c9\u4f38\u56e0\u7d20\uff0c\u6062\u590d\u56fe\u7247\u521d\u59cb\u72b6\u6001",
// "ver": 1, // "ver": 1,
// "pos": 30, // "pos": 30,
// "type": "bool", // "type": "bool",
@ -65,8 +65,8 @@ class gb_json;
// "fb-split": { // "fb-split": {
// "cat": "CIS", // "cat": "CIS",
// "group": "CIS", // "group": "CIS",
// "title": "拆分正反面", // "title": "\u62c6\u5206\u6b63\u53cd\u9762",
// "desc": "将正反面合成的一张图片拆分成正面和反面图片", // "desc": "\u5c06\u6b63\u53cd\u9762\u5408\u6210\u7684\u4e00\u5f20\u56fe\u7247\u62c6\u5206\u6210\u6b63\u9762\u548c\u53cd\u9762\u56fe\u7247",
// "ver": 1, // "ver": 1,
// "pos": 40, // "pos": 40,
// "type": "bool", // "type": "bool",
@ -82,8 +82,8 @@ class gb_json;
// "page": { // "page": {
// "cat": "CIS", // "cat": "CIS",
// "group": "base", // "group": "base",
// "title": "页面", // "title": "\u9875\u9762",
// "desc": "获取纸张指定面的图片", // "desc": "\u83b7\u53d6\u7eb8\u5f20\u6307\u5b9a\u9762\u7684\u56fe\u7247",
// "ver": 1, // "ver": 1,
// "pos": 50, // "pos": 50,
// "type": "string", // "type": "string",
@ -93,16 +93,16 @@ class gb_json;
// "visible": true, // "visible": true,
// "enabled": true, // "enabled": true,
// "size": 30, // "size": 30,
// "cur": "双面", // "cur": "\u53cc\u9762",
// "default": "双面", // "default": "\u53cc\u9762",
// "range": ["正面", "背面", "双面"], // "range": ["\u6b63\u9762", "\u80cc\u9762", "\u53cc\u9762"],
// "depend_or": ["fb-split==true"] // "depend_or": ["fb-split==true"]
// }, // },
// "is-exchange": { // "is-exchange": {
// "cat": "CIS", // "cat": "CIS",
// "group": "base", // "group": "base",
// "title": "交换正反面", // "title": "\u4ea4\u6362\u6b63\u53cd\u9762",
// "desc": "交换每张文稿的正反面出图顺序", // "desc": "\u4ea4\u6362\u6bcf\u5f20\u6587\u7a3f\u7684\u6b63\u53cd\u9762\u51fa\u56fe\u987a\u5e8f",
// "ver": 1, // "ver": 1,
// "pos": 60, // "pos": 60,
// "type": "bool", // "type": "bool",
@ -114,7 +114,25 @@ class gb_json;
// "size": 4, // "size": 4,
// "cur": false, // "cur": false,
// "default": false, // "default": false,
// "depend_and": ["fb-split==true", "page==双面"] // "depend_and": ["fb-split==true", "page==\u53cc\u9762"]
// },
// "is-rotate-bkg-180": {
// "cat": "CIS",
// "group": "base",
// "title": "\u80cc\u9762\u65cb\u8f6c180\u00b0",
// "desc": "\u80cc\u9762\u626b\u63cf\u7684\u56fe\u50cf\u65cb\u8f6c180\u00b0",
// "ver": 1,
// "pos": 70,
// "type": "bool",
// "unit": "none",
// "affect": 0,
// "readonly": false,
// "visible": true,
// "enabled": true,
// "size": 4,
// "cur": false,
// "default": false,
// "depend_and": ["fb-split==true", "page!=\u6b63\u9762"]
// } // }
// } // }
@ -129,6 +147,7 @@ class cis_pre_do : public sane_cfg_provider
bool photo_mode_; bool photo_mode_;
bool is_correct_; bool is_correct_;
bool is_exchg_; bool is_exchg_;
bool is_bkg_rot_180_;
enum enum
{ {

View File

@ -22,21 +22,24 @@ extern int32_t (*set_image_process_over)(bool);
img_processor::img_processor(std::function<IMG_SENDER_PROTO> img_sender img_processor::img_processor(std::function<IMG_SENDER_PROTO> img_sender
, std::function<int32_t(const char*, void*, size_t*)> get_opt) , std::function<int32_t(const char*, void*, size_t*)> get_opt)
: img_sender_(img_sender), get_opt_val_(get_opt), speed_first_(true), run_(true) : img_sender_(img_sender), get_opt_val_(get_opt), run_(true)
, scan_staus_(0), busy_cnt_(0) , scan_staus_(0), busy_cnt_(0), pool_(6)
{ {
cis_pre_ = new cis_pre_do(); cis_pre_ = new cis_pre_do();
encoder_ = new img_encoder(); encoder_ = new img_encoder();
load_processors(); load_processors();
worker_ = new thread_pool<img_processor>(this); // worker_ = new thread_pool<img_processor>(this);
worker_->thread_new(&img_processor::worker_thread, true); // worker_->thread_new(&img_processor::worker_thread, true);
// worker_->thread_new(&img_processor::worker_thread, false);
// worker_->thread_new(&img_processor::worker_thread, false);
// worker_->thread_new(&img_processor::worker_thread, false);
} }
img_processor::~img_processor() img_processor::~img_processor()
{ {
stop(); stop();
worker_->thread_stop(); // worker_->thread_stop();
worker_->release(); // worker_->release();
cis_pre_->release(); cis_pre_->release();
encoder_->release(); encoder_->release();
@ -185,52 +188,50 @@ uint32_t img_processor::add_busy_count(int adden)
} }
void img_processor::worker_thread(bool first) void img_processor::worker_thread(bool first)
{ {
log_cls::log(LOG_LEVEL_ALL, "+img_processor::worker_thread(%p) entered ...\n", sys_util::thread_id(std::this_thread::get_id())); // while(run_)
// {
while(run_)
{
img_one_paper* img = nullptr; img_one_paper* img = nullptr;
if(img_que_.take(img, true)) // if(img_que_.take(img, true))
{ // {
if(img) // if(img)
{ // {
int paper = img->images_queue()[0].head.pos.paper_ind; // int paper = img->images_queue()[0].head.pos.paper_ind;
add_busy_count(); // handle_image(img);
handle_image(img);
add_busy_count(-1);
// img->release(); // release in 'handle_image' // // img->release(); // release in 'handle_image'
} // }
else // else
{ // {
while(add_busy_count(0)) // while(add_busy_count(0))
std::this_thread::sleep_for(std::chrono::milliseconds(50)); // std::this_thread::sleep_for(std::chrono::milliseconds(50));
img_sender_(nullptr, nullptr, nullptr, scan_staus_); // img_sender_(nullptr, nullptr, nullptr, scan_staus_);
set_image_process_over(true); // set_image_process_over(true);
for(auto& v: tids_) // // for(auto& v: tids_)
img_que_.quit(); // // img_que_.quit();
img_que_.quit(); // // img_que_.quit();
} // }
} // }
else if(first) // else if(first)
{ // {
for(auto& v: tids_) // for(auto& v: tids_)
worker_->thread_stop(v); // worker_->thread_stop(v);
tids_.clear(); // tids_.clear();
} // }
else // else
{ // {
break; // break;
} // }
} // }
log_cls::log(LOG_LEVEL_ALL, "-img_processor::worker_thread(%p) exited.\n", sys_util::thread_id(std::this_thread::get_id())); log_cls::log(LOG_LEVEL_ALL, "-img_processor::worker_thread(%p) exited.\n", sys_util::thread_id(std::this_thread::get_id()));
} }
void img_processor::handle_image(img_one_paper* img) void img_processor::handle_image(img_one_paper* img)
{ {
img_one_paper* doing = nullptr; img_one_paper* doing = nullptr;
add_busy_count();
// img->add_ref(); // release it right now // img->add_ref(); // release it right now
// CIS pre-do ... // CIS pre-do ...
@ -255,6 +256,7 @@ void img_processor::handle_image(img_one_paper* img)
img_sender_(&v.head, imgf, v.info.c_str(), v.info.length()); img_sender_(&v.head, imgf, v.info.c_str(), v.info.length());
} }
img->release(); img->release();
add_busy_count(-1);
} }
int32_t img_processor::get_config(void* buf, size_t* len, const char* cfg_name, std::string* strval) int32_t img_processor::get_config(void* buf, size_t* len, const char* cfg_name, std::string* strval)
@ -373,22 +375,43 @@ int32_t img_processor::push_image(img_one_paper* img, bool over)
{ {
if(run_) if(run_)
{ {
if(over) // if(over)
{ // {
scan_staus_ = (uint32_t)(uint64_t)img; // scan_staus_ = (uint32_t)(uint64_t)img;
img_que_.save(nullptr, true); // img_que_.save(nullptr, true);
} // }
else // else
{ // {
// img->add_ref();
// size_t cnt = img_que_.save(img, true);
// // if(speed_first_ && cnt >= 4 && worker_->count() < 4)
// // {
// // tids_.push_back(worker_->thread_new(&img_processor::worker_thread, false));
// // }
// }
if(!over)
img->add_ref(); img->add_ref();
size_t cnt = img_que_.save(img, true); results_.emplace(
pool_.enqueue([this, img, over]
{
if(over)
{
scan_staus_ = (size_t)(uint64_t)img;
while(add_busy_count(0))
std::this_thread::sleep_for(std::chrono::milliseconds(50));
if(speed_first_ && cnt >= 4 && worker_->count() < 2) img_sender_(nullptr, nullptr, nullptr, scan_staus_);
{ set_image_process_over(true);
tids_.push_back(worker_->thread_new(&img_processor::worker_thread, false)); }
} else
} {
handle_image(img);
}
}
));
} }
return 0; return 0;
@ -396,18 +419,28 @@ int32_t img_processor::push_image(img_one_paper* img, bool over)
int32_t img_processor::stop(void) int32_t img_processor::stop(void)
{ {
run_ = false; run_ = false;
for(size_t i = 0; i < worker_->count(); ++i) // for(size_t i = 0; i < worker_->count(); ++i)
img_que_.quit(); // img_que_.quit();
int wait = 0;
while(add_busy_count(0) && wait++ < 100)
std::this_thread::sleep_for(std::chrono::milliseconds(5));
clear();
return 0; return 0;
} }
int32_t img_processor::set_speed_first(bool first) int32_t img_processor::set_speed_first(bool first)
{ {
speed_first_ = first; // speed_first_ = first;
return 0; return 0;
} }
int32_t img_processor::que_size(void) int32_t img_processor::que_size(void)
{ {
return img_que_.size(); return add_busy_count(0);
} }
void img_processor::clear(void)
{
while (results_.size() > 0)
results_.pop();
}

View File

@ -13,6 +13,7 @@
#include <functional> #include <functional>
#include <vector> #include <vector>
#include "imemory.h" #include "imemory.h"
#include "ThreadPool.h"
#define IMG_SENDER_PROTO void(LPPACKIMAGE /*image head, nullptr for scan over*/, MemoryPtr /*image data, nullptr for scan over*/, const void* /*image info*/, size_t/*image info bytes, scanner status for scan over*/) #define IMG_SENDER_PROTO void(LPPACKIMAGE /*image head, nullptr for scan over*/, MemoryPtr /*image data, nullptr for scan over*/, const void* /*image info*/, size_t/*image info bytes, scanner status for scan over*/)
@ -32,10 +33,14 @@ class img_processor : public sane_cfg_provider
std::vector<img_alg*> cur_proc_; std::vector<img_alg*> cur_proc_;
img_encoder* encoder_; img_encoder* encoder_;
safe_fifo<img_one_paper*> img_que_; // safe_fifo<img_one_paper*> img_que_;
thread_pool<img_processor>* worker_; // thread_pool<img_processor>* worker_;
std::vector<uint64_t> tids_; // std::vector<uint64_t> tids_;
volatile bool speed_first_; // volatile bool speed_first_;
ThreadPool pool_;
std::queue<std::future<void>> results_;
volatile bool run_; volatile bool run_;
uint32_t scan_staus_; uint32_t scan_staus_;
uint32_t busy_cnt_; uint32_t busy_cnt_;
@ -71,5 +76,6 @@ public:
int32_t stop(void); int32_t stop(void);
int32_t set_speed_first(bool first); // start as many threads as possible if 'first' was true, or down to ONE thread int32_t set_speed_first(bool first); // start as many threads as possible if 'first' was true, or down to ONE thread
int32_t que_size(void); int32_t que_size(void);
void clear(void);
}; };

View File

@ -7,8 +7,8 @@
// //
image_packet::image_packet(LPPACKIMAGE head, MemoryPtr img, uint32_t scanid, uint32_t sn, const void* info, size_t info_size) image_packet::image_packet(LPPACKIMAGE head, MemoryPtr img, uint32_t scanid, const void* info, size_t info_size)
: img_(img), offset_(0), sn_(sn), info_over_(false) : img_(img), offset_(0), info_over_(false)
{ {
LPPACK_BASE pack = nullptr; LPPACK_BASE pack = nullptr;
LPPACKIMAGE pimg = nullptr; LPPACKIMAGE pimg = nullptr;
@ -31,7 +31,19 @@ image_packet::image_packet(LPPACKIMAGE head, MemoryPtr img, uint32_t scanid, uin
head_->set_len(sizeof(PACK_BASE) + sizeof(PACKIMAGE)); head_->set_len(sizeof(PACK_BASE) + sizeof(PACKIMAGE));
info_over_ = info_.empty(); info_over_ = info_.empty();
// log_cls::log(LOG_LEVEL_ALL, "Image-%04u wait to be sent: size = %u\n", sn_, img->size() + info_.length()); char buf[128] = {0};
sprintf(buf, "Image-%04u", head->pos.paper_ind);
pos_str_ = buf;
if(head->pos.paper_side == PAPER_SIDE_FRONT)
pos_str_ += "F_";
else if(head->pos.paper_side == PAPER_SIDE_BACK)
pos_str_ += "B_";
else
pos_str_ += "C_";
pos_str_ += std::to_string(head->pos.split_ind);
log_cls::log(LOG_LEVEL_ALL, "%s wait to be sent: size = %u\n", pos_str_.c_str(), img->size() + info_.length());
} }
image_packet::~image_packet() image_packet::~image_packet()
{ {
@ -39,7 +51,7 @@ image_packet::~image_packet()
head_->release(); head_->release();
img_.reset(); img_.reset();
// log_cls::log(LOG_LEVEL_ALL, "Image-%04u sending complete: %u/%u\n", sn_, offset_, size); log_cls::log(LOG_LEVEL_ALL, "%s sending complete: %u/%u\n", pos_str_.c_str(), offset_, size);
} }
bool image_packet::is_memory_block(void) bool image_packet::is_memory_block(void)

View File

@ -12,12 +12,12 @@ class image_packet : public data_source
MemoryPtr img_; MemoryPtr img_;
dyn_mem_ptr head_; dyn_mem_ptr head_;
uint32_t offset_; uint32_t offset_;
uint32_t sn_;
std::string info_; std::string info_;
bool info_over_; bool info_over_;
std::string pos_str_;
public: public:
image_packet(LPPACKIMAGE head, MemoryPtr img, uint32_t scanid, uint32_t sn, const void* info = nullptr, size_t info_size = 0); image_packet(LPPACKIMAGE head, MemoryPtr img, uint32_t scanid, const void* info = nullptr, size_t info_size = 0);
protected: protected:
virtual ~image_packet(); virtual ~image_packet();

View File

@ -410,7 +410,7 @@ int async_usb_gadget::inner_write_bulk(data_source_ptr data, int* err)
} }
buf->release(); buf->release();
off = total; off = total;
log_cls::log(LOG_LEVEL_ALL, "Finished in sending large content with %u bytes.\n", total); // log_cls::log(LOG_LEVEL_ALL, "Finished in sending large content with %u bytes.\n", total);
} }
return off; return off;

View File

@ -154,7 +154,7 @@ void async_scanner::push_image(int data_type, void* data, size_t w, size_t h, in
{ {
img_one_paper *paper = new img_one_paper(); img_one_paper *paper = new img_one_paper();
paper->init_from(data, w, h, dpi_x, dpi_y, paper_ind, side, clr, status, img_new, img_over); paper->init_from(data, w, h, dpi_x, dpi_y, paper_ind, side, clr, status, img_new, img_over, ratio_h, ratio_v);
img_prc_->push_image(paper); img_prc_->push_image(paper);
paper->release(); paper->release();
@ -256,13 +256,7 @@ void async_scanner::init(void)
if(head) if(head)
{ {
{ imgp = new image_packet(head, img, scan_id_, info, info_size);
LOCKER lock(locker_);
ind = ++img_cnt_;
}
imgp = new image_packet(head, img, scan_id_, ind, info, info_size);
usb_->write_bulk(imgp); usb_->write_bulk(imgp);
imgp->release(); imgp->release();
} }
@ -354,6 +348,13 @@ dyn_mem_ptr async_scanner::handle_get_opt_all(LPPACK_BASE pack, uint32_t* used,
dyn_mem_ptr reply = nullptr; dyn_mem_ptr reply = nullptr;
LPPACK_BASE pk = nullptr; LPPACK_BASE pk = nullptr;
#ifdef TEMPORARY_API
if(reg_img_cb)
{
reg_img_cb = set_image_receiver(::push_image, this);
}
#endif
*used = base_head_size; *used = base_head_size;
{ {
std::string val(""); std::string val("");
@ -548,281 +549,3 @@ uint32_t async_scanner::stop(void)
} }
} }
// void async_scanner::save_image(MemoryPtr data, bool img)
// {
// static uint64_t max_mem = 0;
// if(img)
// {
// uint64_t n = sys_util::get_memory_usage("scan");
// uint32_t que = 0;
// image_packet *ip = new image_packet(data, ++img_cnt_, scan_id_, n);
// if(max_mem < n)
// max_mem = n;
// que = usb_->write_bulk(ip);
// ip->release();
// // check has completed ?
// if(scan_over_pack_)
// {
// ctrl_handler(-2, (usb_ctrlrequest*)SR_GET_IMAGEPROCESSDONE, (unsigned char*)&n);
// if(n)
// {
// usb_->write_bulk(scan_over_pack_);
// scan_over_pack_->release();
// scan_over_pack_ = nullptr;
// }
// }
// }
// else if(data)
// {
// HGIntInfo* info = (HGIntInfo*)data->data();
// dyn_mem_ptr reply = dyn_mem::memory(sizeof(PACK_BASE));
// int cmd = /*PACK_CMD_SCAN_FINISHED_ROGER*/0,
// err = 0;
// if(info->From != HGType::MBEvent || scan_id_ == 0)
// log_cls::log(LOG_LEVEL_ALL, "Scanner event: From = %d, Code = %d, Img_Index = %d\n", info->From, info->Code, info->Img_Index);
// if(info->From == HGType::MtBoard)
// {
// cmd = PACK_CMD_SCAN_FINISHED_ROGER;
// switch(info->Code)
// {
// case 2:
// err = SCANNER_STATUS_NO_PAPER;
// break;
// case 4:
// err = SCANNER_STATUS_COVER_OPENNED;
// break;
// case 8:
// err = SCANNER_STATUS_FEED_FAILED;
// break;
// case 0x10:
// err = SCANNER_STATUS_PAPER_JAMMED;
// break;
// case 0x20:
// err = SCANNER_STATUS_DOUBLE_FEEDED;
// break;
// case 0x40:
// err = SCANNER_STATUS_STAPLE_ON;
// break;
// case 0x80:
// err = SCANNER_STATUS_PAPER_ASKEW;
// break;
// case 0x20000:
// break;
// }
// }
// else if(info->From == HGType::IMG)
// {
// if(info->Code == 1)
// {
// err = SCANNER_STATUS_DOGEAR;
// cmd = PACK_CMD_SCAN_FINISHED_ROGER;
// }
// else if(info->Code == 2)
// {
// err = SCANNER_STATUS_SIZE_ERR;
// cmd = PACK_CMD_SCAN_FINISHED_ROGER;
// }
// }
// else if(info->From == HGType::V4L2 || info->From == HGType::STOPSCAN)
// {
// cmd = PACK_CMD_SCAN_FINISHED_ROGER;
// }
// if(scan_id_ == 0 && info->From == HGType::MBEvent)
// {
// BASE_PACKET_REPLY(*((LPPACK_BASE)reply->ptr()), PACK_CMD_STATUS_ROGER, 0, info->Code);
// reply->set_len(sizeof(PACK_BASE));
// usb_->write_bulk(reply);
// }
// else
// {
// if(err && scan_err_ == 0)
// scan_err_ = err;
// if(scan_id_ && /*cmd == PACK_CMD_SCAN_FINISHED_ROGER*/info->From == HGType::STOPSCAN && scan_over_pack_ == nullptr)
// {
// char ebuf[20] = {0};
// err = scan_err_;
// log_cls::log(LOG_LEVEL_ALL, "Scan over with error: %s; Max memory usage: %s\n", log_cls::str_scanner_status((scanner_status)scan_err_, ebuf), sys_util::format_readable_bytes(max_mem).c_str());
// max_mem = 0;
// BASE_PACKET_REPLY(*((LPPACK_BASE)reply->ptr()), cmd, scan_id_, err);
// reply->set_len(sizeof(PACK_BASE));
// scan_id_ = 0;
// // check if the image-proc-queue has completed ...
// // ctrl_handler(-2, (usb_ctrlrequest*)SR_GET_IMAGEPROCESSDONE, (unsigned char*)&err);
// err = 1;
// if(err)
// usb_->write_bulk(reply);
// else
// {
// scan_over_pack_ = reply;
// scan_over_pack_->add_ref();
// }
// }
// }
// reply->release();
// }
// else
// {
// // paper count ...
// dyn_mem_ptr reply = dyn_mem::memory(sizeof(PACK_BASE));
// BASE_PACKET_REPLY(*((LPPACK_BASE)reply->ptr()), PACK_CMD_SCAN_PAPER_ROGER, 0, 0);
// reply->set_len(sizeof(PACK_BASE));
// usb_->write_bulk(reply);
// reply->release();
// }
// }
// int32_t async_scanner::get_config(void* buf, size_t* len, const char* cfg_name, std::string* strval)
// {
// int32_t ret = EINVAL;
// if(!len)
// return ret;
// if(cfg_name)
// {
// gb_json *jsn = new gb_json();
// if(jsn->attach_text(&cfg_text_[0]))
// {
// ret = inner_get_config(jsn, buf, len, cfg_name, strval);
// // gb_json* child = nullptr;
// // ret = ENOENT;
// // if(jsn->get_value(cfg_name, child) && child)
// // {
// // std::string val(sane_cfg_provider::sane_option_value_get(child, "cur", strval));
// // child->release();
// // if(*len < val.length())
// // {
// // *len = val.length();
// // ret = ENOMEM;
// // }
// // else
// // {
// // memcpy(buf, val.c_str(), val.length());
// // *len = val.length();
// // }
// // }
// jsn->release();
// }
// }
// else
// {
// if(*len < cfg_text_.length() + 1)
// {
// *len = cfg_text_.length() + 4;
// ret = ENOMEM;
// }
// else
// {
// strcpy((char*)buf, cfg_text_.c_str());
// *len = cfg_text_.length();
// ret = 0;
// }
// }
// return ret;
// }
// int32_t async_scanner::set_config(const char* cfg_name, void* data, size_t* len, uint32_t* afterdo)
// {
// gb_json *jsn = new gb_json();
// int32_t ret = EINVAL;
// if(jsn->attach_text(&cfg_text_[0]))
// {
// gb_json* child = nullptr;
// ret = ENOENT;
// if(jsn->get_value(cfg_name, child) && child)
// {
// int val = 0;
// child->get_value("affect", val);
// if(afterdo)
// *afterdo = val;
// if(strcmp(cfg_name, "resolution") == 0)
// {
// child->get_value("cur", val);
// ret = EUCLEAN;
// val = *(int*)data;
// if(val == 100 || val == 150 || val == 200 || val == 300 || val == 600)
// ret = 0;
// else if(val < 125)
// val = 100;
// else if(val < 175)
// val = 150;
// else if(val < 250)
// val = 200;
// else if(val < 450)
// val = 300;
// else
// val = 600;
// *(int*)data = val;
// child->set_value("cur", val);
// dpi_ = val;
// log_cls::log(LOG_LEVEL_ALL, "Set %s to %d\n", cfg_name, dpi_);
// cfg_text_ = jsn->to_string();
// }
// else if(strcmp(cfg_name, "count") == 0)
// {
// child->get_value("cur", val);
// ret = EUCLEAN;
// val = *(int*)data;
// if(val == -1 || val == 1)
// ret = 0;
// else
// val = -1;
// *(int*)data = val;
// child->set_value("cur", val);
// scan_cnt_ = val;
// log_cls::log(LOG_LEVEL_ALL, "Set %s to %d\n", cfg_name, scan_cnt_);
// cfg_text_ = jsn->to_string();
// }
// child->release();
// }
// jsn->release();
// }
// return ret;
// }
// void async_scanner::update_enabled(std::function<GET_SANE_OPT_PROTO> get_opt)
// {
// gb_json *jsn = new gb_json();
// int32_t ret = EINVAL;
// if(jsn->attach_text(&cfg_text_[0]))
// {
// sane_cfg_provider::update_option_enable_status(jsn, get_opt);
// cfg_text_ = std::move(jsn->to_string());
// }
// jsn->release();
// }
// int32_t async_scanner::get_value(const char* name, const char* key, std::string& val)
// {
// gb_json* root = new gb_json(), *child = nullptr;
// int32_t ret = ENOENT;
// if(root->attach_text(&cfg_text_[0]))
// {
// if(root->get_value(name, child) && child)
// {
// if(sane_cfg_provider::raw_value_in_json(child, key, val))
// ret = 0;
// child->release();
// }
// }
// root->release();
// return ret;
// }

View File

@ -13,6 +13,7 @@
class UsbImageProcQueue class UsbImageProcQueue
{ {
void (*push_image_)(int data_type, void* data, size_t w, size_t h, int dpi_x, int dpi_y, size_t paper_ind, paper_side side, clr_channel clr, img_status status, bool img_new, bool img_over, float ratio_h, float ratio_v, void* param) = nullptr;
void(*img_keeper_)(MemoryPtr, bool, void*); void(*img_keeper_)(MemoryPtr, bool, void*);
void* kp_param_; void* kp_param_;
int scan_status_; int scan_status_;
@ -32,6 +33,9 @@ class UsbImageProcQueue
case 4: case 4:
ss = SCANNER_STATUS_COVER_OPENNED; ss = SCANNER_STATUS_COVER_OPENNED;
break; break;
case 5:
ss = SCANNER_STATUS_COVER_CLOSED;
break;
case 8: case 8:
ss = SCANNER_STATUS_FEED_FAILED; ss = SCANNER_STATUS_FEED_FAILED;
break; break;
@ -62,25 +66,25 @@ public:
void push(MemoryPtr image,bool containsimg) void push(MemoryPtr image,bool containsimg)
{ {
#ifdef ASYNC_EP
if(!containsimg) if(!containsimg)
{ {
void (*push_image)(int data_type, void* data, size_t w, size_t h, int dpi_x, int dpi_y, size_t paper_ind, paper_side side, clr_channel clr, img_status status, bool img_new, bool img_over, float ratio_h, float ratio_v, void* param) = nullptr; HGIntInfo* info = (HGIntInfo*)image->data();
HGIntInfo* info = (HGIntInfo*)image->data();
*(uint64_t*)&push_image = (uint64_t)img_keeper_; if(info->From == HGType::STOPSCAN)
if(info->From == HGType::STOPSCAN)
{ {
if(push_image) if(push_image_)
push_image(IMG_CB_STOPPED, nullptr, sensor_status_2_scanner_status(info->Code), 0, dpi_x_, dpi_y_, 0, PAPER_SIDE_LEFT, (clr_channel)0, (img_status)0, true, true, ratio_h_, ratio_v_, kp_param_); push_image_(IMG_CB_STOPPED, nullptr, sensor_status_2_scanner_status(info->Code), 0, dpi_x_, dpi_y_, 0, PAPER_SIDE_LEFT, (clr_channel)0, (img_status)0, true, true, ratio_h_, ratio_v_, kp_param_);
} }
else else
{ {
scan_status_ = sensor_status_2_scanner_status(info->Code); scan_status_ = sensor_status_2_scanner_status(info->Code);
if(push_image) if(push_image_)
push_image(IMG_CB_STATUS, nullptr, sensor_status_2_scanner_status(info->Code), 0, dpi_x_, dpi_y_, 0, PAPER_SIDE_LEFT, (clr_channel)0, (img_status)0, true, true, ratio_h_, ratio_v_, kp_param_); push_image_(IMG_CB_STATUS, nullptr, sensor_status_2_scanner_status(info->Code), 0, dpi_x_, dpi_y_, 0, PAPER_SIDE_LEFT, (clr_channel)0, (img_status)0, true, true, ratio_h_, ratio_v_, kp_param_);
} }
} }
return; return;
#endif
if(img_keeper_) if(img_keeper_)
img_keeper_(image, containsimg, kp_param_); img_keeper_(image, containsimg, kp_param_);
@ -113,12 +117,9 @@ public:
imgp_over_ = false; imgp_over_ = false;
} }
void (*push_image)(int data_type, void* data, size_t w, size_t h, int dpi_x, int dpi_y, size_t paper_ind, paper_side side, clr_channel clr, img_status status, bool img_new, bool img_over, float ratio_h, float ratio_v, void* param) = nullptr; if(push_image_)
*(uint64_t*)&push_image = (uint64_t)img_keeper_;
if(push_image)
{ {
push_image(IMG_CB_IMAGE, data, width, height, dpi_x_, dpi_y_, scannnum, PAPER_SIDE_LEFT, (clr_channel)type, (img_status)status, true, true, ratio_h_, ratio_v_, kp_param_); push_image_(IMG_CB_IMAGE, data, width, height, dpi_x_, dpi_y_, scannnum, PAPER_SIDE_LEFT, (clr_channel)type, (img_status)status, true, true, ratio_h_, ratio_v_, kp_param_);
return true; return true;
} }
@ -131,6 +132,7 @@ public:
img_keeper_ = img_keeper; img_keeper_ = img_keeper;
kp_param_ = param; kp_param_ = param;
*(uint64_t*)&push_image_ = (uint64_t)img_keeper_;
} }
void set_dpi(int x, int y) void set_dpi(int x, int y)
{ {

View File

@ -654,6 +654,49 @@ const wchar_t* scanner_status(int s, wchar_t unk[20])
return unk; return unk;
} }
static DWORD thread_open_id_ = 0;
static safe_fifo<std::string> images_;
static DWORD WINAPI thread_open_image(void* lp)
{
while (1)
{
std::string file("");
if (images_.take(file, true))
{
if (file.empty())
break;
ShellExecuteA(NULL, "Open", file.c_str(), NULL, NULL, SW_SHOWNORMAL);
}
}
return 0;
MSG msg = { 0 };
BOOL ret = TRUE;
while ((ret = GetMessage(&msg, NULL, 0, 0)))
{
if ((DWORD)ret == -1)
break;
if (msg.message == WM_USER + 1001)
break;
if (msg.message == WM_USER + 1)
{
std::string* file = (std::string*)msg.lParam;
ShellExecuteA(NULL, "Open", file->c_str(), NULL, NULL, SW_SHOWNORMAL);
delete file;
}
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return 0;
}
// CDlgScanner 对话框 // CDlgScanner 对话框
IMPLEMENT_DYNAMIC(CDlgScanner, CDialogEx) IMPLEMENT_DYNAMIC(CDlgScanner, CDialogEx)
@ -668,13 +711,37 @@ CDlgScanner::CDlgScanner(CWnd* pParent /*=nullptr*/)
threads_ = new thread_pool<CDlgScanner>(this); threads_ = new thread_pool<CDlgScanner>(this);
parent_ = pParent ? pParent->m_hWnd : NULL; parent_ = pParent ? pParent->m_hWnd : NULL;
auto_wait_ = CreateEvent(NULL, TRUE, FALSE, NULL); auto_wait_ = CreateEvent(NULL, TRUE, FALSE, NULL);
HANDLE h = CreateThread(NULL, 0, thread_open_image, NULL, 0, &thread_open_id_);
CloseHandle(h);
char buf[40] = { 0 }; std::string tj("{\"resolution\":{\"cat\":\"imgp\",\"group\":\"base\",\"title\":\"\\u5206\\u8fa8\\u7387\",\"desc\":\"\\u8bbe\\u7f6e\\u626b\\u63cf\\u56fe\\u50cf\\u7684\\u5206\\u8fa8\\u7387\",\"ver\":1,\"pos\":200,\"type\":\"int\",\"unit\":\"dpi\",\"affect\":6,\"readonly\":false,\"visible\":true,\"enabled\":true,\"size\":4,\"cur\":400,\"default\":200,\"range\":{\"min\":100,\"max\":600,\"step\":50}}}");
sscanf(" ether fe:26:f4:f3:29:07 txqueuelen 1000 (Ethernet)", " ether %s", buf); gb_json* jsn = new gb_json();
if (jsn->attach_text(&tj[0]))
{
gb_json* child = jsn->first_child();
if (child)
{
bool bv = false, r = false;
int nv = 0;
double dv = .0f;
std::string sv("");
r = child->get_value("cur", bv);
r = child->get_value("cur", nv);
r = child->get_value("cur", dv);
r = child->get_value("cur", sv);
child->release();
}
}
jsn->release();
} }
CDlgScanner::~CDlgScanner() CDlgScanner::~CDlgScanner()
{ {
::PostThreadMessage(thread_open_id_, WM_USER + 1001, 0, 0);
images_.save("", true);
if (scanner_) if (scanner_)
{ {
scanner_->close(); scanner_->close();
@ -689,6 +756,11 @@ void CDlgScanner::DoDataExchange(CDataExchange* pDX)
DDX_Control(pDX, IDC_TAB_OPER, tab_oper_); DDX_Control(pDX, IDC_TAB_OPER, tab_oper_);
} }
typedef struct _prog_data
{
CDlgScanner* obj;
std::string file;
}PROGD, *LPPROGD;
void CDlgScanner::set_device(usb::LPUSBPNP pnp) void CDlgScanner::set_device(usb::LPUSBPNP pnp)
{ {
if (!pnp) if (!pnp)
@ -715,11 +787,10 @@ void CDlgScanner::set_device(usb::LPUSBPNP pnp)
setting_ui_ = NULL; setting_ui_ = NULL;
} }
static std::string cur_img_file("");
auto progresser = [&](uint64_t total, uint64_t cur, uint32_t err, void* user_data) -> int auto progresser = [&](uint64_t total, uint64_t cur, uint32_t err, void* user_data) -> int
{ {
CDlgScanner* dlg = (CDlgScanner*)user_data; LPPROGD param = (LPPROGD)user_data;
CDlgScanner* dlg = param->obj;
if (cur >= total) if (cur >= total)
log_cls::log(LOG_LEVEL_DEBUG, "Finished in receiving new image = %d\r\n", err); log_cls::log(LOG_LEVEL_DEBUG, "Finished in receiving new image = %d\r\n", err);
@ -732,7 +803,16 @@ void CDlgScanner::set_device(usb::LPUSBPNP pnp)
dlg->set_text(IDC_EDIT_COUNT, (std::to_wstring(dlg->img_cnt_) + L"/" + std::to_wstring(dlg->paper_cnt_)).c_str()); dlg->set_text(IDC_EDIT_COUNT, (std::to_wstring(dlg->img_cnt_) + L"/" + std::to_wstring(dlg->paper_cnt_)).c_str());
if (dlg->is_checked(IDC_CHECK_AUTO_OPEN_IMG)) if (dlg->is_checked(IDC_CHECK_AUTO_OPEN_IMG))
ShellExecuteA(dlg->m_hWnd, "Open", cur_img_file.c_str(), NULL, NULL, SW_SHOWNORMAL); {
images_.save(param->file, true);
//std::string* file(new std::string(param->file));
//if (!PostThreadMessage(thread_open_id_, WM_USER + 1, NULL, (LPARAM)file))
//{
// delete file;
// ShellExecuteA(dlg->m_hWnd, "Open", param->file.c_str(), NULL, NULL, SW_SHOWNORMAL);
//}
}
delete param;
} }
return 0; return 0;
@ -781,9 +861,22 @@ void CDlgScanner::set_device(usb::LPUSBPNP pnp)
ext = "png"; ext = "png";
else if (img->format == IMG_FMT_TIFF) else if (img->format == IMG_FMT_TIFF)
ext = "tiff"; ext = "tiff";
sprintf_s(name, _countof(name) - 1, "scan_%04d.%s", ++img_cnt_, ext.c_str()); if (paper_cnt_ < img->pos.paper_ind)
err = saver->open((root + name).c_str(), size); paper_cnt_ = img->pos.paper_ind;
log_cls::log(LOG_LEVEL_DEBUG, "Begin receiving new image (%s + %llu) = %d\r\n", (root + name).c_str(), size, err); ++img_cnt_;
sprintf_s(name, _countof(name) - 1, "scan_%04d", (int)img->pos.paper_ind);
root += name;
if (img->pos.paper_side == PAPER_SIDE_FRONT)
root += "F";
else if (img->pos.paper_side == PAPER_SIDE_BACK)
root += "B";
else
root += "C";
sprintf_s(name, _countof(name) - 1, "_%d.%s", (int)img->pos.split_ind, ext.c_str());
root += name;
err = saver->open(root.c_str(), size);
log_cls::log(LOG_LEVEL_DEBUG, "Begin receiving new image (%s + %llu) = %d\r\n", root.c_str(), size, err);
if (err) if (err)
{ {
saver->release(); saver->release();
@ -791,8 +884,10 @@ void CDlgScanner::set_device(usb::LPUSBPNP pnp)
} }
else else
{ {
saver->set_progress_notify(progresser, this); LPPROGD param = new PROGD;
cur_img_file = root + name; param->file = root;
param->obj = this;
saver->set_progress_notify(progresser, param);
} }
return dynamic_cast<data_holder_ptr>(saver); return dynamic_cast<data_holder_ptr>(saver);
@ -834,8 +929,11 @@ void CDlgScanner::set_device(usb::LPUSBPNP pnp)
msg_box(m_hWnd, MB_OK, L"Unsupported Scanner", L"Failed to get protocol version with error %d.", err); msg_box(m_hWnd, MB_OK, L"Unsupported Scanner", L"Failed to get protocol version with error %d.", err);
else else
msg_box(m_hWnd, MB_OK, L"Unsupported Scanner", L"Protocol version is mismatch: expect %u.%u but return %u.%u", HIBYTE(PROTOCOL_VER), LOBYTE(PROTOCOL_VER), HIBYTE(ver), LOBYTE(ver)); msg_box(m_hWnd, MB_OK, L"Unsupported Scanner", L"Protocol version is mismatch: expect %u.%u but return %u.%u", HIBYTE(PROTOCOL_VER), LOBYTE(PROTOCOL_VER), HIBYTE(ver), LOBYTE(ver));
scanner_->release(); if (scanner_)
scanner_ = NULL; {
scanner_->release();
scanner_ = NULL;
}
enable_buttons(false); enable_buttons(false);
OnDeviceStatus(0, (LPARAM)SCANNER_STATUS_NOT_OPEN); OnDeviceStatus(0, (LPARAM)SCANNER_STATUS_NOT_OPEN);
} }