#include "LimitUpCapture.h" #include "THSActionUtil.h" #include #include "Win32Util.h" OpenCLExcuter* LimitUpCapture::openCLExcuter; bool LimitUpCapture::inited; //ÊÇ·ñÕýÔÚÖ´ÐÐ bool LimitUpCapture::running; CallbackFun_Limit_Up LimitUpCapture::data_callback; std::list LimitUpCapture::pointList; void* LimitUpCapture::context; HWND LimitUpCapture::win; HWND LimitUpCapture::menuWin; RecognitionManager* LimitUpCapture::recognitionManager; HWND getWindow() { return THSActionUtil::getThirdWindow(); } void LimitUpCapture::_run() { while (true) { if (running && inited) { clock_t start = clock(); list codes = captureLimitUpCodes(); cout << "ºÄʱ:" << clock() - start << " ÊýÁ¿£º" << codes.size() << endl; data_callback(codes, context); codes.clear(); Sleep(3000); } } } void LimitUpCapture::init(CallbackFun_Limit_Up callback, void* contex) { data_callback = callback; context = contex; running = false; recognitionManager = new RecognitionManager(); openCLExcuter = new OpenCLExcuter(); openCLExcuter->init(); thread rt(&(LimitUpCapture::_run)); rt.detach(); inited = true; refreshHWND(); } void LimitUpCapture::refreshHWND() { HWND hwnd = getWindow(); if (hwnd <= 0) throw string("ͬ»¨Ë³¸±ÆÁ2δ´ò¿ª"); HWND content = FindWindowExA(hwnd, NULL, "AfxFrameOrView100s", NULL); if (content <= 0) throw string("δ»ñÈ¡µ½ÄÚÈÝ´°¿Ú¾ä±ú"); win = content; HWND child = 0; RECT tempRect; int maxCount = 1; do { maxCount++; child = FindWindowExA(content, child, "AfxWnd100s", NULL); GetWindowRect(child, &tempRect); } while ((!IsWindowVisible(child) || tempRect.right - tempRect.left > tempRect.bottom - tempRect.top) && maxCount < 10);//ûÏÔʾ»òÕß¿í´óÓÚ¸ß HWND temp= FindWindowExA(child, NULL, NULL, NULL); for (int i = 0;i < 10;i++) { GetWindowRect(temp, &tempRect); if (!IsWindowVisible(temp) || tempRect.bottom - tempRect.top < 100) { temp= FindWindowExA(child, temp, NULL, NULL); } else { break; } } temp= FindWindowExA(temp, NULL, "block_list_page", NULL); menuWin = temp; if (menuWin <= 0) throw string("δ»ñÈ¡µ½ÄÚÈÝ´°¿ÚµÄ²Ëµ¥¾ä±ú"); //²éÕҲ˵¥µÄλÖà cv::Mat grayImg = ImgUtil::grayImage(CaptureUtil::capture(menuWin)); int full_start = -1; int full_end = -1; int start_row = -1; int end_row = -1; int count = 0; pointList.clear(); for (int r = grayImg.rows - 1;r>=0;r --) { if (ImgDivider::isRowFull(grayImg,r,0, grayImg.cols-1,2,33,48)) { if (full_start < 0) { full_start = r; full_end = r; } else { full_end = r; } if (start_row > 0 && end_row > 0 && (start_row - end_row) > 5) { count++; printf("%d-%d\n", start_row, end_row); full_start = r; full_end = r; string path = "C:\\Users\\Administrator\\Desktop\\ocr\\menu\\"; path.append("menu_").append(to_string(count)).append(".jpg"); cv::imwrite(path, cv::Mat(grayImg,cv::Rect(0,end_row,grayImg.cols,start_row-end_row))); pointList.push_back(cv::Point( ( 0 + grayImg.cols)/2, (start_row + end_row)/2)); if (pointList.size() >= 2) { break; } start_row = -1; end_row = -1; } } else { if (full_start >= 0) { if (start_row < 0) { start_row = r; end_row = r; } else { end_row = r; } } } } //cv::imwrite("C:\\Users\\Administrator\\Desktop\\ocr\\menu.jpg", ); } bool LimitUpCapture::isRunning() { return running; } list LimitUpCapture::captureLimitUpCodes(cv::Mat oimg) { cv::Mat grayImg = cv::Mat::zeros(oimg.rows, oimg.cols, CV_8UC1);//ImgUtil::grayImage(oimg); uchar* imgData = (uchar*)malloc(sizeof(uchar) * oimg.rows * oimg.cols); if (oimg.channels() == 3) { openCLExcuter->rgb2Gray(oimg.data, oimg.cols, oimg.rows, imgData); } else { openCLExcuter->rgba2Gray(oimg.data, oimg.cols, oimg.rows, imgData); } grayImg.data = imgData; list rowData = THSActionUtil::splitPlateRowArea(grayImg); //ÿÐеÄÔªËØ¸öÊý int ele_count_per_line = 4; int* splitResult = (int*)malloc(sizeof(int) * 4 * 4 * rowData.size()); int* rowIndex = (int*)malloc(sizeof(int) * 4 * rowData.size()); int count = 0; for (std::list::iterator ele = rowData.begin();ele != rowData.end();ele++) { string path = "C:\\Users\\Administrator\\Desktop\\ocr\\limit_up\\"; path.append(to_string(count)).append(".jpg"); //cv::imwrite(path, cv::Mat(grayImg, cv::Rect((*ele)[0], (*ele)[1], (*ele)[2] - (*ele)[0] + 1, (*ele)[3] - (*ele)[1] + 1))); rowIndex[4 * count + 0] = (*ele)[0]; rowIndex[4 * count + 1] = (*ele)[1]; rowIndex[4 * count + 2] = (*ele)[2]; rowIndex[4 * count + 3] = (*ele)[3]; free(*ele); count++; } int line_number_count = 4 * 6; openCLExcuter->splitPlateContentRowData(grayImg.data, grayImg.cols, grayImg.rows, rowIndex, rowData.size(), ele_count_per_line,1,4,splitResult); /* *²âÊÔ for (int i = 0;i < rowData.size();i++) { for (int j = 0;j < line_number_count;j++) { int sx = splitResult[(line_number_count * i + j) * 4 + 0]; int sy = splitResult[(line_number_count * i + j) * 4 + 1]; int ex = splitResult[(line_number_count * i + j) * 4 + 2]; int ey = splitResult[(line_number_count * i + j) * 4 + 3]; string path = "C:\\Users\\Administrator\\Desktop\\ocr\\limit_up\\"; path.append(to_string(i)).append("_").append(to_string(j)).append(".jpg"); //cv::imwrite(path, cv::Mat(grayImg, cv::Rect(sx, sy, ex - sx + 1, ey - sy + 1))); } } */ int start = 4 * 4 * 1 + 4 * 1; string path = "C:\\Users\\Administrator\\Desktop\\ocr\\limit_up\\"; path.append(to_string(start)).append(".jpg"); //cv::imwrite(path, cv::Mat(grayImg,cv::Rect(splitResult[start], splitResult[start+1], splitResult[start+2]- splitResult[start]+1, splitResult[start+3]- splitResult[start+1]+1))); //cv::imwrite(path, cv::Mat(grayImg, cv::Rect(447, 102, 454-447+1,111-102+1 ))); //·Ö¸îÊý×Ö unsigned char* zeroData = (unsigned char*)malloc(sizeof(unsigned char) * _NUMBER_GP_CODE_WIDTH * _NUMBER_GP_CODE_HEIGHT); for (int r = 0;r < _NUMBER_GP_CODE_HEIGHT;r++) { for (int c = 0;c < _NUMBER_GP_CODE_WIDTH;c++) { zeroData[r * _NUMBER_GP_CODE_WIDTH + c] = ImgUtil::NUMS_GP_CODE[0].data.ptr(r)[c]; } } unsigned char* totalNumberData = (unsigned char*)malloc(sizeof(unsigned char) * (_NUMBER_GP_CODE_HEIGHT * rowData.size()) * _NUMBER_GP_CODE_WIDTH * 10 * line_number_count); openCLExcuter->splitPlateNum(grayImg.data, grayImg.cols, grayImg.rows, splitResult, 4 * rowData.size(), zeroData, _NUMBER_GP_CODE_WIDTH, _NUMBER_GP_CODE_HEIGHT, line_number_count, totalNumberData); //ʶ±ðÊý×Ö uchar* templateNums = (unsigned char*)malloc(sizeof(unsigned char) * (_NUMBER_GP_CODE_HEIGHT * rowData.size()) * _NUMBER_GP_CODE_WIDTH * 10 * line_number_count); openCLExcuter->createNumberTemplates(rowData.size(), _NUMBER_GP_CODE_WIDTH, _NUMBER_GP_CODE_HEIGHT, line_number_count, ImgUtil::numsOneLevel_gpcode, templateNums); uchar** numberResult = openCLExcuter->recognition_numbers(totalNumberData, templateNums, rowData.size() * _NUMBER_GP_CODE_HEIGHT, _NUMBER_GP_CODE_WIDTH * 10 * line_number_count, _NUMBER_GP_CODE_WIDTH, _NUMBER_GP_CODE_HEIGHT, line_number_count); list dataList; for (int i = 0;i < rowData.size();i++) { LimitUpData limitUpData = LimitUpData(); string code = ""; for (int j = 0;j < 6;j++) { code.append(to_string(numberResult[i][j])); } string time = ""; for (int j = 0;j < 6;j++) { if (j == 2 || j == 4) { time.append(":"); } time.append(to_string(numberResult[i][6 + j])); } string price = ""; for (int j = 0;j < 6;j++) { if (j == 4) { price.append("."); } price.append(to_string(numberResult[i][6 * 2 + j])); } string money = ""; for (int j = 0;j < 6;j++) { if (j == 4) { money.append("."); } money.append(to_string(numberResult[i][6 * 3 + j])); } limitUpData.index = i; limitUpData.code = code; limitUpData.time = time; limitUpData.price = price; limitUpData.limitMoney = money; if (limitUpData.time != "00:00:00" && limitUpData.price != "0000.00" && limitUpData.limitMoney != "0000.00") { dataList.push_back(limitUpData); } free(numberResult[i]); } free(numberResult); int* unitData = (int*)malloc(sizeof(int) * 4 * dataList.size()); //ʶ±ð½ð¶îµ¥Î» int index = 0; for (list::iterator ele = dataList.begin();ele != dataList.end();ele++) { unitData[index * 4 + 0] = splitResult[(*ele).index * 4 * 4 + 4 * 3 + 0]; unitData[index * 4 + 1] = splitResult[(*ele).index * 4 * 4 + 4 * 3 + 1]; unitData[index * 4 + 2] = splitResult[(*ele).index * 4 * 4 + 4 * 3 + 2]; unitData[index * 4 + 3] = splitResult[(*ele).index * 4 * 4 + 4 * 3 + 3]; index++; } int* unitResult = (int*)malloc(sizeof(int) * dataList.size()); openCLExcuter->recognitionPlateMoneyUnit(grayImg.data, grayImg.cols, grayImg.rows, unitData, 1, dataList.size(), unitResult); index = 0; for (list::iterator ele = dataList.begin();ele != dataList.end();ele++) { switch (unitResult[index]) { case 0: (*ele).limitMoneyUnit = MONEY_UNIT_Y; break; case 1: (*ele).limitMoneyUnit = MONEY_UNIT_W; break; default: break; } index++; } free(rowIndex); free(splitResult); free(zeroData); free(templateNums); free(unitData); free(unitResult); free(imgData); grayImg.release(); return dataList; } list LimitUpCapture::captureLimitUpCodes() { cout << "¿ªÊ¼ÔËÐÐ" << endl; HWND hwnd = getWindow(); cout << "ͬ»¨Ë³¾ä±ú£º"<< hwnd << endl; RECT wrect; GetWindowRect(win, &wrect); list flist; set codesSet; string codestr = ""; RECT menuRect; GetWindowRect(menuWin, &menuRect); list::iterator ele; for (ele = pointList.begin();ele != pointList.end();ele++) { int x = (*ele).x;//+ menuRect.left; int y = (*ele).y;//+ menuRect.top; printf("x:%d y:%d\n", x, y); SendMessage(menuWin, WM_LBUTTONDOWN, 0, MAKELONG(x, y)); Sleep(10); SendMessage(menuWin, WM_LBUTTONUP, 0, MAKELONG(x, y)); //SendMessage(menuWin, WM_SETCURSOR,(int) menuWin, 0x02000001); //Win32Util::focus(menuWin); //Win32Util::click(x, y); Sleep(100); for (int i = 0;i < 3;i++) { int x = wrect.right - 50; int y = wrect.top + 50; SendMessage(win, WM_MOUSEWHEEL, 0, MAKEWORD(x, y)); Sleep(100); cv::Mat oimg = CaptureUtil::capture(win); list codes = captureLimitUpCodes(oimg); for (list::iterator ele = codes.begin();ele != codes.end();ele++) { string code = (*ele).code; if (codesSet.count(code) == 0) { codesSet.insert(code); flist.push_back(*ele); } } codes.clear(); Sleep(50); } } return flist; } //È«²¿¿ªÊ¼ void LimitUpCapture::start() { running = true; } //È«²¿½áÊø void LimitUpCapture::stop() { running = false; } bool LimitUpCapture::isInited() { return inited; }