Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/windows/16.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 如果过早获取窗口句柄,控制台窗口会被窃听。。?_C++_Windows_Winapi_Console_Console Application - Fatal编程技术网

C++ 如果过早获取窗口句柄,控制台窗口会被窃听。。?

C++ 如果过早获取窗口句柄,控制台窗口会被窃听。。?,c++,windows,winapi,console,console-application,C++,Windows,Winapi,Console,Console Application,我正在制作一个控制台应用程序,它必须是无边界的;为了实现这一点,我更改了控制台窗口样式和窗口区域,如下所示。 在某个时候,我遇到了一个问题,使得控制台窗口的大小通常约为2x1个字符,或者有时完全被窃听(不可见的客户端区域、部分白色、部分透明、随机边框等)。 有人告诉我添加ShowWindow(hWnd,SW_HIDE)到它现在所在的行可以解决问题。确实如此。 现在我想弄清楚为什么问题首先存在,还有没有其他方法来阻止呢 有人告诉我,问题可能会发生,因为Windows试图在我的程序运行的同时访问窗口

我正在制作一个控制台应用程序,它必须是无边界的;为了实现这一点,我更改了控制台窗口样式和窗口区域,如下所示。
在某个时候,我遇到了一个问题,使得控制台窗口的大小通常约为2x1个字符,或者有时完全被窃听(不可见的客户端区域、部分白色、部分透明、随机边框等)。
有人告诉我添加
ShowWindow(hWnd,SW_HIDE)到它现在所在的行可以解决问题。确实如此。
现在我想弄清楚为什么问题首先存在,还有没有其他方法来阻止呢

有人告诉我,问题可能会发生,因为Windows试图在我的程序运行的同时访问窗口属性(位置、样式、大小等)。不过,我不知道这是不是真的

#include <Windows.h>
#include <iostream>
int main()
{
    HANDLE hCon = GetStdHandle(STD_OUTPUT_HANDLE);

    SMALL_RECT srWnd = {0, 0, 1, 1};
    SetConsoleWindowInfo(hCon, 1, &srWnd);
    COORD cBuffSize = {81, 26};
    SetConsoleScreenBufferSize(hCon, cBuffSize);
    srWnd.Top = 0;
    srWnd.Right = 80;
    srWnd.Bottom = 25;
    srWnd.Left = 0;
    SetConsoleWindowInfo(hCon, 1, &srWnd);

    // When the next two lines are moved so that they are the first two lines inside main(), the window gets bugged.
    HWND hWnd = GetConsoleWindow();
    ShowWindow(hWnd, SW_HIDE); // Or if you just remove this line

    RECT rClnt;
    GetClientRect(hWnd, &rClnt);

    SetWindowLong(hWnd, GWL_STYLE, WS_POPUP);
    LONG exStyle = GetWindowLong(hWnd, GWL_EXSTYLE);
    exStyle &= ~(WS_EX_CLIENTEDGE | WS_EX_APPWINDOW);
    SetWindowLongPtr(hWnd, GWL_EXSTYLE, exStyle | WS_EX_TOOLWINDOW);

    rClnt.right += 1;
    HRGN rgnClnt = CreateRectRgnIndirect(&rClnt);
    SetWindowRgn(hWnd, rgnClnt, 1);

    RECT rScrn;
    GetWindowRect(GetDesktopWindow(), &rScrn);
    SetWindowPos(hWnd, HWND_TOPMOST, rScrn.right / 2 - rClnt.right / 2, rScrn.bottom / 2 - rClnt.bottom / 2, 0, 0, SWP_NOSIZE | SWP_FRAMECHANGED);

    ShowWindow(hWnd, SW_SHOW);

    std::cin.get();
    return 0;
}
#包括
#包括
int main()
{
句柄hCon=GetStdHandle(标准输出句柄);
SMALL_-RECT srWnd={0,0,1,1};
设置ConsoleWindowInfo(hCon、1和srWnd);
COORD cBuffSize={81,26};
设置控制台屏幕缓冲区大小(hCon、cBuffSize);
srWnd.Top=0;
srWnd.Right=80;
srWnd.Bottom=25;
srWnd.Left=0;
设置ConsoleWindowInfo(hCon、1和srWnd);
//当移动下两行以使其成为main()中的前两行时,窗口会被窃听。
HWND HWND=GetConsoleWindow();
ShowWindow(hWnd,SW_HIDE);//或者如果您只是删除这一行
RECT RCNT;
GetClientRect(hWnd和rClnt);
SetWindowLong(hWnd、GWL_样式、WS_弹出窗口);
LONG exStyle=GetWindowLong(hWnd,GWL_exStyle);
exStyle&=~(WS_EX_CLIENTEDGE | WS_EX_APPWINDOW);
SetWindowLongPtr(hWnd、GWL_EXSTYLE、EXSTYLE | WS_EX_TOOLWINDOW);
rClnt.right+=1;
HRGN rgnClnt=CreateRectRgnIndirect(&rClnt);
设置窗口rgn(hWnd,rgnClnt,1);
RECT-rScrn;
GetWindowRect(GetDesktopWindow(),&rScrn);
设置窗口位置(hWnd、hWnd_最上面、rScrn.right/2-RCNT.right/2、rScrn.bottom/2-RCNT.bottom/2、0、0、SWP_NOSIZE | SWP_框架已更改);
展示窗口(hWnd、SW_展示);
std::cin.get();
返回0;
}

以下是Windows 8的工作示例。但每次移动/调整/恢复控制台时,都需要刷新窗口区域

#include <windows.h>
#include <tchar.h>
#include <conio.h>
#include <dwmapi.h>

//#pragma comment(lib, "uxtheme.lib")
#pragma comment(lib, "dwmapi.lib")

int _tmain(int argc, _TCHAR* argv[])
{
    HWND hWnd = GetConsoleWindow();
    DWMNCRENDERINGPOLICY policy = DWMNCRP_DISABLED;
    DwmSetWindowAttribute(hWnd, DWMWA_NCRENDERING_POLICY, &policy, sizeof(DWMNCRENDERINGPOLICY));
    //SetThemeAppProperties(0);
    //SetWindowThemeNonClientAttributes(hWnd, STAP_VALIDBITS, 0);
    //SetWindowPos(hWnd, NULL, 0, 0, 0, 0, SWP_NOSIZE | SWP_NOMOVE | SWP_NOZORDER | SWP_FRAMECHANGED);
    //RedrawWindow(hWnd, NULL, NULL, RDW_INVALIDATE | RDW_UPDATENOW);
    RECT rClnt, rWnd;
    GetClientRect(hWnd, &rClnt);
    GetWindowRect(hWnd, &rWnd);
    POINT pt = {0,0};
    MapWindowPoints(hWnd, NULL, &pt, 1);
    OffsetRect(&rClnt, pt.x-rWnd.left, pt.y-rWnd.top);
    HRGN rgnClnt = CreateRectRgnIndirect(&rClnt);
    SetWindowRgn(hWnd, rgnClnt, 1);

    _getch();
    return 0;
}
#包括
#包括
#包括
#包括
//#pragma注释(lib,“uxtheme.lib”)
#pragma注释(lib,“dwmapi.lib”)
int _tmain(int argc,_TCHAR*argv[]
{
HWND HWND=GetConsoleWindow();
DWMNCRENDERINGPOLICY policy=DWMNCRP_已禁用;
DwmSetWindowAttribute(hWnd、DWMWA_NCRENDERING_POLICY和POLICY、sizeof(DWMNCRENDERINGPOLICY));
//设置EAPProperties(0);
//设置WindowTheMeNonClientAttributes(hWnd,STAP_有效位,0);
//设置窗口位置(hWnd、NULL、0、0、0、SWP|u NOSIZE | SWP|u NOMOVE | SWP|u NOZORDER | SWP|u FRAMECHANGED);
//重画窗口(hWnd,NULL,NULL,RDW_INVALIDATE | RDW_UPDATENOW);
RECT RCNT,rWnd;
GetClientRect(hWnd和rClnt);
GetWindowRect(hWnd和rWnd);
点pt={0,0};
MapWindowPoints(hWnd、NULL和pt,1);
偏斜(&RCNT,横截面x-rWnd.left,横截面y-rWnd.top);
HRGN rgnClnt=CreateRectRgnIndirect(&rClnt);
设置窗口rgn(hWnd,rgnClnt,1);
_getch();
返回0;
}