• .net core/5/6/7中WPF如何优雅的开始开发


    WPF是微软的.net平台中的一个桌面客户端应用程序框架,经常用于企业开发windows桌面客户端,广泛应用于中小企业快速开发一款工具,本人也是比较喜欢利用WPF开发一些小工具。

    知名案例

    1.虎牙直播客户端
    2.西门子医疗上位机
    其中西门子医疗的上位机程序称得上使用WPF技术的极其优秀的项目。(:德国人写代码真的很严格工整。
    当然西门子的.net还是基于framework,模块之间通信用的WCF,依赖注入使用的spring.net我在的时候好像准备改成Autofac了。扯远了~

    .net core/5/6/7中开发WPF

    伴随着.net5这个半成品出世,.net framework和core正式合并到一起,在core中也是支持创建WPF模板代码的,那么我们如何在新的平台下优雅的使用WPF开发一个小工具呢?

    MVVM

    老的framework我喜欢使用MvvmLightLibs,但是目前用过的都知道该包已经被标记为弃用了,推荐使用微软的CommunityToolkit.Mvvm,我们可以在项目文件中添加该包的引用

    <PackageReference Include="CommunityToolkit.Mvvm" Version="8.0.0" />
    

    添加好了之后我们将我们的viewmodel继承ObservableObject具体使用可以看园子里的一篇文章https://www.cnblogs.com/dino623/p/building_MVVM_programs_using_MVVM_Toolkit.html
    示例代码:

    public class MainWindowViewModel : ObservableObject
        {
            /// 
            /// 属性变更通知
            /// 
            private Page _currentPage;
            public Page CurrentPage
            {
                get => _currentPage;
                set => SetProperty(ref _currentPage, value);
            }
    
            //命令绑定
            public RelayCommand ShiftWorkPageCommand { get; set; }
            public RelayCommand OpenWorkSpaceCommand { get; set; }
            }
        }
    

    当然该包还带了同进程下模块发布订阅的实现。本身的事件也支持绑定异步方法。

    DI

    常用的依赖注入组件有spring.net,autofac,当然autofac在现在看来也是非常流行强大的。.net一直有一个自带的依赖注入容器,功能没有autofac强大,但是一般也够用。我们需要在项目文件中导入微软提供的相关的包。

    <PackageReference Include="Microsoft.Extensions.Hosting" Version="6.0.1" />
    <PackageReference Include="Microsoft.Extensions.Hosting.Abstractions" Version="6.0.0" />
    

    我们会在程序启动的时候创建一个默认的Host宿主对象,WPF的起始类就是app.cs里,我们可以覆写OnStartup方法,在其中启动一个Host,并且将一些服务注册进来。如日志,配置文件,数据库配置等。

    public partial class App : Application
        {
            public static IServiceProvider ServiceProvider;
            protected async override void OnStartup(StartupEventArgs e)
            {
                base.OnStartup(e);
    
                var hostbuilder = CreateHostBuilder(e.Args);
                var host = await hostbuilder.StartAsync();
                ServiceProvider = host.Services;
                host.Services.GetRequiredService()?.Show();
            }
    
            public static IHostBuilder CreateHostBuilder(string[] args)
            {
                var hostBuilder = Host.CreateDefaultBuilder(args).UseSerilog((context, logger) =>//注册Serilog
                {
                    logger.ReadFrom.Configuration(context.Configuration);
                    logger.Enrich.FromLogContext();
                });
                hostBuilder.ConfigureServices((ctx, services) =>
                {
                    services.AddSingleton();
                    services.AddSingleton();
                });
    
                return hostBuilder;
            }
        }
    

    tips :记得把App.xaml中的StartUpUri删除掉。
    上面的代码中,我们就注册了serilog日志,以及一些我们需要注入的对象,我们可以控制他们的生命周期,关于如何使用.net自带的依赖注入以及为什么需要控制反转可以看这篇网址:https://www.cnblogs.com/youring2/p/10926590.html。

    那么如何使用呢?
    我们可以在需要注入的地方通过构造器注入,比如我们的MainWindowViewModel是需要绑定到MainWindow的上下文对象上的,我们可以这样做:

    public partial class MainWindow : Window
        {
            public MainWindow(MainWindowViewModel viewModel)
            {
                InitializeComponent();
                DataContext = viewModel;
            }
        }
    

    这样程序在实例化MainWindow的时候就会从容器中取到MainWindowViewModel实例放到构造中,不需要我们关心如何去new这样一个对象。

    我们还在App.cs中放了一个静态的ServiceProvider存储ServiceProvider的实例,方便我们全局使用,这是因为有的地方我们不方便构造器的依赖注入,我们就可以利用该对象使用依赖查找的办法获取对象实例:

    ServiceProvider.GetRequiredService<MainWindowViewModel>();
    

    Configuration

    如何按照上面做的我们在WPF启动的时候注册一个默认的Host,那么也会将配置模块带入到项目中,我们如何使用配置模块?我们可以在项目根目录下创建一个appsettings.json文件,并且右键->属性
    设置成这样

    这样我们就可以使用.net自带的IConfiguration进行配置文件的读取。这个IConfiguration也是可以通过构造方法注入的,我们想在程序里或者配置文件里这个节点的配置就可以如下操作:


    当然了具体更多操作和用法,包括需要根据不同环境区分加载不同的配置以及不喜欢appsettings.json这个名字,想用其他名字都是可以配置的。appsettings.json是他框架默认的配置文件名字,会去找根目录下这个文件,如果你没有配置成其他名字的话。更多配置的操作可以查看该网址:https://www.cnblogs.com/stulzq/p/8570496.html

    结尾

    目前为止我们只是介绍了几个方面的WPF的在.net core/5/6/7中的优雅用法。也是一个基础的搭建,当然只有一个良好的基础,一个低耦合,符合规范的基础才能hold住之后写代码天高任鸟飞的愿景哈哈哈哈。
    我自己做的一个lol插件也是使用WPF做的,目前全网下载量破万,github star 180+,也是基于这些概念开发的,有兴趣的小伙伴可以了解也好,学习也好。
    https://github.com/BruceQiu1996/NPhoenix

  • 相关阅读:
    【Python 实战基础】如何绘制饼状图分析商品库存
    java数组训练题(用方法复制数组并且打印)
    利用PHP开发具有注册、登陆、文件上传、发布动态功能的网站
    计算机网络复习
    Java 复习笔记 - 常用API 中
    树莓派4b安装xenomai3(xenomai3 on raspberry4b)
    烟感报警器单片机方案开发,解决方案
    网络基础1
    Linux教程
    3D点云数据集制作实录【LiDAR】
  • 原文地址:https://www.cnblogs.com/qwqwQAQ/p/16925274.html