代码之家  ›  专栏  ›  技术社区  ›  Ralph Shillington

导航逻辑属于何处、视图、ViewModel或其他位置?

  •  12
  • Ralph Shillington  · 技术社区  · 15 年前

    我在视图中创建了一个按钮,绑定到ViewModel的ICommand属性(实际上它是mvvv light的RelayCommand)

    执行任务的首选选项是什么导航服务。导航打电话?

    2 回复  |  直到 15 年前
        1
  •  12
  •   4levels    6 年前

    如果您已经在使用mvvmlight,一个选择就是使用它包含的消息总线。因此,您将按钮绑定到视图模型上的RelayCommand,正如您所说的那样。在RelayCommand的处理程序中,您可以决定导航到哪个视图。这将在视图模型中保留所有逻辑。

    为此,我定义了一个视图模型可以发布的NavigationMessage类,以及一个视图继承的视图基类,其中包含侦听器。导航消息如下所示:

    public class NavigationMessage : NotificationMessage
    {
        public string PageName
        {
            get { return base.Notification; }
        }
    
        public Dictionary<string, string> QueryStringParams { get; private set; }
    
        public NavigationMessage(string pageName) : base(pageName) { }
    
        public NavigationMessage(string pageName, Dictionary<string, string> queryStringParams) : this(pageName)
        {
            QueryStringParams = queryStringParams;
        }
    }
    

    这允许简单地传递页面名称,或者还可以选择包含任何必要的查询字符串参数。RelayCommand处理程序将按如下方式发布此消息:

    private void RelayCommandHandler()
    {
        //Logic for determining next view, then ...
        Messenger.Default.Send(new NavigationMessage("ViewToNavigate"));
    }
    

    最后,视图基类如下所示:

    public class BasePage : PhoneApplicationPage
    {
        public BasePage()
        {
            Messenger.Default.Register<NavigationMessage>(this, NavigateToPage);
        }
    
        protected void NavigateToPage(NavigationMessage message)
        {
            //GetQueryString isn't shown, but is simply a helper method for formatting the query string from the dictionary
            string queryStringParams = message.QueryStringParams == null ? "" : GetQueryString(message);
    
            string uri = string.Format("/Views/{0}.xaml{1}", message.PageName, queryStringParams);
            NavigationService.Navigate(new Uri(uri, UriKind.Relative));
        }
    }
    

        2
  •  6
  •   Jon Skeet    15 年前

    警告:固执己见的MVVM新手提醒:)(我对MVVM非常陌生,但到目前为止我非常喜欢它。)

    NavigationService 并通过 INavigationService 类型 (作为类型参数)而不是字符串URI。

    因此,还不是一个完美的解决方案-但至少ViewModel可以负责“现在导航”(或“返回”)的操作。