XAML WPF:自动更新列表视图

wf82jlnq  于 2022-12-07  发布在  其他
关注(0)|答案(1)|浏览(142)

我有一个ListView,它可以显示特定文件夹中的.txt文件。我希望在向该文件夹中添加(或删除)文件时,ListView能够自动更新。我在Internet上找到了FileSystemWatcher类,但无法使程序正常运行。有人有什么提示吗?我对C#编程还比较陌生。
我的XAML代码:

<ScrollViewer Grid.Row="1" Grid.ColumnSpan="2" DockPanel.Dock="Top">
        <ListView x:Name="TxtListView"  SelectionMode="Multiple">
            <ListView.View>
                <GridView>
                    <GridView.Columns>
                        <GridViewColumn>
                            <GridViewColumn.CellTemplate>
                                <DataTemplate>
                                    <CheckBox Tag="{Binding .}" IsChecked="{Binding RelativeSource={RelativeSource AncestorType={x:Type ListViewItem}}, Path=IsSelected}" />
                                </DataTemplate>
                            </GridViewColumn.CellTemplate>
                        </GridViewColumn>
                        <GridViewColumn/>
                        <GridViewColumn/>
                        <GridViewColumn/>
                        <GridViewColumn/>
                    </GridView.Columns>
                </GridView>
            </ListView.View>
        </ListView>
    </ScrollViewer>

程式码后置:

public partial class MainWindow : Window
{
    public string path = @"C:\txt";
    public MainWindow()
    {
        InitializeComponent();

        //Read txt Files
        DirectoryInfo d = new DirectoryInfo(path);
        FileInfo[] txtFiles = d.GetFiles();
        TxtListView.ItemsSource = txtFiles;

        MonitorDirectory(path);
    }

    public void MonitorDirectory(string path)

    {

        FileSystemWatcher fileSystemWatcher = new FileSystemWatcher();

        fileSystemWatcher.Path = path;

        fileSystemWatcher.Created += FileSystemWatcher_Created;

        fileSystemWatcher.EnableRaisingEvents = true;

    }

    private void FileSystemWatcher_Created(object sender, FileSystemEventArgs e)
    {
        DirectoryInfo d = new DirectoryInfo(path);
        FileInfo[] txtFiles = d.GetFiles();
        TxtListView.ItemsSource = txtFiles;
    }
    //Refresh-Button
    private void Refresh(object sender, RoutedEventArgs e)
    {
        DirectoryInfo d = new DirectoryInfo(path);
        FileInfo[] txtFiles = d.GetFiles();
        TxtListView.ItemsSource = txtFiles;
    }
}
uqzxnwby

uqzxnwby1#

下面是一个使用MVVM体系结构模式的简单示例。
有一个视图模型类,它包含FileSystemWatcherFileInfo对象的ObservableCollection,这些对象用作视图中数据绑定的源。
您必须注意FileSystemWatcher的事件是在后台线程中激发的,例如,通过使用EnableCollectionSynchronization方法。

public class ViewModel
{
    private readonly object filesLock = new object();

    public ObservableCollection<FileInfo> Files { get; }
        = new ObservableCollection<FileInfo>();

    public ViewModel(string path)
    {
        BindingOperations.EnableCollectionSynchronization(Files, filesLock);

        foreach (var fileInfo in new DirectoryInfo(path).EnumerateFiles())
        {
            Files.Add(fileInfo);
        }

        var fsw = new FileSystemWatcher(path);
        fsw.Created += FileCreated;
        fsw.Deleted += FileDeleted;
        fsw.EnableRaisingEvents = true;
    }

    private void FileCreated(object sender, FileSystemEventArgs e)
    {
        lock (filesLock)
        {
            Files.Add(new FileInfo(e.FullPath));
        }
    }

    private void FileDeleted(object sender, FileSystemEventArgs e)
    {
        lock (filesLock)
        {
            var removed = Files.FirstOrDefault(fi => fi.Name == e.Name);

            if (removed != null)
            {
                Files.Remove(removed);
            }
        }
    }
}

将视图模型的示例分配给MainWindow的DataContext属性

public partial class MainWindow : Window
{
    public MainWindow()
    {
        InitializeComponent();

        DataContext = new ViewModel(...); // insert the directory path here
    }
}

表示在检视中启用数据系结。
下面的XAML也使用CollectionViewSource来启用排序。

<Window x:Class="FileSystemWatcherTest.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:scm="clr-namespace:System.ComponentModel;assembly=WindowsBase"
        Title="MainWindow" Height="450" Width="800">
    <Window.Resources>
        <CollectionViewSource x:Key="cvs" Source="{Binding Files}">
            <CollectionViewSource.SortDescriptions>
                <scm:SortDescription PropertyName="Name"/>
            </CollectionViewSource.SortDescriptions>
        </CollectionViewSource>
    </Window.Resources>
    <Grid>
        <ListView ItemsSource="{Binding Source={StaticResource cvs}}">
            <ListView.View>
                <GridView>
                    <GridView.Columns>
                        <GridViewColumn>
                            <GridViewColumn.CellTemplate>
                                <DataTemplate>
                                    <TextBlock Text="{Binding Name}"/>
                                </DataTemplate>
                            </GridViewColumn.CellTemplate>
                        </GridViewColumn>
                    </GridView.Columns>
                </GridView>
            </ListView.View>
        </ListView>
    </Grid>
</Window>

相关问题