Dav*_*ave 3 c# wpf user-controls
我的应用程序在屏幕上显示图像(基于本地计算机上的文件的图像),用户可以根据需要删除它们。
每次我尝试删除文件时,都会出现以下错误消息:
"The process cannot access the file 'C:\\Users\\Dave\\Desktop\\Duplicate\\Swim.JPG' because it is being used by another process."
Run Code Online (Sandbox Code Playgroud)
我理解错误消息。
我有一个UserControl接受文件路径(通过构造函数中的参数),然后将其绑定到它的 (UserControl) DataContext。
作为调试此问题的一部分,我发现问题是由于在 UserControl 中设置 DataContext 造成的。如果我this.DataContext = this;从用户控件中删除,那么我可以删除该文件。
所以,我的测试单元看起来像
Ui.UserControls.ImageControl ic = new ImageControl(
@"C:\Users\Dave\Desktop\Duplicate\Swim.JPG");
try
{
File.Delete(@"C:\Users\Dave\Desktop\Duplicate\Swim.JPG");
}
catch (Exception ex)
{
Assert.Fail(ex.Message);
}
Run Code Online (Sandbox Code Playgroud)
用户控制代码隐藏
public ImageControl(string path)
{
this.FilePath = path;
this.DataContext = this; // removing this line allows me to delete the file!
InitializeComponent();
}
#region Properties
private string _filePath;
public string FilePath
{
get { return _filePath; }
set
{
_filePath = value;
OnPropertyChanged("FilePath");
}
}
Run Code Online (Sandbox Code Playgroud)
如果重要的话,我的 UserControl XAML 正在使用“Image”控件,绑定到“FilePath”
我尝试在删除之前将 UserControl 设置为空,但这没有帮助。
我尝试将 IDisposible 接口添加到我的 UserControl 和Dispose()方法设置中this.DataContext = null;,但这没有帮助。
我究竟做错了什么?我怎样才能删除这个文件(或者更准确地说,让它不被使用)。
问题不在于 DataContext,而在于 WPF 从文件加载图像的方式。
当您将SourceImage 控件的属性绑定到包含文件路径的字符串时,WPF 在内部从该路径创建一个新的 BitmapFrame 对象,基本上如下所示:
string path = ...
var bitmapImage = BitmapFrame.Create(new Uri(path));
Run Code Online (Sandbox Code Playgroud)
不幸的是,这会保留 WPF 打开的图像文件,因此您无法删除它。
要解决此问题,您必须将图像属性的类型更改为ImageSource(或派生类型)并手动加载图像,如下所示。
public ImageSource ImageSource { get; set; } // omitted OnPropertyChanged for brevity
private ImageSource LoadImage(string path)
{
var bitmapImage = new BitmapImage();
using (var stream = new FileStream(path, FileMode.Open))
{
bitmapImage.BeginInit();
bitmapImage.CacheOption = BitmapCacheOption.OnLoad;
bitmapImage.StreamSource = stream;
bitmapImage.EndInit();
bitmapImage.Freeze(); // optional
}
return bitmapImage;
}
...
ImageSource = LoadImage(@"C:\Users\Dave\Desktop\Duplicate\Swim.JPG");
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
913 次 |
| 最近记录: |