如何调整图片的大小c#

作为SizeWidthHeightSystem.Drawing.ImageGet()属性 我如何在c#运行时调整图像对象的大小?< / p >

现在,我只是创建了一个新的Image,使用:

// objImage is the original Image
Bitmap objBitmap = new Bitmap(objImage, new Size(227, 171));
670795 次浏览

这个问题中,你会得到一些答案,包括我的:

public Image resizeImage(int newWidth, int newHeight, string stPhotoPath)
{
Image imgPhoto = Image.FromFile(stPhotoPath);


int sourceWidth = imgPhoto.Width;
int sourceHeight = imgPhoto.Height;


//Consider vertical pics
if (sourceWidth < sourceHeight)
{
int buff = newWidth;


newWidth = newHeight;
newHeight = buff;
}


int sourceX = 0, sourceY = 0, destX = 0, destY = 0;
float nPercent = 0, nPercentW = 0, nPercentH = 0;


nPercentW = ((float)newWidth / (float)sourceWidth);
nPercentH = ((float)newHeight / (float)sourceHeight);
if (nPercentH < nPercentW)
{
nPercent = nPercentH;
destX = System.Convert.ToInt16((newWidth -
(sourceWidth * nPercent)) / 2);
}
else
{
nPercent = nPercentW;
destY = System.Convert.ToInt16((newHeight -
(sourceHeight * nPercent)) / 2);
}


int destWidth = (int)(sourceWidth * nPercent);
int destHeight = (int)(sourceHeight * nPercent);




Bitmap bmPhoto = new Bitmap(newWidth, newHeight,
PixelFormat.Format24bppRgb);


bmPhoto.SetResolution(imgPhoto.HorizontalResolution,
imgPhoto.VerticalResolution);


Graphics grPhoto = Graphics.FromImage(bmPhoto);
grPhoto.Clear(Color.Black);
grPhoto.InterpolationMode =
System.Drawing.Drawing2D.InterpolationMode.HighQualityBicubic;


grPhoto.DrawImage(imgPhoto,
new Rectangle(destX, destY, destWidth, destHeight),
new Rectangle(sourceX, sourceY, sourceWidth, sourceHeight),
GraphicsUnit.Pixel);


grPhoto.Dispose();
imgPhoto.Dispose();
return bmPhoto;
}

本遗嘱-

  • 调整宽度和高度,不需要循环
  • 不超过图像的原始尺寸

//////////////

private void ResizeImage(Image img, double maxWidth, double maxHeight)
{
double resizeWidth = img.Source.Width;
double resizeHeight = img.Source.Height;


double aspect = resizeWidth / resizeHeight;


if (resizeWidth > maxWidth)
{
resizeWidth = maxWidth;
resizeHeight = resizeWidth / aspect;
}
if (resizeHeight > maxHeight)
{
aspect = resizeWidth / resizeHeight;
resizeHeight = maxHeight;
resizeWidth = resizeHeight * aspect;
}


img.Width = resizeWidth;
img.Height = resizeHeight;
}

这是我为特定要求编写的代码,即:目的地总是在景观比例。这会给你一个好的开始。

public Image ResizeImage(Image source, RectangleF destinationBounds)
{
RectangleF sourceBounds = new RectangleF(0.0f,0.0f,(float)source.Width, (float)source.Height);
RectangleF scaleBounds = new RectangleF();


Image destinationImage = new Bitmap((int)destinationBounds.Width, (int)destinationBounds.Height);
Graphics graph = Graphics.FromImage(destinationImage);
graph.InterpolationMode =
System.Drawing.Drawing2D.InterpolationMode.HighQualityBicubic;


// Fill with background color
graph.FillRectangle(new SolidBrush(System.Drawing.Color.White), destinationBounds);


float resizeRatio, sourceRatio;
float scaleWidth, scaleHeight;


sourceRatio = (float)source.Width / (float)source.Height;


if (sourceRatio >= 1.0f)
{
//landscape
resizeRatio = destinationBounds.Width / sourceBounds.Width;
scaleWidth = destinationBounds.Width;
scaleHeight = sourceBounds.Height * resizeRatio;
float trimValue = destinationBounds.Height - scaleHeight;
graph.DrawImage(source, 0, (trimValue / 2), destinationBounds.Width, scaleHeight);
}
else
{
//portrait
resizeRatio = destinationBounds.Height/sourceBounds.Height;
scaleWidth = sourceBounds.Width * resizeRatio;
scaleHeight = destinationBounds.Height;
float trimValue = destinationBounds.Width - scaleWidth;
graph.DrawImage(source, (trimValue / 2), 0, scaleWidth, destinationBounds.Height);
}


return destinationImage;


}

在我做的应用程序中,有必要创建一个具有多个选项的函数。它相当大,但它可以调整图像的大小,可以保持纵横比,并可以切割边缘,只返回图像的中心:

/// <summary>
/// Resize image with a directory as source
/// </summary>
/// <param name="OriginalFileLocation">Image location</param>
/// <param name="heigth">new height</param>
/// <param name="width">new width</param>
/// <param name="keepAspectRatio">keep the aspect ratio</param>
/// <param name="getCenter">return the center bit of the image</param>
/// <returns>image with new dimentions</returns>
public Image resizeImageFromFile(String OriginalFileLocation, int heigth, int width, Boolean keepAspectRatio, Boolean getCenter)
{
int newheigth = heigth;
System.Drawing.Image FullsizeImage = System.Drawing.Image.FromFile(OriginalFileLocation);


// Prevent using images internal thumbnail
FullsizeImage.RotateFlip(System.Drawing.RotateFlipType.Rotate180FlipNone);
FullsizeImage.RotateFlip(System.Drawing.RotateFlipType.Rotate180FlipNone);


if (keepAspectRatio || getCenter)
{
int bmpY = 0;
double resize = (double)FullsizeImage.Width / (double)width;//get the resize vector
if (getCenter)
{
bmpY = (int)((FullsizeImage.Height - (heigth * resize)) / 2);// gives the Y value of the part that will be cut off, to show only the part in the center
Rectangle section = new Rectangle(new Point(0, bmpY), new Size(FullsizeImage.Width, (int)(heigth * resize)));// create the section to cut of the original image
//System.Console.WriteLine("the section that will be cut off: " + section.Size.ToString() + " the Y value is minimized by: " + bmpY);
Bitmap orImg = new Bitmap((Bitmap)FullsizeImage);//for the correct effect convert image to bitmap.
FullsizeImage.Dispose();//clear the original image
using (Bitmap tempImg = new Bitmap(section.Width, section.Height))
{
Graphics cutImg = Graphics.FromImage(tempImg);//              set the file to save the new image to.
cutImg.DrawImage(orImg, 0, 0, section, GraphicsUnit.Pixel);// cut the image and save it to tempImg
FullsizeImage = tempImg;//save the tempImg as FullsizeImage for resizing later
orImg.Dispose();
cutImg.Dispose();
return FullsizeImage.GetThumbnailImage(width, heigth, null, IntPtr.Zero);
}
}
else newheigth = (int)(FullsizeImage.Height / resize);//  set the new heigth of the current image
}//return the image resized to the given heigth and width
return FullsizeImage.GetThumbnailImage(width, newheigth, null, IntPtr.Zero);
}

为了更容易访问函数,可以添加一些重载函数:

/// <summary>
/// Resize image with a directory as source
/// </summary>
/// <param name="OriginalFileLocation">Image location</param>
/// <param name="heigth">new height</param>
/// <param name="width">new width</param>
/// <returns>image with new dimentions</returns>
public Image resizeImageFromFile(String OriginalFileLocation, int heigth, int width)
{
return resizeImageFromFile(OriginalFileLocation, heigth, width, false, false);
}


/// <summary>
/// Resize image with a directory as source
/// </summary>
/// <param name="OriginalFileLocation">Image location</param>
/// <param name="heigth">new height</param>
/// <param name="width">new width</param>
/// <param name="keepAspectRatio">keep the aspect ratio</param>
/// <returns>image with new dimentions</returns>
public Image resizeImageFromFile(String OriginalFileLocation, int heigth, int width, Boolean keepAspectRatio)
{
return resizeImageFromFile(OriginalFileLocation, heigth, width, keepAspectRatio, false);
}

现在是最后两个可选设置的布尔值。 像这样调用函数:

System.Drawing.Image ResizedImage = resizeImageFromFile(imageLocation, 800, 400, true, true);

不知道这有什么困难,做你正在做的,使用重载Bitmap构造函数来创建一个重新大小的图像,你唯一缺少的是转换回image数据类型:

public static Image resizeImage(Image imgToResize, Size size)
{
return (Image)(new Bitmap(imgToResize, size));
}


yourImage = resizeImage(yourImage, new Size(50,50));

为什么不使用System.Drawing.Image.GetThumbnailImage方法呢?

public Image GetThumbnailImage(
int thumbWidth,
int thumbHeight,
Image.GetThumbnailImageAbort callback,
IntPtr callbackData)

例子:

Image originalImage = System.Drawing.Image.FromStream(inputStream, true, true);
Image resizedImage = originalImage.GetThumbnailImage(newWidth, (newWidth * originalImage.Height) / originalWidth, null, IntPtr.Zero);
resizedImage.Save(imagePath, ImageFormat.Png);
< p >来源: http://msdn.microsoft.com/en-us/library/system.drawing.image.getthumbnailimage.aspx < / p >

这将执行高质量的调整大小:

/// <summary>
/// Resize the image to the specified width and height.
/// </summary>
/// <param name="image">The image to resize.</param>
/// <param name="width">The width to resize to.</param>
/// <param name="height">The height to resize to.</param>
/// <returns>The resized image.</returns>
public static Bitmap ResizeImage(Image image, int width, int height)
{
var destRect = new Rectangle(0, 0, width, height);
var destImage = new Bitmap(width, height);


destImage.SetResolution(image.HorizontalResolution, image.VerticalResolution);


using (var graphics = Graphics.FromImage(destImage))
{
graphics.CompositingMode = CompositingMode.SourceCopy;
graphics.CompositingQuality = CompositingQuality.HighQuality;
graphics.InterpolationMode = InterpolationMode.HighQualityBicubic;
graphics.SmoothingMode = SmoothingMode.HighQuality;
graphics.PixelOffsetMode = PixelOffsetMode.HighQuality;


using (var wrapMode = new ImageAttributes())
{
wrapMode.SetWrapMode(WrapMode.TileFlipXY);
graphics.DrawImage(image, destRect, 0, 0, image.Width,image.Height, GraphicsUnit.Pixel, wrapMode);
}
}


return destImage;
}
  • wrapMode.SetWrapMode(WrapMode.TileFlipXY)防止图像边界附近的重影——naïve调整大小将采样超出图像边界的透明像素,但通过镜像图像,我们可以得到更好的样本(这个设置非常明显)
  • destImage.SetResolution保持DPI而不管物理大小-可能会增加质量时,减少图像尺寸或打印
  • 合成控制像素如何与背景混合-可能不需要,因为我们只画一个东西。

    保持纵横比是留给读者的练习(实际上,我只是不认为这个函数的工作是为您做这件事)。

    此外,这是一篇好文章描述了图像调整的一些陷阱。上面的函数将涵盖其中的大部分,但你仍然需要担心储蓄

public string CreateThumbnail(int maxWidth, int maxHeight, string path)
{


var image = System.Drawing.Image.FromFile(path);
var ratioX = (double)maxWidth / image.Width;
var ratioY = (double)maxHeight / image.Height;
var ratio = Math.Min(ratioX, ratioY);
var newWidth = (int)(image.Width * ratio);
var newHeight = (int)(image.Height * ratio);
var newImage = new Bitmap(newWidth, newHeight);
Graphics thumbGraph = Graphics.FromImage(newImage);


thumbGraph.CompositingQuality = CompositingQuality.HighQuality;
thumbGraph.SmoothingMode = SmoothingMode.HighQuality;
//thumbGraph.InterpolationMode = InterpolationMode.HighQualityBicubic;


thumbGraph.DrawImage(image, 0, 0, newWidth, newHeight);
image.Dispose();


string fileRelativePath = "newsizeimages/" + maxWidth + Path.GetFileName(path);
newImage.Save(Server.MapPath(fileRelativePath), newImage.RawFormat);
return fileRelativePath;
}

点击这里http://bhupendrasinghsaini.blogspot.in/2014/07/resize-image-in-c.html

public static Image resizeImage(Image image, int new_height, int new_width)
{
Bitmap new_image = new Bitmap(new_width, new_height);
Graphics g = Graphics.FromImage((Image)new_image );
g.InterpolationMode = InterpolationMode.High;
g.DrawImage(image, 0, 0, new_width, new_height);
return new_image;
}

如果你正在使用BitmapSource:

var resizedBitmap = new TransformedBitmap(
bitmapSource,
new ScaleTransform(scaleX, scaleY));

如果你想要更好的控制质量,首先运行这个:

RenderOptions.SetBitmapScalingMode(
bitmapSource,
BitmapScalingMode.HighQuality);

(默认值是BitmapScalingMode.Linear,相当于BitmapScalingMode.LowQuality。)

注意:这将不适用于ASP。因为WebImage依赖于系统。Web,但在以前版本的ASP。我在Net中多次使用了这个片段,它很有用。

String ThumbfullPath = Path.GetFileNameWithoutExtension(file.FileName) + "80x80.jpg";
var ThumbfullPath2 = Path.Combine(ThumbfullPath, fileThumb);
using (MemoryStream stream = new MemoryStream(System.IO.File.ReadAllBytes(fullPath)))
{
var thumbnail = new WebImage(stream).Resize(80, 80);
thumbnail.Save(ThumbfullPath2, "jpg");
}

调整大小并保存图像以适应宽度和高度,就像画布保持图像成比例

using System;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.Drawing.Imaging;
using System.IO;


namespace Infra.Files
{
public static class GenerateThumb
{
/// <summary>
/// Resize and save an image to fit under width and height like a canvas keeping things proportional
/// </summary>
/// <param name="originalImagePath"></param>
/// <param name="thumbImagePath"></param>
/// <param name="newWidth"></param>
/// <param name="newHeight"></param>
public static void GenerateThumbImage(string originalImagePath, string thumbImagePath, int newWidth, int newHeight)
{
Bitmap srcBmp = new Bitmap(originalImagePath);
float ratio = 1;
float minSize = Math.Min(newHeight, newHeight);


if (srcBmp.Width > srcBmp.Height)
{
ratio = minSize / (float)srcBmp.Width;
}
else
{
ratio = minSize / (float)srcBmp.Height;
}


SizeF newSize = new SizeF(srcBmp.Width * ratio, srcBmp.Height * ratio);
Bitmap target = new Bitmap((int)newSize.Width, (int)newSize.Height);


using (Graphics graphics = Graphics.FromImage(target))
{
graphics.CompositingQuality = CompositingQuality.HighSpeed;
graphics.InterpolationMode = InterpolationMode.HighQualityBicubic;
graphics.CompositingMode = CompositingMode.SourceCopy;
graphics.DrawImage(srcBmp, 0, 0, newSize.Width, newSize.Height);


using (MemoryStream memoryStream = new MemoryStream())
{
target.Save(thumbImagePath);
}
}
}
}
}

这个代码与上面的一个答案相同。但将透明像素转换为白色而不是黑色…谢谢:)

    public Image resizeImage(int newWidth, int newHeight, string stPhotoPath)
{
Image imgPhoto = Image.FromFile(stPhotoPath);


int sourceWidth = imgPhoto.Width;
int sourceHeight = imgPhoto.Height;


//Consider vertical pics
if (sourceWidth < sourceHeight)
{
int buff = newWidth;


newWidth = newHeight;
newHeight = buff;
}


int sourceX = 0, sourceY = 0, destX = 0, destY = 0;
float nPercent = 0, nPercentW = 0, nPercentH = 0;


nPercentW = ((float)newWidth / (float)sourceWidth);
nPercentH = ((float)newHeight / (float)sourceHeight);
if (nPercentH < nPercentW)
{
nPercent = nPercentH;
destX = System.Convert.ToInt16((newWidth -
(sourceWidth * nPercent)) / 2);
}
else
{
nPercent = nPercentW;
destY = System.Convert.ToInt16((newHeight -
(sourceHeight * nPercent)) / 2);
}


int destWidth = (int)(sourceWidth * nPercent);
int destHeight = (int)(sourceHeight * nPercent);




Bitmap bmPhoto = new Bitmap(newWidth, newHeight,
PixelFormat.Format24bppRgb);


bmPhoto.SetResolution(imgPhoto.HorizontalResolution,
imgPhoto.VerticalResolution);


Graphics grPhoto = Graphics.FromImage(bmPhoto);
grPhoto.Clear(Color.White);
grPhoto.InterpolationMode =
System.Drawing.Drawing2D.InterpolationMode.HighQualityBicubic;


grPhoto.DrawImage(imgPhoto,
new Rectangle(destX, destY, destWidth, destHeight),
new Rectangle(sourceX, sourceY, sourceWidth, sourceHeight),
GraphicsUnit.Pixel);


grPhoto.Dispose();
imgPhoto.Dispose();


return bmPhoto;
}

使用下面的函数和下面的例子来改变图像大小:

//Example :
System.Net.Mime.MediaTypeNames.Image newImage = System.Net.Mime.MediaTypeNames.Image.FromFile("SampImag.jpg");
System.Net.Mime.MediaTypeNames.Image temImag = FormatImage(newImage, 100, 100);


//image size modification unction
public static System.Net.Mime.MediaTypeNames.Image FormatImage(System.Net.Mime.MediaTypeNames.Image img, int outputWidth, int outputHeight)
{


Bitmap outputImage = null;
Graphics graphics = null;
try
{
outputImage = new Bitmap(outputWidth, outputHeight, System.Drawing.Imaging.PixelFormat.Format16bppRgb555);
graphics = Graphics.FromImage(outputImage);
graphics.DrawImage(img, new Rectangle(0, 0, outputWidth, outputHeight),
new Rectangle(0, 0, img.Width, img.Height), GraphicsUnit.Pixel);


return outputImage;
}
catch (Exception ex)
{
return img;
}
}

你可以尝试net-vips,它是libvips的c#绑定。它是一个懒惰的、流的、需求驱动的图像处理库,所以它可以做这样的操作,而不需要加载整个图像。

例如,它附带了一个方便的图像缩略图:

using Image image = Image.Thumbnail("image.jpg", 300, 300);
image.WriteToFile("my-thumbnail.jpg");

它还支持智能裁剪,这是一种智能确定图像中最重要的部分并在裁剪图像时保持对焦的方法。例如:

using Image image = Image.Thumbnail("owl.jpg", 128, crop: Enums.Interesting.Attention);
image.WriteToFile("tn_owl.jpg");

其中owl.jpg是一个偏离中心的组合:

Owl

给出如下结果:

猫头鹰智能作物

首先,它将图像缩小到垂直轴为128像素,然后使用attention策略将图像裁剪到128像素。这一个搜索图像的特征,可能会抓住人的眼睛,详情见Smartcrop()

下面的函数将返回显示图像的新大小。这在这里可能没有帮助。但它将返回调整大小的显示矩形大小。

 public static  class ResizeImage
{
/// <summary>
/// Return new resized size to display the image
/// </summary>
/// <param name="srcrectanle">source rectangle of image or you can pass the bitmap and set the size accrodingly</param>
/// <param name="initSize">initial size of the page to draw image</param>
/// <returns></returns>
public static SizeF getResizedRectangle(RectangleF srcrectanle, SizeF initSize)
{
float sw = srcrectanle.Width;
float sh = srcrectanle.Height;
float dw = initSize.Width;
float dh = initSize.Height;
float finalHeight, finalWidth;
float Sourceratio = sw / sh;


if (Sourceratio >= 1)
{
finalWidth = (int)dw;
float ratio = sw / dw;
finalHeight = (sh / ratio);
}
else
{
finalHeight = (int)dh;
float ratio = sh / dh;
finalWidth = (sw / ratio);
}
return new SizeF(finalHeight, finalHeight);




}
}