比较Word文件中的图片和文件夹中的图片?
问题的出现原因是需要比较Microsoft Word文档中的图片和文件夹中的图片是否相同。解决方法是将文档中的图片表示为位图实例,然后逐像素地与文件夹中的位图实例进行比较。比较的过程包括将内联形状复制到剪贴板中,并将其转换为位图,然后按大小和像素逐个比较。
以下是一个示例的C#控制台应用程序,使用.NET 4.5,Microsoft Office对象库版本15.0和Microsoft Word对象库版本15.0实现:
using System; using System.Drawing; using System.Threading; using System.Windows.Forms; using Application = Microsoft.Office.Interop.Word.Application; namespace WordDocStats { class Program { static void Main() { var wordApplication = new Application(); var document = wordApplication.Documents.Open(@"C:\Users\Username\Documents\document.docx"); var bitmapToCompareAgainst = new Bitmap(@"C:\Users\Username\Documents\image.png"); for (var i = 1; i <= wordApplication.ActiveDocument.InlineShapes.Count; i++) { var inlineShapeId = i; var thread = new Thread(() => CompareInlineShapeAndBitmap(inlineShapeId, bitmapToCompareAgainst, wordApplication)); thread.SetApartmentState(ApartmentState.STA); thread.Start(); thread.Join(); } wordApplication.Quit(); Console.ReadLine(); } protected static void CompareInlineShapeAndBitmap(int inlineShapeId, Bitmap bitmapToCompareAgainst, Application wordApplication) { var inlineShape = wordApplication.ActiveDocument.InlineShapes[inlineShapeId]; inlineShape.Select(); wordApplication.Selection.Copy(); if (Clipboard.GetDataObject() != null) { var data = Clipboard.GetDataObject(); if (data != null && data.GetDataPresent(DataFormats.Bitmap)) { var image = (Image)data.GetData(DataFormats.Bitmap, true); var currentBitmap = new Bitmap(image); var imagesAreEqual = true; if(currentBitmap.Width == bitmapToCompareAgainst.Width && currentBitmap.Height == bitmapToCompareAgainst.Height) { for (var i = 0; i < currentBitmap.Width; i++) { if(!imagesAreEqual) break; for (var j = 0; j < currentBitmap.Height; j++) { if (currentBitmap.GetPixel(i, j).Equals(bitmapToCompareAgainst.GetPixel(i, j))) continue; imagesAreEqual = false; break; } } } else { imagesAreEqual = false; } Console.WriteLine("Inline shape #{0} is equal to the 'external' bitmap: {1}", inlineShapeId, imagesAreEqual); } else { Console.WriteLine("Clipboard data is not in an image format"); } } else { Console.WriteLine("Clipboard is empty"); } } } }
参考:
- Threadstart with params: https://stackoverflow.com/a/1195915/700926
- Extracting inline shapes as images from word in C#: https://stackoverflow.com/a/7937590/700926
- Comparing images in C#: http://www.c-sharpcorner.com/uploadfile/prathore/image-comparison-using-C-Sharp/
- Details on how to retrieve an image from the clipboard in C#: https://stackoverflow.com/a/998825/700926
- Details on how to access the clipboard from C#: https://stackoverflow.com/a/518724/700926