2016-11-16 3 views
0

В моем UWP приложение, когда модель слоя пытается обновить (перезаписать) файл, он бросает UnauthorizedAccessException «отказано в доступе» исключение, поскольку файл заблокирован видовым в BitmapImage.BitmapImage.UriSource блокирует локальный файл

Посмотреть

var bitmap = new BitmapImage(); 
bitmap.UriSource = new Uri("ms-appdata:///local/image.jpg"); 

Модель

private async UpdateImage() 
{ 
    // this line throws! 
    var file = await ApplicationData.Current.LocalFolder.CreateFileAsync("image.jpg", CreationCollisionOption.ReplaceExisting); 
    ... 
} 

Как я могу остановить BitmapImage от блокировки локального файла, используемого в качестве UriSource?

ответ

0

он бросает в UnauthorizedAccessException «отказано в доступе» исключение, поскольку файл заблокирован видовым в BitmapImage.

Как известно, если использовать BitmapImage.UriSource свойство для установки источника для BitmapImage файла поток файла будет блокировать занят. Чтобы решить эту проблему, мы можем прочитать поток файлов с помощью нашего кода IRandomAccessStream, и в этом случае мы можем контролировать, когда нужно удалять поток файлов, чтобы разблокировать файл. Код обновляется следующим образом:

private async void btncreate_Click(object sender, RoutedEventArgs e) 
{ 
    var file = await ApplicationData.Current.LocalFolder.CreateFileAsync("image.jpg", CreationCollisionOption.ReplaceExisting); 
} 

private async void Page_Loaded(object sender, RoutedEventArgs e) 
{ 
    var bitmap = new BitmapImage(); 
    //bitmap.UriSource = new Uri("ms-appdata:///local/image.jpg"); 
    //imgshow.Source = bitmap; 
    StorageFile imagefile = await StorageFile.GetFileFromApplicationUriAsync(new Uri("ms-appdata:///local/image.jpg")); 
    using (IRandomAccessStream stream = await imagefile.OpenAsync(FileAccessMode.Read)) 
    { 
     bitmap.SetSource(stream); 
     imgshow.Source = bitmap; 
    } 
} 
0

Попробуйте это:

var bitmap = new BitmapImage(); 
bitmap.BeginInit(); 
bitmap.CacheOption = BitmapCacheOption.OnLoad; 
bitmap.CreateOption = BitmapCreateOptions.IgnoreImageCache; 
bitmap.UriSource = new Uri("ms-appdata:///local/image.jpg");  
bitmap.EndInit(); 
+0

'bitmap.CacheOption' сделал бы это, но он не поддерживается UWP, насколько я знаю. – Vitaly

+0

Спасибо, но, к сожалению, свойство 'CacheOption' отсутствует в UWP. – Vitaly

+1

Извините, вы правы. Я не заметил, что это UWP. Думаю, вам следует управлять «перезагрузкой» объекта BitMapImage вашего представления перед вызовом Model UpdateImage, а затем перезагрузить в представлении обновленного изображения. –

0

Работа вокруг «Sunteen В - MSFT» почти правильно, так как bitmap.SetSource подразумевается асинхронный, поток может получить расположенный перед тем SetSource закончена. Вам нужно использовать явную функцию SetSourceAsync и ждать ее.

В любом случае, это решение использует много памяти. URI-решение каким-то образом совместимо с памятью (хотелось бы знать, почему).

URI-решение заблокирует файл для неопределенного долгого времени. Несмотря на то, что другое решение не блокирует файлы, оно будет выделять много памяти для необоснованного времени.

Я могу поделиться своим решением: Я копирую исходный файл в папку temp, а затем открываю его с соответствующим Uri. Но тогда файл не будет удален мной, что может привести к большому количеству дискового пространства.

Есть ли у кого-нибудь подобные проблемы? Другие решения?

Смежные вопросы