如晦 發表於 2025-3-24 02:54:00

WinForm 使用 Win32 API 实现的无边框窗口

<h1 id="winform-使用-win32-api-实现的无边框窗口">WinForm 使用 Win32 API 实现的无边框窗口</h1>
<p><img src="https://img2024.cnblogs.com/blog/352785/202503/352785-20250324025113271-1175315250.png" alt="效果图" loading="lazy"></p>
<h2 id="前言">前言</h2>
<p>时光荏苒,转眼已近是2025年了。不知不觉两年多没有研究代码了,在这期间 .NET 10 都快 RC 了,前几天刷手机看到张队公众号里有关于 .NET 9.0 AOT 发布的内容,所以写了这些代码来测试一下 AOT 编译的效果,并评估未来是否开发支持 AOT 编译的 NanUI 新版本。</p>
<p>关于 NanUI 项目,如果你还不了解,可以通过这个链接了解。</p>
<h2 id="项目介绍">项目介绍</h2>
<p>这个项目参考了老外的 C++ 代码,我用 C# 代码基于 WinForm 进行开发实现了一个简单的无边框窗口。其实在 NanUI 项目了已经有现成的无边框窗口实现,但那是基于 Form 类实现的。作为 Cef 浏览器的承载窗口其实只需要简单的窗体功能,Form 类提供的东西太多太杂反而在不同的 .NET 版本中还存在各种奇奇怪怪的问题。</p>
<p>所以我计划在未来版本的 NanUI 项目中,承载窗体将直接使用了 Win32 API 来创建,这样可以更好的统一窗体的行为。</p>
<p>本来这个项目可以使用纯 Win32 API 来实现,为什么我还是基于 WinForm 项目来编写呢?因为我懒得处理消息循环、DPI缩放等等问题, WinForm 已经帮我们处理好了。</p>
<p>目前代码已经推至 Gitee 仓库,有兴趣的朋友可以自行拉去研究。</p>
<h2 id="第三方库">第三方库</h2>
<ul>
<li>Vanara - MIT License</li>
</ul>
<h2 id="使用说明">使用说明</h2>
<p>不出意外的话,直接打开项目就可以运行了。运行后将打开一个无边框的窗体,你可以通过以下快捷键进行操作:</p>
<ul>
<li>F1 : 在普通窗体和无边框窗体之间进行实时切换</li>
<li>F2 : 在无边框窗体模式切换 DWM 的窗体阴影效果(Win7/Win10/Win11)</li>
<li>F3 : 在无边框窗体模式切换拖动窗体移动功能</li>
<li>F4 : 切换窗体的拖动改变大小功能</li>
</ul>
<h2 id="关于-aot-编译">关于 AOT 编译</h2>
<p>当前代码已经支持 .NET 9.0 AOT 编译,并且已经在 Windows 10 x64 系统和 Windows 11 上测试通过。如果你需要在其他平台上运行,请自行测试。</p>
<p>我在代码中尝试使用 WS_EX_NOREDIRECTIONBITMAP 来创建无重定向表面的窗口,并用 DwmSetWindowAttribute 方法设置 DWM_SYSTEMBACKDROP_TYPE 属性来启用 Windows 11 系统下面的 Mica 窗体背景特效。但可能是 Vanara 库的问题,一旦使用了 DwmSetWindowAttribute 方法,那么 AOT 编译后的程序运行就会崩溃。这个问题我还没有找到解决方案,我已经到 Vanara 的项目主页提交了 Issue,目前还没有得到该项目作者的回复。</p>
<p>由于 AOT 我并没有太深入的研究,所以如果有朋友知道如何解决欢迎交流。</p><br><br>
来源:https://www.cnblogs.com/linxuanchen/p/18788616
頁: [1]
查看完整版本: WinForm 使用 Win32 API 实现的无边框窗口