【问题标题】:Saving a TransformedBitmap Object to disk.将 TransformedBitmap 对象保存到磁盘。
【发布时间】:2011-04-09 05:05:42
【问题描述】:

在 WPF 和 C# 中工作,我有一个 TransformedBitmap 对象:

  1. 需要作为位图类型的文件保存到磁盘(理想情况下,我将允许用户选择是否将其保存为 BMP、JPG、TIF 等,不过,我还没有到那个阶段... )
  2. 需要转换为 BitmapImage 对象,因为我知道如何从 BitmapImage 对象获取 byte[]。

不幸的是,在这一点上,我真的很难完成这两件事中的任何一件。

谁能提供任何帮助或指出我可能遗漏的任何方法?

【问题讨论】:

标签: c# wpf image bitmap save


【解决方案1】:

您所有的编码器都使用BitmapFrame 类来创建将添加到编码器的Frames 集合属性中的帧。 BitmapFrame.Create 方法有多种重载,其中之一接受BitmapSource 类型的参数。所以我们知道TransformedBitmap 继承自BitmapSource,我们可以将它作为参数传递给BitmapFrame.Create 方法。以下是您所描述的有效方法:

public bool WriteTransformedBitmapToFile<T>(BitmapSource bitmapSource, string fileName) where T : BitmapEncoder, new()
        {
            if (string.IsNullOrEmpty(fileName) || bitmapSource == null)
                return false;

            //creating frame and putting it to Frames collection of selected encoder
            var frame = BitmapFrame.Create(bitmapSource);
            var encoder = new T();
            encoder.Frames.Add(frame);
            try
            {
                using (var fs = new FileStream(fileName, FileMode.Create))
                {
                    encoder.Save(fs);
                }
            }
            catch (Exception e)
            {
                return false;
            }
            return true;
        }

        private BitmapImage GetBitmapImage<T>(BitmapSource bitmapSource) where T : BitmapEncoder, new()
        {
            var frame = BitmapFrame.Create(bitmapSource);
            var encoder = new T();
            encoder.Frames.Add(frame);
            var bitmapImage = new BitmapImage();
            bool isCreated;
            try
            {
                using (var ms = new MemoryStream())
                {
                    encoder.Save(ms);
                    ms.Position = 0;

                    bitmapImage.BeginInit();
                    bitmapImage.StreamSource = ms;
                    bitmapImage.CacheOption = BitmapCacheOption.OnLoad;
                    bitmapImage.EndInit();
                    isCreated = true;
                }
            }
            catch
            {
                isCreated = false;
            }
            return isCreated ? bitmapImage : null;
        }

它们接受任何 BitmapSource 作为第一个参数,接受任何 BitmapEncoder 作为泛型类型参数。

希望这会有所帮助。

【讨论】:

  • 哇,非常棒!我真的不知道不同的编码器是如何工作的(或如何应用它们)。非常感谢!
  • 请注意,虽然 OP 声称“需要转换为 BitmapImage 对象,因为我知道如何从 BitmapImage 对象获取字节 []”,但转换是完全多余。当您从 BitmapSource 创建 BitmapFrame 并将其编码到 MemoryStream 时,您确实已经拥有了由 MemoryStream 包装的字节数组。无需创建另一个 BitmapImage。
  • 但是,如果从 EndInit() 之后关闭的流创建 BitmapImage,则需要将其 CacheOption 属性设置为BitmapCacheOption.OnLoad。一些解码器(如 JPEG)还要求在编码后将流的 Position 重置为零。
猜你喜欢
  • 1970-01-01
  • 2014-05-30
  • 1970-01-01
  • 1970-01-01
  • 2012-11-02
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多