C++ Win32 GUI 应用程序,控制台提示符在程序退出后覆盖以前记录的文本

C++ Win32 GUI App, Console prompt overwrites previous logged text after program exit

提问人:Igor Teixeira 提问时间:8/18/2023 最后编辑:Igor Teixeira 更新时间:8/18/2023 访问量:111

问:

操作系统是 Windows 10

应用程序与 /SUBSYSTEM:WINDOWS 链接,控制台 Attached/Allocated 和 Input/Output 流重定向如下:

void InitConsole()
{
    if (AttachConsole(ATTACH_PARENT_PROCESS) || AllocConsole()) {
        SetConsoleOutputCP(CP_UTF8);

        FILE* dummy;
        freopen_s(&dummy, "CONIN$", "r", stdin);
        freopen_s(&dummy, "CONOUT$", "w", stdout);
        freopen_s(&dummy, "CONOUT$", "w", stderr);

        DWORD consoleMode;
        GetConsoleMode(GetStdHandle(STD_OUTPUT_HANDLE), &consoleMode);
        consoleMode |= ENABLE_VIRTUAL_TERMINAL_PROCESSING;
        SetConsoleMode(GetStdHandle(STD_OUTPUT_HANDLE), consoleMode);

        std::ios::sync_with_stdio(true);

        std::wcout.clear();
        std::cout.clear();
        std::wcerr.clear();
        std::cerr.clear();
        std::wcin.clear();
        std::cin.clear();
    }
}

这有效,文本以颜色等显示,但是在程序退出后,控制台提示符会覆盖记录的文本,而不是从结束的地方继续:

提示的 GIF 覆盖了记录的文本

这发生在 Windows 终端、PowerShell命令提示符以及 VSCode 集成终端上。

使用 fmtlib 记录文本。然而,行为同样错误。std::coutprintf()

有没有办法将此行为更正为更熟悉的控制台提示,从使用 /SUBSYSTEM:WINDOWS 时记录的文本结束的位置继续?这样:

预期行为的图像

预期行为是通过在不调用函数的情况下使用 /SUBSYSTEM:CONSOLE 实现的。InitConsole()

最小可重现示例:(与 /SUBSYSTEM:WINDOWS 链接)

#define UNICODE
#define _UNICODE
#include <iostream>
#include <windows.h>

int WINAPI wWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, PWSTR pCmdLine, int nCmdShow)
{
    if (AttachConsole(ATTACH_PARENT_PROCESS) || AllocConsole()) {
        SetConsoleOutputCP(CP_UTF8);

        FILE* dummy;
        freopen_s(&dummy, "CONIN$", "r", stdin);
        freopen_s(&dummy, "CONOUT$", "w", stdout);
        freopen_s(&dummy, "CONOUT$", "w", stderr);

        DWORD consoleMode;
        GetConsoleMode(GetStdHandle(STD_OUTPUT_HANDLE), &consoleMode);
        consoleMode |= ENABLE_VIRTUAL_TERMINAL_PROCESSING;
        SetConsoleMode(GetStdHandle(STD_OUTPUT_HANDLE), consoleMode);

        std::ios::sync_with_stdio(true);

        std::wcout.clear();
        std::cout.clear();
        std::wcerr.clear();
        std::cerr.clear();
        std::wcin.clear();
        std::cin.clear();
    }

    std::cout << "Test Text 1\n";
    std::cout << "Test Text 2\n";
    std::cout << "Test Text 3\n";

    FreeConsole();

    return 0;
}

C++ WinAPI 控制台 cout

评论


答:

0赞 Ted Lyngmo 8/18/2023 #1

当编译为 Windows 程序时,它会异步启动 - 可以说是在后台 - 并且命令提示符立即出现。它不会等待程序完成。

如果您不希望命令提示符在程序完成之前出现,我建议将其编译为控制台程序。