private void BubbleDetectBtn_Click(object sender, EventArgs e) { //Applying Operations on transformed Image transformedImage = transformedImage.Resize(400, 400, Emgu.CV.CvEnum.Inter.Linear); Image <Bgr, byte> transCopy = transformedImage.Copy(); Emgu.CV.Util.VectorOfVectorOfPoint qtnVect = new Emgu.CV.Util.VectorOfVectorOfPoint(); Image <Gray, byte> qtnGray = transCopy.Convert <Gray, byte>(); Image <Gray, byte> copyG = qtnGray.Copy(); CvInvoke.GaussianBlur(qtnGray, qtnGray, new Size(5, 5), 0); CvInvoke.AdaptiveThreshold(qtnGray, qtnGray, 255, Emgu.CV.CvEnum.AdaptiveThresholdType.GaussianC, Emgu.CV.CvEnum.ThresholdType.Binary, 55, 9); CvInvoke.BitwiseNot(qtnGray, qtnGray); CvInvoke.FindContours(qtnGray, qtnVect, null, Emgu.CV.CvEnum.RetrType.External, Emgu.CV.CvEnum.ChainApproxMethod.ChainApproxSimple, default); //CIRCLE METHOD List <CircleF> circList = new List <CircleF>(); Emgu.CV.Util.VectorOfVectorOfPoint test = new Emgu.CV.Util.VectorOfVectorOfPoint(); Emgu.CV.Util.VectorOfPoint qtnApprox = new Emgu.CV.Util.VectorOfPoint(); Dictionary <int, double> qtnDict = new Dictionary <int, double>(); if (qtnVect.Size > 0) { for (int i = 0; i < qtnVect.Size; i++) { double area = CvInvoke.ContourArea(qtnVect[i]); if (area > 70) { qtnDict.Add(i, area); } } var item = qtnDict.OrderByDescending(v => v.Value); //.Take(1); Emgu.CV.Util.VectorOfPoint approxList = new Emgu.CV.Util.VectorOfPoint(); foreach (var it in item) { int key = Convert.ToInt32(it.Key.ToString()); double peri = CvInvoke.ArcLength(qtnVect[key], true); CvInvoke.ApproxPolyDP(qtnVect[key], qtnApprox, 0.02 * peri, true); if (qtnApprox.Size == 0) { } else if (qtnApprox.Size > 6) { CircleF circle = CvInvoke.MinEnclosingCircle(qtnVect[key]); Point centre = new Point(); centre.X = (int)circle.Center.X; centre.Y = (int)circle.Center.Y; CvInvoke.Circle(transformedImage, centre, (int)circle.Radius, new MCvScalar(0, 255, 0), 2, Emgu.CV.CvEnum.LineType.Filled, 0); //break; } } MessageBox.Show("Bubbles Detected"); bubbleImage.Image = transformedImage; } }
public List <Rectangle> sort_contours(Emgu.CV.Util.VectorOfVectorOfPoint cnts, string method) { List <Rectangle> BoundingBoxes = new List <Rectangle>(); //get the boxes into a list for (int i = 0; i < cnts.Size; i++) { Emgu.CV.Util.VectorOfPoint contour = cnts[i]; Rectangle BoundingBox = CvInvoke.BoundingRectangle(contour); BoundingBoxes.Add(BoundingBox); } // if no method specified defaut to l to r top to bottom List <Rectangle> SortedBoxes = BoundingBoxes.OrderBy(Rectangle => Rectangle.X).ThenBy(Rectangle => Rectangle.Y).ToList(); if (method == "right-to-left") { SortedBoxes = BoundingBoxes.OrderByDescending(Rectangle => Rectangle.X).ThenBy(Rectangle => Rectangle.Y).ToList(); } else if (method == "top-to-bottom") { SortedBoxes = BoundingBoxes.OrderBy(Rectangle => Rectangle.Y).ThenBy(Rectangle => Rectangle.X).ToList(); } else if (method == "bottom-to-top") { SortedBoxes = BoundingBoxes.OrderByDescending(Rectangle => Rectangle.Y).ThenBy(Rectangle => Rectangle.X).ToList(); } return(SortedBoxes); }
static void DrawContoursOnImage(Mat imageCopy, Emgu.CV.Util.VectorOfPoint cornerPoints) { for (int i = 0; i < cornerPoints.Size - 1; i++) { CvInvoke.Line(imageCopy, new Point(cornerPoints[i].X, cornerPoints[i].Y), new Point(cornerPoints[i + 1].X, cornerPoints[i + 1].Y), new Bgr(System.Drawing.Color.Red).MCvScalar, 1); } CvInvoke.Line(imageCopy, new Point(cornerPoints[cornerPoints.Size - 1].X, cornerPoints[cornerPoints.Size - 1].Y), new Point(cornerPoints[0].X, cornerPoints[0].Y), new Bgr(System.Drawing.Color.Red).MCvScalar, 1); }
public static Emgu.CV.Structure.RotatedRect FindMinAreaRect(this Emgu.CV.Util.VectorOfPoint points) { if ((points is null) || (points.Size < 1)) { return(Emgu.CV.Structure.RotatedRect.Empty); } return(Emgu.CV.CvInvoke.MinAreaRect(points: points)); }
private static double AverageDistanceToEllipse(Emgu.CV.Util.VectorOfPoint contour, RotatedRect rect) { var n = contour.Size; var dist = 0d; for (int i = 0; i < n; i++) { dist = dist + DistanceToEllipse(new clsPoint(contour[i].X, contour[i].Y), rect); } return(dist / n); }
public static System.Double CalculateContourArea(this Emgu.CV.Util.VectorOfPoint countourPoints, System.Boolean orientationSigned = false) { if (countourPoints is null) { throw new System.ArgumentNullException(nameof(countourPoints)); } return(Emgu.CV.CvInvoke.ContourArea(contour: countourPoints, oriented: orientationSigned)); }
public static Emgu.CV.Util.VectorOfPoint ToClockwise(this Emgu.CV.Util.VectorOfPoint vectorOfPoint) { var array = new List <Point>(vectorOfPoint.ToArray()); array.Reverse(); if (Emgu.CV.CvInvoke.ContourArea(vectorOfPoint, true) < 0) { return(new Emgu.CV.Util.VectorOfPoint(array.ToArray())); } return(vectorOfPoint); }
private static double FurthestDistanceToEllipse(Emgu.CV.Util.VectorOfPoint contour, RotatedRect rect) { var n = contour.Size; var dist = 0d; for (int i = 0; i < n; i++) { var d = DistanceToEllipse(new clsPoint(contour[i].X, contour[i].Y), rect); if (d > dist) { dist = d; } } return(dist); }
PointF[] order(Emgu.CV.Util.VectorOfPoint p) { PointF[] rectPoint = new PointF[4]; int[] sum = new int[4]; for (int i = 0; i < sum.Length; i++) //Traversing for sum of p(x+y) & save in array { sum[i] = p[i].X + p[i].Y; } // Getting Index of Point with Maximum (x+y) sum:: Bottom Right Point [2] int maxValue = sum.Max(); int maxIndex = sum.ToList <int>().IndexOf(maxValue); rectPoint[2] = p[maxIndex]; //Setting to bottom-right point // Getting index of Point with Minimum (x+y) sum :: Top-Left Point [0] int minValue = sum.Min(); int minIndex = sum.ToList <int>().IndexOf(minValue); rectPoint[0] = p[minIndex]; //setting to Top-left Point int[] diff = new int[4]; for (int i = 0; i < diff.Length; i++) //Traversing for difference p(x-y) and save in array { diff[i] = p[i].X - p[i].Y; MessageBox.Show("diff " + i + " = " + diff[i]); } // Getting index of Point with minimum (x-y) diff:: Top-right Point [1] int minDiff = diff.Min(); int minDiffIndex = diff.ToList <int>().IndexOf(minDiff); rectPoint[1] = p[minDiffIndex]; // Setting Top-Right Point // Getting Index of point with maximum (x-y) diff :: Bottom-Left Point [3] int maxDiff = diff.Max(); int maxDiffIndex = diff.ToList <int>().IndexOf(maxDiff); rectPoint[3] = p[maxDiffIndex]; // Setting Bottom-left Point MessageBox.Show("max diff: " + rectPoint[3]); //return rectPoint top-left [0] : top-right [1]: bottom-right [2]: bottom-left [3] return(rectPoint); }
static bool CheckConnectedComponents(Mat grayImage) { // Threshold using Otsu bi-modal (black&white) assumption Mat binaryImage = grayImage.Clone(); double otsuThreshold = CvInvoke.Threshold(grayImage, binaryImage, 0.0, 255.0, Emgu.CV.CvEnum.ThresholdType.Otsu | Emgu.CV.CvEnum.ThresholdType.Binary); // dilate to connect two squares Mat kernel = new Mat(); CvInvoke.Dilate(binaryImage, binaryImage, kernel, new Point(-1, -1), 1, Emgu.CV.CvEnum.BorderType.Constant, CvInvoke.MorphologyDefaultBorderValue); CvInvoke.Imwrite("C:\\Temp\\Dilate.png", binaryImage, new KeyValuePair <Emgu.CV.CvEnum.ImwriteFlags, int>(Emgu.CV.CvEnum.ImwriteFlags.PngCompression, 3)); // compute number of labels (should be 2: 0 for background, 1 for white) Mat labelRegion = new Mat(new System.Drawing.Size(binaryImage.Width, binaryImage.Height), Emgu.CV.CvEnum.DepthType.Cv32S, 1); Mat statistics = new Mat(); Mat centroids = new Mat(); var numberOfLabels = CvInvoke.ConnectedComponentsWithStats(binaryImage, labelRegion, statistics, centroids, Emgu.CV.CvEnum.LineType.EightConnected, Emgu.CV.CvEnum.DepthType.Cv32S); Console.WriteLine(" - Number of labels: %d\n", numberOfLabels); if (numberOfLabels != 2) { return(false); } // compute centers of background and foreground (should also be close to image center) Emgu.CV.Util.VectorOfPoint imageCentre = new Emgu.CV.Util.VectorOfPoint(new Point [] { new Point((int)(grayImage.Cols / 2.0f), (int)(grayImage.Rows / 2.0f)) }); Emgu.CV.Util.VectorOfPointF blackCenter = new Emgu.CV.Util.VectorOfPointF(new PointF[] { new PointF((float)centroids.GetDoubleValue(0, 0), (float)centroids.GetDoubleValue(0, 1)) }); Emgu.CV.Util.VectorOfPointF whiteCenter = new Emgu.CV.Util.VectorOfPointF(new PointF[] { new PointF((float)centroids.GetDoubleValue(1, 0), (float)centroids.GetDoubleValue(1, 1)) }); var blackCentroidDistance = CvInvoke.Norm(blackCenter, imageCentre, Emgu.CV.CvEnum.NormType.L2); var whiteCentroidDistance = CvInvoke.Norm(whiteCenter, imageCentre, Emgu.CV.CvEnum.NormType.L2); for (var label = 0; label < numberOfLabels; label++) { Console.WriteLine(" - [%d] centroid at (%.1lf,%.1lf)\n", label, (float)centroids.GetDoubleValue(label, 0), (float)centroids.GetDoubleValue(label, 1)); } return(numberOfLabels == 2 && blackCentroidDistance < 10.0 && whiteCentroidDistance < 10.0); }
private void button3_Click(object sender, EventArgs e) { if (Image1 != null) { //---แปลงเป็น hsv------------------------------------------------ Image <Hsv, byte> hsv = Image1.Convert <Hsv, byte>(); //แปลงเป็น ภาพเทา แบบ อาเรย์-Create result image---------------------------------------- Image <Gray, byte>[] channels = hsv.Split(); CvInvoke.InRange(channels[0], new ScalarArray(new MCvScalar(20)), new ScalarArray(new MCvScalar(160)), channels[0]); //อันแรกคือ H อันสอง คือ S channels[0]._Not(); channels[1]._ThresholdBinary(new Gray(100), new Gray(255)); //อันนี้ คือV new Gray(10) IInputArray mask = null; CvInvoke.BitwiseAnd(channels[0], channels[1], channels[0], mask); image2 = channels[0].Canny(150, 0); //-------------------------วาดกรอบโดยการใช้contour--------------------------------- Emgu.CV.Util.VectorOfVectorOfPoint contour = new Emgu.CV.Util.VectorOfVectorOfPoint(); // คือการประกาศตัวแปรcountor Mat hier = new Mat(); CvInvoke.FindContours(image2, contour, hier, Emgu.CV.CvEnum.RetrType.External, Emgu.CV.CvEnum.ChainApproxMethod.ChainApproxSimple); //คือการค้นหา contours //--------------------------------------------------------------------------- //ทำการวนลูป for (int i = 0; i < contour.Size; i++) { double paramiter = CvInvoke.ArcLength(contour[i], true); Emgu.CV.Util.VectorOfPoint approx = new Emgu.CV.Util.VectorOfPoint(); CvInvoke.ApproxPolyDP(contour[i], approx, 0.04 * paramiter, true); CvInvoke.DrawContours(Image1, contour, i, new MCvScalar(0, 0, 0), 6); // i บอกจำนวนที่วาด ku++; //-------------หาศูนย์กลาง-------------- var moment = CvInvoke.Moments(contour[i]); int x = (int)(moment.M10 / moment.M00); int y = (int)(moment.M01 / moment.M00); if (approx.Size == 3) { CvInvoke.PutText(Image1, ". ", new Point(x, y), Emgu.CV.CvEnum.FontFace.HersheyScriptSimplex, 1.5, new MCvScalar(0, 0, 0), 10); } if (approx.Size == 5) { CvInvoke.PutText(Image1, ". ", new Point(x, y), Emgu.CV.CvEnum.FontFace.HersheyScriptSimplex, 1.5, new MCvScalar(0, 0, 0), 10); } if (approx.Size == 6) { CvInvoke.PutText(Image1, ". ", new Point(x, y), Emgu.CV.CvEnum.FontFace.HersheyScriptSimplex, 1.5, new MCvScalar(0, 0, 0), 10); } if (approx.Size > 6) { CvInvoke.PutText(Image1, ". ", new Point(x, y), Emgu.CV.CvEnum.FontFace.HersheyScriptSimplex, 1.5, new MCvScalar(0, 0, 0), 10); } imageBox2.Image = Image1; } textBox1.Text = ku.ToString(); ku = 0; } } //แดง
public Bitmap FindEllipseArc() { Bitmap bmp; Emgu.CV.Util.VectorOfVectorOfPoint contour = new Emgu.CV.Util.VectorOfVectorOfPoint(); Emgu.CV.Util.VectorOfPoint arcOfEllipse = new Emgu.CV.Util.VectorOfPoint(); List <Point> ptsOfArc = new List <Point>(); //List<Emgu.CV.Util.VectorOfPoint> listOfArcOfEllipse = new List<Emgu.CV.Util.VectorOfPoint>(); // Find of contours of ellipse CvInvoke.FindContours(imgEdgesROI, contour, null, RetrType.List, ChainApproxMethod.ChainApproxNone); for (int i = 0; i < contour.Size; i++) { if (contour[i].Size > 50) { int length; arcOfEllipse.Push(contour[i]); //listOfArcOfEllipse.Add(contour[i]); length = contour[i].Size; //System.Windows.Forms.MessageBox.Show("Size:" + contour[i].Size.ToString()); /* * for (int j = 0; j < contour[i].Size; j++) * { * Console.WriteLine(contour[i][j].X.ToString() + "\t" + contour[i][j].Y.ToString()); * } * * Console.WriteLine("--------------------------------"); */ } } //System.Windows.Forms.MessageBox.Show(endPtsOfArc.Count.ToString()); rRect = CvInvoke.FitEllipse(arcOfEllipse); // Transfer the point vector(EMGU) to List(System) and get sorted for (int i = 0; i < arcOfEllipse.Size; i++) { ptsOfArc.Add(arcOfEllipse[i]); } ptsOfArc.Sort(SortRadianCompare); /* * for (int i = 0; i < ptsOfArc.Count; i++) * { * Console.WriteLine(ptsOfArc[i].X.ToString() + "\t" + ptsOfArc[i].Y.ToString()); * } */ Point beginPoint = new Point(); Point endPoint = new Point(); double maxRadian = 0.0; // Find the gap for (int i = 0; i < ptsOfArc.Count - 1; i++) { double deltaY1 = (double)(ptsOfArc[i + 1].Y - rRect.Center.Y); double deltaX1 = (double)(ptsOfArc[i + 1].X - rRect.Center.X); double deltaY2 = (double)(ptsOfArc[i].Y - rRect.Center.Y); double deltaX2 = (double)(ptsOfArc[i].X - rRect.Center.X); if (System.Math.Atan2(deltaY1, deltaX1) - System.Math.Atan2(deltaY2, deltaX2) > maxRadian) { maxRadian = System.Math.Atan2(deltaY1, deltaX1) - System.Math.Atan2(deltaY2, deltaX2); beginPoint = ptsOfArc[i]; endPoint = ptsOfArc[i + 1]; } } Emgu.CV.Image <Bgr, byte> imgWithRect = img.Convert <Bgr, byte>(); /* * List<Point>[] pointslistOfElliSegment = new List<Point>[listOfArcOfEllipse.Count]; * * // Transfer the point vector(EMGU) to List(System) and get sorted * for(int i = 0; i < listOfArcOfEllipse.Count; i ++) * { * for(int j = 0; j < listOfArcOfEllipse[i].Size; j++) * { * pointslistOfElliSegment[i].Add(listOfArcOfEllipse[i][j]); * } * * pointslistOfElliSegment[i].Sort(SortRadianCompare); * } */ Point gapCenter = new Point((beginPoint.X + endPoint.X) / 2, (beginPoint.Y + endPoint.Y) / 2); Point rectCenter = new Point((int)rRect.Center.X, (int)rRect.Center.Y); imgWithRect.Draw(new Ellipse(rRect), new Bgr(0, 0, 255), 2, LineType.EightConnected); imgWithRect.Draw(new LineSegment2D(gapCenter, rectCenter), new Bgr(0, 0, 255), 2, LineType.EightConnected); bmp = imgWithRect.Bitmap; return(bmp); }
public static Point[] findCutPoint(Emgu.CV.Util.VectorOfPoint contours) { Point[] con1 = contours.ToArray(); Array.Sort(con1, compareY); int size = con1.Length; int top_x = con1[0].X; int top_y = con1[0].Y; int bottom_x = con1[size - 1].X; int bottom_y = con1[size - 1].Y; int top_x_count = 1; int bottom_x_count = 1; int flag1 = 0; for (int i = 1; i < size / 10; i++) { if (top_y == con1[i].Y) { flag1 = 1; top_x_count += 1; top_x += con1[i].X; } if (bottom_y == con1[size - 1 - i].Y) { flag1 = 1; bottom_x_count += 1; bottom_x += con1[size - 1 - i].X; } if (flag1 == 0) { break; } } float top_x_temp = (float)(top_x * 1.0F / top_x_count * 1.0); float bottom_x_temp = (float)(bottom_x * 1.0F / bottom_x_count * 1.0); Point[] con2 = con1; Array.Sort(con2, compareX); int left_x = con2[0].X; int left_y = con2[0].Y; int right_x = con2[size - 1].X; int right_y = con2[size - 1].Y; int left_y_count = 1; int right_y_count = 1; int flag2 = 0; for (int i = 1; i < size / 10; i++) { if (left_x == con2[i].X) { flag2 = 1; left_y_count += 1; left_y += con2[i].Y; } if (right_x == con2[size - 1 - i].X) { flag2 = 1; right_y_count += 1; right_y += con2[size - 1 - i].Y; } if (flag2 == 0) { break; } } float left_y_temp = left_y * 1.0F / (float)(left_y_count * 1.0F); float right_y_temp = right_y * 1.0F / (float)right_y_count * 1.0F; System.Drawing.Point[] p1 = new Point[4]; p1[0].X = (int)top_x_temp; p1[0].Y = top_y; p1[1].X = right_x; p1[1].Y = (int)right_y_temp; p1[2].X = (int)bottom_x_temp; p1[2].Y = bottom_y; p1[3].X = left_x; p1[3].Y = (int)left_y_temp; return(p1); }
Image <Bgr, float> transformImage(Image <Bgr, float> image, Emgu.CV.Util.VectorOfPoint points) { var orderPoints = order(points); // Ordering the Points in Particular Order for (int i = 0; i < points.Size; i++) { MessageBox.Show("X= " + orderPoints[i].X + "Y= " + orderPoints[i].Y); } //Assigning to Points Orderwise For Mathematical Operations PointF topLeft = orderPoints[0]; PointF topRight = orderPoints[1]; PointF bottomRight = orderPoints[2]; PointF bottomLeft = orderPoints[3]; // Calculating Width double widthSqrt = Math.Pow(bottomRight.X - bottomLeft.X, 2) + Math.Pow(bottomRight.Y - bottomLeft.Y, 2); double widthA = Math.Sqrt(widthSqrt); double widthBsqrt = Math.Pow(topRight.X - topLeft.X, 2) + Math.Pow(topRight.Y - topLeft.Y, 2); double widthB = Math.Sqrt(widthBsqrt); int maxWidth = Convert.ToInt32(Math.Max(widthA, widthB)); // Calculating Height double heightSqrt = Math.Pow(topRight.X - bottomRight.X, 2) + Math.Pow(topRight.Y - bottomRight.Y, 2); double heightA = Math.Sqrt(heightSqrt); double heightBSqrt = Math.Pow(topLeft.X - bottomLeft.X, 2) + Math.Pow(topLeft.Y - bottomLeft.Y, 2); double heightB = Math.Sqrt(heightBSqrt); int maxHeight = Convert.ToInt32(Math.Max(heightA, heightB)); // getting dest Points MessageBox.Show("Max Width: " + maxWidth + " Max Height: " + maxHeight); PointF[] destPoints = new PointF[4] { new PointF { X = 0, Y = 0 }, new PointF { X = maxWidth - 1, Y = 0 }, new PointF { X = maxWidth - 1, Y = maxHeight - 1 }, new PointF { X = 0, Y = maxHeight - 1 } }; //var mat=CvInvoke.FindHomography(orderPoints, destPoints, Emgu.CV.CvEnum.RobustEstimationAlgorithm.AllPoints, 3, null); //var mat=Mat.Zeros(3, 3, Emgu.CV.CvEnum.DepthType.Cv32F, 0); var mat = CvInvoke.GetPerspectiveTransform(orderPoints, destPoints); MessageBox.Show("Mat rows: " + mat.Rows + " Mat cols: " + mat.Cols); Matrix <float> matrix = new Matrix <float>(3, 3); mat.CopyTo(matrix); //var mat = CvInvoke.GetAffineTransform(orderPoints, destPoints); //image = image.WarpAffine(mat, Emgu.CV.CvEnum.Inter.Linear, Emgu.CV.CvEnum.Warp.Default, Emgu.CV.CvEnum.BorderType.Constant,new Bgr(23,40,60)); //image = mat.ToImage<Bgr, float>(); //CvInvoke.Invert(mat, mat, Emgu.CV.CvEnum.DecompMethod.LU); Image <Bgr, float> destImage = new Image <Bgr, float>(maxWidth, maxHeight); image = image.Resize(maxWidth, maxHeight, Emgu.CV.CvEnum.Inter.Linear); MessageBox.Show("Size of Image: " + image.Size); CvInvoke.WarpPerspective(image, image, mat, image.Size, Emgu.CV.CvEnum.Inter.Lanczos4, Emgu.CV.CvEnum.Warp.FillOutliers, Emgu.CV.CvEnum.BorderType.Constant, new MCvScalar(255, 255, 255)); //image = image.WarpPerspective<float>(matrix, maxWidth, maxHeight, Emgu.CV.CvEnum.Inter.Nearest, Emgu.CV.CvEnum.Warp.Default, Emgu.CV.CvEnum.BorderType.Default, new Bgr(255, 255, 255)); //CvInvoke.Rotate(image, image, Emgu.CV.CvEnum.RotateFlags.Rotate90CounterClockwise); //destImage = mat.ToImage<Bgr, float>(); return(image); }
private void Button4_Click(object sender, EventArgs e) { Emgu.CV.Util.VectorOfPoint approx = new Emgu.CV.Util.VectorOfPoint(); Emgu.CV.Util.VectorOfVectorOfPoint vecOut = new Emgu.CV.Util.VectorOfVectorOfPoint(); CvInvoke.FindContours(cannyImage, vecOut, null, Emgu.CV.CvEnum.RetrType.External, Emgu.CV.CvEnum.ChainApproxMethod.ChainApproxSimple); //Point defines the x-y coordinates in 2d-plane Dictionary <int, double> dict = new Dictionary <int, double>(); AForge.IntPoint[] point = new AForge.IntPoint[4]; if (vecOut.Size > 0) { for (int i = 0; i < vecOut.Size; i++) { //calculating area of contours double area = CvInvoke.ContourArea(vecOut[i]); dict.Add(i, area); //adding areas in dictionary } var item = dict.OrderByDescending(v => v.Value); //Preparing for perspective transformation foreach (var it in item) { int key = Convert.ToInt32(it.Key.ToString()); //generating arc length wrapping the doc double peri = CvInvoke.ArcLength(vecOut[key], true); CvInvoke.ApproxPolyDP(vecOut[key], approx, 0.02 * peri, true); if (approx.Size == 0) { } else if (approx.Size == 4) { try { CvInvoke.DrawContours(copyImage, vecOut, key, new MCvScalar(255, 0, 0), 5); for (int i = 0; i < approx.Size; i++) { point[i].X = approx[i].X; point[i].Y = approx[i].Y; } } catch (Exception ex) { MessageBox.Show(ex.Message); } break; } } } sheetDetectImage.Image = copyImage; try { List <AForge.IntPoint> pointList = new List <AForge.IntPoint>(); for (int i = 0; i < 4; i++) { pointList.Add(new AForge.IntPoint(point[i].X, point[i].Y)); } AForge.Imaging.Filters.SimpleQuadrilateralTransformation simple = new AForge.Imaging.Filters.SimpleQuadrilateralTransformation(pointList, 200, 200); Bitmap abc1 = simple.Apply(bitmapImage); AForge.Imaging.Filters.Mirror m = new AForge.Imaging.Filters.Mirror(false, true); m.ApplyInPlace(abc1); Image <Bgr, byte> newIm = new Image <Bgr, byte>(abc1); CvInvoke.Rotate(newIm, newIm, Emgu.CV.CvEnum.RotateFlags.Rotate90CounterClockwise); MessageBox.Show("Scanned Document"); sheetDetectImage.Image = newIm; transformedImage = newIm.Copy(); } catch (Exception er) { MessageBox.Show(er.StackTrace); } }
private void Generator_DoWork(object sender, DoWorkEventArgs e) { DataPass data = (DataPass)e.Argument; //e.Result = result; Random randomGen = new Random(data.settings.Seed);; GaussianRandom gausRandomGen = new GaussianRandom(data.settings.Seed); Dictionary <String, Detector[]> detectors = new Dictionary <string, Detector[]>(); //Generate detectors foreach (String currentImage in data.inputData.Keys) { detectors.Add(currentImage, new Detector[data.settings.NumberOfNegativeDetectors]); for (int i = 0; i < data.settings.NumberOfNegativeDetectors; i++) { int attempts = 0; bool found = false; while (!found && attempts < 10) { attempts++; // To prevent infinite loop //TODO (Anthony): Width and height should be individual per image int randomX = randomGen.Next(0, data.settings.Width); int randomY = randomGen.Next(0, data.settings.Height); //TODO (Anthony): Setting perhaps? int radius = randomGen.Next(10, 50); int doubleRadius = radius * radius; Detector newDetector = new Detector(randomX, randomY, radius); int numDetectSelf = 0; //check for collisions with points in each image foreach (System.Drawing.Point[] currentObjectList in data.inputData[currentImage].ToArrayOfArray()) // loop over each object in image { foreach (System.Drawing.Point point in currentObjectList) // loop over each point { //check if detect self if (Math.Pow(point.X - randomX, 2) + Math.Pow(point.Y - randomY, 2) < doubleRadius) { numDetectSelf++; } } } //TODO (Anthony): Detting for maximum self detection if (numDetectSelf < 10) { found = true; detectors[currentImage][i] = newDetector; } /* * //check for overlap with other detectors * for (int k = 0; k < i;k++) * { * * } */ } } } //start generation and mutation //Step 1: generate initial //Step 2: mutate according to affinities //Step 3: calculate affinities //Step 4: Select best //Step 5: go to step 2 and repeat BoundBox[] sizes = new BoundBox[data.objects.Size]; for (int i = 0; i < sizes.Length; i++) { sizes[i] = ImageManipulation.getBoundBox(data.objects[i]); } int numImagesClones = 20; //list of integer and vector of vector of points, where int is the affinities and VectorOfVectorOfPoint is each objects in scene List <Tuple <int, Emgu.CV.Util.VectorOfVectorOfPoint> > imagesObjects = new List <Tuple <int, Emgu.CV.Util.VectorOfVectorOfPoint> >(); Emgu.CV.Util.VectorOfPoint[] objects = new Emgu.CV.Util.VectorOfPoint[data.settings.NumberOfObjects]; for (int k = 0; k < numImagesClones; k++) { //generate image with affinity of zero int affinity = 0; for (int i = 0; i < data.settings.NumberOfObjects; i++) { int objectIndex = randomGen.Next(data.objects.Size); int shiftX = Math.Max(0, data.settings.Width - sizes[objectIndex].Width); int shiftY = Math.Max(0, data.settings.Height - sizes[objectIndex].Height); objects[i] = ImageManipulation.offsetContour(data.objects[objectIndex], new System.Drawing.Point(randomGen.Next(shiftX), randomGen.Next(shiftY))); } imagesObjects.Add(new Tuple <int, Emgu.CV.Util.VectorOfVectorOfPoint>(affinity, new Emgu.CV.Util.VectorOfVectorOfPoint(objects))); } int maxIterations = 5; int loopCounter = 0; bool perfected = false; while (loopCounter < maxIterations && !perfected) { loopCounter++; //calculate affinities for (int i = 0; i < numImagesClones; i++) // loop through each clone { int affinity = 0; //TODO (Anthony): Check affinities for all images for (int k = 0; k < imagesObjects[i].Item2.Size; k++) // loop through each object { for (int f = 0; f < imagesObjects[i].Item2[k].Size; f++) // loop through each point { foreach (Detector[] detectorsOfEachImage in detectors.Values) { for (int c = 0; c < detectorsOfEachImage.Length; c++) { affinity += checkDistance(detectorsOfEachImage[c], imagesObjects[i].Item2[k][f]); } } } } imagesObjects[i] = new Tuple <int, Emgu.CV.Util.VectorOfVectorOfPoint>(affinity, imagesObjects[i].Item2); } //mutate according to affinity for (int i = 0; i < numImagesClones; i++) // loop through each clone { int affinity = imagesObjects[i].Item1; //TODO (Anthony): Check affinities for all images for (int k = 0; k < imagesObjects[i].Item2.Size; k++) // loop through each object { for (int f = 0; f < imagesObjects[i].Item2[k].Size; f++) // loop through each point { int x = (int)(gausRandomGen.NextValue() * affinity); int y = (int)(gausRandomGen.NextValue() * affinity); imagesObjects[i].Item2[k][f].Offset(x, y); } } } //replace bad ones } e.Result = imagesObjects[randomGen.Next(numImagesClones)].Item2; }
private void button2_Click(object sender, EventArgs e) { Image triangleRectangleImageBox1; Image circleImageBox1; Image lineImageBox1; StringBuilder msgBuilder = new StringBuilder("Performance: "); Bitmap clip_bmp = new Bitmap(cliped_image); //Load the image from file and resize it for display Image <Bgr, Byte> img = new Image <Bgr, byte>(clip_bmp).Resize(400, 400, Emgu.CV.CvEnum.Inter.Linear, true); //Convert the image to grayscale and filter out the noise UMat uimage = new UMat(); CvInvoke.CvtColor(img, uimage, ColorConversion.Bgr2Gray); //use image pyr to remove noise UMat pyrDown = new UMat(); CvInvoke.PyrDown(uimage, pyrDown); CvInvoke.PyrUp(pyrDown, uimage); #region circle detection Stopwatch watch = Stopwatch.StartNew(); double cannyThreshold = 180.0; // 180 double circleAccumulatorThreshold = 120.0; // 120 CircleF[] circles = CvInvoke.HoughCircles(uimage, HoughType.Gradient, 2.0, 20.0, cannyThreshold, circleAccumulatorThreshold, 5); watch.Stop(); msgBuilder.Append(String.Format("Hough circles - {0} ms; ", watch.ElapsedMilliseconds)); #endregion #region Canny and edge detection watch.Reset(); watch.Start(); double cannyThresholdLinking = 120.0; // 120 UMat cannyEdges = new UMat(); CvInvoke.Canny(uimage, cannyEdges, cannyThreshold, cannyThresholdLinking); LineSegment2D[] lines = CvInvoke.HoughLinesP( cannyEdges, 1, //Distance resolution in pixel-related units - 1 Math.PI / 45.0, //Angle resolution measured in radians. 0, //threshold - 20 0, //min Line width - 30 10); //gap between lines - 10 watch.Stop(); msgBuilder.Append(String.Format("Canny & Hough lines - {0} ms; ", watch.ElapsedMilliseconds)); #endregion #region Find triangles and rectangles watch.Reset(); watch.Start(); List <Triangle2DF> triangleList = new List <Triangle2DF>(); List <RotatedRect> boxList = new List <RotatedRect>(); //a box is a rotated rectangle using (Emgu.CV.Util.VectorOfVectorOfPoint contours = new Emgu.CV.Util.VectorOfVectorOfPoint()) { CvInvoke.FindContours(cannyEdges, contours, null, RetrType.List, ChainApproxMethod.ChainApproxSimple); int count = contours.Size; for (int i = 0; i < count; i++) { using (Emgu.CV.Util.VectorOfPoint contour = contours[i]) using (Emgu.CV.Util.VectorOfPoint approxContour = new Emgu.CV.Util.VectorOfPoint()) { CvInvoke.ApproxPolyDP(contour, approxContour, CvInvoke.ArcLength(contour, true) * 0.05, true); if (CvInvoke.ContourArea(approxContour, false) > 250) //only consider contours with area greater than 250 { if (approxContour.Size == 3) //The contour has 3 vertices, it is a triangle { Point[] pts = approxContour.ToArray(); triangleList.Add(new Triangle2DF( pts[0], pts[1], pts[2] )); } else if (approxContour.Size == 4) //The contour has 4 vertices. { #region determine if all the angles in the contour are within [80, 100] degree bool isRectangle = true; Point[] pts = approxContour.ToArray(); LineSegment2D[] edges = PointCollection.PolyLine(pts, true); for (int j = 0; j < edges.Length; j++) { double angle = Math.Abs( edges[(j + 1) % edges.Length].GetExteriorAngleDegree(edges[j])); if (angle < 80 || angle > 100) { isRectangle = false; break; } } #endregion if (isRectangle) { boxList.Add(CvInvoke.MinAreaRect(approxContour)); } } } } } } watch.Stop(); msgBuilder.Append(String.Format("Triangles & Rectangles - {0} ms; ", watch.ElapsedMilliseconds)); #endregion //originalImageBox.Image = img.ToBitmap(); this.Text = msgBuilder.ToString(); #region draw triangles and rectangles Image <Bgr, Byte> triangleRectangleImage = img.CopyBlank(); foreach (Triangle2DF triangle in triangleList) { triangleRectangleImage.Draw(triangle, new Bgr(Color.DarkBlue), 2); } foreach (RotatedRect box in boxList) { triangleRectangleImage.Draw(box, new Bgr(Color.DarkOrange), 2); } triangleRectangleImageBox1 = triangleRectangleImage.ToBitmap(); #endregion #region draw circles Image <Bgr, Byte> circleImage = img.CopyBlank(); foreach (CircleF circle in circles) { circleImage.Draw(circle, new Bgr(Color.Brown), 2); } circleImageBox1 = circleImage.ToBitmap(); #endregion #region draw lines Image <Bgr, Byte> lineImage = img.CopyBlank(); foreach (LineSegment2D line in lines) { lineImage.Draw(line, new Bgr(Color.Green), 2); } lineImageBox1 = lineImage.ToBitmap(); #endregion cv_image = lineImageBox1; pictureBox2.Image = lineImageBox1; }