总之,我想知道使用MVVM模式从WPF启动子对话框/窗口的公认最佳方法/行业标准。我看到了以下文章:
A. CodeProject -在使用MVVM模式时显示对话框
这种方法似乎不错,但对我来说太过分了。这是某种程度的代码复制,我不相信这是正确的方法。
这简单地贯穿了三个选项,不同的链接,这些都是相当/非常差的解释方法或主题。
请有人解释一下使用MVVM从WPF应用程序中启动对话框的行业标准方法/方法,并最好提供一些指向进一步阅读材料的链接。如果你能自己举个例子,我当然会非常感激!
耽误您时间,实在对不起。
发布于 2013-06-25 23:57:13
首先,我不知道任何使用MVVM显示对话框的“行业标准”方法,因为没有这样的东西。
其次,欢迎来到MVVM,您刚刚谈到了MVVM没有标准的领域。
说实话,MVVM有很多痛苦之处,这就是为什么有大量的MVVM框架存在,仅举几个MVVM、PRISM、Caliburn.Micro、Cinch、Catel、WAF、Baboon、shell I stop或您想要的更多。
现在,为了回答您的问题,在处理了大多数这些框架之后,我注意到了一个共同点,它们都使用DI/IoC容器,然后为您提供一个接口,类似于IDialogManager以及它们自己的实现,然后他们要求您在视图模型中接受这个接口,并使用它来显示对话框。因此,总之,我将使用依赖项注入,有一个显示对话框的接口,然后提供并实现它,并将其注册到di容器中,然后从我的视图模型或视图中使用它。
编辑:,所以您已经选择了PRISM (在我看来)在它们之间显示对话框是最困难的。撇开这一点不谈,有一种困难的方法是使用交互请求 (查看本文的中间部分),或者您可以使用这个回答作为一种更快的方法。
发布于 2013-06-26 00:37:56
最近,我为WPF实现了我自己的导航服务,它使用了杯标( WindowManager )(但您可以用其他东西代替它)。
示例(如何使用):
_navigationService.GetWindow<ClientDetailsViewModel>()
.WithParam(vm => vm.IsEditing, true)
.WithParam(vm => vm.Client, SelectedClient)
.DoIfSuccess(() => RefreshSelectedClient())
.ShowWindowModal();
Implementation:
namespace ClientApplication.Utilities
{
public class NavigationService : INavigationService
{
SimpleContainer _container;
IWindowManager _windowManager;
public NavigationService(SimpleContainer container, IWindowManager windowManager)
{
_container = container;
_windowManager = windowManager;
}
public INavigationService<TViewModel> GetWindow<TViewModel>()
{
return new NavigationService<TViewModel>(_windowManager, (TViewModel)_container.GetInstance(typeof(TViewModel), null));
}
}
public class NavigationService<TVM> : INavigationService<TVM>
{
IWindowManager _windowManager;
TVM _viewModel;
System.Action _action;
public NavigationService(IWindowManager windowManager, TVM viewModel)
{
_windowManager = windowManager;
_viewModel = viewModel;
}
public INavigationService<TVM> WithParam<TProperty>(Expression<Func<TVM, TProperty>> property, TProperty value)
{
var prop = (PropertyInfo)((MemberExpression)property.Body).Member;
prop.SetValue(_viewModel, value, null);
return this;
}
public INavigationService<TVM> DoBeforeShow(Action<TVM> action)
{
action(_viewModel);
return this;
}
public INavigationService<TVM> DoIfSuccess(System.Action action)
{
_action = action;
return this;
}
public void ShowWindow(IDictionary<string, object> settings = null)
{
_windowManager.ShowWindow(_viewModel, null, settings);
}
public bool ShowWindowModal(IDictionary<string, object> settings = null)
{
bool result = _windowManager.ShowDialog(_viewModel, null, settings) ?? false;
if (result && _action != null)
_action();
return result;
}
}
}
接口:
namespace Common
{
public interface INavigationService<TVM>
{
INavigationService<TVM> WithParam<TProperty>(Expression<Func<TVM, TProperty>> property, TProperty value);
INavigationService<TVM> DoIfSuccess(System.Action action);
INavigationService<TVM> DoBeforeShow(Action<TVM> action);
void ShowWindow(IDictionary<string, object> settings = null);
bool ShowWindowModal(IDictionary<string, object> settings = null);
}
public interface INavigationService
{
INavigationService<TViewModel> GetWindow<TViewModel>();
}
}
发布于 2013-06-26 01:02:17
最近发布的Prism (在这里下载)包含一个称为“股票交易”的MVVM应用程序的“参考实现”。我的理由是,如果Prism团队称它为“参考实现”,那么从他们的角度来看,这是最“标准”的(如果在MVVM中有标准的话),以及继续推进的逻辑选择。
源代码包含一个用于提高模态对话框的基础设施库,而且它非常好。因此,我采用了这个库,并成功地部署了它(我将这样的应用程序上传到Codeplex)。
我需要将代码调整为1,将父程序的图标添加到标题栏中,因为库没有为其提供;2向标题栏添加一些有意义的文本,因为库将其保留为空白,而3在对话框关闭时添加要调用的委托。抽象的程度是,VM可以通过向中介传递两个字符串(即统一注册名称)来引发对话。这些更改可在Codeplex上使用。
因此,在所有其他“标准”中,“参考实施”应尽可能少地作为一个可行的选择。对您的问题的更间接的回答是,如果您的View模型足够孤立,并且完全通过POCO接口工作,那么从理论上讲,这并不重要,因为切换到另一个“标准”应该是一个微不足道的练习。
https://stackoverflow.com/questions/17308945
复制相似问题