c# - WPF MVVM 中与 TAP 的异步(async/await)

标签 c# wpf mvvm

我正在寻找以下设置的最佳实践。

View 是绑定(bind)到 ViewModel 的数据(通过 WPF)。 ViewModel 通过 INotifyPropertyChanged 更新 View 。模型通过事件更新 ViewModel。模型知道来自外部世界的东西,比如如何通过 WebClient 从互联网上获取东西,以及如何从数据库中检索数据。

获取和向外界发送东西应该异步完成,以便 UI(以及用户)不会因为等待外界而受苦。

解决此问题的最佳实践方法是什么?

1. ViewModel 应该负责异步调用模型方法。
这将具有能够编写类似内容的优势

GetWebPage(string url) {
  var result = await Model.GetWebPageAsync(url);
  Url = result.Url;
}

在 ViewModel 中,Url 是一个带有 INotifyPropertyChanged 的​​ ViewModel 属性,用于更新 View 。 甚至

GetWebPage(string url) {
  var result = await Model.GetWebPageAsync(url);
  _view.Url = result.Url;
}

我们可以一起避免 INotifyPropertyChanged 的​​地方。您更喜欢以下哪种方式?

但是,让模型本身执行异步工作可能更明智。我们可能希望能够在没有 View 和 ViewModel 的情况下使用 Model,同时仍然让它异步工作。另一个论点是,谁更清楚模型最好异步处理哪些内容。

2. 模型自己处理所有异步内容。 ViewModel 代码变得更像

GetWebPage(string url) {
  Model.GetWebPage(url);
}

在模型中

GetWebPage(string url) {
  var result = await Model.GetWebPageAsync(url);
  if (UrlChanged != null);
     UrlChanged(this, new UrlChangedEventArgs(url));
}

ViewModel 可以订阅并相应地更新 View。

您认为哪种方式是最佳做法?

最佳答案

第三种方式:view model 异步调用,但是它使用客户端服务来获取网页,model 本身是贫血的(它对外界一无所知):

GetWebPage(string url) 
{
  var dataService = anyServiceLocator.GetService<IDataService>();
  var result = await dataService.GetWebPageAsync(url, Model);
  Url = result.Url;
}

这允许更改实际数据下载算法,例如用于测试目的。

关于c# - WPF MVVM 中与 TAP 的异步(async/await),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13119584/

相关文章:

c# - 处理不同的非托管整数大小

c# - 有什么简单的方法可以将 XML 输出从共享点 GetListItems() 转换为 DataTable

wpf - 如何以编程方式在 WPF TabControl 中选择 TabItem

用于平铺 ListView 的 WPF 工具包

wpf - 如何防止在第一次单击时选择整个DataGrid行?

vb.net - WP7 MVVM 如何从 ViewModel 调用 me.setfocus()?

mvvm - Caliburn Micro 中的命令类

c# - 如何将整数四舍五入到百位?

c# - 无法使用 Mapbox "Create an Upload"api 上传数据文件

c# - 如何将渲染变换应用于鼠标位置