图像处理单独线程处理

This commit is contained in:
masayume 2021-07-21 10:41:17 +08:00
parent d3c784a8b2
commit e580e312a8
3 changed files with 90 additions and 39 deletions

View File

@ -10,20 +10,27 @@ static std::mutex mx_ctrl;
static int scanner_read_reg(std::shared_ptr<IUsb>& usb, int addr)
{
if (usb.get() && usb->is_connected()) {
int val = 0;
std::lock_guard<std::mutex> lck(mx_ctrl);
usb->control_msg(0xc0, USB_REQ_GET_DEV_REGS, addr, 0, 4, &val);
return val;
}
return 0;
}
static void scanner_write_reg(std::shared_ptr<IUsb>& usb, int addr, int val)
{
if (usb.get() && usb->is_connected())
{
std::lock_guard<std::mutex> lck(mx_ctrl);
usb->control_msg(0x40, USB_REQ_SET_DEV_REGS, addr, 0, 4, &val);
}
}
static void scanner_cmd(std::shared_ptr<IUsb>& usb, int cmd)
{
if (usb.get() && usb->is_connected())
scanner_write_reg(usb, 0, cmd);
}
@ -31,6 +38,7 @@ static void scanner_cmd(std::shared_ptr<IUsb>& usb, int cmd)
GScanO1003399::GScanO1003399():
m_imgthread(1)
,m_imgprocthread(1)
{
im_data.reset(new std::vector<char>());
open(0, 0);
@ -40,12 +48,14 @@ GScanO1003399::GScanO1003399():
GScanO1003399::~GScanO1003399()
{
image = 0;
if (m_usbthread.get() && m_usbthread->joinable())
{
b_usbthread = false;
m_usbthread->join();
m_usbthread.reset();
}
m_usb.reset();
}
void GScanO1003399::open(int vid, int pid)
@ -64,35 +74,55 @@ void GScanO1003399::open(int vid, int pid)
{
m_usb = *lsusb.begin();
m_usb->open();
if (m_usb->is_open())
m_usb->set_usbhotplug_callback(usbhotplug_callback, this);
}
}
void GScanO1003399::regist_deviceevent_callback(deviceevent_callback callback, void* usrdata)
{
huagods = usrdata;
dev_callback = callback;
}
void GScanO1003399::usbhotplug_callback(bool isconnect, void* userdata)
{
GScanO1003399* This = (GScanO1003399*)userdata;
This->usbhotplug(isconnect);
}
void GScanO1003399::usbhotplug(bool isleft)
{
FileTools::writelog(log_ERROR, "enable usb callback ");
if (isleft) {
devState = DEV_WRONG;
Error_Code = USB_DISCONNECTED;
scanflag = false;
if (m_usb.get())
m_usb.reset();
if (huagods)
dev_callback(USB_DISCONNECTED, huagods);
}
}
void GScanO1003399::DogEar_callback(std::function<void(int)> fun)
{
}
static int aquirenum = 0;
static int getimgnum = 0;
static StopWatch stopwatch;
int GScanO1003399::aquire_bmpdata(std::vector<unsigned char>& bmpdata)
{
StopWatch sw;
while (true)
{
if ((image==0)&&(!is_runing())&&(!scanflag))
if ((image == 0) && (!is_runing()) && (!scanflag) || (sw.elapsed_s() > 30))
{
DoEvents();
this_thread::sleep_for(chrono::milliseconds(1));
if (!is_runing())
{
int roller_num_new= count();
set_scannum(abs(roller_num_new - roller_num));
if (devState == DEV_WRONG)
return get_ErrorCode();
return -1;
}
if (sw.elapsed_s() > 30.0)
{
devState = DEV_STOP;
@ -102,6 +132,14 @@ int GScanO1003399::aquire_bmpdata(std::vector<unsigned char>& bmpdata)
set_scannum(abs(roller_num_new - roller_num));
return AQUIRE_IMAGE_TIMEOUT;
}
if (!is_runing())
{
int roller_num_new = count();
set_scannum(abs(roller_num_new - roller_num));
if (devState == DEV_WRONG)
return get_ErrorCode();
return -1;
}
}
else
{
@ -111,6 +149,9 @@ int GScanO1003399::aquire_bmpdata(std::vector<unsigned char>& bmpdata)
bmpdata = *(m_imagedata.Take());
UpdateScanInfo(get_imgnReaded(), countNTransfered());
image--;
sw.reset();
FileTools::writelog(log_DEBUG, "3399上层取图间隔 " + to_string(stopwatch.elapsed_ms()));
stopwatch.reset();
return 0;
}
DoEvents();
@ -407,7 +448,7 @@ void GScanO1003399::usb_run()
}
if ((codeconvter(info) != 0))
{
if (info.Code==0x10||info.Code==0x20||info.Code==0x40)
if (info.Code == 0x10 || info.Code == 0x20 || info.Code == 0x40)
{
while (scanner_read_reg(m_usb, SR_STATUS) & 0x1)
this_thread::sleep_for(chrono::microseconds(10));
@ -415,7 +456,7 @@ void GScanO1003399::usb_run()
pop_dev_im();
pop_dev_im();
}
else
if ((get_ErrorCode() != PAPER_JAM) && (get_ErrorCode() != DETECT_DOUBLE_FEED) && (get_ErrorCode() != DETECT_STAPLE))
{
keeplastimg = false;
im_rx();
@ -492,7 +533,7 @@ bool GScanO1003399::is_dev_tx()
{
return scanner_read_reg(m_usb, SR_IM_TXING);
}
static StopWatch swatch;
void GScanO1003399::im_rx()
{
if (!is_rx() && !is_dev_tx())
@ -510,7 +551,8 @@ void GScanO1003399::im_rx()
if(im_dev_count()<2)
continue;
}
auto &buffi = im_data;
//auto &buffi = im_data;
std::shared_ptr<std::vector<char>> buffi(new std::vector<char>);
int count = front_datasize();
buffi->resize(count);
rx_cmd();
@ -518,13 +560,22 @@ void GScanO1003399::im_rx()
count = read_data(buffi->data(), count, count / (0.01 * 1024 * 1024));
pop_dev_im();
vector<cv::Mat> mats;
auto& buffs = G400Decode(buffi).getImageBuffs();
if (m_param.multi_output_red)
image += 2;
else
image++;
UpdateScanInfo(countNReaded(), get_imgTransfered());
imgproce(buffs);
FileTools::writelog(log_DEBUG, "3399usb取图间隔 " + to_string(swatch.elapsed_ms()));
swatch.reset();
imgs.Put(buffi);
fu_imgpro.push(m_imgprocthread.enqueue([this] {
imgproce(imgs.Take());
}));
while (fu_imgpro.size()>1)
{
fu_imgpro.front().get();
fu_imgpro.pop();
}
}
});
}
@ -532,6 +583,8 @@ void GScanO1003399::im_rx()
int GScanO1003399::read_data(void* data, int length, int timeout)
{
if (!m_usb.get() && !m_usb->is_connected())
return 0;
int readed = 0;
int reading = 0;
const int buffer_size = 2 * 1024 * 1024;
@ -561,9 +614,11 @@ int GScanO1003399::im_dev_count()
return scanner_read_reg(m_usb, SR_IM_COUNT); //!< to-list ;
}
void GScanO1003399::imgproce(std::vector<std::shared_ptr<std::vector<char>>>& buffs)
void GScanO1003399::imgproce(std::shared_ptr<std::vector<char>>& buff)
{
auto& buffs= G400Decode(buff).getImageBuffs();
vector<cv::Mat> mats;
StopWatch sw;
bool isbwimg = false;
for (auto& buf : buffs) {
cv::ImreadModes rmc = m_param.pixtype == 2 ? cv::IMREAD_COLOR : cv::IMREAD_GRAYSCALE;
@ -580,36 +635,27 @@ void GScanO1003399::imgproce(std::vector<std::shared_ptr<std::vector<char>>>& bu
continue;
}
buf.reset();
//if (isbwimg)
// cv::flip(mat, mat, 0);
mats.push_back(mat);
FileTools::writelog(log_INFO, "push_back image num= " + to_string(getimgnum++));
}
catch (const std::exception& e)
{
//writelog(e.what());
FileTools::writelog(log_ERROR, e.what());
}
}
FileTools::writelog(log_DEBUG, "3399图像解码耗时 " + to_string(sw.elapsed_ms()));
buffs.clear();
if (m_param.automaticcolor)
{
CImageApplyColorRecognition(m_param.automaticcolortype == 1 ? CImageApplyColorRecognition::ColorRecognitionMode::Color_Gray : CImageApplyColorRecognition::ColorRecognitionMode::Color_Mono).apply(mats,m_param.is_duplex);
}
for (int i = 0; i < mats.size(); i++) {
//if (!m_param.is_duplex && i == 1) {
// mats[i].release();
// break;
//}
if (!mats[i].empty()) {
IMat2Bmp idata;
if (m_param.pixtype == 1 && m_param.hsvcorrect)
if (mats[i].channels() == 3)
cvtColor(mats[i], mats[i], cv::COLOR_BGR2GRAY);
idata = (isbwimg|| m_param.pixtype == 0 || (((m_param.automaticcolortype == 0) && (m_param.automaticcolor == true)) && (mats[i].channels() == 1))) ? (IMat2Bmp)Mat2BmpBw(mats[i], m_param.resolution_dst) : Mat2Bmp(mats[i], m_param.resolution_dst);
//if (!m_param.multi_output_red)
// mats[i].release();
m_imagedata.Put(idata.getBmpDataBuffer());
}
}

View File

@ -65,8 +65,10 @@ private:
void pop_dev_im();
int front_datasize();
int im_dev_count();
void imgproce(std::vector<std::shared_ptr<std::vector<char>>>& buffs);
void imgproce(std::shared_ptr<std::vector<char>>& buffs);
int codeconvter(HGEIntInfo code);
static void usbhotplug_callback(bool isconnect, void* userdata);
void usbhotplug(bool isleft);
private:
volatile int devState;
@ -76,12 +78,16 @@ private:
GScanCap m_param;
std::shared_ptr<IUsb> m_usb;
volatile bool b_usbthread;
BlockingQueue<std::shared_ptr<std::vector<char>>> imgs;
std::future<void> fu_rx;
std::queue<std::future<void>> fu_imgpro;
ThreadPool m_imgthread;
ThreadPool m_imgprocthread;
std::shared_ptr<std::thread> m_usbthread;
std::shared_ptr<std::vector<char>> im_data;
BlockingQueue<std::shared_ptr<std::vector<unsigned char>>> m_imagedata;
std::atomic_int image;
void* huagods;
deviceevent_callback dev_callback;
};

View File

@ -2,7 +2,8 @@
#include "UsbScanEx.h"
#include <tchar.h>
#include <winioctl.h>
//#include "filetools.h"
#include "filetools.h"
UsbScanEx::UsbScanEx(int index)
{
@ -177,7 +178,6 @@ int UsbScanEx::read_bulk(void* data, int len)
}
break;
default:
//FileTools::writelog(log_INFO,"Usb read_bulk error code : " + std::to_string(error_code));
break;
}
}
@ -211,13 +211,11 @@ int UsbScanEx::write_bulk(void* data, int len)
case ERROR_FILE_NOT_FOUND:
case ERROR_ACCESS_DENIED:
m_b_is_connected = false;
//FileTools::writelog(log_lv::log_WARN,"errorcode ="+ std::to_string(errorcode));
if (hotplug_call) {
hotplug_call(true, usrdata);
}
break;
default:
//FileTools::writelog(log_INFO,"Usb write_bulk error code: " + std::to_string(errorcode));
break;
}
}
@ -283,6 +281,7 @@ int UsbScanEx::read_int(void* data, int len)
return dw_ret;
case ERROR_FILE_NOT_FOUND:
case ERROR_ACCESS_DENIED:
m_b_is_connected = false;
if (hotplug_call) {
hotplug_call(true, usrdata);