比较图像与图像处理- WinForms c#

本教程展示了如何使用图像处理技术来计算WinForms c#应用程序中使用LEADTOOLS SDK的两个图像之间的不同相似性度量。

概述
总结 本教程展示了如何在WinForms c#应用程序中使用图像处理来比较图像。
完成时间 30分钟
Visual Studio项目 下载教程项目(12kb)
平台 Windows WinForms c#应用程序
IDE Visual Studio 2017, 2019
开发许可 下载LEADTOOLS

所需的知识

来熟悉创建项目的基本步骤添加引用和设置License教程,在工作之前比较图像与图像处理- WinForms c#教程。

创建项目并添加LEADTOOLS引用

中创建的项目的副本开始添加引用和设置License教程。如果您没有该项目,请按照该教程中的步骤创建它。

所需的参考资料取决于项目的目的。可以通过以下两种方法中的一种或另一种添加引用(但不能同时添加)。

如果使用NuGet引用,本教程需要以下NuGet包:

如果使用本地DLL引用,则需要以下DLL。

dll位于< INSTALL_DIR > \ LEADTOOLS22 \ Bin \ Dotnet4 \ x64

有关应用程序需要哪些DLL文件的完整列表,请参阅与您的应用程序包含的文件

设置License文件

许可证解锁项目所需的特性。它必须在调用任何工具包函数之前设置。有关详细信息,包括针对不同平台的教程,请参阅设置运行时License

有两种类型的运行时许可证:

请注意

中更详细地介绍了添加LEADTOOLS NuGet和本地引用以及设置许可证添加引用和设置License教程。

创建用户界面

随着项目的创建、引用的添加和许可证的设置,编码就可以开始了。

解决方案资源管理器,双击Form1.cs来显示设计师.打开工具箱加上2标签到…的顶端Form1,如下面的截图所示。留下新的名字标签事实就是这样。编辑他们的文本到哪里label1的文本物业说1日图片,label2的文本2图像

工具放置在窗体上部的截图。

添加两个面板在表单的中间,如下所示。的默认名称面板

工具放置在窗体中间部分的截图。

添加五个新的按钮在左下方Form1.参见下表的新按钮的的名字而且文本属性。

的名字 文本
btnLoadFirst 加载第一张图片
btnLoadSecond 加载第二张图片
btnCompare 比较
btnCopy 是结果
btnClearList 明确的结果

添加一个列表框在右边按钮如下所示。的名字列表框lstResult

工具放置在窗体下部的截图。

初始化图像查看器并加载图像

设计好UI后,单击Form1在设计师身上。去Form1属性并双击负载事件来创建负载窗体的事件处理程序。这将显示表单背后的代码。添加使用下面的声明到顶部。

c#
使用系统;使用System.Drawing;使用先;使用System.Windows.Forms;使用Leadtools;使用Leadtools.Codecs;使用Leadtools.Controls;使用Leadtools.ImageProcessing;使用Leadtools.ImageProcessing.Color;使用Leadtools.ImageProcessing.Core;使用Leadtools.ImageProcessing.Effects;

将以下全局变量添加到Form1类。

c#
私人imageview _viewer1;私人imageview _viewer2;私人RasterCodecs _codecs;私人RasterImage _image1;私人RasterImage _image2;

将下面的代码添加到Form1_Load事件处理程序来初始化imageview对象。

c#
私人无效Form1_Load (对象发送器,EventArgs试一试_viewer1 =imageview ();_viewer1。Dock = DockStyle.Fill;_viewer1。BackColor = Color.DarkGray;panel1.Controls.Add (_viewer1);_viewer1.BringToFront ();_viewer1.Zoom (ControlSizeMode。Fit, 1.0, _viewer1.DefaultZoomOrigin);_viewer2 =imageview ();_viewer2。Dock = DockStyle.Fill;_viewer2。BackColor = Color.DarkGray;panel2.Controls.Add (_viewer2);_viewer2.BringToFront ();_viewer2.Zoom (ControlSizeMode。Fit, 1.0, _viewer1.DefaultZoomOrigin);_codecs =RasterCodecs ();(异常交货)MessageBox.Show (ex.ToString ());

使用解决方案资源管理器,导航回Form1设计师。双击两者加载第一张图片而且加载第二张图片按钮,为两者分别创建一个事件处理程序按钮然后打开表单后面的代码。将下面的代码添加到各自的事件处理程序中,以加载两个图像进行比较。

c#
私人无效btnLoadFirst_Click (对象发送器,EventArgs试一试字符串_filePath = GetFilePath();字符串_fileName = Path.GetFileName(_filePath);_image1 = _codecs.Load(_filePath);_viewer1。Image = _image1;label1。文本= $"第一个图像:{_fileName}"(异常交货)MessageBox.Show (ex.ToString ());
c#
私人无效btnLoadSecond_Click (对象发送器,EventArgs试一试字符串_filePath = GetFilePath();字符串_fileName = Path.GetFileName(_filePath);_image2 = _codecs.Load(_filePath);_viewer2。Image = _image2;label2。文本= $"第二张图片:{_fileName}"(异常交货)MessageBox.Show (ex.ToString ());

方法中创建一个新方法Form1类命名GetFilePath ().在上面显示的事件处理程序中调用此方法。添加下面的代码以使用OpeFileDialog选择您想要比较的图像。

c#
私人字符串GetFilePath ()字符串_filePath =OpenFileDialog dlg =OpenFileDialog ();了解地理。InitialDirectory =@“C: \ LEADTOOLS22 \ Resources \图片”如果(了解。ShowDialog () ==对话sult. ok)_filePath = dgl . filename;返回_filePath;

添加图像比较代码

导航回Form1设计器,使用解决方案资源管理器.双击比较复制的结果,明确的结果按钮来创建它们的事件处理程序并打开表单背后的代码。

将下面的代码添加到btnCompare_Click事件处理程序,以运行本教程中用于图像比较的6种图像处理算法中的5种。

c#
私人无效btnCompare_Click (对象发送器,EventArgs如果(_viewer1。形象= =| | _viewer2。形象= =对话框。显示(“请先加载图片”);返回lstResult.Items.Add ("************** 比较……**************");intnewItem;//第一个方法:通过XOR-ing逐像素进行比较使用(RasterImage dstImage = _image2.Clone())LeadRect rc =LeadRect(0,0, _viewer1.Image.)宽度,_viewer1.Image.Height);CombineCommand combine =CombineCommand (_image1 rc,LeadPoint (0, 0),CombineCommandFlags.OperationXor);combine.Run (dstImage);// XOR后,相同像素将显示为黑色。接下来的代码将计算结果图像的黑比//定义一个所有黑色像素的区域dstImage.AddColorToRegion (RasterColor。黑色,RasterRegionCombineMode.Set);//找到黑色区域的面积,除以图像的总面积percentBlack = dstImage. calculateregionarea () * 100.0 / (dstImage. calculateregionarea)。宽度* dstImage.Height);newItem = lstResult.Items.Add(字符串.Format (“比较精确像素:{0:N2}%相同”percentBlack));lstResult。TopIndex = newItem;//制作灰度副本来计算强度值grayscalcommand gray =GrayscaleCommand (8);// Statistics info命令将始终用于查找图像像素的平均值statisticinformationcommand stats =StatisticsInformationCommand (RasterColorChannel。Master, 0, 255);使用(rasterimage2gray = _image2.Clone())使用(rasterimage1gray = _image1.Clone())LeadRect rc =LeadRect(0,0, image2Gray.)宽度,image2Gray.Height);//单独获取强度值,转换为灰度gray.Run (image1Gray);gray.Run (image2Gray);//第二个度量:总体强度值stats.Run (image1Gray);intensityAverage1 = stats.Mean;stats.Run (image2Gray);intensityAverage2 = stats.Mean;AvgSimilarity = 100.0 -(数学。Abs(intensityAverage2 - intensityAverage1) * 100.0 / 255);newItem = lstResult.Items.Add(字符串.Format ("整体图像强度:{0:N2}%相似"AvgSimilarity));lstResult。TopIndex = newItem;//第三种方法:像素强度相似度CombineCommand combine =CombineCommand (image1Gray rc,LeadPoint (0, 0),CombineCommandFlags.AbsoluteDifference);combine.Run (image2Gray);// image2Gray现在有两个图像的强度的减法结果。//平均值将是强度差的平均值stats.Run (image2Gray);pixelsSimilarity = 100.0 -(统计。平均值* 100.0 / 255);newItem = lstResult.Items.Add(字符串.Format (对应像素强度:{0:N2}%相似pixelsSimilarity));lstResult。TopIndex = newItem;//第四个和第五个测量:比较平均色相和平均饱和度//分离颜色以获得色相和饱和度平面colorseparatcommand colorSep =ColorSeparateCommand (ColorSeparateCommandType.Hsv);colorSep.Run (_image1);colorSep.DestinationImage.Page = 1;stats.Run (colorSep.DestinationImage);//存储第一个色调平面的平均值averageHue1 = stats.Mean;//从色相平面移动到第二页的饱和度平面colorSep.DestinationImage.Page = 2;stats.Run (colorSep.DestinationImage);//存储第一个饱和平面的平均值averageSat1 = stats.Mean;//对第二幅图像进行分色colorSep.Run (_image2);colorSep.DestinationImage.Page = 1;stats.Run (colorSep.DestinationImage);//存储第二个图像的色调平面的平均值averageHue2 = stats.Mean;//从色相平面移动到第二页的饱和度平面colorSep.DestinationImage.Page = 2;stats.Run (colorSep.DestinationImage);//存储第二幅图像饱和平面的平均值averageSat2 = stats.Mean;HueDiff =数学。Abs(averageHue1 - averageHue2);//如果一个色调很高,另一个很低,它们实际上是//彼此很接近,因为0在255的旁边如果(HueDiff > 127)HueDiff =数学。Abs(HueDiff - 254);SatDiff =数学。Abs(averageSat1 - averageSat2);husimilarity = (255 - HueDiff) * 100 / 255.0;satSimilarity = (255 - SatDiff) * 100 / 255.0;lstResult.Items.Add (字符串.Format (两个图像的平均色调值:{0:N2}%相似hueSimilarity));newItem = lstResult.Items.Add(字符串.Format (2幅图像的平均饱和度:{0:N2}%相似satSimilarity));lstResult。TopIndex = newItem;//第六种方法:频率内容应该有自己的功能_image2.Clone CompareFrequencyContent (_image1.Clone () ());

对象中添加一个新方法Form1类命名比较频率内容(RasterImage img1, RasterImage img2).的末尾调用此方法btnCompare_Click事件处理程序,如上所示。添加下面的代码,运行第6个图像处理算法,该算法将计算频率内容。

c#
公共无效比较频率内容(RasterImage img1, RasterImage img2)//确保图像大小相同如果((img1。= img1. Width) || (img1. Width)高度!= img2.Height)SizeCommand =SizeCommand(256,256, Leadtools.RasterSizeFlags.Bicubic);sizecommand.Run (img1);sizecommand.Run (img2);//为两个图像使用相同的标志//包含填充标志,以便FFT能够处理非2次方大小的图像fftFlags = FastFourierTransformCommandFlags。FastFourierTransform| FastFourierTransformCommandFlags。灰色| fastfouriertransformcommandflags . padadoptimally;//存放FFT结果的2个数组傅里叶变换信息FTArray1 =FourierTransformInformation (img1 fftFlags);FTArray2 =FourierTransformInformation (img2 fftFlags);//对第一张图像进行FFT处理FastFourierTransformCommand命令=FastFourierTransformCommand (FTArray1 fftFlags);command.Run (img1);//对第二幅图像进行FFT处理命令。傅立叶变换信息= FTArray2;command.Run (img2);//每个频率分量幅值与其对应图像的幅值之差的总和magDiff = 0;//两幅图像中所有频率分量的两个幅值的总和magSum = 0;intdataLen = FTArray1.Data.Length;不安全的//最快的处理方法是使用命令提供的数据指针* pData1 = (*) FTArray1.DataPointer;* pData2 = (*) FTArray2.DataPointer;intI = 0;i < dataLen;+ + i)r1 = *pData1;+ + pData1;i1 = *pData1;+ + pData1;//大小是实部和虚部的平方根mag1 =数学。根号(r1 * r1 + i1 * i1);r2 = *pData2;+ + pData2;i2 = *pData2;+ + pData2;mag2 =数学。√(r2 * r2 + i2 * i2);//计算数量级和magSum += (mag1 + mag2);//计算幅度差异magDiff +=数学。Abs(mag1 - mag2);如果(magSum == 0)magSum = 1;//不除以0= (magSum - magDiff) * 100 / magSum;intnewItem = lstResult.Items.Add(字符串.Format (2幅图像的频率内容:{0:N2}%相似freqSimilarity));lstResult。TopIndex = newItem;img1.Dispose ();img2.Dispose ();

接下来,将下面的代码添加到btnCopy_Click事件处理程序中复制结果列表框到你的剪贴板上。

c#
私人无效btnCopy_Click (对象发送器,EventArgs字符串listText =""foreach字符串三种lstResult.Items)listText += txt + Environment.NewLine;如果(listText = =""返回Clipboard.Clear ();Clipboard.SetText (listText);对话框。显示("结果已复制到剪贴板");

最后,将下面的代码添加到btnClearList_Click事件处理程序来清除列表框

c#
私人无效btnClearList_Click (对象发送器,EventArgslstResult.Items.Clear ();

运行项目

通过按运行项目F5,或选择调试->开始调试

如果正确地执行了这些步骤,应用程序就会运行,表单就会出现。要进行测试,请遵循以下步骤:

  1. 点击加载第一张图片提出OpenFileDialog

  2. 选择要加载的第一个图像。

  3. 重复前面的步骤,但是使用加载第二张图片按钮。

  4. 有了想要比较的2张图片后,单击比较按钮。

    对比结果的窗口截图。

总结

本教程展示了如何使用多种图像处理算法比较两幅图像。

另请参阅

net
iOS
188金宝搏的网址客服|支持|联系我们|知识产权公告
©1991 - 2022领先技术公司版权所有