繁体   English   中英

C#中的高性能位图绘图解决方案

[英]High performing Bitmap Drawing solution in c#

我有一个用例,其中需要渲染位图拼贴作为预览。 该应用程序被实现为基于MVC的REST服务,并且我有一个非常普通的实现:

using (var bitmap = new Bitmap((int)maxWidth, (int)maxHeight))
{
using (var graphic = Graphics.FromImage(bitmap))
{
    graphic.InterpolationMode = InterpolationMode.HighQualityBicubic;

    // now again for each mod
    foreach (var mod in mods)
    {
        var frame = frames.First(f => f.Index == mod.FrameIndex);
        var fileInfo = GetFileInfo(mod);
        using (var modImage = Image.FromFile(fileInfo.FullName))
        {
            graphic.DrawImage(modImage, (int)frame.Left, (int)frame.Top);
        }
    }

    bitmap.Save(previewFileName);
}
}

尽管此代码可以正常工作,但性能却很差(尤其是较大的图像)。 我也愿意使用第三方库,我只需要一个性能更快的解决方案。

任何帮助将不胜感激。

更新

为了弄清楚用例,缓存没有帮助。 这些图像由客户上传,然后请求预览所选拼贴。 将图像写入拼贴很慢。

我现在才意识到,您正在按原始大小绘制modImage(因为您使用的是仅包含左坐标和顶坐标的替代)。 如果那是您想要的,那么也可以只使用graphics类的DrawImageUnscaled()-Method,它应该快得多:

    var frame = frames.First(f => f.Index == mod.FrameIndex);
    var fileInfo = GetFileInfo(mod);
    using (var modImage = Image.FromFile(fileInfo.FullName))
    {
        graphic.DrawImageUnscaled(modImage, (int)frame.Left, (int)frame.Top);
    }

图像质量有多重要? 如果需要更快的结果,则应尝试InterpolationMode.NearestNeighbour,这应该快得多,但结果质量会很差。 HeighQualityBicubic(您当前正在使用的)产生最佳结果,但性能最低。

如果您有固定数量的缩略图(类似于Netflix),我将在内存中创建一个缓存以保留缩略图位图。 这甚至可能是静态对象。 生成缩略图后,就不再需要再次生成它。 这比尝试每次寻找更快的锤子来敲击要更清洁。

范例:

if(MyThumbnailImageDictionary["whateverimageId"] != null)
   return (Bitmap)MyThumbnailImageDictionary["whateverimageId"];

如果缩略图是动态的,例如来自用户上传随机图片的缩略图,则此方法将无济于事,因为图像缓存的大小将变得巨大。

您可以使用以下代码来生成Thubnail,但我不确定它会快多少:

 Image image = Image.FromFile(fileName);
 Image thumb = image.GetThumbnailImage(120, 120, ()=>false, IntPtr.Zero);

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM