I'm doing some simple OCR car plate recognition system. I'm using HaarCascades to find car plate, and next i need to normalize this plate, to put it into my OCR module. I'm using floodfill to find main contours of a car plate, and then i perform Hough transform, to find upper and lower boarders of a car plate:
Here's a part of code, where i perform Hough transform^
HoughLinesP(canny_img, lines, 1, CV_PI/180, 80, 80, 30 );
for ( size_t i = 0; i < lines.size(); i++ ) {
line (output, Point(lines[i][0], lines[i][3]), Point(lines[i][4], lines[i][5]), Scalar(0,0,255), 1, 8 );
}
Now i need to cut and rotate this picture along this two lines. How can i do this? i understand that i need to use point Point(lines[i][0])..Point(linesi), but what i should do with them?
So basically, i need to get something like that:
So at the first step i need to cut only upper and lower boarders.
Automatic Number Plate Recognition – or as it is frequently called “license plate recognition” – is a special form of optical character recognition (OCR), which enables computer systems to read out automatically the registration number (license plate number) of vehicles from a digital pictures.
Step #1: Detect and localize a license plate in an input image/frame. Step #2: Extract the characters from the license plate. Step #3: Apply some form of Optical Character Recognition (OCR) to recognize the extracted characters.
LPR algorithm consists of the following three processing steps: 1) Number plate detection, 2) Character segmentation, and 3) Character recognition. The accuracy of plate extraction relies on the character segmentation and character recognition.
You need to use affine transformations, here there is tutorial. In your situation you need to choose some size of car plate, for example 20x100
. Your destination points will be 3 corners of non rotated rectangle of choosen size and source points will be 3 corners of founded car plate. I hope it is clear, if it is'not, let me know - i will make some example.
*\\EDIT:
Ok, i've made some example. Here is the code:
cv::Mat img = cv::imread("D:\\temp\\car_plate.jpg");
cv::Point2f a1(25, 18), b1(279, 27), c1(279, 79), a2(0, 0), b2(img.size().width, 0), c2(img.size().width, img.size().height);
//cv::Point2f a1(0, 16), b1(303, 28), c1(303, 81), a2(0, 0), b2(img.size().width, 0), c2(img.size().width, img.size().height);
cv::Point2f src[] = {a1, b1, c1};
cv::Point2f dst[] = {a2, b2, c2};
cv::Mat warpMat = cv::getAffineTransform(src, dst);
cv::warpAffine(img, img, warpMat, img.size());
cv::imshow("result", img);
cv::waitKey(-1);
return 0;
And results:
If you will use the code without any modification you will get the first result, if you comment second line and uncomment third line you will get second result (i think that's what you wanted). To get the second result you just need to find the points where upper and lower lines cross the image border. I've marked it here:
So basically you need to use red points. To calculate their positions you just need to find where blue lines (which if i understand correct you already have) cross the image border.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With