2016-07-21 3 views
2

У меня есть команда, как это:многопоточной с ObservesProperty

CancelCommand = new DelegateCommand(Cancel,() => IsProcessing).ObservesProperty(() => IsProcessing); 

А в другой метод, который я называю

Task.Factory.StartNew(() => 
      { 
       IsProcessing = true; // Stop here 
       IsProcessing = false; 
      }); 

Как-то выполнение останавливается, когда IsProcessing набор для true. Но когда я изменяю

Application.Current.Dispatcher.Invoke(() => IsProcessing = true); 
IsProcessing = false; // Hit this line then stop again 
int i = 0; // Never reach here 

Похоже ObservesProperty вызывает проблемы, когда IsProcessing набор в не UI потоке. Это ошибка или работает так, как она была разработана?

ответ

1

Эта проблема не уникальна для Призмы. Вся Призма подключается к INotifyPropertyChanged указанного вами свойства и вызывает событие CanExecuteChanged.

Событие ICommand.CanExecuteChanged может привести к изменению элементов пользовательского интерфейса (например, изменить значение свойства IsEnabled кнопки), поэтому он должен быть вызван из потока пользовательского интерфейса. В отличие от механизма привязки, он не делает этого автоматически.

Вы должны либо:

  • Установите свойство из потока пользовательского интерфейса до/после запуска потока. Использование асинхр/ОЖИДАНИЕ бы сделать это очень просто:

    async Task DoStuff() // start this method from the UI thread 
    { 
        IsProcessing = true; 
        try 
        { 
         await Task.Run(() => { ... }); 
        } 
        finally 
        { 
         IsProcessing = false; 
        } 
    } 
    
  • Использование Dispatcher.InvokeAsync. Do не использовать Invoke - это просто растрачивание потока, ожидающего завершения пользовательского интерфейса.