作者:mobiledu2502897207 | 来源:互联网 | 2023-05-22 16:39
我有一个BGR格式和分辨率1920*1200的位图,并希望在不更改pixelformat的情况下缩放它.
private Bitmap rescale(Size size, Bitmap origin)
{
Bitmap scaled = new Bitmap(origin, size);
return scaled;
}
问题是,缩放结果是一个RGBA位图(所有alphas都在255),这对我来说不仅无用,而且后来我在不同的图像上做AbsDiff(来自EMGU)然后, alpha值总是为零.有没有办法在缩放时不改变pixelformat或者在没有alpha值的情况下进行AbsDiff?因为像这样,当我稍后加载图像时,它是不可见的..
1> Hans Passant..:
Bitmap scaled = new Bitmap(origin, size);
构造函数调用中内置了许多隐式假设.你会得到:
具有32bppPArgb像素格式的位图.它可以帮助程序员陷入成功之中,它是现代PC上最优的像素格式.与视频适配器帧缓冲区的像素格式兼容,可以在没有任何转换的情况下进行blitting.它比其他所有的快十倍.
分辨率设置为视频适配器DPI.这通常不太理想,尽管很难说它应该在重新缩放之后使用源图像的分辨率.您可能想要修改它.
透明的背景.如果源位图具有透明度或者具有将alpha通道设置为值<255的像素,那么这很重要.通常很好,如果源位图是透明的,那么新的位图也是如此.使用alpha不太好,重新缩放位图很可能会对此产生负面影响.因人而异.
源图像的双线性插值.这是相当适度的,你可能更喜欢InterpolationMode.HighQualityBicubic以获得更好的结果,特别是当你缩小它超过50%时.或者NearestNeighbor如果速度是你关心的或者源图像非常小而你放大它的目的是保持像素可见.
很明显,你不高兴,第一颗子弹是你投诉的来源.用可调整的所有细节写出来:
public static Bitmap RescaleImage(Image source, Size size) {
// 1st bullet, pixel format
var bmp = new Bitmap(size.Width, size.Height, source.PixelFormat);
// 2nd bullet, resolution
bmp.SetResolution(source.HorizontalResolution, source.VerticalResolution);
using (var gr = Graphics.FromImage(bmp)) {
// 3rd bullet, background
gr.Clear(Color.Transparent);
// 4th bullet, interpolation
gr.InterpolatiOnMode= System.Drawing.Drawing2D.InterpolationMode.HighQualityBicubic;
gr.DrawImage(source, new Rectangle(0, 0, size.Width, size.Height));
}
return bmp;
}
-
2> thegentlecat..:
(我承认有点难看)我会这样做的方法是用原始的Pixelformat和新的Size创建一个新的Bitmap并将原始位图绘制到它上面(未经测试):
private Bitmap rescale(Size size, Bitmap origin)
{
Bitmap rescaled = new Bitmap(size.Width, size.Height, origin.PixelFormat);
using(Graphics g = Graphics.FromImage(rescaled))
{
g.DrawImage(origin, 0, 0, size.Width, size.Height);
}
return rescaled;
}