prism WPF 导航

导航和浏览器的后退前进是一样的功能

项目结构

App.xaml.cs

复制代码
using Prism.Ioc;
using Prism.Modularity;
using Prism.Unity;
using PrismWpfApp.ViewModels;
using PrismWpfApp.Views;
using System;
using System.Collections.Generic;
using System.Configuration;
using System.Data;
using System.Linq;
using System.Threading.Tasks;
using System.Windows;

namespace PrismWpfApp
{
    /// <summary>
    /// App.xaml 的交互逻辑
    /// </summary>
    public partial class App : PrismApplication
    {
        /// <summary>
        /// 提供主窗口的对象
        /// </summary>
        /// <returns></returns>
        /// <exception cref="NotImplementedException"></exception>
        protected override Window CreateShell()
        {
            //打开第一个窗口 ModuleWindow
            //return Container.Resolve<MainWindow>();
            return Container.Resolve<ModuleWindow>();
            //return new MainWindow();
        }

        /// <summary>
        /// 业务中所有需要注入的对象,在这个方法里注册
        /// </summary>
        /// <param name="containerRegistry"></param>
        /// <exception cref="NotImplementedException"></exception>
        protected override void RegisterTypes(IContainerRegistry containerRegistry)
        {
            //注册 导航 RegisterForNavigation
            containerRegistry.RegisterForNavigation<UserControlA>();
            containerRegistry.RegisterForNavigation<UserControlB>();
            containerRegistry.RegisterForNavigation<UserControlC>();
        }

        /// <summary>
        /// 添加模块(代码引用)
        /// </summary>
        /// <param name="moduleCatalog"></param>
        //protected override void ConfigureModuleCatalog(IModuleCatalog moduleCatalog)
        //{
        //    moduleCatalog.AddModule<ModuleAProfile>();
        //    moduleCatalog.AddModule<ModuleBProfile>();
        //    base.ConfigureModuleCatalog(moduleCatalog);
        //}

        /// <summary>
        /// 创建模块
        /// </summary>
        protected override IModuleCatalog CreateModuleCatalog()
        {
            return new DirectoryModuleCatalog() { ModulePath = @".\Modules" };
        }

        //protected override void OnStartup(StartupEventArgs e)
        //{
        //    base.OnStartup(e);

        //    if (new LoginWindow().ShowDialog() == true)
        //    {
        //        new MainWindow().ShowDialog();
        //    }
        //    Application.Current.Shutdown();
        //}
    }
}

ModuleWindow.xaml

复制代码
<Window x:Class="PrismWpfApp.Views.ModuleWindow"
        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:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:PrismWpfApp.Views"
        xmlns:prism="http://prismlibrary.com/"
        prism:ViewModelLocator.AutoWireViewModel="True"
        mc:Ignorable="d"
        Title="{Binding Title}" Height="450" Width="800">
    <Grid>
        <Grid.RowDefinitions>
            <RowDefinition Height="30"></RowDefinition>
            <RowDefinition ></RowDefinition>
        </Grid.RowDefinitions>
        <StackPanel Grid.Row="0" Orientation="Horizontal">
            <Button Content="模块1" Width="80" Height="30" Command="{Binding ShowContentCommand}" CommandParameter="UserControl1" ></Button>
            <Button Content="模块2" Width="80" Height="30" Command="{Binding ShowContentCommand}" CommandParameter="UserControl2" ></Button>
            <Button Content="后退" Width="80" Height="30" Command="{Binding BackCommand}" ></Button>
        </StackPanel>

        <ContentControl Grid.Row="1" prism:RegionManager.RegionName="ContentRegions"></ContentControl>
    </Grid>
</Window>

ModuleWindowViewModel.cs

复制代码
using Prism.Commands;
using Prism.Regions;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace PrismWpfApp.ViewModels
{
    public class ModuleWindowViewModel : UiViewModelBase
    {
        /// <summary>
        /// Prism 提供 区域管理接口
        /// </summary>
        private readonly IRegionManager _regionManager;

        public ModuleWindowViewModel(IRegionManager regionManager)
        {
            this.Title = "XXX系统";
            _regionManager = regionManager;
        }

        /// <summary>
        /// 记录上一步(导航记录)
        /// </summary>
        private IRegionNavigationJournal _navigationJournal;

        /// <summary>
        /// 显示区域内容
        /// </summary>
        public DelegateCommand<string> ShowContentCommand
        {
            get
            {
                return new DelegateCommand<string>((arg) =>
                {
                    // 区域、模块
                    //_regionManager.Regions["ContentRegions"].RequestNavigate(arg);

                    NavigationParameters paras = new NavigationParameters();
                    paras.Add("MsgA", "大家好,我是A");//模块参数传递
                    paras.Add("MsgB", "大家好,我是B");

                    //_regionManager.Regions["ContentRegions"].RequestNavigate(arg, paras);
                    _regionManager.Regions["ContentRegions"].RequestNavigate(arg, callback =>
                    {
                        _navigationJournal = callback.Context.NavigationService.Journal;
                    }, paras);
                });
            }
        }

        /// <summary>
        /// 后退 (记录好上一步后,就可以后退了)
        /// </summary>
        public DelegateCommand<string> BackCommand
        {
            get
            {
                return new DelegateCommand<string>((arg) =>
                {
                    //判断是否可以后退
                    if (_navigationJournal != null && _navigationJournal.CanGoBack)
                    {
                        _navigationJournal.GoBack();//后退
                    }
                });
            }
        }
    }
}

UiViewModelBase.cs

复制代码
using Prism.Commands;
using Prism.Mvvm;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;

namespace PrismWpfApp.ViewModels
{
    /// <summary>
    /// UI 层的 ViewModelBase 基类
    /// </summary>
    public abstract class UiViewModelBase : BindableBase
    {
        public UiViewModelBase()
        {
            AppDataInstance = AppData.Instance;
            initCommand();
        }

        public AppData _appDataInstance;
        /// <summary>
        /// 公共数据
        /// </summary>
        public AppData AppDataInstance
        {
            get { return _appDataInstance; }
            set
            {
                SetProperty(ref _appDataInstance, value);
            }
        }

        private string _systemName = "一体针焊接系统";
        /// <summary>
        /// 系统名称
        /// </summary>
        public string SystemName
        {
            get { return _systemName; }
            set
            {
                SetProperty(ref _systemName, value);
            }
        }

        private string _title = "标题";
        /// <summary>
        /// 标题
        /// </summary>
        public string Title
        {
            get { return _title; }
            set
            {
                SetProperty(ref _title, value);
            }
        }
        private void initCommand()
        {
            CloseCommand = new DelegateCommand<Window>(close);
        }

        /// <summary>
        /// 关闭(取消) 命令
        /// </summary>
        public DelegateCommand<Window> CloseCommand { get; set; }

        /// <summary>
        /// 关闭(取消) 方法
        /// </summary>
        public void close(Window window)
        {
            if (window != null)
            {
                window.Close();
            }
        }

        /// <summary>
        /// 根据名称获取开关的值
        /// </summary>
        /// <param name="name">名称</param>
        /// <returns>是否开启</returns>
        public bool GetOnOffByName(string name)
        {
            var isOn = false;
            //if (!string.IsNullOrEmpty(name))
            //{
            //    isOn = _serviceSysConfig.GetOnOffByName(name);
            //}
            return isOn;
        }

        /// <summary>
        /// 保存开关配置
        /// </summary>
        /// <param name="connfigName">配置名称</param>
        /// <param name="value">是否开启</param>
        /// <returns>是否成功</returns>
        public bool SaveOnOff(string connfigName, bool value)
        {
            var isOk = false;
            if (!string.IsNullOrEmpty(connfigName))
            {
                //isOk = _serviceSysConfig.SaveModelByName(new SysConfigModel()
                //{
                //    Name = connfigName,
                //    ValueStr = value.ToString(),
                //    UpdatedBy = "ADMIN",
                //    UpdatedOn = DateTime.Now
                //});
            }
            return isOk;
        }
    }
}

ModuleA

UserControl1.xaml

复制代码
<UserControl x:Class="ModuleA.Views.UserControl1"
             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:ModuleA.Views"             
             mc:Ignorable="d" 
             d:DesignHeight="450" d:DesignWidth="800">
    <Grid>
        <!--<TextBlock Text="我是模块1" FontSize="50"/>-->
        <TextBlock Text="{Binding Msg}" FontSize="50"/>
    </Grid>
</UserControl>

UserControl1ViewModel.cs

复制代码
using Prism.Common;
using Prism.Mvvm;
using Prism.Regions;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;

namespace ModuleA.ViewModels
{
    public class UserControl1ViewModel : BindableBase, IConfirmNavigationRequest//INavigationAware(模块切换时没有确认操作),IConfirmNavigationRequest (确认切换导航接口)
    {
		//propfull

		private string _mag;

		public string Msg
		{
			get { return _mag; }
			set { 
				_mag = value;
				RaisePropertyChanged();//属性更新写法2
			}
		}

        /// <summary>
        /// 确认
        /// </summary>
        /// <param name="navigationContext"></param>
        /// <param name="continuationCallback"></param>
        /// <exception cref="NotImplementedException"></exception>
        public void ConfirmNavigationRequest(NavigationContext navigationContext, Action<bool> continuationCallback)
        {
            var boxResult = MessageBox.Show("确定切换吗?","系统提示", MessageBoxButton.YesNo);
            var isYes = boxResult == MessageBoxResult.Yes;

            continuationCallback(isYes);
        }

        /// <summary>
        /// 是否重用实例
        /// </summary>
        /// <param name="navigationContext"></param>
        /// <returns></returns>
        /// <exception cref="NotImplementedException"></exception>
        public bool IsNavigationTarget(NavigationContext navigationContext)
        {
            return true;
        }

        /// <summary>
        /// 拦截
        /// </summary>
        /// <param name="navigationContext"></param>
        /// <exception cref="NotImplementedException"></exception>
        public void OnNavigatedFrom(NavigationContext navigationContext)
        {
            
        }

        /// <summary>
        /// 导航到哪里去
        /// </summary>
        /// <param name="navigationContext"></param>
        /// <exception cref="NotImplementedException"></exception>
        public void OnNavigatedTo(NavigationContext navigationContext)
        {
            //接收参数
            if (navigationContext.Parameters.ContainsKey("MsgA"))
            {
                Msg = navigationContext.Parameters.GetValue<string>("MsgA");
            }
        }
    }
}

ModuleAProfile.cs

复制代码
using ModuleA.ViewModels;
using ModuleA.Views;
using Prism.Ioc;
using Prism.Modularity;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace ModuleA
{
    /// <summary>
    /// 模块要实现 IModule 接口 
    /// </summary>
    public class ModuleAProfile : IModule
    {
        public void OnInitialized(IContainerProvider containerProvider)
        {
            
        }

        /// <summary>
        /// 模块 服务注入
        /// </summary>
        /// <param name="containerRegistry"></param>
        public void RegisterTypes(IContainerRegistry containerRegistry)
        {
            //导航
            //containerRegistry.RegisterForNavigation<UserControl1>();//自动绑定
            containerRegistry.RegisterForNavigation<UserControl1, UserControl1ViewModel>();//View 和 ViewModel 手动指定绑定关系
        }
    }
}

AppData

复制代码
/// <summary>
/// UI层公共数据
/// </summary>
public class AppData : BindableBase
{
    /// <summary>
    ///  这样就可以在事个UI层获取到AppData类的所有公共属性和方法
    /// </summary>
    public static AppData Instance = new Lazy<AppData>(() => new AppData()).Value;

    /// <summary>
    /// 主窗体
    /// </summary>
    public MainWindow MainWindow { get; set; }
}
相关推荐
baivfhpwxf20238 小时前
prism WPF 模块
wpf
军训猫猫头17 小时前
87.在线程中优雅处理TryCatch返回 C#例子 WPF例子
开发语言·ui·c#·wpf
huizhixue-IT2 天前
华为存储考试内容&HCIP-Storage
wpf
桂月二二3 天前
实时事件流处理架构的容错设计
架构·wpf
源之缘-OFD先行者3 天前
GMap.NET + WPF:构建高性能 ADS-B 航空器追踪平台
.net·wpf·ads-b
Marzlam3 天前
WPF学习路线
wpf
weixin_535455793 天前
WPF设计学习记录滴滴滴2
学习·wpf
^@^lemon tea^@^3 天前
WPF 浅述IsHitTestVisible属性
wpf·wpf 穿透
lixy5793 天前
C# WPF 命令机制(关闭CanExecute自动触发,改手动)
c#·wpf