为什么 IrfanView 说我的 jpg 文件是 png 文件?
Why does IrfanView say my jpg file is a png file?
我的实用程序应该调整 .jpg 或 .png 文件的大小。
它似乎在一个地方工作正常(在工作中,我没有安装 IrfanView)。但是在家里,当我打开 *.jpg 然后保存(调整大小)时,我看到:
然而,在任何一种情况下图像仍然显示正常(无论我是 select "Yes" 还是 "No" 在对话框中。
IOW,我可以加载和保存 jpg 和 png,它们可以这样保存,并且显示良好。但是 IrfanView 声称他们搞砸了。
实际上,我不确定图像是如何保存的;我假设它只是根据扩展名以正确的格式 "behind the scenes" 保存它。无论如何,由于这是一个相当简单的实用程序,我将只显示所有代码:
using System;
using System.Drawing;
using System.IO;
using System.Windows.Forms;
namespace FileResizingUtil
{
public partial class FormFileResizer : Form
{
private Image _imgToResize;
String _originalFilename = String.Empty;
public FormFileResizer()
{
InitializeComponent();
}
private void buttonChooseImage_Click(object sender, EventArgs e)
{
OpenFileDialog ofd = new OpenFileDialog
{
InitialDirectory = "c:\",
Filter = "JPG files (*.jpg)|*.jpg| PNG files (*.png)|*.png", FilterIndex = 2, RestoreDirectory = true
};
if (ofd.ShowDialog() == DialogResult.OK)
{
try
{
_originalFilename = ofd.FileName;
_imgToResize = Image.FromFile(_originalFilename);
}
catch (Exception ex)
{
MessageBox.Show("Error: Could not read file from disk. Original error: " + ex.Message);
}
}
// If made it to here, it must be good
String preamble = labelImgSelected.Text;
labelImgSelected.Text = String.Format("{0}{1}", preamble, _originalFilename);
textBoxOrigHeight.Text = _imgToResize.Height.ToString();
textBoxOrigWidth.Text = _imgToResize.Width.ToString();
buttonApplyPercentageChange.Enabled = true;
//buttonResizeImage.Enabled = true;
}
private void buttonResizeImage_Click(object sender, EventArgs e)
{
// Really large images take awhile, so show an hourglass
Cursor.Current = Cursors.WaitCursor;
try
{
var size = new Size { Height = Convert.ToInt32(textBoxNewHeight.Text), Width = int.Parse(textBoxNewWidth.Text) };
// Two different ways of getting the int val
Image resizedImg = FileResizeUtils.GetResizedImage(_imgToResize, size);
String fileNameSansExtension = Path.GetFileNameWithoutExtension(_originalFilename);
String fileNameExtension = Path.GetExtension(_originalFilename);
String newFilename = String.Format("{0}{1}_{2}{3}", fileNameSansExtension, size.Height, size.Width, fileNameExtension);
// If used a different extension (jpg where the original was png, or vice versa) would the Save be intelligent enough to actually save in the other format?
resizedImg.Save(newFilename);
MessageBox.Show(String.Format("Done! File saved as {0}", newFilename));
Recycle();
}
finally
{
Cursor.Current = Cursors.Default;
}
}
private void Recycle()
{
buttonResizeImage.Enabled = false;
buttonApplyPercentageChange.Enabled = false;
labelImgSelected.Text = "Image selected: ";
textBoxOrigHeight.Text = String.Empty;
textBoxOrigWidth.Text = String.Empty;
// Retain the percentage vals, as it may be that all in a batch need to be the same pair of vals
}
private void buttonApplyPercentageChange_Click(object sender, EventArgs e)
{
int origHeight = _imgToResize.Height;
int origWidth = _imgToResize.Width;
// Two ways to convert the val
double heightFactor = (double)numericUpDownHeight.Value / 100.0;
double widthFactor = Convert.ToDouble(numericUpDownWidth.Value) / 100.0;
if (heightFactor < 0 || widthFactor < 0)
{
// show an error - no negative values allowed- using updown, so that should not be possible
}
var newHeight = Convert.ToInt32(origHeight * heightFactor);
var newWidth = Convert.ToInt32(origWidth * widthFactor);
textBoxNewHeight.Text = newHeight.ToString();
textBoxNewWidth.Text = newWidth.ToString();
buttonResizeImage.Enabled = true;
}
private void textBoxNewHeight_TextChanged(object sender, EventArgs e)
{
EnableResizeButtonIfValidDimensionsEntered();
}
private void EnableResizeButtonIfValidDimensionsEntered()
{
if (String.IsNullOrWhiteSpace(textBoxOrigHeight.Text)) return;
String candidateHeight = textBoxNewHeight.Text;
String candidateWidth = textBoxNewWidth.Text;
int validHeight;
int validWidth;
buttonResizeImage.Enabled = (int.TryParse(candidateHeight, out validHeight)) &&
(int.TryParse(candidateWidth, out validWidth));
}
private void numericUpDownHeight_ValueChanged(object sender, EventArgs e)
{
if (checkBoxRetainRatio.Checked)
{
numericUpDownWidth.Value = numericUpDownHeight.Value;
}
}
private void numericUpDownWidth_ValueChanged(object sender, EventArgs e)
{
if (checkBoxRetainRatio.Checked)
{
numericUpDownHeight.Value = numericUpDownWidth.Value;
}
}
}
}
..和 GUI(就在点击 "Resize Image" 按钮之前:
更新
根据 Eugene Sh.ls 的评论,我将保存方法更改为以下块:
bool success = true;
. . .
if (fileNameExtension != null && fileNameExtension.ToLower().Contains("jpg"))
{
resizedImg.Save(newFilename, ImageFormat.Jpeg);
}
else if (fileNameExtension != null &&
fileNameExtension.ToLower().Contains("png"))
{
resizedImg.Save(newFilename, ImageFormat.Png);
}
else
{
success = false;
}
if (success)
{
MessageBox.Show(String.Format("Done! File saved as {0}", newFilename));
}
else
{
MessageBox.Show("Something went awry. The file was not saved");
}
更新 2
这是我的新代码,实现了建议并支持多种新文件类型:
using System;
using System.Drawing;
using System.Drawing.Imaging;
using System.IO;
using System.Windows.Forms;
namespace FileResizingUtil
{
public partial class FormFileResizer : Form
{
private Image _imgToResize;
String _originalFilename = String.Empty;
public FormFileResizer()
{
InitializeComponent();
}
private void buttonChooseImage_Click(object sender, EventArgs e)
{
OpenFileDialog ofd = new OpenFileDialog
{
InitialDirectory = "c:\",
Filter = "JPG files (*.jpg)|*.jpg| PNG files (*.png)|*.png| BMP files (*.bmp)|*.bmp| TIFF files (*.tiff)|*.png| ICO files (*.ico)|*.ico| EMF files (*.emf)|*.emf| WMF files (*.wmf)|*.wmf",
FilterIndex = 1, RestoreDirectory = true
};
if (ofd.ShowDialog() == DialogResult.OK)
{
try
{
_originalFilename = ofd.FileName;
_imgToResize = Image.FromFile(_originalFilename);
}
catch (Exception ex)
{
MessageBox.Show("Error: Could not read file from disk. Original error: " + ex.Message);
}
}
if (String.IsNullOrWhiteSpace(_originalFilename)) return;
// If made it to here, it must be good
String preamble = labelImgSelected.Text;
labelImgSelected.Text = String.Format("{0}{1}", preamble, _originalFilename);
textBoxOrigHeight.Text = _imgToResize.Height.ToString();
textBoxOrigWidth.Text = _imgToResize.Width.ToString();
buttonApplyPercentageChange.Enabled = true;
}
private void buttonResizeImage_Click(object sender, EventArgs e)
{
bool success = true;
// Really large images take awhile, so show an hourglass
Cursor.Current = Cursors.WaitCursor;
try
{
// Two different ways of getting the int val
var size = new Size { Height = Convert.ToInt32(textBoxNewHeight.Text), Width = int.Parse(textBoxNewWidth.Text) };
Image resizedImg = FileResizeUtils.GetResizedImage(_imgToResize, size);
String fileNameSansExtension = Path.GetFileNameWithoutExtension(_originalFilename);
String fileNameExtension = Path.GetExtension(_originalFilename);
String newFilename = String.Format("{0}{1}_{2}{3}", fileNameSansExtension, size.Height, size.Width, fileNameExtension);
if (fileNameExtension != null && fileNameExtension.ToLower().Contains("jpg"))
{
resizedImg.Save(newFilename, ImageFormat.Jpeg);
}
else if (fileNameExtension != null && fileNameExtension.ToLower().Contains("png"))
{
resizedImg.Save(newFilename, ImageFormat.Png);
}
else if (fileNameExtension != null && fileNameExtension.ToLower().Contains("bmp"))
{
resizedImg.Save(newFilename, ImageFormat.Bmp);
}
else if (fileNameExtension != null && fileNameExtension.ToLower().Contains("ico"))
{
resizedImg.Save(newFilename, ImageFormat.Icon);
}
else if (fileNameExtension != null && fileNameExtension.ToLower().Contains("tiff"))
{
resizedImg.Save(newFilename, ImageFormat.Tiff);
}
else if (fileNameExtension != null && fileNameExtension.ToLower().Contains("emf"))
{
resizedImg.Save(newFilename, ImageFormat.Emf);
}
else if (fileNameExtension != null && fileNameExtension.ToLower().Contains("wmf"))
{
resizedImg.Save(newFilename, ImageFormat.Wmf);
}
else
{
success = false;
}
MessageBox.Show(success
? String.Format("Done! File saved as {0}", newFilename)
: "Something went awry. The file was not saved");
Recycle();
}
finally
{
Cursor.Current = Cursors.Default;
}
}
private void Recycle()
{
buttonResizeImage.Enabled = false;
buttonApplyPercentageChange.Enabled = false;
labelImgSelected.Text = "Image selected: ";
textBoxOrigHeight.Text = String.Empty;
textBoxOrigWidth.Text = String.Empty;
// Retain the percentage vals, as it may be that all in a batch need to be the same pair of vals
}
private void buttonApplyPercentageChange_Click(object sender, EventArgs e)
{
int origHeight = _imgToResize.Height;
int origWidth = _imgToResize.Width;
// Two ways to convert the val
double heightFactor = (double)numericUpDownHeight.Value / 100.0;
double widthFactor = Convert.ToDouble(numericUpDownWidth.Value) / 100.0;
if (heightFactor < 0 || widthFactor < 0)
{
// show an error - no negative values allowed- using updown, so that should not be possible
}
var newHeight = Convert.ToInt32(origHeight * heightFactor);
var newWidth = Convert.ToInt32(origWidth * widthFactor);
textBoxNewHeight.Text = newHeight.ToString();
textBoxNewWidth.Text = newWidth.ToString();
buttonResizeImage.Enabled = true;
}
private void textBoxNewHeight_TextChanged(object sender, EventArgs e)
{
EnableResizeButtonIfValidDimensionsEntered();
}
private void EnableResizeButtonIfValidDimensionsEntered()
{
if (String.IsNullOrWhiteSpace(textBoxOrigHeight.Text)) return;
String candidateHeight = textBoxNewHeight.Text;
String candidateWidth = textBoxNewWidth.Text;
int validHeight;
int validWidth;
buttonResizeImage.Enabled = (int.TryParse(candidateHeight, out validHeight)) &&
(int.TryParse(candidateWidth, out validWidth));
}
private void numericUpDownHeight_ValueChanged(object sender, EventArgs e)
{
if (checkBoxRetainRatio.Checked)
{
numericUpDownWidth.Value = numericUpDownHeight.Value;
}
}
private void numericUpDownWidth_ValueChanged(object sender, EventArgs e)
{
if (checkBoxRetainRatio.Checked)
{
numericUpDownHeight.Value = numericUpDownWidth.Value;
}
}
}
}
来自Image.Save
documentation:
If no encoder exists for the file format of the image, the Portable
Network Graphics (PNG) encoder is used. When you use the Save method
to save a graphic image as a Windows Metafile Format (WMF) or Enhanced
Metafile Format (EMF) file, the resulting file is saved as a Portable
Network Graphics (PNG) file. This behavior occurs because the GDI+
component of the .NET Framework does not have an encoder that you can
use to save files as .wmf or .emf files.
如果要以不同的格式保存,请使用重载的 Save
方法,将格式作为第二个参数:
Save(String, ImageFormat)
大多数图像查看器不使用文件的扩展名来确定文件的类型,而是使用所谓的 "magic numbers" (http://en.wikipedia.org/wiki/Magic_number_(programming)#Magic_numbers_in_files)。他们基本上检查文件的前 X 个字节,这通常是特定图像格式所独有的。
我的猜测是,您使用的库默认将文件保存为 PNG(编辑:请参阅 Eugenes 的回答),而不考虑您放在那里的扩展名。 IrfanView 注意到,幻数和扩展名不匹配,但仍显示默认为幻数的图像。
转到控制台并打印文件。如果它是 PNG 文件,您将看到 PNG 显示并停止。
如果是 JPEG,您会得到很多垃圾,但应该会在顶部看到 EXIF 或 JFIF。最开始是 FF D8
由于 JPEG 和 PNG 具有不同的签名,应用程序可以从内容中区分它们并邀请适当的解码器。
图像应用程序通常根据流的内容而不是扩展名来识别图像类型。
我的实用程序应该调整 .jpg 或 .png 文件的大小。
它似乎在一个地方工作正常(在工作中,我没有安装 IrfanView)。但是在家里,当我打开 *.jpg 然后保存(调整大小)时,我看到:
然而,在任何一种情况下图像仍然显示正常(无论我是 select "Yes" 还是 "No" 在对话框中。
IOW,我可以加载和保存 jpg 和 png,它们可以这样保存,并且显示良好。但是 IrfanView 声称他们搞砸了。
实际上,我不确定图像是如何保存的;我假设它只是根据扩展名以正确的格式 "behind the scenes" 保存它。无论如何,由于这是一个相当简单的实用程序,我将只显示所有代码:
using System;
using System.Drawing;
using System.IO;
using System.Windows.Forms;
namespace FileResizingUtil
{
public partial class FormFileResizer : Form
{
private Image _imgToResize;
String _originalFilename = String.Empty;
public FormFileResizer()
{
InitializeComponent();
}
private void buttonChooseImage_Click(object sender, EventArgs e)
{
OpenFileDialog ofd = new OpenFileDialog
{
InitialDirectory = "c:\",
Filter = "JPG files (*.jpg)|*.jpg| PNG files (*.png)|*.png", FilterIndex = 2, RestoreDirectory = true
};
if (ofd.ShowDialog() == DialogResult.OK)
{
try
{
_originalFilename = ofd.FileName;
_imgToResize = Image.FromFile(_originalFilename);
}
catch (Exception ex)
{
MessageBox.Show("Error: Could not read file from disk. Original error: " + ex.Message);
}
}
// If made it to here, it must be good
String preamble = labelImgSelected.Text;
labelImgSelected.Text = String.Format("{0}{1}", preamble, _originalFilename);
textBoxOrigHeight.Text = _imgToResize.Height.ToString();
textBoxOrigWidth.Text = _imgToResize.Width.ToString();
buttonApplyPercentageChange.Enabled = true;
//buttonResizeImage.Enabled = true;
}
private void buttonResizeImage_Click(object sender, EventArgs e)
{
// Really large images take awhile, so show an hourglass
Cursor.Current = Cursors.WaitCursor;
try
{
var size = new Size { Height = Convert.ToInt32(textBoxNewHeight.Text), Width = int.Parse(textBoxNewWidth.Text) };
// Two different ways of getting the int val
Image resizedImg = FileResizeUtils.GetResizedImage(_imgToResize, size);
String fileNameSansExtension = Path.GetFileNameWithoutExtension(_originalFilename);
String fileNameExtension = Path.GetExtension(_originalFilename);
String newFilename = String.Format("{0}{1}_{2}{3}", fileNameSansExtension, size.Height, size.Width, fileNameExtension);
// If used a different extension (jpg where the original was png, or vice versa) would the Save be intelligent enough to actually save in the other format?
resizedImg.Save(newFilename);
MessageBox.Show(String.Format("Done! File saved as {0}", newFilename));
Recycle();
}
finally
{
Cursor.Current = Cursors.Default;
}
}
private void Recycle()
{
buttonResizeImage.Enabled = false;
buttonApplyPercentageChange.Enabled = false;
labelImgSelected.Text = "Image selected: ";
textBoxOrigHeight.Text = String.Empty;
textBoxOrigWidth.Text = String.Empty;
// Retain the percentage vals, as it may be that all in a batch need to be the same pair of vals
}
private void buttonApplyPercentageChange_Click(object sender, EventArgs e)
{
int origHeight = _imgToResize.Height;
int origWidth = _imgToResize.Width;
// Two ways to convert the val
double heightFactor = (double)numericUpDownHeight.Value / 100.0;
double widthFactor = Convert.ToDouble(numericUpDownWidth.Value) / 100.0;
if (heightFactor < 0 || widthFactor < 0)
{
// show an error - no negative values allowed- using updown, so that should not be possible
}
var newHeight = Convert.ToInt32(origHeight * heightFactor);
var newWidth = Convert.ToInt32(origWidth * widthFactor);
textBoxNewHeight.Text = newHeight.ToString();
textBoxNewWidth.Text = newWidth.ToString();
buttonResizeImage.Enabled = true;
}
private void textBoxNewHeight_TextChanged(object sender, EventArgs e)
{
EnableResizeButtonIfValidDimensionsEntered();
}
private void EnableResizeButtonIfValidDimensionsEntered()
{
if (String.IsNullOrWhiteSpace(textBoxOrigHeight.Text)) return;
String candidateHeight = textBoxNewHeight.Text;
String candidateWidth = textBoxNewWidth.Text;
int validHeight;
int validWidth;
buttonResizeImage.Enabled = (int.TryParse(candidateHeight, out validHeight)) &&
(int.TryParse(candidateWidth, out validWidth));
}
private void numericUpDownHeight_ValueChanged(object sender, EventArgs e)
{
if (checkBoxRetainRatio.Checked)
{
numericUpDownWidth.Value = numericUpDownHeight.Value;
}
}
private void numericUpDownWidth_ValueChanged(object sender, EventArgs e)
{
if (checkBoxRetainRatio.Checked)
{
numericUpDownHeight.Value = numericUpDownWidth.Value;
}
}
}
}
..和 GUI(就在点击 "Resize Image" 按钮之前:
更新
根据 Eugene Sh.ls 的评论,我将保存方法更改为以下块:
bool success = true;
. . .
if (fileNameExtension != null && fileNameExtension.ToLower().Contains("jpg"))
{
resizedImg.Save(newFilename, ImageFormat.Jpeg);
}
else if (fileNameExtension != null &&
fileNameExtension.ToLower().Contains("png"))
{
resizedImg.Save(newFilename, ImageFormat.Png);
}
else
{
success = false;
}
if (success)
{
MessageBox.Show(String.Format("Done! File saved as {0}", newFilename));
}
else
{
MessageBox.Show("Something went awry. The file was not saved");
}
更新 2
这是我的新代码,实现了建议并支持多种新文件类型:
using System;
using System.Drawing;
using System.Drawing.Imaging;
using System.IO;
using System.Windows.Forms;
namespace FileResizingUtil
{
public partial class FormFileResizer : Form
{
private Image _imgToResize;
String _originalFilename = String.Empty;
public FormFileResizer()
{
InitializeComponent();
}
private void buttonChooseImage_Click(object sender, EventArgs e)
{
OpenFileDialog ofd = new OpenFileDialog
{
InitialDirectory = "c:\",
Filter = "JPG files (*.jpg)|*.jpg| PNG files (*.png)|*.png| BMP files (*.bmp)|*.bmp| TIFF files (*.tiff)|*.png| ICO files (*.ico)|*.ico| EMF files (*.emf)|*.emf| WMF files (*.wmf)|*.wmf",
FilterIndex = 1, RestoreDirectory = true
};
if (ofd.ShowDialog() == DialogResult.OK)
{
try
{
_originalFilename = ofd.FileName;
_imgToResize = Image.FromFile(_originalFilename);
}
catch (Exception ex)
{
MessageBox.Show("Error: Could not read file from disk. Original error: " + ex.Message);
}
}
if (String.IsNullOrWhiteSpace(_originalFilename)) return;
// If made it to here, it must be good
String preamble = labelImgSelected.Text;
labelImgSelected.Text = String.Format("{0}{1}", preamble, _originalFilename);
textBoxOrigHeight.Text = _imgToResize.Height.ToString();
textBoxOrigWidth.Text = _imgToResize.Width.ToString();
buttonApplyPercentageChange.Enabled = true;
}
private void buttonResizeImage_Click(object sender, EventArgs e)
{
bool success = true;
// Really large images take awhile, so show an hourglass
Cursor.Current = Cursors.WaitCursor;
try
{
// Two different ways of getting the int val
var size = new Size { Height = Convert.ToInt32(textBoxNewHeight.Text), Width = int.Parse(textBoxNewWidth.Text) };
Image resizedImg = FileResizeUtils.GetResizedImage(_imgToResize, size);
String fileNameSansExtension = Path.GetFileNameWithoutExtension(_originalFilename);
String fileNameExtension = Path.GetExtension(_originalFilename);
String newFilename = String.Format("{0}{1}_{2}{3}", fileNameSansExtension, size.Height, size.Width, fileNameExtension);
if (fileNameExtension != null && fileNameExtension.ToLower().Contains("jpg"))
{
resizedImg.Save(newFilename, ImageFormat.Jpeg);
}
else if (fileNameExtension != null && fileNameExtension.ToLower().Contains("png"))
{
resizedImg.Save(newFilename, ImageFormat.Png);
}
else if (fileNameExtension != null && fileNameExtension.ToLower().Contains("bmp"))
{
resizedImg.Save(newFilename, ImageFormat.Bmp);
}
else if (fileNameExtension != null && fileNameExtension.ToLower().Contains("ico"))
{
resizedImg.Save(newFilename, ImageFormat.Icon);
}
else if (fileNameExtension != null && fileNameExtension.ToLower().Contains("tiff"))
{
resizedImg.Save(newFilename, ImageFormat.Tiff);
}
else if (fileNameExtension != null && fileNameExtension.ToLower().Contains("emf"))
{
resizedImg.Save(newFilename, ImageFormat.Emf);
}
else if (fileNameExtension != null && fileNameExtension.ToLower().Contains("wmf"))
{
resizedImg.Save(newFilename, ImageFormat.Wmf);
}
else
{
success = false;
}
MessageBox.Show(success
? String.Format("Done! File saved as {0}", newFilename)
: "Something went awry. The file was not saved");
Recycle();
}
finally
{
Cursor.Current = Cursors.Default;
}
}
private void Recycle()
{
buttonResizeImage.Enabled = false;
buttonApplyPercentageChange.Enabled = false;
labelImgSelected.Text = "Image selected: ";
textBoxOrigHeight.Text = String.Empty;
textBoxOrigWidth.Text = String.Empty;
// Retain the percentage vals, as it may be that all in a batch need to be the same pair of vals
}
private void buttonApplyPercentageChange_Click(object sender, EventArgs e)
{
int origHeight = _imgToResize.Height;
int origWidth = _imgToResize.Width;
// Two ways to convert the val
double heightFactor = (double)numericUpDownHeight.Value / 100.0;
double widthFactor = Convert.ToDouble(numericUpDownWidth.Value) / 100.0;
if (heightFactor < 0 || widthFactor < 0)
{
// show an error - no negative values allowed- using updown, so that should not be possible
}
var newHeight = Convert.ToInt32(origHeight * heightFactor);
var newWidth = Convert.ToInt32(origWidth * widthFactor);
textBoxNewHeight.Text = newHeight.ToString();
textBoxNewWidth.Text = newWidth.ToString();
buttonResizeImage.Enabled = true;
}
private void textBoxNewHeight_TextChanged(object sender, EventArgs e)
{
EnableResizeButtonIfValidDimensionsEntered();
}
private void EnableResizeButtonIfValidDimensionsEntered()
{
if (String.IsNullOrWhiteSpace(textBoxOrigHeight.Text)) return;
String candidateHeight = textBoxNewHeight.Text;
String candidateWidth = textBoxNewWidth.Text;
int validHeight;
int validWidth;
buttonResizeImage.Enabled = (int.TryParse(candidateHeight, out validHeight)) &&
(int.TryParse(candidateWidth, out validWidth));
}
private void numericUpDownHeight_ValueChanged(object sender, EventArgs e)
{
if (checkBoxRetainRatio.Checked)
{
numericUpDownWidth.Value = numericUpDownHeight.Value;
}
}
private void numericUpDownWidth_ValueChanged(object sender, EventArgs e)
{
if (checkBoxRetainRatio.Checked)
{
numericUpDownHeight.Value = numericUpDownWidth.Value;
}
}
}
}
来自Image.Save
documentation:
If no encoder exists for the file format of the image, the Portable Network Graphics (PNG) encoder is used. When you use the Save method to save a graphic image as a Windows Metafile Format (WMF) or Enhanced Metafile Format (EMF) file, the resulting file is saved as a Portable Network Graphics (PNG) file. This behavior occurs because the GDI+ component of the .NET Framework does not have an encoder that you can use to save files as .wmf or .emf files.
如果要以不同的格式保存,请使用重载的 Save
方法,将格式作为第二个参数:
Save(String, ImageFormat)
大多数图像查看器不使用文件的扩展名来确定文件的类型,而是使用所谓的 "magic numbers" (http://en.wikipedia.org/wiki/Magic_number_(programming)#Magic_numbers_in_files)。他们基本上检查文件的前 X 个字节,这通常是特定图像格式所独有的。
我的猜测是,您使用的库默认将文件保存为 PNG(编辑:请参阅 Eugenes 的回答),而不考虑您放在那里的扩展名。 IrfanView 注意到,幻数和扩展名不匹配,但仍显示默认为幻数的图像。
转到控制台并打印文件。如果它是 PNG 文件,您将看到 PNG 显示并停止。
如果是 JPEG,您会得到很多垃圾,但应该会在顶部看到 EXIF 或 JFIF。最开始是 FF D8
由于 JPEG 和 PNG 具有不同的签名,应用程序可以从内容中区分它们并邀请适当的解码器。
图像应用程序通常根据流的内容而不是扩展名来识别图像类型。