Java OpenCV Tesseract OCR“代码”regocnition
我正在尝试自动化某人手动将代码转换为数字代码的过程.
然后我开始阅读有关OCR的内容.所以我安装了tesseract OCR并尝试了一些图像.它甚至没有检测到接近代码的东西. 我在阅读了有关stackoverflow的一些问题之后想到,图像需要一些预处理,例如将图像倾斜到水平图像,这可以通过openCV来完成. 现在我的问题是: >在上述图像的情况下应该使用哪种预处理方法或其他方法? 我希望有一个人可以帮助我! 解决方法
我决定只捕获整张卡而不是代码.通过捕获整张卡片,可以将其转换为简单的视角,然后我可以轻松获得“代码”区域.
我也学到了很多东西.特别是关于速度.此功能在高分辨率图像上很慢.尺寸为3264 x 1836,最多可能需要10秒钟. 我所做的是为了加快速度,将输入矩阵的大小调整为1/4.这使得它的速度提高了4 ^ 2倍,并且给了我最小的精度损失.下一步是缩放我们发现回到正常大小的四边形.这样我们就可以使用原始源将四边形转换为普通视角. 我为检测最大区域而创建的代码很大程度上基于我在stackoverflow上找到的代码.不幸的是,他们没有像我预期的那样工作,所以我结合了更多的代码片段并进行了大量修改. private static double angle(Point p1,Point p2,Point p0 ) { double dx1 = p1.x - p0.x; double dy1 = p1.y - p0.y; double dx2 = p2.x - p0.x; double dy2 = p2.y - p0.y; return (dx1 * dx2 + dy1 * dy2) / Math.sqrt((dx1 * dx1 + dy1 * dy1) * (dx2 * dx2 + dy2 * dy2) + 1e-10); } private static MatOfPoint find(Mat src) throws Exception { Mat blurred = src.clone(); Imgproc.medianBlur(src,blurred,9); Mat gray0 = new Mat(blurred.size(),CvType.CV_8U),gray = new Mat(); List<MatOfPoint> contours = new ArrayList<>(); List<Mat> blurredChannel = new ArrayList<>(); blurredChannel.add(blurred); List<Mat> gray0Channel = new ArrayList<>(); gray0Channel.add(gray0); MatOfPoint2f approxCurve; double maxArea = 0; int maxId = -1; for (int c = 0; c < 3; c++) { int ch[] = {c,0}; Core.mixChannels(blurredChannel,gray0Channel,new MatOfInt(ch)); int thresholdLevel = 1; for (int t = 0; t < thresholdLevel; t++) { if (t == 0) { Imgproc.Canny(gray0,gray,10,20,3,true); // true ? Imgproc.dilate(gray,new Mat(),new Point(-1,-1),1); // 1 ? } else { Imgproc.adaptiveThreshold(gray0,thresholdLevel,Imgproc.ADAPTIVE_THRESH_GAUSSIAN_C,Imgproc.THRESH_BINARY,(src.width() + src.height()) / 200,t); } Imgproc.findContours(gray,contours,Imgproc.RETR_LIST,Imgproc.CHAIN_APPROX_SIMPLE); for (MatOfPoint contour : contours) { MatOfPoint2f temp = new MatOfPoint2f(contour.toArray()); double area = Imgproc.contourArea(contour); approxCurve = new MatOfPoint2f(); Imgproc.approxPolyDP(temp,approxCurve,Imgproc.arcLength(temp,true) * 0.02,true); if (approxCurve.total() == 4 && area >= maxArea) { double maxCosine = 0; List<Point> curves = approxCurve.toList(); for (int j = 2; j < 5; j++) { double cosine = Math.abs(angle(curves.get(j % 4),curves.get(j - 2),curves.get(j - 1))); maxCosine = Math.max(maxCosine,cosine); } if (maxCosine < 0.3) { maxArea = area; maxId = contours.indexOf(contour); //contours.set(maxId,getHull(contour)); } } } } } if (maxId >= 0) { return contours.get(maxId); //Imgproc.drawContours(src,maxId,new Scalar(255,.8),8); } return null; } 你可以像这样调用它: MathOfPoint contour = find(src); 从轮廓中查看此四边形检测的答案并将其转换为简单的视角: (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |