WPF 切换主题使用 luna 复古版本

本文告诉大家如何在 WPF 里面使用 luna 等复古主题

今天在 lsj 说他准备优化 WPF 的程序集时,准备删除 luna 等程序集时,找到了一段有趣的注释,发现在 WPF 里面可以通过一些有趣的反射的方法修改主题,让应用使用 luna 的主题,实现复古的界面

使用方法非常简单,在 App.xaml.cs 的构造函数里面,添加如下代码即可

        public App()
        {
            SetTheme("luna", "normalcolor");
        }

        ///
        /// Sets the WPF system theme.

        ///
        /// The name of the theme. (ie "aero")
        /// The name of the color. (ie "normalcolor")
        /// Copy https://github.com/danielmoore/SystemThemeChange/blob/master/App.xaml.cs
        public static void SetTheme(string themeName, string themeColor)
        {
            const BindingFlags staticNonPublic = BindingFlags.Static | BindingFlags.NonPublic;

            var presentationFrameworkAsm = Assembly.GetAssembly(typeof(Window));

            var themeWrapper = presentationFrameworkAsm.GetType("MS.Win32.UxThemeWrapper");

            var isActiveField = themeWrapper.GetField("_isActive", staticNonPublic);
            var themeColorField = themeWrapper.GetField("_themeColor", staticNonPublic);
            var themeNameField = themeWrapper.GetField("_themeName", staticNonPublic);

            // Set this to true so WPF doesn't default to classic.

            isActiveField.SetValue(null, true);

            themeColorField.SetValue(null, themeColor);
            themeNameField.SetValue(null, themeName);
        }

为了展示界面效果,我添加了如下界面


软件运行效果如下

WPF 切换主题使用 luna 复古版本

再换成 Aero 效果,修改代码如下

        public App()
        {
            SetTheme("areo", "normalcolor");
        }

可以看到界面更加好看

WPF 切换主题使用 luna 复古版本

以上方法实际上在很久之前就有大佬写了,详细请看 danielmoore/SystemThemeChange: A demonstration of a theme change helper for WPF

在 WPF 里面,可以看到 UxThemeWrapper 有如下注释

    internal static class UxThemeWrapper
    {
        // There are apps that override the system theme with one of their own
        // choosing, and intercept (and discard) WM_THEMECHANGED messages to
        // keep their theme in place even when the end-user selects a different
        // theme.   They do this using private reflection to assign values to
        // the three state variables.

        //
        // This state (i.e. where the three variables have values that differ from
        // the ones we choose) is unsupported.  So is the technique for getting
        // into that state (i.e. private reflection).  Nevertheless, .Net wants
        // to preserve some level of compatibility - at the very least, avoid
        // crashing.  [The apps use the result of GetField("_isActive") without
        // checking for null.]
        //
        // We do this in three steps:
        // 1) preserve the three fields;  this fixes the crashes.

        // 2) if the app overrides the values, use the overridden values
        //      in preference to ours.

        // 3) during WM_THEMECHANGED, restore the preference for our values.

        //      If the app overrides them again, step (2) will kick in.

        // Note that step (3) will never happen if the app is intercepting
        // WM_THEMECHANGED.

        private static bool    _isActive;
        private static string  _themeName;
        private static string  _themeColor;
    }

也就是以上的写法是符合预期的

本文以上的测试代码放在githubgitee 欢迎访问

可以通过如下方式获取本文的源代码,先创建一个空文件夹,接着使用命令行 cd 命令进入此空文件夹,在命令行里面输入以下代码,即可获取到本文的代码

git init
git remote add origin https://gitee.com/lindexi/lindexi_gd.git
git pull origin 3a6a955fdd761b3f45d9195abc241c70574413d3

以上使用的是 gitee 的源,如果 gitee 不能访问,请替换为 github 的源

git remote remove origin
git remote add origin https://github.com/lindexi/lindexi_gd.git

获取代码之后,进入 BearweakiqeNurwhallcarnearcowar 文件夹

Original: https://www.cnblogs.com/lindexi/p/16733238.html
Author: lindexi
Title: WPF 切换主题使用 luna 复古版本

原创文章受到原创版权保护。转载请注明出处:https://www.johngo689.com/577724/

转载文章受原作者版权保护。转载请注明原作者出处!

(0)

大家都在看

  • Shiro结合Redis实现分布式或集群环境下的Session共享

    本篇是Shiro系列第二篇,使用Shiro基于Redis实现分布式或集群环境下的Session共享。在讲Session共享之前先说一下为什么要做Session共享。 什么是Sess…

    Linux 2023年5月28日
    0114
  • 聊斋-河间生

    人的善恶在转瞬之间就可以改变,发现错误时往往已经差之千里了,但是发现错误及时改正这不也是很美好的一件事情么?河间生就是讲了这么一件事情。 主角简介:河间某生,家里比较富裕,烧火用的…

    Linux 2023年6月14日
    0111
  • phpcms安装

    【快速安装开始】 下载解压phpcms,复制安装文件到站点目录”/opt/html”里,给予权限(官网无法访问了,所以下载地址需自行寻找上传) cd /us…

    Linux 2023年6月6日
    062
  • 从零开始制作一个linux iso镜像

    一、前言 对于一个极简化的linux系统而言,只需要三个部分就能组成,它们分别是一个linux内核、一个根文件系统和引导。以下是本文制作linux iso镜像所用到的系统和软件: …

    Linux 2023年5月27日
    076
  • EKS助力小白实践云原生——通过k8s部署wordpress应用

    目前云原生在大厂已经有了充分的实践,也逐渐向小厂以及非互联网公司推广。适逢12月20日,腾讯云原生【燎原社】精心打造了云原生在线技术工坊,让零基础的同学也能快速入门和实践 Dock…

    Linux 2023年6月13日
    076
  • 进程与fork

    进程(Process)是计算机中的程序关于某数据集合上的一次运行活动,是系统进行资源分配和调度的基本单位。在早期面向进程设计的计算机结构中,进程是程序的基本执行实体;在当代面向线程…

    Linux 2023年6月7日
    089
  • 使用shell脚本连接钉钉机器人发送消息

    一、前言 服务器上有时 定时任务、重要接口 等出现异常,导致数据不正常,不能及时通知到服务负责人,及时处理问题。所以引入”钉钉”作为通知工具,当服务出现异常…

    Linux 2023年5月28日
    0109
  • 关于连接服务器redis的教程

    第一步:下载RedisDesktopManager 这个百度一搜就有了,但是现在的版本ssh用不了建议找可以用的版本,这个百度,懂得都懂。 第二步:服务器宝塔redis设置 在配置…

    Linux 2023年6月11日
    075
  • Timeout connecting to [localhost/127.0.0.1:9200]

    空服务启动时(或者压根没引入es相关jar包)报Timeout connecting to [localhost/127.0.0.1:9200]错误时,查看pom.xml中是否引用…

    Linux 2023年6月7日
    0115
  • Linux查看服务器内存、磁盘、cpu、网络占用、端口占用情况

    1、查看物理CPU个数:cat cat /proc/cpuinfo | grep “physical id” | sort | uniq | wc -l2、…

    Linux 2023年6月13日
    0122
  • 位图实现

    位图就是用每个字节中的bit位代表一组资源的映射。 例如:一个字节有8位,在操作系统中可以用一个bit位代表一个4K的页,那一个字节就可以代表8页32K内存。 可以利用位图进行资源…

    Linux 2023年6月7日
    071
  • 1:文件与目录

    CD 切换当前工作目录 mkdir 创建目录 re -dir 删除目录 pwd 打印当前工作目录 绝对路径和相对路径 硬链接 和软链接 CP拷贝 MV 移动 dirname 和 b…

    Linux 2023年6月7日
    0128
  • 小白上手Linux系统安装Tomcat教程

    1.准备阶段: 要有JDK环境,在安装好JDK后再配置tomcat,JDK安装详情在我博客中可以看到。 3.导入 进入到Xshell输入在自己的文件中(cd /home/lzh)好…

    Linux 2023年6月13日
    093
  • redis启动失败 提示Unregistered Authentication Agent for unix-process:6176

    使用宝塔软件安装的redis 一直没启动起来。 使用 journalctl -xe 命令查看原因,发现redis.pid已经存在。 进入该目录,删除redis.pid。 再使用sy…

    Linux 2023年5月28日
    0325
  • 多进程知识简单总结

    多进程间的全局变量不共享 一、代码展示 import multiprocessing as mul_p import time egg1 = 1 def write(egg2, q…

    Linux 2023年6月14日
    077
  • Kubernetes 使用kubeadm创建集群

    实践环境 CentOS-7-x86_64-DVD-1810 Docker 19.03.9 Kubernetes version: v1.20.5 开始之前 1台Linux操作或更多…

    Linux 2023年5月27日
    0138
亲爱的 Coder【最近整理,可免费获取】👉 最新必读书单  | 👏 面试题下载  | 🌎 免费的AI知识星球