WPF MVVM框架------ Prism中的对话服务(IDialogService)

在wpf中,我们平时使用对话框最常用的一种方式就是新建一个窗口,然后new 出来后再调用ShowDialog()方法显示弹窗,prism中为我们提供了对话服务接口,我们可以通过这个服务向窗体传递参数或传出参数

这一章就记录一下prism中对话服务的使用

准备工作

大部分信息管理系统在进入系统之前都会有用户信息验证,都需要一个登录页面。右击Views新建一个用户空间命名为LoginView.xaml

简单进行一个布局,添加两个输入框和两个按钮,如下图

LoginView.xaml

<UserControl x:Class="MvvmBase.PrismDemo.Views.LoginView"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
             xmlns:local="clr-namespace:MvvmBase.PrismDemo.Views"
             xmlns:pwd="clr-namespace:Common.Wpf.ControlHelperLib.Password;assembly=Common.Wpf.ControlHelperLib"
             xmlns:prism="http://prismlibrary.com/"
             mc:Ignorable="d"
             d:DesignHeight="200"
             d:DesignWidth="300">
    <!--设置窗体大小-->
    <prism:Dialog.WindowStyle>
        <Style TargetType="Window">
            <!--窗体的宽和高根据内容的大小设置-->
            <Setter Property="SizeToContent"
                    Value="WidthAndHeight" />
            <!--不允许调整窗体尺寸-->
            <Setter Property="ResizeMode"
                    Value="NoResize" />
            <!--设置窗体的启动位置在屏幕中间-->
            <Setter Property="prism:Dialog.WindowStartupLocation"
                    Value="CenterScreen" />
        </Style>
    </prism:Dialog.WindowStyle>
    <Grid>
        <StackPanel Margin="50">
            <StackPanel Orientation="Horizontal"
                        HorizontalAlignment="Center">
                <Label Content="账号" />
                <TextBox  Width="150"
                          VerticalContentAlignment="Center"
                          Text="{Binding UserName}" />
            </StackPanel>
            <StackPanel Orientation="Horizontal"
                        HorizontalAlignment="Center"
                        Margin="0 10 0 0">
                <Label Content="密码" />
                <pwd:LayPassword Width="150"
                                 VerticalContentAlignment="Center"
                                 Style="{StaticResource LayPasswordTemplate}"
                                 Text="{Binding Password}" />
            </StackPanel>
            <StackPanel Orientation="Horizontal"
                        HorizontalAlignment="Center"
                        Margin="0 10 0 0">
                <Button Content="确定"
                        Width="40"
                        Height="25"
                        Margin="0 0 10 0"
                        Command="{Binding LoginCommand}" />
                <Button Content="取消"
                        Width="40"
                        Height="25"
                        Command="{Binding CancelCommand}" />
            </StackPanel>
        </StackPanel>
    </Grid>
</UserControl>

新建对应的ViewModel,右击ViewModels 新建类LoginViewModel.cs,由于这个页面是作为Dialog注册到对话服务的,所以这个ViewModel类需要实现接口IDialogAware

LoginViewModel.cs
public class LoginViewModel : BindableBase, IDialogAware
{
    /// <summary>
    /// 对话框标题
    /// </summary>
    public string Title => "登录";

    /// <summary>
    /// 调用这个事件,可关闭当前对话框并传递一个操作结果出去
    /// </summary>
    public event Action<IDialogResult> RequestClose;

    private string _userName;
    /// <summary>
    /// 用户名
    /// </summary>
    public string UserName
    {
        get { return _userName; }
        set { _userName = value; RaisePropertyChanged(); }
    }

    private string _password;
    /// <summary>
    /// 密码
    /// </summary>
    public string Password
    {
        get { return _password; }
        set { _password = value; RaisePropertyChanged(); }
    }
    /// <summary>
    /// 登录命令
    /// </summary>
    public DelegateCommand LoginCommand { get; private set; }
    /// <summary>
    /// 取消命令
    /// </summary>
    public DelegateCommand CancelCommand { get; private set; }

    public LoginViewModel()
    {
        LoginCommand = new DelegateCommand(DoLoginCommand);
        CancelCommand = new DelegateCommand(DoCancelCommand);
    }

    /// <summary>
    /// 是否可以关闭该页面
    /// </summary>
    /// <returns></returns>
    public bool CanCloseDialog()
    {
        return true;
    }

    /// <summary>
    /// 当窗口关闭时执行此方法
    /// </summary>
    public void OnDialogClosed()
    {
    }

    /// <summary>
    /// 当窗口打开时执行次方法
    /// </summary>
    /// <param name="parameters">可通过parameters这个参数从外界传递参数进来</param>
    public void OnDialogOpened(IDialogParameters parameters)
    {
    }

    public void DoLoginCommand()
    {
        DialogParameters userInfo = new DialogParameters();
        userInfo.Add("userName", UserName);
        userInfo.Add("passWord", Password);
        RequestClose.Invoke(new DialogResult(ButtonResult.OK, userInfo));
    }

    public void DoCancelCommand()
    {
        RequestClose.Invoke(new DialogResult(ButtonResult.Cancel));
    }
}

执行确定命令时,就会调用 RequestClose,关闭对话框,并将用户名和密码作为参数传递出去

 修改App.cs

  1.修改启动项为MainView

  2.在容器中注入对话框LoginView

App.cs

public partial class App : PrismApplication
{
    protected override Window CreateShell()
    {
        return Container.Resolve<MainView>();
    }

    protected override void OnInitialized()
    {
        var dig = Container.Resolve<IDialogService>();
        dig.ShowDialog("LoginView", callback =>
                       {
                           if (callback.Result == ButtonResult.OK)
                           {
                               string userName = callback.Parameters.GetValue<string>("userName");
                               string passWord = callback.Parameters.GetValue<string>("passWord");
                               base.OnInitialized();
                           }
                           else
                           {
                               App.Current.Shutdown();
                               return;
                           }
                       });
    }

    protected override void RegisterTypes(IContainerRegistry containerRegistry)
    {
        containerRegistry.RegisterForNavigation<RegionFirstView, RegionFirstViewModel>();
        containerRegistry.RegisterForNavigation<RegionSecondView, RegionSecondViewModel>();
        containerRegistry.RegisterDialog<LoginView, LoginViewModel>();
    }
}

在初始化化的时候,首先通过容器拿到IDialogService

var dig = Container.Resolve<IDialogService>();
调用ShowDialog(),
第一个参数为调用窗体的别名,根据别名查找对应的View;
第二个参数为一个委托(回调),当窗体关闭时,会进入次此回调,可获取操作结果和传出的参数

演示
账号密码都输入123 点击确定  进到登录方法

 

 点击继续进入回调 在这里可以拿到操作结果和传递过来的参数

 

 

 

  

 

posted @ 2023-02-26 16:29  just--like  阅读(1383)  评论(0编辑  收藏  举报