WPF Prism 弹窗服务

  1. 在Views目录下新建一个用户控件MsgView.xaml
    <UserControl
        x:Class="MCAutomationTestApp.Views.Dialogs.MsgView"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:local="clr-namespace:MCAutomationTestApp.Views.Dialogs"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        Width="380"
        Height="220"
        mc:Ignorable="d">
        <Grid>
            <Grid.RowDefinitions>
                <RowDefinition Height="auto" />
                <RowDefinition />
                <RowDefinition Height="auto" />
            </Grid.RowDefinitions>
            <TextBlock
                Padding="5"
                d:Text="温馨提示"
                FontSize="14"
                Text="{Binding Title}" />
            <TextBlock
                Grid.Row="1"
                Padding="15,0"
                HorizontalAlignment="Center"
                VerticalAlignment="Center"
                d:Text="确认删除该数据吗?"
                FontSize="22"
                Text="{Binding Content}" />
            <StackPanel
                Grid.Row="2"
                Margin="10"
                HorizontalAlignment="Right"
                Orientation="Horizontal">
                <Button
                    Margin="0,0,10,0"
                    Command="{Binding CancelCommand}"
                    Content="取消"
                    Style="{StaticResource MaterialDesignOutlinedButton}" />
                <Button Command="{Binding SaveCommand}" Content="确认" />
            </StackPanel>
        </Grid>
    </UserControl>
    

  2. 新建一个扩展类DialogExtensions,添加常用弹窗接口

    public static class DialogExtensions
        {
            /// <summary>
            /// 询问信息弹框
            /// </summary>
            /// <param name="dialogHost"></param>
            /// <param name="title"></param>
            /// <param name="content"></param>
            /// <param name="dialogHostName"></param>
            /// <returns></returns>
            public static async Task<IDialogResult> Question(this IDialogHostService dialogHost, string title, string content, string dialogHostName= "Root")
            {
                DialogParameters param = new DialogParameters();
                param.Add("Title", title);
                param.Add("Content", content);
                param.Add("dialogHostName", dialogHostName);
    
                var dialogResult = await dialogHost.ShowDialog("MsgView", param, dialogHostName);
    
                return dialogResult;
            }
    
            /// <summary>
            /// 注册提示消息 
            /// </summary>
            /// <param name="aggregator"></param>
            /// <param name="action"></param>
            public static void ResgiterMessage(this IEventAggregator aggregator,
                Action<MessageModel> action, string filterName = "Main")
            {
                aggregator.GetEvent<MessageEvent>().Subscribe(action,
                    ThreadOption.PublisherThread, true, (m) =>
                    {
                        return m.Filter.Equals(filterName);
                    });
            }
    
            /// <summary>
            /// 发送提示消息
            /// </summary>
            /// <param name="aggregator"></param>
            /// <param name="message"></param>
            public static void SendMessage(this IEventAggregator aggregator, string message, string filterName = "Main")
            {
                aggregator.GetEvent<MessageEvent>().Publish(new MessageModel()
                {
                    Filter = filterName,
                    Message = message,
                });
            }
        }

  3.  新建IDialogHostService服务类,继承Prism框架下的IDialogService

        public interface IDialogHostService : IDialogService
        {
            Task<IDialogResult> ShowDialog(string name, IDialogParameters parameters, string dialogHostName = "Root");
        }

  4. 参考Prism弹框服务源代码重写ShowDialog接口

     public class DialogHostService : DialogService, IDialogHostService
        {
            private readonly IContainerExtension containerExtension;
    
            public DialogHostService(IContainerExtension containerExtension) : base(containerExtension)
            {
                this.containerExtension = containerExtension;
            }
    
            public async Task<IDialogResult> ShowDialog(string name, IDialogParameters parameters, string dialogHostName = "Root")
            {
                if (parameters == null)
                    parameters = new DialogParameters();
    
                //从容器当中去除弹出窗口的实例
                var content = containerExtension.Resolve<object>(name);
    
                //验证实例的有效性 
                if (!(content is FrameworkElement dialogContent))
                    throw new NullReferenceException("A dialog's content must be a FrameworkElement");
    
                if (dialogContent is FrameworkElement view && view.DataContext is null && ViewModelLocator.GetAutoWireViewModel(view) is null)
                    ViewModelLocator.SetAutoWireViewModel(view, true);
    
                if (!(dialogContent.DataContext is IDialogHostAware viewModel))
                    throw new NullReferenceException("A dialog's ViewModel must implement the IDialogAware interface");
    
                viewModel.DialogHostName = dialogHostName;
    
                DialogOpenedEventHandler eventHandler = (sender, eventArgs) =>
                {
                    if (viewModel is IDialogHostAware aware)
                    {
                        aware.OnDialogOpend(parameters);
                    }
                    eventArgs.Session.UpdateContent(content);
                };
    
                return (IDialogResult)await DialogHost.Show(dialogContent, viewModel.DialogHostName, eventHandler);
            }
        }

  5. 根据弹窗页面上元素信息编写接口类IDialogHostAware

    public interface IDialogHostAware
        {
            /// <summary>
            /// DialoHost名称
            /// </summary>
            string DialogHostName { get; set; }
    
            /// <summary>
            /// 打开过程中执行
            /// </summary>
            /// <param name="parameters"></param>
            void OnDialogOpend(IDialogParameters parameters);
    
            /// <summary>
            /// 确定
            /// </summary>
            DelegateCommand SaveCommand { get; set; }
    
            /// <summary>
            /// 取消
            /// </summary>
            DelegateCommand CancelCommand { get; set; }
        }

  6. 在ViewModels目录下新家MsgViewModel服务类,并实现相关绑定接口

    public class MsgViewModel : BindableBase, IDialogHostAware
        {
            public string DialogHostName { get; set; }
            public DelegateCommand SaveCommand { get; set; }
            public DelegateCommand CancelCommand { get ; set; }
            private string title;
    
            public string Title
            {
                get { return title; }
                set { title = value; RaisePropertyChanged(); }
            }
            private string content;
    
            public MsgViewModel()
            {
                SaveCommand = new DelegateCommand(Save);
                CancelCommand = new DelegateCommand(Cancel);
            }
    
            private void Cancel()
            {
                if (DialogHost.IsDialogOpen(DialogHostName))
                    DialogHost.Close(DialogHostName, new DialogResult(ButtonResult.No));
            }
    
            private void Save()
            {
                if (DialogHost.IsDialogOpen(DialogHostName))
                {
                    DialogParameters param = new DialogParameters();
                    DialogHost.Close(DialogHostName, new DialogResult(ButtonResult.OK, param));
                }
            }
    
            public string Content
            {
                get { return content; }
                set { content = value; RaisePropertyChanged(); }
            }
    
    
            public void OnDialogOpend(IDialogParameters parameters)
            {
                if (parameters.ContainsKey("Title"))
                    Title = parameters.GetValue<string>("Title");
    
                if (parameters.ContainsKey("Content"))
                    Content = parameters.GetValue<string>("Content");
            }
        }

  7. 在App.xaml.cs文件中RegisterTypes接口里注册两个服务分别是

    protected override void RegisterTypes(IContainerRegistry containerRegistry)
    {
        containerRegistry.RegisterForNavigation<MsgView, MsgViewModel>();
        containerRegistry.Register<IDialogHostService, DialogHostService>();
    }
  8. 在ViewModel中使用弹窗服务需从IContainerProvider中先取出服务窗口类使用

        private readonly IDialogHostService dialogHost; 
        public DelegateCommand<string> AddCommand { get; private set; }     
        public IndexViewModel(IContainerProvider provider)
        {
                AddCommand = new DelegateCommand<string>(Add);
                dialogHost = provider.Resolve<IDialogHostService>();
        }
        private async void Add(string obj)
        {
                var dialogResult =  await dialogHost.Question("温馨提示", "请确认删除该数据?");
                if (dialogResult.Result != Prism.Services.Dialogs.ButtonResult.OK) return;
                Trace.WriteLine("");
         }
  9. 在View中使用可以直接引用IDialogHostService服务类

      private readonly IDialogHostService dialogHostService;
    
            public MainWindow(IEventAggregator aggregator, IDialogHostService dialogHostService)
            {
                InitializeComponent();
    
                aggregator.ResgiterMessage(arg =>
                {
                    Snackbar.MessageQueue.Enqueue(arg.Message);
                });
                btnClose.Click += BtnClose_Click;
                this.dialogHostService = dialogHostService;
            }
             private async void BtnClose_Click(object sender, RoutedEventArgs e)
            {
                var dialogResult = await dialogHostService.Question("温馨提示", "确认退出系统?");
                if (dialogResult.Result != Prism.Services.Dialogs.ButtonResult.OK) return;
                this.Close();
            }

  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值