C# 通过导体的微屏幕过渡

C# 通过导体的微屏幕过渡,c#,.net,xaml,mvvm,caliburn.micro,C#,.net,Xaml,Mvvm,Caliburn.micro,我有一个Caliburn.Micro外壳(即一个包含其他视图的空XAML视图),由导体ViewModel渲染。在那里,我通过以下方式打开一个屏幕: ActivateItem(...) 通常,在新显示的对话框中,用户可以执行一些操作并单击按钮(确定、取消、构建…),这些按钮应在每次转换到另一个屏幕(在shell中)时显示 实现这种对话动作/消息屏幕转换的好方法是什么 简单的.NET事件是可能的——这不是个坏主意吗 CMIEventAggregator也应通过更改视图来工作 通过TryClose

我有一个Caliburn.Micro外壳(即一个包含其他视图的空XAML视图),由导体ViewModel渲染。在那里,我通过以下方式打开一个屏幕

ActivateItem(...)
通常,在新显示的对话框中,用户可以执行一些操作并单击按钮(确定、取消、构建…),这些按钮应在每次转换到另一个屏幕(在shell中)时显示

实现这种对话动作/消息屏幕转换的好方法是什么

  • 简单的.NET事件是可能的——这不是个坏主意吗
  • CM
    IEventAggregator
    也应通过更改视图来工作
  • 通过
    TryClose()
    关闭后,从外壳导体检查ViewModel结果应该是可能的,只是不知道如何在CM中实现这一点
  • 从该屏幕引用外壳导体实例(通过IoC或直接)——这似乎是强耦合

请告知。

我首选的方法是使用EventAggregator来促进虚拟机之间的消息传递

当您有多个窗口正在侦听特定类型的事件时(例如,具有多个工具窗口的Visual Studio样式界面,可能会显示上下文敏感属性),这一点尤其有效,但是对于此实现来说,这听起来有点过分了。当然,优点仍然是VM之间的良好松散耦合和缺少事件(这是一件好事!)

听起来您希望弹出一个模式对话框并显示一个选项,然后在第一个屏幕返回后激活另一个屏幕

您可以将事件处理程序附加到子VM中的
已停用
事件,该事件将在项目停用时触发。它还将在参数中传递一个布尔值,以通知已停用的项目是否已关闭-您可以检查此项并在导体中激活相应的屏幕

e、 g

this.Deactivated+=新事件处理程序(WorkspaceViewModel_已停用);
void WorkspaceViewModel_已停用(对象发送者,停用目标)
{
如果(e.wascolled)//引发一些事件
}
然后把一个活动交给售票员,我不会按照这个活动的路线去做。这会单向耦合虚拟机,因此它可能不是最灵活的解决方案

另一种方法是通过事件聚合器触发一条消息,告诉导体在子VM关闭时需要打开另一个窗口。可以使用相同的方法,但它是解耦的

this.Deactivated += new EventHandler<DeactivationEventArgs>(WorkspaceViewModel_Deactivated);

void WorkspaceViewModel_Deactivated(object sender, DeactivationEventArgs e)
{
    if(e.WasClosed) MainConductor.EventAggregator.Publish(new ActivateWindowMessage(typeof(SomeVM));
}
this.Deactivated+=新事件处理程序(WorkspaceViewModel_已停用);
void WorkspaceViewModel_已停用(对象发送者,停用目标)
{
if(e.WasClosed)MainConductor.EventAggregator.Publish(newactivatewindowmessage)(typeof(SomeVM));
}

关于我的目标,你是对的。我将在“确定”中尝试EventAggregator方法。此外,我还发现该VM依赖于外壳/主导体是很奇怪的。应该是相反的方式。就是说,VM应该自己负责,外壳应该负责显示适当的视图,子VM应该通过消息传递命令父VM应该做什么我可能写了一篇让人困惑的文章!不,不,没关系,我更关注的是我的解决方案中哪一个看起来更好,为什么,如果可能的话,如何实现。我使用了文章中的方法,通过构造函数注入IEvAgg,使它们不紧密耦合。好吧,酷,我没有包括在我的回答中没有任何IoC概念。CM中的聚合器有一个非常自然的实现(基于接口),很高兴您对其进行了分类!找到了一篇描述如何使用
IEventAggregator
的好文章:
this.Deactivated += new EventHandler<DeactivationEventArgs>(WorkspaceViewModel_Deactivated);

void WorkspaceViewModel_Deactivated(object sender, DeactivationEventArgs e)
{
    if(e.WasClosed) // raise some event
}
this.Deactivated += new EventHandler<DeactivationEventArgs>(WorkspaceViewModel_Deactivated);

void WorkspaceViewModel_Deactivated(object sender, DeactivationEventArgs e)
{
    if(e.WasClosed) MainConductor.EventAggregator.Publish(new ActivateWindowMessage(typeof(SomeVM));
}