我有一个图像大小调整程序,它可以工作。问题是当用户在文件选择对话框中选择非图像文件时,它会崩溃。如何检查图像文件?
5 回答
这是0xA3 的答案的 VB.NET 等价物,因为 OP 坚持使用 VB 版本。
Function IsValidImage(filename As String) As Boolean
Try
Dim img As System.Drawing.Image = System.Drawing.Image.FromFile(filename)
Catch generatedExceptionName As OutOfMemoryException
' Image.FromFile throws an OutOfMemoryException
' if the file does not have a valid image format or
' GDI+ does not support the pixel format of the file.
'
Return False
End Try
Return True
End Function
您可以按如下方式使用它:
If IsValidImage("c:\path\to\your\file.ext") Then
'do something
'
Else
'do something else
'
End If
编辑:
我不建议您检查文件扩展名。任何人都可以使用扩展名保存不同的文件(例如文本文档),.jpg
并诱使您的应用程序相信它是图像。
最好的方法是使用上面的函数加载图像或打开前几个字节并检查 JPEG 签名。
您可以在此处找到有关 JPEG 文件及其标题的更多信息:
一个非常原始的检查是简单地尝试加载图像。如果它无效,OutOfMemoryException
将抛出:
static bool IsImageValid(string filename)
{
try
{
System.Drawing.Image img = System.Drawing.Image.FromFile(filename);
}
catch (OutOfMemoryException)
{
// Image.FromFile throws an OutOfMemoryException
// if the file does not have a valid image format or
// GDI+ does not support the pixel format of the file.
//
return false;
}
return true;
}
如果我正确理解了您的问题,您的应用程序无论如何都会加载图像。因此,简单地将加载操作包装在 try/catch 块中并不意味着任何额外的开销。对于这种方法的 VB.NET 解决方案,请检查@Alex Essilfie 的答案。
想知道为什么Image.FromFile
对无效文件抛出 OOM 的人应该阅读Hans Passant对以下问题的回答:
当然,您的第一道防线只是检查文件的扩展名:
Function IsImageFile(ByVal filename As String) As Boolean
Dim ext As String = Path.GetExtension(filename).ToLowerInvariant()
' This supposes your program can deal only with JPG files; '
' you could add other extensions here as necessary. '
Return ext = ".jpg" OrElse ext = ".jpeg"
End Function
更好的是,正如 SLC 在评论中建议的那样,设置对话框的Filter
属性:
dialog.Filter = "Image files|*.jpg;*.jpeg"
这不是保证 - 理想情况下,您希望检查文件本身以验证它是图像,理论上,如果它们实际上是图像文件,您也应该能够加载具有异常扩展名的文件(也许只是要求首先是用户的确认)——但这是一个简单的开始。
VB 和 C# 的答案很好,但如果您打算更改或移动文件,也包含一个“陷阱”:创建的“img”对象将锁定图像文件,除非调用 dispose() 方法来释放它。见下文:
VB
Function IsValidImage(filename As String) As Boolean
Try
Dim img As System.Drawing.Image = System.Drawing.Image.FromFile(filename)
img.dispose() ' Removes file-lock of IIS
Catch generatedExceptionName As OutOfMemoryException
' Image.FromFile throws an OutOfMemoryException
' if the file does not have a valid image format or
' GDI+ does not support the pixel format of the file.
'
Return False
End Try
Return True
End Function
C#
static bool IsImageValid(string filename)
{
try
{
System.Drawing.Image img = System.Drawing.Image.FromFile(filename);
img.dispose(); // Removes file-lock of IIS
}
catch (OutOfMemoryException)
{
// Image.FromFile throws an OutOfMemoryException
// if the file does not have a valid image format or
// GDI+ does not support the pixel format of the file.
//
return false;
}
return true;
}
最可靠的方法是了解您需要加载的文件的签名。
例如,JPEG 具有特定的标题格式。
这样,如果您只查看扩展名,您的代码就不会那么容易被愚弄。
163 的答案应该让你在这些方面得到最大程度的帮助。