Maui的學習之路
作為 Maui
的先行者,我有話要說,微軟你為了讓我成為牛 B 的程序員真的是煞費苦心,你一定是覺得我不夠牛逼所以針對我,存心想氣死我。
好了廢話不多說,Maui
現在也算是正式發布了,我有點想用它來做一個桌面應用最好是支持 Windows
和 Mac
(當然 Linux
我也想,但是微軟不給我),于是我開始著手搞了起來。按照官方教程,下載安裝 vs2022
最新預覽版(Mac
也一樣),勾選 Maui
相關工作負載,創建 Maui
模板程序,直接編譯運行,一頓操作行云流水,順利的讓人直呼有戲。
OK,程序運行完美,Mac 上也很完美,而且一套代碼在 Window
和 Mac
上無縫運行,這很 nice
,我開始有點信心滿滿。作為一名牛逼程序員我必須要有點自己的想法,比如我想做一個無邊框的桌面應用,這應該很 easy
,只需要更改 windowstyle
為 none(我以為是這樣),因為一直以來都是這樣,于是我也準備這樣去做。可是找了半天無論是 Window
類或是 MauiWinUIWindow
還是 UIWindow
都沒有。
我一定是眼花了,我需要更加仔細一點,我提醒自己,于是我又花了半個小時仔細找了一遍,甚至還看了點 Maui
的源碼(雖然我沒看懂)。是的,我沒有看錯,是真的沒有,好吧是我想得太簡單了,作為跨平臺程序要考慮那么多平臺,這不是件容易的事,我安慰自己。
好的此路不通,那么我去看看Maui
的官方教程,這一定有畢竟是官方教程嗎?應該很全面。于是我又花了半個小時,看了一遍教程,很抱歉還是沒有,嗯這是一件極其難的事情,畢竟是跨平臺嗎,可以理解。那我去找找WinUI
的官方教程吧,畢竟是用的WinUI3
。說干就干,我三下五除二直奔主體,功夫不負有心人,終于在標題欄里面找到了答案,雖然有答案,但是我還是想說微軟真有你的,你做的這破玩意兒跟 mfc
有啥區別幾乎就是原生 api
的簡單封裝嗎,不愧是你 --- 我的巨硬(此處喊破喉嚨) 。
我呵呵一笑,于是寫下了 Maui
Windows
桌面程序修改標題欄的葵花寶典,只見上面密密麻麻寫著坑爹。秘籍如下:
1、 你一定要有耐心;
2、 你一定要有耐心;
3、 你一定要有耐心;
4、 在使用該方案前你一定要注冊 Windows 下的生命周期函數,參考文檔:應用生命周期 - .NET MAUI | Microsoft Docs[1],你也可以不用這個方法,而是在 app
下重寫 OnCreate
函數;
注冊
生命周期函數

重寫
OnCreate
方法


5、 你一定要將 Maui Windows
下自帶的 ExtendsContentIntoTitleBar
設置為 false
(這很重要,另外 Maui Window
類下有一個 SetTitleBar
,對不起這不是你想的那樣,怎么修改他都無效,可能是我太水沒找到方法)
6、 使用 Maui 窗口句柄(Windows
平臺),獲取 AppWindow
,修改 AppWindow
下的 TitleBar
的相關屬性,參考文檔:標題欄自定義 - Windows apps | Microsoft Docs [2]

7、 完成以上步驟,那么恭喜你,你可以擁有一個無標題欄的窗口了(實際標題欄還在,只不過和下面的正式內容合并在一起了);
8、 好了完成了上述步驟,那么你一定也想做個,可以任意控制窗體初始化大小,以及最大化窗口的功能,這很抱歉,這真的是太難了。廢話不多說,直接上代碼,參考文檔:AppWindow Class (Microsoft.UI.Windowing) - Windows App SDK | Microsoft Docs [3]
a) 窗體最大化需要調用 Win32Api
,給窗體發送最大化事件(我做了簡單的封裝有需要的小伙伴可以找我要,也許還有別的方案只是我太笨)

b) 改變窗體大小需要調用 AppWindow
的 MoveAndResize
注意這個函數內部并沒有考慮過 Dpi 縮放的問題,需要你自己解決

c) 啟用全屏,需要使用 AppWindowPresenter
,參考文檔:AppWindowPresenter Class (Microsoft.UI.Windowing) - Windows App SDK | Microsoft Docs[4]

終于一個簡單的窗體指定窗體大小、最大化窗體、無邊框的窗體終于完成了,這確實很簡單,滿滿的都是淚(現在還有一些問題就是標題欄拖動會影響按鈕沒法點擊)。
最后,我只能發出無能狂怒,巨硬,下次請把我當傻子可以嗎?
參考資料
[1]
參考文檔:應用生命周期 - .NET MAUI | Microsoft Docs: https://docs.microsoft.com/zh-cn/dotnet/maui/fundamentals/app-lifecycle
[2]參考文檔:標題欄自定義 - Windows apps | Microsoft Docs : https://docs.microsoft.com/zh-cn/windows/apps/develop/title-bar?tabs=wasdk
[3]參考文檔:AppWindow Class (Microsoft.UI.Windowing) - Windows App SDK | Microsoft Docs : https://docs.microsoft.com/zh-CN/windows/windows-app-sdk/api/winrt/microsoft.ui.windowing.appwindow?view=windows-app-sdk-1.0
[4]參考文檔:AppWindowPresenter Class (Microsoft.UI.Windowing) - Windows App SDK | Microsoft Docs: https://docs.microsoft.com/zh-CN/windows/windows-app-sdk/api/winrt/microsoft.ui.windowing.appwindowpresenter?view=windows-app-sdk-1.0