将UWP图像编码为PNG

6

我通过URI(网络或文件系统)获取到一张图片,想要将其编码为PNG格式并保存到临时文件:

var bin = new MemoryStream(raw).AsRandomAccessStream();  //raw is byte[]
var dec = await BitmapDecoder.CreateAsync(bin);
var pix = (await dec.GetPixelDataAsync()).DetachPixelData();

var res = new FileStream(Path.Combine(ApplicationData.Current.LocalFolder.Path, "tmp.png"), FileMode.Create);
var enc = await BitmapEncoder.CreateAsync(BitmapEncoder.PngEncoderId, res.AsRandomAccessStream());
enc.SetPixelData(BitmapPixelFormat.Bgra8, BitmapAlphaMode.Ignore, dec.PixelWidth, dec.PixelHeight, 96, 96, pix);
await enc.FlushAsync();  //hangs here
res.Dispose();

问题是,这段代码在await enc.FlushAsync()行上挂起了。请帮忙!谢谢。

这段代码在UI线程上运行还是在后台线程上运行? - Petter Hesselberg
它被从事件处理程序调用,因此在UI线程中。 - Mike Tsayper
1个回答

6

我不确定为什么您的代码会挂起——但是您使用了几个IDisposable,这可能与此有关。无论如何,以下是一些几乎实现了您尝试完成的工作的代码,它可以正常运行:

StorageFile file = await ApplicationData.Current.TemporaryFolder
    .CreateFileAsync("image", CreationCollisionOption.GenerateUniqueName);
using (IRandomAccessStream outputStream = await file.OpenAsync(FileAccessMode.ReadWrite))
{
    using (MemoryStream imageStream = new MemoryStream())
    {
        using (Stream pixelBufferStream = image.PixelBuffer.AsStream())
        {
            pixelBufferStream.CopyTo(imageStream);
        }

        BitmapEncoder encoder = await BitmapEncoder
            .CreateAsync(BitmapEncoder.PngEncoderId, outputStream);
        encoder.SetPixelData(
            BitmapPixelFormat.Bgra8,
            BitmapAlphaMode.Ignore,
            (uint)image.PixelWidth,
            (uint)image.PixelHeight,
            dpiX: 96,
            dpiY: 96,
            pixels: imageStream.ToArray());
        await encoder.FlushAsync();
    }
}

(我的image是一个WriteableBitmap;不确定你的raw是什么?)
我的图像是一个可写位图,不确定你的原始数据是什么?

"raw" 是一个已下载的图像,一个字节数组。谢谢,我会检查是否有未被处理的内容... - Mike Tsayper
你的原始字节是什么格式?如果它们已经代表了一个PNG图像,那么你可以直接将这些字节转储到文件中,不需要进行其他处理。 - Petter Hesselberg
性能不是问题,因此PNG到PNG的转换可以接受。 - Mike Tsayper

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接