【问题标题】:Console image flickering in windows 10Windows 10 中的控制台图像闪烁
【发布时间】:2016-04-16 19:02:18
【问题描述】:

以下代码在 windows xp 中按预期工作,但在 windows 10 中,图像开始闪烁。如何让它在 Windows 10 中运行?

#include <windows.h>
#include <ctime>
#include <vector>

#define xMax 180
#define yMax 45
#define Fps 250

class dbconsole
{
private:
    int width, height, FPS, delay;
    HANDLE h0, h1;
    std::vector<CHAR_INFO> chiBuffer;
    bool curBuffer;
    int drawingTimer;

    void preparebuffer(HANDLE &h)
    {
        CONSOLE_CURSOR_INFO cursor = {false, 1};
        SMALL_RECT windowRectangle = {0,0,width-1,height-1};
        h = CreateConsoleScreenBuffer(
                GENERIC_READ | GENERIC_WRITE,
                FILE_SHARE_READ | FILE_SHARE_WRITE,
                NULL,
                CONSOLE_TEXTMODE_BUFFER,
                NULL);
        SetConsoleCursorInfo(h, &cursor);
        SetConsoleScreenBufferSize (h, {width,height});
        SetConsoleWindowInfo(h,true,&windowRectangle);
    }

public:

    dbconsole(int Width, int Height, int fps)
    {
        chiBuffer.reserve(Width*Height);
        width = Width;
        height = Height;
        FPS = fps;
        preparebuffer(h0);
        preparebuffer(h1);
        curBuffer = 0;
        drawingTimer = clock();
        for (int i = 0; i < xMax; i++) for (int j = 0; j < yMax; j++) chiBuffer[i+width*j] = {'t',16};
    }

    void depict()
    {
        SMALL_RECT srctWriteRect;
        srctWriteRect.Top = 0;
        srctWriteRect.Left = 0;
        srctWriteRect.Bottom = height-1;
        srctWriteRect.Right = width-1;
        if ((clock()-drawingTimer)*FPS>CLOCKS_PER_SEC)
        {
            if (curBuffer)
            {
                WriteConsoleOutput(h0, &chiBuffer[0], {width,height}, {0,0}, &srctWriteRect);
                SetConsoleActiveScreenBuffer(h0);
            }
            else
            {
                WriteConsoleOutput(h1, &chiBuffer[0], {width,height}, {0,0}, &srctWriteRect);
                SetConsoleActiveScreenBuffer(h1);
            }
            curBuffer=!curBuffer;
            drawingTimer = clock();
        }
    }

};

int main(void)
{
    dbconsole myConsole = dbconsole(xMax,yMax,Fps);
    while (true) myConsole.depict();
}

我希望程序在蓝色背景上显示黑色字母“t”,但没有闪烁和双缓冲

【问题讨论】:

  • 我记得早在 Windows 10 之前就有类似的问题...我不确定,但我认为那是 XP 时代。对我来说,解决方案是为当前屏幕缓冲区编写一个更新例程,而不是频繁切换缓冲区,但是我没有在那里达到 250 fps...
  • 切换到 60 fps 没有帮助。此外,此绘图适用于 Windows 8。我想使用这些控制台显示一些我可能需要立即重绘所有内容的信息,因此双缓冲似乎是必要的。
  • 当然...无论如何,60fps 可能是您的显示器刷新率。您应该降低到 1fps,以便评估单次刷新的效果。只要你能看到任何效果,它就会随着更快的更新而闪烁。
  • 1 fps 没有闪烁,但左上角出现一个光标,而我确信 CONSOLE_CURSOR_INFO cursor = {false, 1};应该隐藏它。
  • 那么,我不知道如何在 Windows 10 中隐藏光标,但我想您现在知道要查找什么就可以弄清楚了;)

标签: c++ console-application windows-10 doublebuffered


【解决方案1】:

好的,无论如何,在调查了问题之后,这是一个答案。

CONSOLE_CURSOR_INFO 被定义为第一个 DWORD dwSize 和第二个 BOOL bVisible 但你使用它就像第一个和第二个成员一样,反之亦然。因此,SetConsoleCursorInfo 失败,返回值 0GetLastError 返回 87,即 ERROR_INVALID_PARAMETER (See error codes)

正确禁用光标应该可以解决问题,尽管我没有可用于测试的 Windows 10。

【讨论】:

  • 谢谢,光标消失了,工作在1fps,但图像仍然在40fps闪烁
猜你喜欢
  • 1970-01-01
  • 2020-05-05
  • 1970-01-01
  • 2013-04-14
  • 1970-01-01
  • 1970-01-01
  • 2010-10-29
  • 2013-10-18
  • 1970-01-01
相关资源
最近更新 更多