【问题标题】:Adding breadcrumb navigation to a WPF MVVM app using Caliburn使用 Caliburn 将面包屑导航添加到 WPF MVVM 应用程序
【发布时间】:2013-08-16 20:40:28
【问题描述】:

我有一个遵循 MVVM 模式和 Caliburn-Micro 框架的现有 WPF 应用程序。我有一个向 UI 添加交互式面包屑的新要求。虽然我可以毫无问题地呈现面包屑,但当用户单击其中一个面包屑时,我很难确定如何处理激活。

我有一个 n 级对象图,其中每个对象都是一个 Conductor.Collection.OneActive。

UI 能够通过调用 ActivateItem 来处理基本的“导航”,并为每个导体激活项目。在每个级别,我都会显示项目列表,当单击一个时,它会被激活。只要激活的项目有子项目,UI 就会显示其子项目列表。单击其中一个时,将激活该子级,依此类推。

我可以通过将此对象图从活动根项向下爬行到活动子项等来构建面包屑跟踪,但我不知道如何在单击面包屑时重新激活一个项目,因为我有对项目的引用,而不是包含/管理该项目的指挥。

有什么想法吗?

【问题讨论】:

    标签: wpf mvvm caliburn.micro caliburn


    【解决方案1】:

    刚刚有了一个可能有用的想法。听起来导体是分层的,所以:

    使用事件聚合器触发一个简单的消息类型,其属性包含您要激活的视图模型

    public class BreadcrumbNavigate
    {
        public IScreen Screen { get; private set; }
    
        public BreadcrumbNavigate(IScreen screen) { Screen = screen; }
    }
    

    指挥应该都在监听这些类型的消息;当他们收到一条消息时,他们应该只在当前处于活动状态时才对其进行响应,这意味着只有面包屑路径的叶节点才会响应第一条消息。

    如果消息中的虚拟机不是指挥者的子节点,指挥者应该关闭自己并重新发布聚合器消息,以便下一个活动指挥者可以处理它(不确定这将如何运作,因为它取决于指挥者关闭自己然后传播信息,但就像我说的,这只是一个想法)。

    最终,树上某处的正确指挥器将处理消息,并且该指挥器将有一个与消息匹配的子 VM - 这是导航目标,也是消息传播停止的地方

    编辑:

    由于导体在有活跃的孩子时处于活跃状态,因此上述方法不起作用 - 所以废弃它!

    您能否发布有关您的设置的更多信息?

    就您所描述的而言,这听起来像是一个简单的面包屑导航场景;为了沿着面包屑返回,您只需在要跳回的 VM 的活动项目上使用 TryClose()

    // on the VM that you want to navigate to...
    
    public void NavigateToMe() 
    {
        // Check if we have a child, if so try and close it...will close all children etc
        if (ActiveItem != null)
        {
            ActiveItem.TryClose();
        }
    }
    

    显然,您可以将其包装在辅助方法中,例如

    public void NavigateTo(IConductActiveItem vm)
    {
        var iClose = vm.ActiveItem as IClose;
        if(iClose != null)
        {
            iClose.TryClose();
        }
    }
    

    因此,您在面包屑中需要的只是对 VM 的引用,在检查它是否有一个可关闭的子节点并调用 TryClose() 时,所有子虚拟机/导体都应在所选子节点下方关闭 - 显然这仅在子节点下方有效虚拟机的始终是项目指挥

    这是假设您只是使用以下对象图:

    导体 -> 导体 -> 导体 -> 导体

    【讨论】:

    • 有趣的想法。不幸的是,事件聚合与事件冒泡不同,前者不保证执行顺序。我正在特别考虑选择孙子或曾孙的用例。父母如何知道它的孩子是包含被选中的孙子的那个 - 特别是在父母首先处理事件/消息的情况下?
    • 我认为让你的想法奏效的关键,以及我可能缺少的,是事件冒泡。我在想经典的树场景,我选择一个节点来通知其父节点,该节点扩展并通知其父节点等等。我认为这更符合您的描述,是吗?并不是所有的节点都监听和处理原始消息。
    • 我更多地考虑只有活动虚拟机才会响应消息 - 嵌套导体场景是否可能是个问题。如果子导体激活孙子,孙子又激活曾孙,那么根导体的激活状态是什么?如果它是“不活跃的”(它可能不会知道我的运气!)那么你可以逃脱这个,因为只有活跃的指挥应该响应“关闭”消息。从技术上讲,我认为它正在冒泡——你可以在里面放一个冒泡系统
    • 我认为聚合器更像是一种霰弹枪方法 - 冒泡听起来是个好主意!
    • 我在我的答案中添加了更多内容 - 快速浏览后听起来很简单,是不是比我想象的更复杂?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-02-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多