在“更新视图”中;实时”;MVVMLight中的ObservableCollection数据

本文关键字:实时 MVVMLight 中的 数据 ObservableCollection 更新 新视图 更新视图 | 更新日期: 2023-09-27 18:20:01

我正在C#/WPF中使用MVVMLight和Fody编写一个排序算法可视化工具。在我的ViewModel中,我有一个可观察的集合,如下所示:

public ObservableCollection<int> NumbersCollection{ get; set; }

现在,在一个命令(方法)中,我更改集合的内容(在本例中,我正在进行冒泡排序)。像这样:

        IMutableSortAlgorithm sorter = ServiceLocator.Current.GetInstance<IMutableSortAlgorithm>();
        sorter.MuatbleSort(this.NumbersCollection);
        while (!sorter.Finished())
        {
            sorter.NextStep();                   
            this.RaisePropertyChanged("NumbersCollection"); // not neccesary   
            Thread.Sleep(400);
        }

经过分拣员的呼叫。NextStep()集合已更改。在每一步之后,我都试图通过调用RaisePropertyChanged和睡眠400ms来更新视图。

所以我基本上希望视图在每次更改(步骤)后更新,但视图只有在方法完成后才会更新。(为此,我甚至不需要调用RaisePropertychanged…)

为了方便起见,我可以请一名背景工作人员。但我首先想在没有额外工作线程的情况下解决这个问题。由于我在主GUI线程中,所以不需要调用Dispatcher.Invoke,对吧?(我试过了,但还是没用。)。

有人知道如何在每一步之后刷新UI吗?

编辑:分拣机。NextStep()不会向列表中插入或删除项,但会交换值。就像col[i]=col[j]。。。你知道的,整理东西。我想在UI上的实时中获得这些更改。

在“更新视图”中;实时”;MVVMLight中的ObservableCollection数据

UI线程中的集合,它正在更新/休眠,从不处理属性更改事件。

该集合需要在单独的线程中更新。任务运行、BackgroundWorker、异步操作等

这会让你半途而废,导致错误"这种类型的CollectionView不支持从不同于Dispatcher线程的线程更改其SourceCollection。"

一些谷歌搜索发现了一个线程安全的可观察集合:在哪里可以获得线程安全的CollectionView?

决定随机化数字,而不是对它们进行排序,这对我有效

    public MTObservableCollection<int> NumbersCollection
    {
        get { return _item.NumbersCollection; }
    }
    public ICommand RandomizeCommand
    {
        get
        {
            if (_randomizeCommand == null)
                _randomizeCommand = new RelayCommand(() =>
                {                        
                    Task.Run(()=>
                    {
                        for (int i = 0; i < 10; i++)
                        {
                            _dataService.Randomize();                                
                            Thread.Sleep(TimeSpan.FromSeconds(3));
                        }
                    });                        
                });
            return _randomizeCommand;
        }
    }

编辑:另一种方法(我刚刚从中学习)在代码c#中插入延迟/等待

利用DispatcherHelper.RunAsync()wait Task.Delay在UI线程中运行而不阻塞,您可以使用常规的Observable集合,而不是线程安全的集合。

    public  ObservableCollection<int> NumbersCollection
    {
        get { return _item.NumbersCollection; }
    }
    public ICommand RandomizeCommand
    {
        get
        {
            if (_randomizeCommand == null)
                _randomizeCommand = new RelayCommand(() =>
                {
                    //Task.Run(() =>
                    DispatcherHelper.RunAsync(async () =>
                    {
                        for (var i = 0; i < 10; i++)
                        {
                            _dataService.Randomize();
                            //Thread.Sleep(TimeSpan.FromSeconds(3));
                            await Task.Delay(TimeSpan.FromSeconds(3));
                        }
                    });
                });
            return _randomizeCommand;
        }
    }