///''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
        //use Pythagorean theorem to calculate distance between two chars
        public double distanceBetweenChars(PossibleChar firstChar, PossibleChar secondChar)
        {
            int intX = Math.Abs(firstChar.intCenterX - secondChar.intCenterX);
            int intY = Math.Abs(firstChar.intCenterY - secondChar.intCenterY);

            return(Math.Sqrt((Math.Pow(intX, 2)) + (Math.Pow(intY, 2))));
        }
        ///''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
        public List <PossibleChar> findPossibleCharsInPlate(Mat imgGrayscale, Mat imgThresh)
        {
            List <PossibleChar> listOfPossibleChars = new List <PossibleChar>();
            //this will be the return value

            Mat imgThreshCopy = new Mat();

            VectorOfVectorOfPoint contours = new VectorOfVectorOfPoint();

            imgThreshCopy = imgThresh.Clone();

            CvInvoke.FindContours(imgThreshCopy, contours, null, RetrType.List, ChainApproxMethod.ChainApproxSimple);
            //find all contours in plate

            //for each contour
            for (int i = 0; i <= contours.Size - 1; i++)
            {
                PossibleChar possibleChar = new PossibleChar(contours[i]);

                //if contour is a possible char, note this does not compare to other chars (yet) . . .
                if ((checkIfPossibleChar(possibleChar)))
                {
                    listOfPossibleChars.Add(possibleChar);
                    //add to list of possible chars
                }
            }

            return(listOfPossibleChars);
        }
        ///''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
        //use basic trigonometry (SOH CAH TOA) to calculate angle between chars
        public double angleBetweenChars(PossibleChar firstChar, PossibleChar secondChar)
        {
            double dblAdj = Convert.ToDouble(Math.Abs(firstChar.intCenterX - secondChar.intCenterX));
            double dblOpp = Convert.ToDouble(Math.Abs(firstChar.intCenterY - secondChar.intCenterY));

            double dblAngleInRad = Math.Atan(dblOpp / dblAdj);

            double dblAngleInDeg = dblAngleInRad * (180.0 / Math.PI);

            return(dblAngleInDeg);
        }
 ///''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
 public bool checkIfPossibleChar(PossibleChar possibleChar)
 {
     //this function is a 'first pass' that does a rough check on a contour to see if it could be a char,
     //note that we are not (yet) comparing the char to other chars to look for a group
     if ((possibleChar.intRectArea > MIN_RECT_AREA & possibleChar.boundingRect.Width > MIN_PIXEL_WIDTH & possibleChar.boundingRect.Height > MIN_PIXEL_HEIGHT & MIN_ASPECT_RATIO < possibleChar.dblAspectRatio & possibleChar.dblAspectRatio < MAX_ASPECT_RATIO))
     {
         return(true);
     }
     else
     {
         return(false);
     }
 }
Esempio n. 5
0
        ///''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
        public List <PossibleChar> findPossibleCharsInScene(Mat imgThresh)
        {
            List <PossibleChar> listOfPossibleChars = new List <PossibleChar>();
            //this is the return value

            Mat imgContours             = new Mat(imgThresh.Size, DepthType.Cv8U, 3);
            int intCountOfPossibleChars = 0;

            Mat imgThreshCopy = imgThresh.Clone();

            VectorOfVectorOfPoint contours = new VectorOfVectorOfPoint();

            CvInvoke.FindContours(imgThreshCopy, contours, null, RetrType.List, ChainApproxMethod.ChainApproxSimple);
            //find all contours

            //for each contour
            for (int i = 0; i <= contours.Size - 1; i++)
            {
                // show steps '''''''''''''''''''''''''''''
                if ((frm.cbShowSteps.Checked == true))
                {
                    CvInvoke.DrawContours(imgContours, contours, i, SCALAR_WHITE);
                }
                // show steps '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''

                PossibleChar possibleChar = new PossibleChar(contours[i]);

                //if contour is a possible char, note this does not compare to other chars (yet) . . .
                if ((detectChars.checkIfPossibleChar(possibleChar)))
                {
                    intCountOfPossibleChars = intCountOfPossibleChars + 1;
                    //increment count of possible chars
                    listOfPossibleChars.Add(possibleChar);
                    //and add to list of possible chars
                }
            }

            // show steps '''''''''''''''''''''''''''''''''
            if ((frm.cbShowSteps.Checked == true))
            {
                frm.txtInfo.AppendText("\r\n" + "step 2 - contours.Size() = " + contours.Size.ToString() + "\r\n");
                //2362 with MCLRNF1 image
                frm.txtInfo.AppendText("step 2 - intCountOfPossibleChars = " + intCountOfPossibleChars.ToString() + "\r\n");
                //131 with MCLRNF1 image
                CvInvoke.Imshow("2a", imgContours);
            }
            // show steps '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''

            return(listOfPossibleChars);
        }
        ///''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
        public List <PossibleChar> findListOfMatchingChars(PossibleChar possibleChar, List <PossibleChar> listOfChars)
        {
            //the purpose of this function is, given a possible char and a big list of possible chars,
            //find all chars in the big list that are a match for the single possible char, and return those matching chars as a list
            List <PossibleChar> listOfMatchingChars = new List <PossibleChar>();

            //this will be the return value

            //for each char in big list
            foreach (PossibleChar possibleMatchingChar in listOfChars)
            {
                //if the char we attempting to find matches for is the exact same char as the char in the big list we are currently checking
                if ((possibleMatchingChar.Equals(possibleChar)))
                {
                    //then we should not include it in the list of matches b/c that would end up double including the current char
                    continue;
                    //so do not add to list of matches and jump back to top of for loop
                }
                //compute stuff to see if chars are a match
                double dblDistanceBetweenChars = distanceBetweenChars(possibleChar, possibleMatchingChar);

                double dblAngleBetweenChars = angleBetweenChars(possibleChar, possibleMatchingChar);

                double dblChangeInArea = Math.Abs(possibleMatchingChar.intRectArea - possibleChar.intRectArea) / possibleChar.intRectArea;

                double dblChangeInWidth  = Math.Abs(possibleMatchingChar.boundingRect.Width - possibleChar.boundingRect.Width) / possibleChar.boundingRect.Width;
                double dblChangeInHeight = Math.Abs(possibleMatchingChar.boundingRect.Height - possibleChar.boundingRect.Height) / possibleChar.boundingRect.Height;

                //check if chars match

                if ((dblDistanceBetweenChars < (possibleChar.dblDiagonalSize * MAX_DIAG_SIZE_MULTIPLE_AWAY)
                     & dblAngleBetweenChars < MAX_ANGLE_BETWEEN_CHARS
                     & dblChangeInArea < MAX_CHANGE_IN_AREA
                     & dblChangeInWidth < MAX_CHANGE_IN_WIDTH
                     & dblChangeInHeight < MAX_CHANGE_IN_HEIGHT))
                {
                    listOfMatchingChars.Add(possibleMatchingChar);
                    //if the chars are a match, add the current char to list of matching chars
                }
            }

            return(listOfMatchingChars);
            //return result
        }