Wpf 无法删除其他进程使用的文件

Wpf 无法删除其他进程使用的文件,wpf,c#-4.0,file-io,ioexception,Wpf,C# 4.0,File Io,Ioexception,我正在使用以下代码在我的wpf应用程序中显示一些图像: <Image Source="{Binding Path=TemplateImagePath, Mode=TwoWay}" Grid.Row="3" Grid.Column="2" Width="400" Height="200"/> 但是,如果用户上传了一些其他图像,那么我需要删除这个旧图像,我正在按照以下方式进行操作,并将图像绑定设置为null: DirectoryInfo Dir = new DirectoryIn

我正在使用以下代码在我的wpf应用程序中显示一些图像:

 <Image Source="{Binding Path=TemplateImagePath, Mode=TwoWay}"  Grid.Row="3" Grid.Column="2"  Width="400" Height="200"/>
但是,如果用户上传了一些其他图像,那么我需要删除这个旧图像,我正在按照以下方式进行操作,并将图像绑定设置为null:

DirectoryInfo Dir = new DirectoryInfo(@"D:/Template");
                if (Dir.Exists)
                {
                    if (Dir.GetFiles().Count() > 0)
                    {
                        foreach (FileInfo item in Dir.GetFiles())
                        {
                            TemplateImagePath= null;
                            File.Delete(item.FullName);
                        }
                    }
                }
但我遇到异常,无法删除其他进程使用的文件。
如何删除它?

为了能够在图像控件中显示图像时删除图像,您必须创建一个新的或已设置的对象。然后,位图将立即从文件中加载,之后文件不会被锁定

将属性从
string TemplateImagePath
更改为
ImageSource TemplateImage
并按如下方式绑定:

<Image Source="{Binding TemplateImage}"/>
BitmapImage image = new BitmapImage();
image.BeginInit();
image.CacheOption = BitmapCacheOption.OnLoad;
image.UriSource = new Uri(item.FullName);
image.EndInit();
TemplateImage = image;
或者这个:

TemplateImage = BitmapFrame.Create(
    new Uri(item.FullName),
    BitmapCreateOptions.None,
    BitmapCacheOption.OnLoad);


如果要保持与
TemplateImagePath
属性的绑定,可以使用将字符串转换为如上所示的ImageSource的绑定转换器。

根据克莱门斯的建议,以下是绑定转换器,以实现良好的代码重用:

例如,有一个用于绑定的字符串

在UI中使用转换器,在我的例子中是从名为“控件”的库中使用的



您是否尝试不使用双向绑定?另一个可行的解决方案是不直接设置路径,而是从该路径创建位图图像并绑定到该位图图像。如何做到这一点。我是WPF的新手。任何代码示例对不起,没时间,请使用谷歌。另外我需要添加'System.GC.Collect();System.GC.WaitForPendingFinalizers();'删除该行之前的文件之前:file.Delete(item.FullName)在此上花费了很长时间,但添加了'GC.Collect();'和'GC.WaitForPendingFinalizers();'在删除之前解决了我的问题。谢谢@SST@Jon您可能还需要查看以下内容:。触发GC可能会起作用,“正确的”(即有文档记录的)解决方案是设置StreamSource而不是UriSource属性。@Clemens谢谢,我来看看您是如何使用视频实现这一点的?
TemplateImage = BitmapFrame.Create(
    new Uri(item.FullName),
    BitmapCreateOptions.None,
    BitmapCacheOption.OnLoad);
namespace Controls
{
    [ValueConversion(typeof(String), typeof(ImageSource))]
    public class StringToImageSourceConverter : IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
        {
            if (!(value is string valueString))
            {
                return null;
            }
            try
            {
                ImageSource image = BitmapFrame.Create(new Uri(valueString), BitmapCreateOptions.IgnoreImageCache, BitmapCacheOption.OnLoad);
                return image;
            }
            catch { return null; }
        }

        public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
        {
            throw new NotImplementedException();
        }
    }
}
public string MyImageString { get; set; } = @"C:\test.jpg"
<Window x:Class="MainFrame"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:controls="clr-namespace:Controls;assembly=Controls">
    <Window.Resources>
        <controls:StringToImageSourceConverter x:Key="StringToImageSourceConverter" />
    </Window.Resources>
    <Grid>
        <Image Source="{Binding MyImageString, Converter={StaticResource StringToImageSourceConverter}}" />
    </Grid>
</Window>