长春网站建设吉网传媒实力牜,wordpress seo怎么做,多语言建设外贸网站,百度热搜风云榜随着Win11的普及#xff0c;越来越多的人都能发现获取控制台窗口不能再使用以下两种传统方法了#xff1a;
HWND hwnd GetConsoleWindow();HWND hwnd FindWindowA(ConsoleWindowClass,NULL);那是因为win11换了新的终端窗口#xff0c;叫做WindowsTerminal越来越多的人都能发现获取控制台窗口不能再使用以下两种传统方法了
HWND hwnd GetConsoleWindow();HWND hwnd FindWindowA(ConsoleWindowClass,NULL);那是因为win11换了新的终端窗口叫做WindowsTerminal高端大气字体看得也舒服。 ↑如果你想换回旧版控制台主机可以右键标题栏“Settings”进入设置按上图操作
不过这个窗口是真的很难抓 第一 不推荐使用GetForegroundWindow风险太大容易抓成别的窗口准确率低 第二 GetConsoleWindow已经无法获取该窗口 第三 FindWindow(“ConsoleWindowClass”,NULL)也不能抓新的终端 第四 抓类名用第三方工具获得新终端类名我这里是CASCADIA_HOSTING_WINDOW_CLASS 。用FindWindow我这里失败了。。 第五 我去问ChatGPT(3.5)它的回答是
在 Windows 11 中Windows Terminal 可能使用了不同的机制来管理其窗口句柄可能会导致传统的方法无法准确地获取到正确的窗口句柄。 尝试使用 FindWindow 可能不会成功是因为该函数是基于窗口类名或窗口标题来查找窗口的而 Windows Terminal 可能没有传统的类名或标题。 另一个选择是尝试使用 Windows 11 的新 API例如 Windows.UI.Xaml 应用程序的 API。你可以考虑使用 Universal Windows Platform (UWP) 或 Windows Runtime (WinRT) API来与 Windows Terminal 进行交互。 以下是可能用于获取 Windows Terminal 窗口句柄的一种方法但请注意这只是一个示例并不保证可以直接适用于你的情况而且需要你对 UWP 或 WinRT 有一定的了解
#include windows.h
#include winrt/Windows.UI.Composition.h
#include winrt/Windows.UI.Xaml.Hosting.husing namespace winrt::Windows::UI::Composition;
using namespace winrt::Windows::UI::Xaml::Hosting;HWND GetWindowsTerminalWindowHandle() {HWND terminalWindowHandle nullptr;try {// 初始化Windows Runtimewinrt::init_apartment();// 获取Windows Terminal的主机对象auto terminalHost DesktopWindowXamlSource();// 获取Windows Terminal的根Visual对象auto terminalVisual ElementCompositionPreview::GetElementVisual(terminalHost);// 获取Windows Terminal的窗口句柄terminalHost.Handle(terminalWindowHandle);} catch (winrt::hresult_error const ex) {// 处理异常// 可以在这里输出错误信息调试问题}return terminalWindowHandle;
}int main() {HWND terminalWindow GetWindowsTerminalWindowHandle();if (terminalWindow ! nullptr) {// 在这里使用获取到的窗口句柄进行你需要的操作} else {// 获取窗口句柄失败处理错误}return 0;
}请注意这段代码假设你已经配置好了相应的开发环境并且能够正确地使用 WinRT 和 UWP API。在使用这些 API 时你需要适当的访问权限和合适的配置。 记住由于 Windows Terminal 可能采用了新的技术和 API因此获取其窗口句柄可能需要更多针对性的方法并且需要根据具体情况进行调整。
有没有那俩头文件、能不能用是一回事不过这明摆的是C(11)啊我要求是C语言。
于是我的方案是 第一FindWindow只抓标题。 没试过但应该可以不过标题一定要一字不差。
第二枚举窗口如果有窗口对应的PID对应的进程名叫WindowsTerminal.exe且标题是正确的标题则为正确的窗口句柄。 这个方案成功了我把代码放一下该代码的作用是自动判断是否用的是新终端如果是则抓如果不是则抓旧版控制台
HWND hwnd NULL;
bool ExistProcess(LPCSTR lpName) //判断是否存在指定进程
{ //******警告区分大小写******// //*****警告必须加扩展名*****// HANDLE hSnapshot CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0); if (INVALID_HANDLE_VALUE hSnapshot) { return false; } PROCESSENTRY32 pe { sizeof(pe) }; BOOL fOk; for (fOk Process32First(hSnapshot, pe); fOk; fOk Process32Next(hSnapshot, pe)) { if (! stricmp(pe.szExeFile, lpName)) { CloseHandle(hSnapshot); return true; } } return false;
}
bool TerminalCheck(DWORD dwPid, HWND _hwnd)
{HANDLE hSnapshot CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0); if (INVALID_HANDLE_VALUE hSnapshot) { return false; } PROCESSENTRY32 pe { sizeof(pe) }; BOOL fOk; for (fOk Process32First(hSnapshot, pe); fOk; fOk Process32Next(hSnapshot, pe)) { if (! stricmp(pe.szExeFile, WindowsTerminal.exe) //进程名 pe.th32ProcessID dwPid) { //stricmp不区分大小写的字符串比较CloseHandle(hSnapshot); {char title[MAX_PATH];GetWindowText(_hwnd, title, MAX_PATH);if(strcmp(title, _pgmptr) strcmp(title, 学生管理系统 CURRENT_VERSION)) //_pgmptr是本体路径用于还没来得及改标题的情况 后面那个则是具体你设的标题自定义即可return false;return true;} } } return false;
}
BOOL CALLBACK EnumWindowsProc(HWND _hwnd, LPARAM lParam)
{ //回调函数DWORD pid;GetWindowThreadProcessId(_hwnd, pid);if(TerminalCheck(pid, _hwnd)){printf(Terminal Found! pid%ld hwnd%p\n, pid, _hwnd);hwnd _hwnd;return FALSE; //返回false中断枚举}return TRUE;
}int main(int argc, char* argv[])
{if(ExistProcess(WindowsTerminal.exe)){ //win11电脑且使用新版终端EnumWindows(EnumWindowsProc, 0);}else{ //旧版控制台主机hwnd GetConsoleWindow();}//再不行就只能GetForegroundWindow了if(!hwnd || hwnd INVALID_HANDLE_VALUE){hwnd GetForegroundWindow();printf(Failed! using GetForegroundWindow...);}//其他的一些事情...return 0;
}必要的头文件stdio.h stdlib.h windows.h tlhelp32.h stdbool.h string.h
去试试看行不行我刚试成功的代码