0

OpenFileDialog用来获取图像的路径,然后imgSelected.Source = new BitmapImage(new Uri(filenameSteg, UriKind.Absolute));在 WPF 应用程序中将其设置为我的图像源属性。

问题是,我需要稍后再次打开该文件,但我无法打开它,因为该文件正在被另一个进程System.IO.IOException-> The process cannot access the file pathToFile because it is being used by another process.)使用。

稍后需要访问它的代码如下:

 bitmapSource = JpegBitmapDecoder.Create(File.Open(filenameSteg, FileMode.Open),
                BitmapCreateOptions.None, BitmapCacheOption.OnLoad).Frames[0];

bitmapSource用于将该图像提供给 aWriteableBitmap并从那里遍历像素。

有没有办法处理用 OpenFileDialog 打开的文件?

我试图转换为 IDisposable,使用 using 块等等,但这个东西是持久的。

编辑 :

1 - 我试过这个(@ctacke 回答):

 using (var stream = File.Open(filenameSteg, FileMode.Open)){
        bitmapSource = JpegBitmapDecoder.Create(stream, BitmapCreateOptions.None,
        BitmapCacheOption.OnLoad).Frames[0];}

但它仍然给我关于该进程已被另一个进程使用的错误,因为即使它会在之后被释放,我仍然试图打开与filenameSteg我在OpenFileDialog. (或者至少,我是这么看的。)

2 - 然后我尝试了这个(基于@ctacke推荐的链接

using (FileStream fileStream = new FileStream(filenameSteg+1, FileMode.Create)){
       MemoryStream memoryStream = new MemoryStream();
       BitmapImage bi = new BitmapImage();
       byte[] fileBytes = File.ReadAllBytes(filenameSteg);
       memoryStream.Write(fileBytes, 0, fileBytes.Length);
       memoryStream.Position = 0;

       bi.BeginInit();
       bi.StreamSource = memoryStream;
       bi.EndInit();

       bitmapSource = bi;}

注意:请注意,我在这里要求filenameSteg +1。那是因为我想测试我的方法的其余部分,所以我创建了一个文件副本并简单地将 1 添加到它的名称中。话虽如此,当filenameSteg实际使用时,它给了我关于已经在使用中的相同错误,我再次怀疑我仍然要求打开以前在OpenFileDialog.

3 - 我想到了另一种不需要我处理打开的图像的方法:

当我第一次在 中打开图像时OpenFileDialog,我将图像的字节数组存储在一个变量中,这样我就可以WriteableBitmap使用BitmapFactory和 字节数组来创建。

// This is in the OpenFileDialog. It is where I stock the image "pixels" in a byte array.
bytesArrayImage = File.ReadAllBytes(filenameSteg); 
//And then later when I needed the WriteableBitmap, I used the byte array and the BitmapFactory
//imgSelected being the Image containing the image I opened in the OpenFileDialog, I used it's
//width and height 
wb = BitmapFactory.New(Convert.ToInt32(imgSelected.Width),
     Convert.ToInt32(imgSelected.Height)).FromByteArray(bytesArrayImage);

这种方法的问题是,一些图片工作正常,我可以使用字节数组来创建WriteableBitmap并遍历它的像素,但在其他情况下它给了我一个AccessViolationException说明:Attempted to read or write protected memory. This is often an indication that other memory is corrupt.。换句话说,试图绕过 dispose 问题让我陷入了另一个问题。

4

1 回答 1

0

您应该释放原始图像,如下所示:

if(imgSelected.Source != null)
{
    imgSelected.Source.Dispose;
}
imgSelected.Source = new BitmapImage(new Uri(filenameSteg, UriKind.Absolute));

接下来,File.Open返回一个您需要显式释放的流。

using(var stream = File.Open(filenameSteg, FileMode.Open))
{
    var bitmapSource = JpegBitmapDecoder.Create(stream,
        BitmapCreateOptions.None, BitmapCacheOption.OnLoad).Frames[0];
}

另请参阅:加载 BitmapSource 并在 WPF 中使用相同名称保存 -> IOException

于 2016-05-15T03:09:15.567 回答