public static void FindNeedleLoc(Bitmap bmp, HWindow Window, double[] data, double[] offset) //图像处理代码 { #region //声明控制变量 HTuple hv_Width = null, hv_Height = null; #endregion #region//声明需要用到的图像变量 HObject ho_src_image; #endregion #region//初始化将要用到的图像变量 HOperatorSet.GenEmptyObj(out ho_src_image); #endregion //将bitmap转换成HObject. Bitmap2HObject.Bitmap2HObj(bmp, out ho_src_image); HWindow hWindow = Window; //获取图片尺寸信息 HOperatorSet.GetImageSize(ho_src_image, out hv_Width, out hv_Height); HOperatorSet.SetPart(hWindow, 0, 0, hv_Height - 1, hv_Width - 1); HOperatorSet.DispObj(ho_src_image, hWindow); SetString(Window, "OK", "green", 100); HOperatorSet.DispText(Window, "X方向偏差:" + System.Math.Round(offset[0], 4) + " mm", "window", 12, 7, "black", new HTuple(), new HTuple()); HOperatorSet.DispText(Window, "Y方向偏差:" + System.Math.Round(offset[1], 4) + " mm", "window", 30, 7, "black", new HTuple(), new HTuple()); HOperatorSet.DispText(Window, "圆心X轴坐标:" + System.Math.Round(data[0], 4) + " pix", "window", 48, 7, "black", new HTuple(), new HTuple()); HOperatorSet.DispText(Window, "圆心Y轴坐标:" + System.Math.Round(data[1], 4) + " pix", "window", 66, 7, "black", new HTuple(), new HTuple()); #region//释放图像变量 ho_src_image.Dispose(); #endregion }
public static void GlueCheck_C(Bitmap bmp, HWindow window, bool ok, double[] distance) { try { HObject image, img_old; HOperatorSet.GenEmptyObj(out image); HOperatorSet.GenEmptyObj(out img_old); img_old.Dispose(); Bitmap2HObject.Bitmap2HObj(bmp, out img_old); HTuple htuple; HOperatorSet.CountChannels(img_old, out htuple); image.Dispose(); if (htuple == 3) { HOperatorSet.Rgb1ToGray(img_old, out image); } else { image = img_old.Clone(); } HTuple width, height; HOperatorSet.GetImageSize(image, out width, out height); HOperatorSet.SetPart(window, 0, 0, height - 1, width - 1); HOperatorSet.DispObj(image, window); HOperatorSet.SetLineWidth(window, 3); HOperatorSet.SetColor(window, "red"); HOperatorSet.DispText(window, "胶水外边缘最大偏差:" + System.Math.Round(distance[0], 4) + " pix", "window", 30, 7, "black", new HTuple(), new HTuple()); HOperatorSet.DispText(window, "胶水内边缘最大偏差:" + System.Math.Round(distance[1], 4) + " pix", "window", 60, 7, "black", new HTuple(), new HTuple()); HOperatorSet.DispText(window, "胶水外边缘阈值:" + System.Math.Round(Position.Instance.OutsideDistance, 4) + " pix", "window", 90, 7, "black", new HTuple(), new HTuple()); HOperatorSet.DispText(window, "胶水内边缘阈值:" + System.Math.Round(Position.Instance.insideDistance, 4) + " pix", "window", 120, 7, "black", new HTuple(), new HTuple()); HOperatorSet.DispText(window, "胶圈X轴偏移:" + System.Math.Round(distance[2], 4) + " mm", "window", 150, 7, "black", new HTuple(), new HTuple()); HOperatorSet.DispText(window, "胶圈Y轴偏移:" + System.Math.Round(distance[3], 4) + "mm", "window", 180, 7, "black", new HTuple(), new HTuple()); if (ok) { //LastCenterLocateBMP = bmp; SetString(window, "OK", "green", 100); } else { SetString(window, "NG", "red", 100); } } catch { try { SetString(window, "NG", "red", 100); } catch { } Marking.CenterLocateTestSucceed = false; } }
public static void CircularMatch(Bitmap bmp, HWindow window, bool ok) { try { HObject image, img_old; HOperatorSet.GenEmptyObj(out image); HOperatorSet.GenEmptyObj(out img_old); img_old.Dispose(); Bitmap2HObject.Bitmap2HObj(bmp, out img_old); HTuple htuple; HOperatorSet.CountChannels(img_old, out htuple); image.Dispose(); if (htuple == 3) { HOperatorSet.Rgb1ToGray(img_old, out image); } else { image = img_old.Clone(); } HTuple width, height; HOperatorSet.GetImageSize(image, out width, out height); HOperatorSet.SetPart(window, 0, 0, height - 1, width - 1); HOperatorSet.DispObj(image, window); HOperatorSet.SetLineWidth(window, 3); HOperatorSet.SetColor(window, "red"); if (ok) { //LastCenterLocateBMP = bmp; HOperatorSet.DispText(window, "圆心X方向偏差:" + System.Math.Round(Position.Instance.PCB2CCDOffset.X / 96, 4) + " mm", "window", 30, 7, "black", new HTuple(), new HTuple()); HOperatorSet.DispText(window, "圆心Y方向偏差:" + System.Math.Round(Position.Instance.PCB2CCDOffset.Y / 96, 4) + " mm", "window", 60, 7, "black", new HTuple(), new HTuple()); Marking.CenterLocateTestSucceed = true; SetString(window, "OK", "green", 100); } else { SetString(window, "NG", "red", 100); Marking.CenterLocateTestSucceed = false; } } catch { try { SetString(window, "NG", "red", 100); } catch { } Marking.CenterLocateTestSucceed = false; } }
public static void RectangleMatch(Bitmap bmp, HWindow window, bool ok) { try { HObject image, img_old; HOperatorSet.GenEmptyObj(out image); HOperatorSet.GenEmptyObj(out img_old); img_old.Dispose(); Bitmap2HObject.Bitmap2HObj(bmp, out img_old); HTuple htuple; HOperatorSet.CountChannels(img_old, out htuple); image.Dispose(); if (htuple == 3) { HOperatorSet.Rgb1ToGray(img_old, out image); } else { image = img_old.Clone(); } HTuple width, height; HOperatorSet.GetImageSize(image, out width, out height); HOperatorSet.SetPart(window, 0, 0, height - 1, width - 1); HOperatorSet.DispObj(image, window); HOperatorSet.SetLineWidth(window, 3); if (ok) { HOperatorSet.DispText(window, "矩形X方向偏差:" + System.Math.Round(AcqToolEdit.offset_x / 96, 4) + " mm", "window", 30, 7, "black", new HTuple(), new HTuple()); HOperatorSet.DispText(window, "矩形Y方向偏差:" + System.Math.Round(AcqToolEdit.offset_y / 96, 4) + " mm", "window", 50, 7, "black", new HTuple(), new HTuple()); Marking.CenterLocateTestSucceed = true; SetString(window, "OK", "green", 100); } else { SetString(window, "NG", "red", 100); } } catch { try { SetString(window, "NG", "red", 100); } catch { } Marking.CenterLocateTestSucceed = false; } }
private void button1_Click(object sender, EventArgs e) { Acquire(); try { //ho_Image.Dispose(); Bitmap2HObject.Bitmap2HObj(ImageFactory.CreateBitmap(_Subject.OutputImageData), out ho_Image); HOperatorSet.GetImageSize(ho_Image, out hv_Width, out hv_Height); str_imgSize = string.Format("{0}X{1}", hv_Width, hv_Height); HOperatorSet.SetPart(hWindowControl1.HalconWindow, 0, 0, hv_Height - 1, hv_Width - 1); HOperatorSet.DispObj(ho_Image, hWindowControl1.HalconWindow); } catch { MessageBox.Show("无图像"); } }
public CenterLocateParameter(Bitmap bmpin) { InitializeComponent(); bmp = bmpin; Bitmap2HObject.Bitmap2HObj(bmpin, out image); HOperatorSet.GetImageSize(image, out width, out height); HOperatorSet.SetPart(WinCtro_CLP.HalconWindow, 0, 0, height - 1, width - 1); HOperatorSet.DispObj(image, WinCtro_CLP.HalconWindow); tB_x.Text = Convert.ToString(CenterLocate.circleCenter_x); tB_y.Text = Convert.ToString(CenterLocate.circleCenter_y); tB_r.Text = Convert.ToString(CenterLocate.circleRadius); textBox1.Text = Convert.ToString(CenterLocate.threshold_min); textBox2.Text = Convert.ToString(CenterLocate.threshold_max); textBox3.Text = this.Text = Convert.ToString(CenterLocate.eroKernel); textBox4.Text = Convert.ToString(CenterLocate.areaMax); textBox5.Text = Convert.ToString(CenterLocate.areaMin); }
public static void ShowIMg(Bitmap bmp, HWindow window) { try { HObject image = null; HOperatorSet.GenEmptyObj(out image); image.Dispose(); Bitmap2HObject.Bitmap2HObj(bmp, out image); HTuple width, height; HOperatorSet.GetImageSize(image, out width, out height); HOperatorSet.SetPart(window, 0, 0, height - 1, width - 1); HOperatorSet.DispObj(image, window); } catch { } }
public frmGlueCheck(Bitmap bmpin) { InitializeComponent(); Bitmap2HObject.Bitmap2HObj(bmpin, out image); HOperatorSet.GetImageSize(image, out width, out height); str_imgSize = string.Format("{0}X{1}", width, height); HOperatorSet.SetPart(winContr_GCP.HalconWindow, 0, 0, height - 1, width - 1); HOperatorSet.DispObj(image, winContr_GCP.HalconWindow); tB_GlueInnerCircle.Text = Convert.ToString((double)GlueCheck.GlueInnerCircle); tB_GlueWidth.Text = Convert.ToString((double)GlueCheck.GlueWidth); textBox1.Text = Convert.ToString((double)GlueCheck.tol[0]); textBox2.Text = Convert.ToString((double)GlueCheck.area); textBox3.Text = Convert.ToString((double)GlueCheck.kernel); textBox4.Text = Convert.ToString((double)GlueCheck.glueOverflowOutter); textBox5.Text = Convert.ToString((double)GlueCheck.glueOverflowInner); textBox6.Text = Convert.ToString((double)GlueCheck.glueOffset); textBox7.Text = Convert.ToString((double)GlueCheck.glueLackOutter); textBox8.Text = Convert.ToString((double)GlueCheck.glueLackInner); }
public static void PosCheck_C(Bitmap bmp, HWindow window, string[] str) { try { HObject image, img_old; HOperatorSet.GenEmptyObj(out image); HOperatorSet.GenEmptyObj(out img_old); img_old.Dispose(); Bitmap2HObject.Bitmap2HObj(bmp, out img_old); HTuple htuple; HOperatorSet.CountChannels(img_old, out htuple); image.Dispose(); if (htuple == 3) { HOperatorSet.Rgb1ToGray(img_old, out image); } else { image = img_old.Clone(); } HTuple width, height; HOperatorSet.GetImageSize(image, out width, out height); HOperatorSet.SetPart(window, 0, 0, height - 1, width - 1); HOperatorSet.DispObj(image, window); HOperatorSet.SetLineWidth(window, 3); HOperatorSet.SetColor(window, "red"); HTuple font; HOperatorSet.QueryFont(window, out font); HOperatorSet.SetFont(window, font[0] + "-Normal-12"); HOperatorSet.DispText(window, "左上偏差:" + str[0], "window", 30, 7, "blue", new HTuple(), new HTuple()); HOperatorSet.DispText(window, "右上偏差:" + str[1], "window", 50, 7, "blue", new HTuple(), new HTuple()); HOperatorSet.DispText(window, "右下偏差:" + str[2], "window", 70, 7, "blue", new HTuple(), new HTuple()); HOperatorSet.DispText(window, "左下偏差:" + str[3], "window", 90, 7, "blue", new HTuple(), new HTuple()); } catch { log.Debug("PosCheck_C,图像处理异常!"); } }
private void Acquire() { if (_Subject == null) { return; } _Subject.Acquire(); if (SaveImage) { try { ho_Image.Dispose(); Bitmap2HObject.Bitmap2HObj(ImageFactory.CreateBitmap(_Subject.OutputImageData), out ho_Image); if (!Directory.Exists(_filePath)) { Directory.CreateDirectory(_filePath); } //SaveImg($"{_filePath }//{ DateTime.Now.ToString("yy_MM_dd_HH_mm_ss")}.bmp"); SaveImg_JPG($"{_filePath }//{ DateTime.Now.ToString("yy_MM_dd_HH_mm_ss_fff")}.jpg"); } catch {; } } }
public static void GlueCheck_C(Bitmap bmp, HWindow window, bool[] result, double[] data, PointContour[] MaxDisContours) { try { HObject image, img_old; HOperatorSet.GenEmptyObj(out image); HOperatorSet.GenEmptyObj(out img_old); img_old.Dispose(); Bitmap2HObject.Bitmap2HObj(bmp, out img_old); HTuple htuple; HOperatorSet.CountChannels(img_old, out htuple); image.Dispose(); if (htuple == 3) { HOperatorSet.Rgb1ToGray(img_old, out image); } else { image = img_old.Clone(); } HTuple width, height; HOperatorSet.GetImageSize(image, out width, out height); HOperatorSet.SetPart(window, 0, 0, height - 1, width - 1); HOperatorSet.DispObj(image, window); HOperatorSet.SetLineWidth(window, 3); HTuple font; HOperatorSet.QueryFont(window, out font); HOperatorSet.SetFont(window, font[0] + "-Normal-12"); HOperatorSet.DispText(window, "外胶宽偏差:" + data[0].ToString("f3"), "window", 20, 3, "blue", new HTuple(), new HTuple()); HOperatorSet.DispText(window, "内胶宽偏差:" + data[1].ToString("f3"), "window", 40, 3, "blue", new HTuple(), new HTuple()); HOperatorSet.DispText(window, "外接点偏差:" + data[2].ToString("f3"), "window", 60, 3, "blue", new HTuple(), new HTuple()); HOperatorSet.DispText(window, "内接点偏差:" + data[3].ToString("f3"), "window", 80, 3, "blue", new HTuple(), new HTuple()); HObject region; HOperatorSet.SetColor(window, result[0]?"blue":"red"); HOperatorSet.SetLineWidth(window, 1); HOperatorSet.SetDraw(window, "margin"); HTuple row1 = MaxDisContours[0].Y; HTuple column1 = MaxDisContours[0].X; HTuple phi = 0; HTuple Length1 = 100; HTuple Length2 = 100; HOperatorSet.GenRectangle2(out region, row1, column1, phi, Length1, Length2); HOperatorSet.DispObj(region, window); HObject region1; HOperatorSet.SetColor(window, result[1]?"blue":"red"); HOperatorSet.SetLineWidth(window, 1); HOperatorSet.SetDraw(window, "margin"); row1 = MaxDisContours[1].Y; column1 = MaxDisContours[1].X; HOperatorSet.GenRectangle2(out region1, row1, column1, phi, Length1, Length2); HOperatorSet.DispObj(region1, window); HObject region2; HOperatorSet.SetColor(window, result[2]?"blue":"red"); HOperatorSet.SetLineWidth(window, 1); HOperatorSet.SetDraw(window, "margin"); row1 = MaxDisContours[2].Y; column1 = MaxDisContours[2].X; HOperatorSet.GenRectangle2(out region2, row1, column1, phi, Length1, Length2); HOperatorSet.DispObj(region2, window); HObject region3; HOperatorSet.SetColor(window, result[3]?"blue":"red"); HOperatorSet.SetLineWidth(window, 1); HOperatorSet.SetDraw(window, "margin"); row1 = MaxDisContours[3].Y; column1 = MaxDisContours[3].X; HOperatorSet.GenRectangle2(out region3, row1, column1, phi, Length1, Length2); HOperatorSet.DispObj(region3, window); if (result[0] && result[1] && result[2] && result[3]) { SetString(window, "OK", "green", 60); } else { SetString(window, "NG", "red", 60); } } catch { log.Debug("GlueCheck_C,图像处理异常!"); } }
private static bool action(Bitmap bmp_with_no_glue, Bitmap bmp_with_glue, HWindow Window) { try { #region// 声明图像变量 HObject ho_ImageT, ho_ImageF, ho_TransImage; HObject ho_ImageSub, ho_ImageGauss, ho_Regions_R, ho_RegionClosing; HObject ho_RegionOpening1, ho_RegionUnion, ho_Rectangle; HObject ho_RegionDifference, ho_RegionOpening, ho_Regionc; HObject ho_ConnectedRegions, ho_SelectedRegions, ho_RegionFillUp1; HObject ho_RegionErosion, ho_Contours1, ho_Circle_mask_S = null; HObject ho_target_ring = null, ho_target_ring_scale = null; HObject ho_Regions = null, ho_RegionFillUp = null, ho_RegionTrans = null; HObject ho_Contours = null, ho_glueOutterContour = null, ho_glueInnerContour = null; HObject ho_Contour_I_sap = null, ho_Contour_O_sap = null, ho_ContCircle_outter = null; HObject ho_ContCircle_Inner = null, Regionoping = null; HObject SmoothedGlueOutterContour = null, SmoothedGlueInnerContour = null; #endregion #region//初始化图像变量 HOperatorSet.GenEmptyObj(out ho_ImageT); HOperatorSet.GenEmptyObj(out ho_ImageF); HOperatorSet.GenEmptyObj(out ho_TransImage); HOperatorSet.GenEmptyObj(out ho_ImageSub); HOperatorSet.GenEmptyObj(out ho_ImageGauss); HOperatorSet.GenEmptyObj(out ho_Regions_R); HOperatorSet.GenEmptyObj(out ho_RegionClosing); HOperatorSet.GenEmptyObj(out ho_RegionOpening1); HOperatorSet.GenEmptyObj(out ho_RegionUnion); HOperatorSet.GenEmptyObj(out ho_Rectangle); HOperatorSet.GenEmptyObj(out ho_RegionDifference); HOperatorSet.GenEmptyObj(out ho_RegionOpening); HOperatorSet.GenEmptyObj(out ho_Regionc); HOperatorSet.GenEmptyObj(out ho_ConnectedRegions); HOperatorSet.GenEmptyObj(out ho_SelectedRegions); HOperatorSet.GenEmptyObj(out ho_RegionFillUp1); HOperatorSet.GenEmptyObj(out ho_RegionErosion); HOperatorSet.GenEmptyObj(out ho_Contours1); HOperatorSet.GenEmptyObj(out ho_Circle_mask_S); HOperatorSet.GenEmptyObj(out ho_target_ring); HOperatorSet.GenEmptyObj(out ho_target_ring_scale); HOperatorSet.GenEmptyObj(out ho_Regions); HOperatorSet.GenEmptyObj(out ho_RegionFillUp); HOperatorSet.GenEmptyObj(out ho_RegionTrans); HOperatorSet.GenEmptyObj(out ho_Contours); HOperatorSet.GenEmptyObj(out ho_glueOutterContour); HOperatorSet.GenEmptyObj(out ho_glueInnerContour); HOperatorSet.GenEmptyObj(out ho_Contour_I_sap); HOperatorSet.GenEmptyObj(out ho_Contour_O_sap); HOperatorSet.GenEmptyObj(out ho_ContCircle_outter); HOperatorSet.GenEmptyObj(out ho_ContCircle_Inner); HOperatorSet.GenEmptyObj(out Regionoping); #endregion #region// 初始化控制变量 // Local control variables HTuple hv_Width = null, hv_Height = null, hv_WindowHandle = new HTuple(); HTuple hv_RowsF = null, hv_ColsF = null, hv_RowsT = null; HTuple hv_ColsT = null, hv_HomMat2D = null, hv_Points1 = null; HTuple hv_Points2 = null, hv_Number1 = null, hv_Number2 = null; HTuple hv_Row = new HTuple(); HTuple hv_Column = new HTuple(), hv_Radius = new HTuple(); HTuple hv_StartPhi = new HTuple(), hv_EndPhi = new HTuple(); HTuple hv_PointOrder = new HTuple(); //HTuple hv_glueInnerCircle = new HTuple(), hv_glueWidth = new HTuple(); HTuple hv_glueOutterCircle = new HTuple(); HTuple hv_glueCenter = new HTuple(), hv_Row2 = new HTuple(); HTuple hv_Col1 = new HTuple(), hv_Row3 = new HTuple(); HTuple hv_Col2 = new HTuple(), hv_Row_Inner_sampling = new HTuple(); HTuple hv_Col_Inner_sampling = new HTuple(), hv_k = new HTuple(); HTuple hv_i = new HTuple(), hv_Row_Outter_sampling = new HTuple(); HTuple hv_Col_Outter_sampling = new HTuple(), hv_DistanceMin = new HTuple(); HTuple hv_DistanceMax = new HTuple(), hv_glueWidthMin = new HTuple(); HTuple hv_glueWidthMax = new HTuple(), hv_DistanceMin1 = new HTuple(); HTuple hv_DistanceMax1 = new HTuple(), hv_Distance_inner_min = new HTuple(); HTuple hv_Distance_inner_max = new HTuple(), hv_DistanceMin2 = new HTuple(); HTuple hv_DistanceMax2 = new HTuple(), hv_Distance_outter_min = new HTuple(); HTuple hv_Distance_outter_max = new HTuple(), hv_Row_Outter = new HTuple(); HTuple hv_Column_Outter = new HTuple(), hv_Radius_Outter = new HTuple(); HTuple hv_StartPhi1 = new HTuple(), hv_EndPhi1 = new HTuple(); HTuple hv_PointOrder1 = new HTuple(), hv_DistanceMin_Outter = new HTuple(); HTuple hv_DistanceMax_Outter = new HTuple(), hv_Ddistance_Outter = new HTuple(); HTuple hv_Sdistance_Outter = new HTuple(), hv_Row_Inner = new HTuple(); HTuple hv_Column_Inner = new HTuple(), hv_Radius_Inner = new HTuple(); HTuple hv_StartPhi2 = new HTuple(), hv_EndPhi2 = new HTuple(); HTuple hv_PointOrder2 = new HTuple(), hv_DistanceMin_Inner = new HTuple(); HTuple hv_DistanceMax_Inner = new HTuple(), hv_Ddistance_Inner = new HTuple(); HTuple hv_Sdistance_Inner = new HTuple(), hv_Row_glue = new HTuple(); HTuple hv_Col_glue = new HTuple(), hv_Distance_offset = new HTuple(); HTuple hv_Font = new HTuple(); #endregion is_qualified = true; ho_ImageT.Dispose(); Bitmap2HObject.Bitmap2HObj(bmp_with_no_glue, out ho_ImageT); bmp_with_no_glue = null; HObject img_old; HOperatorSet.GenEmptyObj(out img_old); HTuple htuple; //彩色变灰色 HOperatorSet.CountChannels(ho_ImageT, out htuple); img_old.Dispose(); if (htuple == 3) { HOperatorSet.Rgb1ToGray(ho_ImageT, out img_old); ho_ImageT.Dispose(); ho_ImageT = img_old.Clone(); } //CenterLocate.LastCenterLocateBMP.Dispose(); ho_ImageF.Dispose(); Bitmap2HObject.Bitmap2HObj(bmp_with_glue, out ho_ImageF); bmp_with_glue.Dispose(); //彩色变灰色 HOperatorSet.CountChannels(ho_ImageF, out htuple); img_old.Dispose(); if (htuple == 3) { HOperatorSet.Rgb1ToGray(ho_ImageF, out img_old); ho_ImageF.Dispose(); ho_ImageF = img_old.Clone(); } //获取图像的尺寸信息 HOperatorSet.GetImageSize(ho_ImageF, out hv_Width, out hv_Height); //*******************主逻辑 #region//提取特征点,根据特征点求两张图之间的仿射矩阵:HomMat2D,并对齐图像 HOperatorSet.PointsHarris(ho_ImageF, 2.5, 2, 0.08, 2500, out hv_RowsF, out hv_ColsF); HOperatorSet.PointsHarris(ho_ImageT, 2.5, 2, 0.08, 2500, out hv_RowsT, out hv_ColsT); //* 根据特征点求两张图之间的仿射矩阵:HomMat2D HOperatorSet.ProjMatchPointsRansac(ho_ImageT, ho_ImageF, hv_RowsT, hv_ColsT, hv_RowsF, hv_ColsF, "sad", 10, 0, 0, 100, 100, (new HTuple((new HTuple(-0.2)).TupleRad() )).TupleConcat((new HTuple(0.2)).TupleRad()), 10, "gold_standard", 0.2, 0, out hv_HomMat2D, out hv_Points1, out hv_Points2); //*将ImageT进行放射变换以对齐两张图片 ho_TransImage.Dispose(); HOperatorSet.ProjectiveTransImage(ho_ImageT, out ho_TransImage, hv_HomMat2D, "bilinear", "false", "false"); //ho_ImageT.Dispose(); #endregion #region//提取胶圈轮廓 ////将对齐后点胶之后的图片减去点胶之前图片 //ho_ImageSub.Dispose(); //HOperatorSet.SubImage(ho_ImageF, ho_TransImage, out ho_ImageSub, 0.95,110); ////**对相减得到的图片进行处理,提出胶圈轮廓 ////平滑图像 //ho_ImageGauss.Dispose(); ////HOperatorSet.GaussFilter(ho_ImageSub, out ho_ImageGauss, 9); //HOperatorSet.MedianImage(ho_ImageSub, out ho_ImageGauss,"circle", 2.5,"cyclic"); //ho_ImageSub.Dispose(); ////*阈值分割,采用区域生长法,控制参数tol=3, region阈值500000 //ho_Regions_R.Dispose(); //HOperatorSet.Regiongrowing(ho_ImageGauss, out ho_Regions_R, 4, 4, tol, area); //ho_ImageGauss.Dispose(); ////对region进行开运算和闭运算,并合并region //ho_RegionClosing.Dispose(); //HOperatorSet.ClosingCircle(ho_Regions_R, out ho_RegionClosing, 30); //ho_RegionOpening1.Dispose(); //HOperatorSet.OpeningCircle(ho_RegionClosing, out ho_RegionOpening1, 11); //ho_RegionUnion.Dispose(); //HOperatorSet.Union1(ho_RegionOpening1, out ho_RegionUnion); ho_ImageSub.Dispose(); //HOperatorSet.AbsDiffImage(ho_ImageF, ho_TransImage, out ho_ImageSub, GlueFindParam.Instance.abs_diff_image_value); HOperatorSet.SubImage(ho_ImageF, ho_TransImage, out ho_ImageSub, 0.95, 110); try { HOperatorSet.WriteImage(ho_ImageSub, "jpg", 0, "C:\\Sub.jpg"); } catch { } HObject hpowimage, hscareimage; HOperatorSet.GenEmptyObj(out hpowimage); HOperatorSet.GenEmptyObj(out hscareimage); hpowimage.Dispose(); HOperatorSet.PowImage(ho_ImageSub, out hpowimage, 1.0); hscareimage.Dispose(); HOperatorSet.ScaleImageMax(hpowimage, out hscareimage); //**对相减得到的图片进行处理,提出胶圈轮廓 //平滑图像 ho_ImageGauss.Dispose(); //HOperatorSet.GaussFilter(ho_ImageSub, out ho_ImageGauss, 11); HOperatorSet.MedianImage(hscareimage, out ho_ImageGauss, "circle", 2, "cyclic"); ho_ImageSub.Dispose(); //*阈值分割,采用区域生长法,控制参数tol=3, region阈值500000 ho_Regions_R.Dispose(); HOperatorSet.Regiongrowing(ho_ImageGauss, out ho_Regions_R, 4, 4, tol, area); //提取胶圈区域region ho_Rectangle.Dispose(); HOperatorSet.GenRectangle1(out ho_Rectangle, 0, 0, hv_Height, hv_Width); ho_RegionDifference.Dispose(); //HOperatorSet.Difference(ho_Rectangle, ho_RegionUnion, out ho_RegionDifference); HOperatorSet.Difference(ho_Rectangle, ho_Regions_R, out ho_RegionDifference); HOperatorSet.CountObj(ho_RegionDifference, out hv_Number1); ho_RegionOpening.Dispose(); HOperatorSet.OpeningCircle(ho_RegionDifference, out ho_RegionOpening, 30); ho_Regionc.Dispose(); HOperatorSet.ClosingCircle(ho_RegionOpening, out ho_Regionc, 30); ho_ConnectedRegions.Dispose(); HOperatorSet.Connection(ho_Regionc, out ho_ConnectedRegions); ho_SelectedRegions.Dispose(); HOperatorSet.SelectShapeStd(ho_ConnectedRegions, out ho_SelectedRegions, "max_area", 70); ho_RegionFillUp1.Dispose(); HOperatorSet.FillUpShape(ho_SelectedRegions, out ho_RegionFillUp1, "area", 1, 500); ho_RegionErosion.Dispose(); HOperatorSet.ErosionCircle(ho_RegionFillUp1, out ho_RegionErosion, 2.5); ho_Contours1.Dispose(); HOperatorSet.GenContourRegionXld(ho_RegionErosion, out ho_Contours1, "border_holes"); HOperatorSet.CountObj(ho_Contours1, out hv_Number2); #endregion HOperatorSet.QueryFont(Window, out hv_Font); HOperatorSet.SetFont(Window, (hv_Font.TupleSelect(0)) + "-Bold-13"); #region//计算点胶区域内外圆 //*********************** //理论胶圈外圆 hv_glueOutterCircle = hv_glueInnerCircle + hv_glueWidth; //理论胶圈圆心 hv_glueCenter = new HTuple(2); hv_glueCenter[0] = CenterLocate.CenterLoc[1]; hv_glueCenter[1] = CenterLocate.CenterLoc[0]; HObject ho_Cross, ho_cir1, ho_cir2; HOperatorSet.GenEmptyObj(out ho_Cross); HOperatorSet.GenEmptyObj(out ho_cir1); HOperatorSet.GenEmptyObj(out ho_cir2); //xmz 显示 内外圆区域 HOperatorSet.SetColor(Window, "green"); HOperatorSet.SetDraw(Window, "margin");; ho_Cross.Dispose();; HOperatorSet.GenCrossContourXld(out ho_Cross, CenterLocate.CenterLoc[1], CenterLocate.CenterLoc[0], 180, 0.785398); HOperatorSet.DispObj(ho_ImageF, Window); HOperatorSet.DispObj(ho_Cross, Window); ho_cir1.Dispose(); HOperatorSet.GenCircle(out ho_cir1, CenterLocate.CenterLoc[1], CenterLocate.CenterLoc[0], hv_glueInnerCircle); HOperatorSet.DispObj(ho_cir1, Window); ho_cir2.Dispose(); HOperatorSet.GenCircle(out ho_cir2, CenterLocate.CenterLoc[1], CenterLocate.CenterLoc[0], hv_glueOutterCircle); HOperatorSet.DispObj(ho_cir2, Window); //*********************** #endregion #region//检测胶圈是否封闭 if ((int)((new HTuple((new HTuple(hv_Number2.TupleEqual(2))).TupleAnd(new HTuple(hv_Number1.TupleEqual( 1))))).TupleNot()) != 0) { is_qualified = false; //HOperatorSet.DispObj(ho_ImageF, Window); HOperatorSet.SetLineWidth(Window, 2); HOperatorSet.SetColor(Window, "red"); HOperatorSet.DispObj(ho_Contours1, Window); HOperatorSet.DispText(Window, "无胶或胶圈不完整NG", "window", 15, 480, "red", "box", "false"); SetString(Window, "NG", "red", 100); #region ho_ImageT.Dispose(); ho_ImageF.Dispose(); ho_TransImage.Dispose(); ho_ImageSub.Dispose(); ho_ImageGauss.Dispose(); ho_Regions_R.Dispose(); ho_RegionClosing.Dispose(); ho_RegionOpening1.Dispose(); ho_RegionUnion.Dispose(); ho_Rectangle.Dispose(); ho_RegionDifference.Dispose(); ho_RegionOpening.Dispose(); ho_Regionc.Dispose(); ho_ConnectedRegions.Dispose(); ho_SelectedRegions.Dispose(); ho_RegionFillUp1.Dispose(); ho_RegionErosion.Dispose(); ho_Contours1.Dispose(); ho_Circle_mask_S.Dispose(); ho_target_ring.Dispose(); ho_target_ring_scale.Dispose(); ho_Regions.Dispose(); ho_RegionFillUp.Dispose(); ho_RegionTrans.Dispose(); ho_Contours.Dispose(); ho_glueOutterContour.Dispose(); ho_glueInnerContour.Dispose(); ho_Contour_I_sap.Dispose(); ho_Contour_O_sap.Dispose(); ho_ContCircle_outter.Dispose(); ho_ContCircle_Inner.Dispose(); #endregion return(is_qualified); } #endregion #region//胶圈封闭则进一步检查其它指标是否合格 else { #region ho_RegionClosing.Dispose(); HOperatorSet.ClosingCircle(ho_Regions_R, out ho_RegionClosing, kernel); ho_RegionOpening1.Dispose(); HOperatorSet.OpeningCircle(ho_RegionClosing, out ho_RegionOpening1, 15); ho_RegionUnion.Dispose(); HOperatorSet.Union1(ho_RegionOpening1, out ho_RegionUnion); ho_Rectangle.Dispose(); HOperatorSet.GenRectangle1(out ho_Rectangle, 0, 0, hv_Height, hv_Width); ho_RegionDifference.Dispose(); HOperatorSet.Difference(ho_Rectangle, ho_RegionUnion, out ho_RegionDifference ); ho_RegionOpening.Dispose(); HOperatorSet.OpeningCircle(ho_RegionDifference, out ho_RegionOpening, 7); ho_Regionc.Dispose(); HOperatorSet.ClosingCircle(ho_RegionOpening, out ho_Regionc, 9); ho_ConnectedRegions.Dispose(); HOperatorSet.Connection(ho_Regionc, out ho_ConnectedRegions); ho_SelectedRegions.Dispose(); HOperatorSet.SelectShapeStd(ho_ConnectedRegions, out ho_SelectedRegions, "max_area", 70); ho_RegionFillUp1.Dispose(); HOperatorSet.FillUpShape(ho_SelectedRegions, out ho_RegionFillUp1, "area", 1, 20000); ho_RegionErosion.Dispose(); HOperatorSet.ErosionCircle(ho_RegionFillUp1, out ho_RegionErosion, 2.5); ho_Contours.Dispose(); HOperatorSet.GenContourRegionXld(ho_RegionErosion, out ho_Contours, "border_holes"); ho_glueOutterContour.Dispose(); HOperatorSet.SelectObj(ho_Contours, out ho_glueOutterContour, 1); ho_glueInnerContour.Dispose(); HOperatorSet.SelectObj(ho_Contours, out ho_glueInnerContour, 2); HOperatorSet.GetContourXld(ho_glueInnerContour, out hv_Row2, out hv_Col1); HOperatorSet.GetContourXld(ho_glueOutterContour, out hv_Row3, out hv_Col2); hv_Row_Inner_sampling = new HTuple(); hv_Col_Inner_sampling = new HTuple(); hv_k = 0; for (hv_i = 0; (int)hv_i <= (int)((new HTuple(hv_Row2.TupleLength())) - 1); hv_i = (int)hv_i + 50) { if (hv_Row_Inner_sampling == null) { hv_Row_Inner_sampling = new HTuple(); } hv_Row_Inner_sampling[hv_k] = hv_Row2.TupleSelect(hv_i); if (hv_Col_Inner_sampling == null) { hv_Col_Inner_sampling = new HTuple(); } hv_Col_Inner_sampling[hv_k] = hv_Col1.TupleSelect(hv_i); hv_k = hv_k + 1; } if (hv_Row_Inner_sampling == null) { hv_Row_Inner_sampling = new HTuple(); } hv_Row_Inner_sampling[new HTuple(hv_Row_Inner_sampling.TupleLength())] = hv_Row_Inner_sampling.TupleSelect( 0); if (hv_Col_Inner_sampling == null) { hv_Col_Inner_sampling = new HTuple(); } hv_Col_Inner_sampling[new HTuple(hv_Col_Inner_sampling.TupleLength())] = hv_Col_Inner_sampling.TupleSelect( 0); hv_Row_Outter_sampling = new HTuple(); hv_Col_Outter_sampling = new HTuple(); hv_k = 0; for (hv_i = 0; (int)hv_i <= (int)((new HTuple(hv_Row3.TupleLength())) - 1); hv_i = (int)hv_i + 50) { if (hv_Row_Outter_sampling == null) { hv_Row_Outter_sampling = new HTuple(); } hv_Row_Outter_sampling[hv_k] = hv_Row3.TupleSelect(hv_i); if (hv_Col_Outter_sampling == null) { hv_Col_Outter_sampling = new HTuple(); } hv_Col_Outter_sampling[hv_k] = hv_Col2.TupleSelect(hv_i); hv_k = hv_k + 1; } if (hv_Row_Outter_sampling == null) { hv_Row_Outter_sampling = new HTuple(); } hv_Row_Outter_sampling[new HTuple(hv_Row_Outter_sampling.TupleLength())] = hv_Row_Outter_sampling.TupleSelect( 0); if (hv_Col_Outter_sampling == null) { hv_Col_Outter_sampling = new HTuple(); } hv_Col_Outter_sampling[new HTuple(hv_Col_Outter_sampling.TupleLength())] = hv_Col_Outter_sampling.TupleSelect( 0); ho_Contour_I_sap.Dispose(); HOperatorSet.GenContourPolygonXld(out ho_Contour_I_sap, hv_Row_Inner_sampling, hv_Col_Inner_sampling); ho_Contour_O_sap.Dispose(); HOperatorSet.GenContourPolygonXld(out ho_Contour_O_sap, hv_Row_Outter_sampling, hv_Col_Outter_sampling); ho_glueInnerContour.Dispose(); ho_glueInnerContour = ho_Contour_I_sap.CopyObj(1, -1); ho_glueOutterContour.Dispose(); ho_glueOutterContour = ho_Contour_O_sap.CopyObj(1, -1); //*最大最小胶宽 HOperatorSet.DistancePc(ho_glueOutterContour, hv_Row2, hv_Col1, out hv_DistanceMin, out hv_DistanceMax); HOperatorSet.TupleMin(hv_DistanceMin, out hv_glueWidthMin); HOperatorSet.TupleMax(hv_DistanceMin, out hv_glueWidthMax); //*胶水内轮廓离边界的距离最大值最小值 HOperatorSet.DistancePc(ho_glueInnerContour, hv_glueCenter.TupleSelect(0), hv_glueCenter.TupleSelect(1), out hv_DistanceMin1, out hv_DistanceMax1); hv_Distance_inner_min = hv_DistanceMin1 - hv_glueInnerCircle; hv_Distance_inner_max = hv_DistanceMax1 - hv_glueInnerCircle; //*胶水外轮廓离边界的距离最大最小值 HOperatorSet.DistancePc(ho_glueOutterContour, hv_glueCenter.TupleSelect(0), hv_glueCenter.TupleSelect(1), out hv_DistanceMin2, out hv_DistanceMax2); hv_Distance_outter_min = hv_DistanceMin2 - hv_glueOutterCircle; hv_Distance_outter_max = hv_DistanceMax2 - hv_glueOutterCircle; //*用胶轮廓与拟合圆间的最大距离判断缺胶溢胶情况 HOperatorSet.FitCircleContourXld(ho_glueOutterContour, "algebraic", -1, 0, 0, 3, 2, out hv_Row_Outter, out hv_Column_Outter, out hv_Radius_Outter, out hv_StartPhi1, out hv_EndPhi1, out hv_PointOrder1); ho_ContCircle_outter.Dispose(); HOperatorSet.GenCircleContourXld(out ho_ContCircle_outter, hv_Row_Outter, hv_Column_Outter, hv_Radius_Outter, 0, 6.28318, "positive", 1); HOperatorSet.DistancePc(ho_glueOutterContour, hv_Row_Outter, hv_Column_Outter, out hv_DistanceMin_Outter, out hv_DistanceMax_Outter); hv_Ddistance_Outter = hv_DistanceMax_Outter - hv_Radius_Outter; hv_Sdistance_Outter = hv_Radius_Outter - hv_DistanceMin_Outter; HOperatorSet.FitCircleContourXld(ho_glueInnerContour, "algebraic", -1, 0, 0, 3, 2, out hv_Row_Inner, out hv_Column_Inner, out hv_Radius_Inner, out hv_StartPhi2, out hv_EndPhi2, out hv_PointOrder2); ho_ContCircle_Inner.Dispose(); HOperatorSet.GenCircleContourXld(out ho_ContCircle_Inner, hv_Row_Inner, hv_Column_Inner, hv_Radius_Inner, 0, 6.28318, "positive", 1); HOperatorSet.DistancePc(ho_glueInnerContour, hv_Row_Inner, hv_Column_Inner, out hv_DistanceMin_Inner, out hv_DistanceMax_Inner); hv_Ddistance_Inner = hv_Radius_Inner - hv_DistanceMin_Inner; hv_Sdistance_Inner = hv_DistanceMax_Inner - hv_Radius_Inner; //*利用拟合内外胶的圆心的平均值与拟合基准圆的圆心坐标判断偏移情况 hv_Row_glue = (hv_Row_Outter + hv_Row_Inner) / 2; hv_Col_glue = (hv_Column_Outter + hv_Column_Inner) / 2; HOperatorSet.DistancePp(hv_glueCenter.TupleSelect(0), hv_glueCenter.TupleSelect( 1), hv_Row_glue, hv_Col_glue, out hv_Distance_offset); //*算出拟合胶水的宽度 hv_Radius = hv_Radius_Outter - hv_Radius_Inner; //平滑轮廓 HOperatorSet.SmoothContoursXld(ho_glueOutterContour, out SmoothedGlueOutterContour, 5); HOperatorSet.SmoothContoursXld(ho_glueInnerContour, out SmoothedGlueInnerContour, 5); //HOperatorSet.WriteString() #endregion if ((int)(new HTuple(hv_Distance_offset.TupleGreater(glueOffset_))) != 0) { is_qualified = false; HOperatorSet.SetColor(Window, "red"); HOperatorSet.SetLineWidth(Window, 2); HOperatorSet.DispObj(ho_ImageF, Window); HOperatorSet.DispObj(ho_glueOutterContour, Window); HOperatorSet.DispObj(ho_glueInnerContour, Window); //**显示 HOperatorSet.DispText(Window, (("胶离内边界最大 / 最小距离:" + hv_Distance_inner_max) + " / ") + hv_Distance_inner_min, "window", 15, 7, "green", "box", "false"); HOperatorSet.DispText(Window, (("胶离外边界最大 / 最小距离:" + hv_Distance_outter_max) + " / ") + hv_Distance_outter_min, "window", 40, 7, "green", "box", "false"); HOperatorSet.DispText(Window, "内外胶拟合圆宽度:" + hv_Radius, "window", 65, 7, "green", "box", "false"); HOperatorSet.DispText(Window, "最小胶宽度:" + hv_glueWidthMin, "window", 90, 7, "green", "box", "false"); HOperatorSet.DispText(Window, "最大胶宽度:" + hv_glueWidthMax, "window", 115, 7, "green", "box", "false"); HOperatorSet.DispText(Window, "胶偏移距离:" + hv_Distance_offset, "window", 140, 7, "green", "box", "false"); HOperatorSet.DispText(Window, "标准胶宽:" + hv_glueWidth, "window", 165, 7, "green", "box", "false"); HOperatorSet.DispText(Window, "胶圈偏移NG", "window", 40, 400, "red", "box", "false"); SetString(Window, "NG", "red", 100);; #region//释放图像变量 ho_ImageT.Dispose(); ho_ImageF.Dispose(); ho_TransImage.Dispose(); ho_ImageSub.Dispose(); ho_ImageGauss.Dispose(); ho_Regions_R.Dispose(); ho_RegionClosing.Dispose(); ho_RegionOpening1.Dispose(); ho_RegionUnion.Dispose(); ho_Rectangle.Dispose(); ho_RegionDifference.Dispose(); ho_RegionOpening.Dispose(); ho_Regionc.Dispose(); ho_ConnectedRegions.Dispose(); ho_SelectedRegions.Dispose(); ho_RegionFillUp1.Dispose(); ho_RegionErosion.Dispose(); ho_Contours1.Dispose(); ho_Circle_mask_S.Dispose(); ho_target_ring.Dispose(); ho_target_ring_scale.Dispose(); ho_Regions.Dispose(); ho_RegionFillUp.Dispose(); ho_RegionTrans.Dispose(); ho_Contours.Dispose(); ho_glueOutterContour.Dispose(); ho_glueInnerContour.Dispose(); ho_Contour_I_sap.Dispose(); ho_Contour_O_sap.Dispose(); ho_ContCircle_outter.Dispose(); ho_ContCircle_Inner.Dispose(); #endregion return(is_qualified); } else { HOperatorSet.SetColor(Window, "green"); HOperatorSet.SetLineWidth(Window, 2); HOperatorSet.DispObj(ho_ImageF, Window); HOperatorSet.DispObj(ho_glueOutterContour, Window); HOperatorSet.DispObj(ho_glueInnerContour, Window); if ((int)(new HTuple(hv_Distance_outter_max.TupleGreater(glueoverflow_Outter))) != 0) { HOperatorSet.DispText(Window, "外胶溢胶!NG", "window", 15, 400, "red", "box", "false"); is_qualified = false; } if ((int)(new HTuple(((hv_Distance_outter_min.TupleAbs())).TupleGreater(glueLack_Outter))) != 0) { HOperatorSet.DispText(Window, "外胶缺胶!NG", "window", 40, 400, "red", "box", "false"); is_qualified = false; } if ((int)(new HTuple(((hv_Distance_inner_min.TupleAbs())).TupleGreater(glueoverflow_Inner))) != 0) { HOperatorSet.DispText(Window, "内胶溢胶!NG", "window", 65, 400, "red", "box", "false"); is_qualified = false; } if ((int)(new HTuple(hv_Distance_inner_max.TupleGreater(glueLack_Inner))) != 0) { HOperatorSet.DispText(Window, "内胶缺胶!NG", "window", 90, 400, "red", "box", "false"); is_qualified = false; } //if (hv_glueWidthMax > (hv_glueWidth + (glueOverflowOutter + glueOverflowInner) / 2.0)) //{ // HOperatorSet.DispText(Window, "最大胶宽度超出!NG", "window", 115, 400, "red", "box", "false"); // is_qualified = false; //} //if (hv_glueWidthMin < (hv_glueWidth - (glueLackOutter + glueLackInner) / 2.0)) //{ // HOperatorSet.DispText(Window, "最小胶宽度超出!NG", "window", 140, 400, "red", "box", "false"); // is_qualified = false; //} //**显示 HOperatorSet.DispText(Window, (("胶离内边界最大 / 最小距离:" + hv_Distance_inner_max) + " / ") + hv_Distance_inner_min, "window", 15, 7, "green", "box", "false"); HOperatorSet.DispText(Window, (("胶离外边界最大 / 最小距离:" + hv_Distance_outter_max) + " / ") + hv_Distance_outter_min, "window", 40, 7, "green", "box", "false"); HOperatorSet.DispText(Window, "内外胶拟合圆宽度:" + hv_Radius, "window", 65, 7, "green", "box", "false"); HOperatorSet.DispText(Window, "最小胶宽度:" + hv_glueWidthMin, "window", 90, 7, "green", "box", "false"); HOperatorSet.DispText(Window, "最大胶宽度:" + hv_glueWidthMax, "window", 115, 7, "green", "box", "false"); HOperatorSet.DispText(Window, "胶偏移距离:" + hv_Distance_offset, "window", 140, 7, "green", "box", "false"); HOperatorSet.DispText(Window, "标准胶宽:" + hv_glueWidth, "window", 165, 7, "green", "box", "false"); if (is_qualified) { SetString(Window, "OK", "green", 100); } else { SetString(Window, "NG", "red", 100); } #region//释放图像变量 ho_ImageT.Dispose(); ho_ImageF.Dispose(); ho_TransImage.Dispose(); ho_ImageSub.Dispose(); ho_ImageGauss.Dispose(); ho_Regions_R.Dispose(); ho_RegionClosing.Dispose(); ho_RegionOpening1.Dispose(); ho_RegionUnion.Dispose(); ho_Rectangle.Dispose(); ho_RegionDifference.Dispose(); ho_RegionOpening.Dispose(); ho_Regionc.Dispose(); ho_ConnectedRegions.Dispose(); ho_SelectedRegions.Dispose(); ho_RegionFillUp1.Dispose(); ho_RegionErosion.Dispose(); ho_Contours1.Dispose(); ho_Circle_mask_S.Dispose(); ho_target_ring.Dispose(); ho_target_ring_scale.Dispose(); ho_Regions.Dispose(); ho_RegionFillUp.Dispose(); ho_RegionTrans.Dispose(); ho_Contours.Dispose(); ho_glueOutterContour.Dispose(); ho_glueInnerContour.Dispose(); ho_Contour_I_sap.Dispose(); ho_Contour_O_sap.Dispose(); ho_ContCircle_outter.Dispose(); ho_ContCircle_Inner.Dispose(); #endregion return(is_qualified); } } #endregion } catch (HalconException ex) { SetString(Window, "NG", "red", 100); HOperatorSet.DispText(Window, ex.GetErrorMessage(), "window", 100, 0, "red", new HTuple(), new HTuple()); return(false); } }
public static double[] action(Bitmap bmp, HWindow Window) { // 声明图像变量 #region HObject ho_src_image, ho_Circle_mask_S, ho_Circle_mask_L; HObject ho_ImageReduced, ho_target_ring_mask, ho_target_ring; HObject ho_target_ring_scale, ho_Regions, ho_ConnectedRegions; HObject ho_SelectedRegions, ho_RegionErosion, ho_Rectangle; HObject ho_Contours, ho_Cross; #endregion // 声明控制变量 #region HTuple hv_Width = null, hv_Height = null; HTuple hv_Row = null, hv_Column = null; HTuple hv_Row2 = null, hv_Column2 = null; HTuple hv_target_center_X = null, hv_target_center_Y = null; #endregion //初始化图像变量 #region // Initialize local and output iconic variables HOperatorSet.GenEmptyObj(out ho_src_image); HOperatorSet.GenEmptyObj(out ho_Circle_mask_S); HOperatorSet.GenEmptyObj(out ho_Circle_mask_L); HOperatorSet.GenEmptyObj(out ho_ImageReduced); HOperatorSet.GenEmptyObj(out ho_target_ring_mask); HOperatorSet.GenEmptyObj(out ho_target_ring); HOperatorSet.GenEmptyObj(out ho_target_ring_scale); HOperatorSet.GenEmptyObj(out ho_Regions); HOperatorSet.GenEmptyObj(out ho_ConnectedRegions); HOperatorSet.GenEmptyObj(out ho_SelectedRegions); HOperatorSet.GenEmptyObj(out ho_RegionErosion); HOperatorSet.GenEmptyObj(out ho_Rectangle); HOperatorSet.GenEmptyObj(out ho_Contours); HOperatorSet.GenEmptyObj(out ho_Cross); #endregion //**2020-6-18 //识别点胶的环形区域 //读取图片 ho_src_image.Dispose(); Bitmap2HObject.Bitmap2HObj(bmp, out ho_src_image); //获取图片尺寸 HOperatorSet.GetImageSize(ho_src_image, out hv_Width, out hv_Height); //显示图片 HOperatorSet.SetPart(Window, 0, 0, hv_Height - 1, hv_Width - 1); HOperatorSet.DispObj(ho_src_image, Window); //**将点胶区域target_ring粗略划分出来 //创建圆并取得圆环状Region ho_Circle_mask_S.Dispose(); HOperatorSet.GenCircle(out ho_Circle_mask_S, hv_circle_center_x, hv_circle_center_y, hv_circle_radius); ho_Circle_mask_L.Dispose(); HOperatorSet.GenCircle(out ho_Circle_mask_L, hv_circle_center_x, hv_circle_center_y, hv_circle_radius + hv_offset); ho_ImageReduced.Dispose(); HOperatorSet.ReduceDomain(ho_src_image, ho_Circle_mask_S, out ho_ImageReduced ); ho_target_ring_mask.Dispose(); HOperatorSet.Difference(ho_ImageReduced, ho_Circle_mask_L, out ho_target_ring_mask ); ho_target_ring.Dispose(); HOperatorSet.ReduceDomain(ho_ImageReduced, ho_target_ring_mask, out ho_target_ring ); ho_Circle_mask_S.Dispose(); ho_ImageReduced.Dispose(); ho_target_ring_mask.Dispose(); ho_Circle_mask_L.Dispose(); //**精确定位点胶区域 //增强对比度 ho_target_ring_scale.Dispose(); HOperatorSet.ScaleImageMax(ho_target_ring, out ho_target_ring_scale); //阈值划分 ho_Regions.Dispose(); HOperatorSet.Threshold(ho_target_ring_scale, out ho_Regions, hv_threshold_gray_min, hv_threshold_gray_max); //腐蚀,去除“毛边” ho_RegionErosion.Dispose(); HOperatorSet.ErosionCircle(ho_Regions, out ho_RegionErosion, ero); //联通区域 ho_ConnectedRegions.Dispose(); HOperatorSet.Connection(ho_RegionErosion, out ho_ConnectedRegions); //选出面积最大的Region ho_SelectedRegions.Dispose(); HOperatorSet.SelectShape(ho_ConnectedRegions, out ho_SelectedRegions, "area", "and", _areaMin, _areaMax); //求region的最小外接矩形 HOperatorSet.SmallestRectangle1(ho_SelectedRegions, out hv_Row, out hv_Column, out hv_Row2, out hv_Column2); //创建矩形region并取得XLD轮廓,用于显示 ho_Rectangle.Dispose(); HOperatorSet.GenRectangle1(out ho_Rectangle, hv_Row, hv_Column, hv_Row2, hv_Column2); ho_Contours.Dispose(); HOperatorSet.GenContourRegionXld(ho_Rectangle, out ho_Contours, "border"); hv_target_center_X = hv_Column + ((hv_Column2 - hv_Column) / 2); hv_target_center_Y = hv_Row + ((hv_Row2 - hv_Row) / 2); ho_Cross.Dispose(); HOperatorSet.GenCrossContourXld(out ho_Cross, hv_target_center_Y, hv_target_center_X, 180, 0.785398); HOperatorSet.SetLineWidth(Window, 2); HOperatorSet.SetColor(Window, "green"); HOperatorSet.DispObj(ho_Cross, Window); HOperatorSet.DispObj(ho_Contours, Window); //释放图像变量 #region ho_src_image.Dispose(); ho_target_ring.Dispose(); ho_target_ring_scale.Dispose(); ho_Regions.Dispose(); ho_ConnectedRegions.Dispose(); ho_SelectedRegions.Dispose(); ho_RegionErosion.Dispose(); ho_Rectangle.Dispose(); ho_Contours.Dispose(); ho_Cross.Dispose(); #endregion double[] offset = new double[2]; offset[0] = ((hv_target_center_X[0] - (hv_Width[0] / 2)) * 0.0096); offset[1] = -1 * ((hv_target_center_Y[0] - (hv_Height[0] / 2)) * 0.0096); HOperatorSet.DispText(Window, "X方向偏差:" + System.Math.Round(offset[0], 4) + " mm", "window", 12, 7, "black", new HTuple(), new HTuple()); HOperatorSet.DispText(Window, "Y方向偏差:" + System.Math.Round(offset[1], 4) + " mm", "window", 30, 7, "black", new HTuple(), new HTuple()); return(offset); }
/// <summary> /// 圆心模板匹配 /// </summary> /// <param name="window"></param> /// <param name="image"></param> /// <param name="ROIFileName"></param> /// <param name="ModelFileName"></param> /// <returns></returns> public static double[] CenterMatch(Bitmap bmp, HWindow window) { try { HObject image, img_old; HOperatorSet.GenEmptyObj(out image); HOperatorSet.GenEmptyObj(out img_old); img_old.Dispose(); Bitmap2HObject.Bitmap2HObj(bmp, out img_old); HTuple htuple; HOperatorSet.CountChannels(img_old, out htuple); image.Dispose(); if (htuple == 3) { HOperatorSet.Rgb1ToGray(img_old, out image); } else { image = img_old.Clone(); } HTuple width, height; HOperatorSet.GetImageSize(image, out width, out height); HOperatorSet.SetPart(window, 0, 0, height - 1, width - 1); HOperatorSet.DispObj(image, window); HOperatorSet.SetLineWidth(window, 3); HOperatorSet.SetColor(window, "red"); double[] data = TempalteMatch.action(window, image, AppConfig.VisonPath + "\\CenterLocROI.hobj", AppConfig.VisonPath + "\\CenterModle.shm"); if (data[0] == -100 || data[1] == -100) { HOperatorSet.DispText(window, "识别失败", "window", 12, 7, "black", new HTuple(), new HTuple()); try { SetString(window, "NG", "red", 100); } catch { } return(data); } else { CenterLoc[0] = data[0]; CenterLoc[1] = data[1]; HObject ho_Cross = null; HOperatorSet.DispText(window, "X像素:" + System.Math.Round(data[0], 4) + " Y像素:" + System.Math.Round(data[1], 4) + " pixel", "window", 10, 7, "black", new HTuple(), new HTuple()); HOperatorSet.GenEmptyObj(out ho_Cross); ho_Cross.Dispose(); HOperatorSet.GenCrossContourXld(out ho_Cross, data[1], data[0], 180, 0.785398); //data[0] = (data[0] - width / 2) * 0.0096; //data[1] = -1 * ((data[1] - height / 2) * 0.0096); data[0] = (data[0] - width / 2) * Config.Instance.CameraPixelMM_X; data[1] = 1 * ((data[1] - height / 2) * Config.Instance.CameraPixelMM_Y); HOperatorSet.DispObj(ho_Cross, window); HOperatorSet.DispText(window, "X方向偏差:" + System.Math.Round(data[0], 4) + " mm", "window", 30, 7, "black", new HTuple(), new HTuple()); HOperatorSet.DispText(window, "Y方向偏差:" + System.Math.Round(data[1], 4) + " mm", "window", 50, 7, "black", new HTuple(), new HTuple()); Marking.CenterLocateTestSucceed = true; SetString(window, "OK", "green", 100); return(data); } } catch { try { SetString(window, "NG", "red", 100); } catch { } Marking.CenterLocateTestSucceed = false; return(null); } }
//图像处理主逻辑 public static double[] action(Bitmap bmp, HWindow Window, Point3D <double> Needlepos, Point3D <double> CamPos) //图像处理代码 { #region //声明控制变量 HTuple hv_Width = null, hv_Height = null; HTuple hv_target_circle_center_X = null, hv_target_circle_center_Y = null; HTuple hv_Radius = null, hv_StartPhi = null, hv_EndPhi = null; HTuple hv_PointOrder = null; #endregion #region//声明需要用到的图像变量 HObject ho_src_image; HObject ho_circle_mask; HObject ho_target_ROI; HObject ho_ImageGauss, ho_Regions, ho_SelectedRegions, ho_RegionOpening; HObject ho_RegionTrans, ho_Contours, ho_Cross; #endregion #region//初始化将要用到的图像变量 HOperatorSet.GenEmptyObj(out ho_src_image); HOperatorSet.GenEmptyObj(out ho_circle_mask); HOperatorSet.GenEmptyObj(out ho_target_ROI); HOperatorSet.GenEmptyObj(out ho_ImageGauss); HOperatorSet.GenEmptyObj(out ho_Regions); HOperatorSet.GenEmptyObj(out ho_SelectedRegions); HOperatorSet.GenEmptyObj(out ho_RegionOpening); HOperatorSet.GenEmptyObj(out ho_RegionTrans); HOperatorSet.GenEmptyObj(out ho_Contours); HOperatorSet.GenEmptyObj(out ho_Cross); #endregion //将bitmap转换成HObject. Bitmap2HObject.Bitmap2HObj(bmp, out ho_src_image); HWindow hWindow = Window; //获取图片尺寸信息 HOperatorSet.GetImageSize(ho_src_image, out hv_Width, out hv_Height); HOperatorSet.SetPart(hWindow, 0, 0, hv_Height - 1, hv_Width - 1); HOperatorSet.DispObj(ho_src_image, hWindow); //*粗略划分出ROI //圆区域控制参数 ho_circle_mask.Dispose(); HOperatorSet.GenCircle(out ho_circle_mask, hv_circle_center_x, hv_circle_center_y, hv_circle_radius); ho_target_ROI.Dispose(); HOperatorSet.ReduceDomain(ho_src_image, ho_circle_mask, out ho_target_ROI); //去噪 ho_ImageGauss.Dispose(); HOperatorSet.GaussFilter(ho_target_ROI, out ho_ImageGauss, 3); //**阈值分割,采用区域生长法,tol=2, 区域阈值500000 ho_Regions.Dispose(); HOperatorSet.Regiongrowing(ho_ImageGauss, out ho_Regions, 4, 4, 1, areaMin); //选出圆度大于0.7的region ho_SelectedRegions.Dispose(); HOperatorSet.SelectShape(ho_Regions, out ho_SelectedRegions, "circularity", "and", 0.8, 1); //对选出来的region进行开运算,去除“毛刺,杂点” ho_RegionOpening.Dispose(); HOperatorSet.OpeningCircle(ho_SelectedRegions, out ho_RegionOpening, 15); //将region形状转换成圆 ho_RegionTrans.Dispose(); HOperatorSet.ShapeTrans(ho_RegionOpening, out ho_RegionTrans, "outer_circle"); //取得圆的XLD轮廓 ho_Contours.Dispose(); HOperatorSet.GenContourRegionXld(ho_RegionTrans, out ho_Contours, "border"); //用圆拟合XLD轮廓,得到圆心坐标 HOperatorSet.FitCircleContourXld(ho_Contours, "algebraic", -1, 0, 0, 3, 2, out hv_target_circle_center_Y, out hv_target_circle_center_X, out hv_Radius, out hv_StartPhi, out hv_EndPhi, out hv_PointOrder); ho_Cross.Dispose(); HOperatorSet.GenCrossContourXld(out ho_Cross, hv_target_circle_center_Y, hv_target_circle_center_X, 180, 0.785398); HOperatorSet.SetLineWidth(Window, 2); HOperatorSet.SetColor(Window, "red"); HOperatorSet.DispObj(ho_Cross, Window); HOperatorSet.DispObj(ho_Contours, Window); //**圆心坐标到图像中心的距离*像素分辨率 double[] offset = new double[2]; double offset_x = 1 * ((hv_target_circle_center_X[0] - (hv_Width[0] / 2)) * Config.Instance.CameraPixelMM_X); double offset_y = 1 * ((hv_target_circle_center_Y[0] - (hv_Height[0] / 2)) * Config.Instance.CameraPixelMM_Y); HOperatorSet.DispText(Window, "X方向偏差:" + System.Math.Round(offset_x, 4) + " mm", "window", 12, 7, "black", new HTuple(), new HTuple()); HOperatorSet.DispText(Window, "Y方向偏差:" + System.Math.Round(offset_y, 4) + " mm", "window", 30, 7, "black", new HTuple(), new HTuple()); HOperatorSet.DispText(Window, "圆心X轴坐标:" + System.Math.Round((double)(1 * hv_target_circle_center_X[0]), 4) + " pix", "window", 48, 7, "black", new HTuple(), new HTuple()); HOperatorSet.DispText(Window, "圆心Y轴坐标:" + System.Math.Round((double)(1 * hv_target_circle_center_Y[0]), 4) + " pix", "window", 66, 7, "black", new HTuple(), new HTuple()); #region//释放图像变量 ho_src_image.Dispose(); ho_circle_mask.Dispose(); ho_target_ROI.Dispose(); ho_ImageGauss.Dispose(); ho_Regions.Dispose(); ho_SelectedRegions.Dispose(); ho_RegionOpening.Dispose(); ho_RegionTrans.Dispose(); ho_Contours.Dispose(); ho_Cross.Dispose(); #endregion offset[0] = CamPos.X - Needlepos.X - offset_x; offset[1] = CamPos.Y - Needlepos.Y + offset_y; return(offset); }