【问题标题】:How to best add popup to visual tree when using MVVM on WP7在 WP7 上使用 MVVM 时如何最好地将弹出窗口添加到可视化树
【发布时间】:2011-03-11 10:59:11
【问题描述】:

我在 WP7 上通过 Caliburn Micro 使用 MVVM。我有一个从 VM 显示的弹出窗口。弹出窗口上有一个性能进度条。当 IsIndeterminate 设置为 true 时,进度条不显示,因为弹出窗口不在可视树中(它是自定义控件)。

如果我从视图模型中获取视图并强制弹出窗口进入可视化树,进度条会正确显示。不过我真的不想这样做。

在保持视图和视图模型分离的同时,最好的方法是什么。弹出窗口是否可以通过某种方式将自身插入到根页面或框架中?

【问题讨论】:

    标签: windows-phone-7 popup


    【解决方案1】:

    我的方法是使用由视图模型公开并绑定到控件的子视图模型/控制器/事件源。

    该控件可以监听源上的事件来完成它的工作,它很好地分离,甚至可以进行单元测试。

    我的Status Indicator Control 就是一个很好的例子,视图模型通过 Display 和 Clear 等方法公开了一个 StatusSource。控件本身绑定到源并侦听更改。从那里您可以做任何事情,包括创建弹出窗口并将其插入到可视化树中。

    【讨论】:

    • 好主意 - 将在页面 VM 和控件之间放置一个子 VM。我仍然需要一种弹出窗口可以将自身插入到可视树中的方法。我应该能够用 RootVisual 做一些事情——PhoneApplicationPage 或 PhoneApplicationFrame。这样,弹出窗口可以在任何地方使用。只是看不到如何做到这一点?
    • 据我与 Popup 合作的一点点我可以看出,它根本不是可视化树的一部分(这可能会导致方向问题)。您可以创建一个弹出窗口,将其设置为您的控件,然后调用 show 而不添加到可视化树中。一个例子是devlicio.us/blogs/derik_whittaker/archive/2010/08/27/…
    • 是的,你可以,这就是我正在做的,但后来我添加了一个进度条,但它不起作用。一旦我将弹出窗口添加到可视化树中,进度条就开始工作了。
    • 奇怪,我没遇到过这个问题,抱歉帮不上忙。
    【解决方案2】:

    您与设计师合作吗?我发现在代码中做任何基于视图的事情,除了加载数据,都会让他们感到困惑和/或沮丧。我建议创建 2 种视觉状态,一种显示弹出窗口,一种隐藏,以便设计人员可以看到应用程序的外观并可以在 Blend 中切换(和设置样式)弹出窗口。然后我使用 DataStateBehavior 或 DataStateSwitchBehavior 来控制来自我的 VM 的弹出窗口。

    【讨论】:

    • 弹出窗口本身可以很好地显示和隐藏。进度条虽然不起作用。我需要一种将弹出窗口插入可视树的通用方法。一旦我得到了这个,我就可以创建一个基本的弹出控件,我的其他弹出窗口可以从中继承。
    【解决方案3】:

    我最终创建了一个基本弹出类并将此代码添加到:

    private void HookIntoPage()
    {
        if (UserControlHelper.RootVisual != null)
        {
            PhoneApplicationPage page = (PhoneApplicationPage)UserControlHelper.RootVisual.Content;
    
            // Hook up into the back key press event of the current page
            page.BackKeyPress += BackKeyPress;
    
            FrameworkElement element = page.FindVisualChild("MainGrid");
    
            if (element != null && element is Grid)
            {
                Grid grid = element as Grid;
                grid.Children.Add(this);
            }
            else
            {
                throw new Exception("Popup cannot find MainGrid");
            }
        }
    }
    

    它在寻找 MainGrid 网格控件时有点硬编码。这可以改进以寻找合适的顶级容器。

    这里有 2 个辅助类。 UserControlHelper 有以下方法:

    public static PhoneApplicationFrame RootVisual
    {
        get
        {
            return Application.Current == null ? null : Application.Current.RootVisual as PhoneApplicationFrame;
        }
    }
    

    FindVisualChild 来自 Phone7.Fx.preview 附带的 VisualTreeHelperExtension 类,我将其用于可绑定的应用栏。

    【讨论】:

      猜你喜欢
      • 2023-01-25
      • 1970-01-01
      • 2019-11-18
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-01-20
      • 1970-01-01
      相关资源
      最近更新 更多