Windows 桌面應用程式(WinUI 3、WPF、WinForms、控制台)有時需要呼叫其管理框架外的 API。 本頁能幫助你了解何時發生這種情況,並選擇合適的技巧。
兩個 API 表面,兩個互操作模式
Windows 透過兩個主要的 API 介面來展示功能:
Win32 API — 從系統 DLL
user32.dll(、kernel32.dllshell32.dll等)匯出的經典 C 風格函式。 這些內容涵蓋了低階操作,如視窗管理、檔案輸入輸出、流程控制及硬體存取。 它們自 Windows 的早期版本以來就已存在,至今仍是存取許多沒有對應受控版本之作業系統功能的途徑。Windows 執行階段(WinRT)API — 一種現代化的物件導向 API 表面(命名空間以
Windows.*以 開頭),於 Windows 8 中引入。 WinRT API 涵蓋通知、媒體擷取、藍牙、地理定位等領域。 大多數 WinRT API 都可直接透過 .NET 存取,無需特別處理,但有些 API 在桌面應用程式中會受到限制,或需要視窗控制代碼(HWND)才能運作。
當你遇到互通性時
通常當你的應用程式框架沒有直接暴露特定作業系統能力時,你需要互通性。 常見情況包括:
| Scenario | 哪個 API 介面 | Example |
|---|---|---|
| 自訂標題列或視窗位置 | Win32 |
SetWindowPos、DwmExtendFrameIntoClientArea |
| 將視窗設為「永遠在上方」或控制 Z 順序 | Win32 |
SetWindowPos 和 HWND_TOPMOST |
| 顯示 WinUI 3 中的檔案選擇器或分享對話框 | WinRT(需要 HWND) |
FileOpenPicker 和 InitializeWithWindow |
| 讀取系統記憶體或效能計數器 | Win32 |
GlobalMemoryStatusEx、QueryPerformanceCounter |
| 註冊一個全域熱鍵 | Win32 | RegisterHotKey |
| 發送吐司通知(未封裝應用程式) | WinRT(搭配 App SDK) | AppNotificationManager |
在所有這些情況下,你都是寫一般的 C# 程式碼,但透過互操作層呼叫 Windows。 以下主題將引導你了解每種方法。
決策指南
| 我需要...... | 建議方法 | Topic |
|---|---|---|
| 從 C 調用 Win32 API (user32、kernel32、shell32 等)# | 使用 CsWin32 原始碼產生器 — 類型安全,無手寫簽章 | 從 C# 呼叫 Win32 API(CsWin32) |
| 初始化一個帶有視窗句柄的 WinRT 物件 (選擇器、對話框、共享介面) | 使用 .NET WinRT COM 互操作類別(InitializeWithWindow、 WindowNative、 等) |
從 .NET 應用程式呼叫 Interop API |
| 檢查 WinRT API 是否能在 桌面(非 UWP)應用程式中運作 | 請參閱限制與替代方案清單 | 桌面應用程式不支援的 WinRT API |
| 請參考完整的 WinUI 3 範例 ,利用 Win32 呼叫自訂視窗 | 請跟隨端到端的攻略 | 攻略:WinUI 3 應用程式與 Win32 互通 |
快速流程圖
API 是否位於
Windows.*WinRT 命名空間中?- 是的 → 請參閱 桌面應用程式不支援的 WinRT API,了解相關限制。 如果 API 需要視窗句柄,請參考 .NET 應用程式的呼叫互操作 API。
- 沒有→繼續第二步。
它是 Win32/原生 API(定義於 Windows SDK 標頭檔中)嗎?
- 是的,→使用 CsWin32 來產生型別安全的 P/Invoke 綁定。
- 不→可能是 COM 介面或第三方原生函式庫。 如需 P/Invoke 的一般指引,請參閱 .NET 與原生程式碼互通。