我如何制作屏幕缓冲区C ++

时间:2019-02-05 16:40:21

标签: c++ windows graphics

我希望能够将所有文本,线条,三角形和其他内容绘制到屏幕上,然后清除屏幕并绘制一些新内容,但是此方法会使屏幕闪烁,并且所有图形都不会同时出现

我的想法是绘制某种缓冲区,然后将该缓冲区绘制到屏幕上并清除缓冲区,然后重复。这样,屏幕将不会闪烁,并且所有画面将同时绘制。

我正在使用Windows.h和Visual Studio。

#include <Windows.h>
#include <iostream>
using namespace std;

struct vec2d
{
    int x, y;
};

void Line(HDC dc, vec2d a, vec2d b)
{
    MoveToEx(dc, a.x, a.y, NULL);
    LineTo(dc, b.x, b.y);
}

vec2d GetMousePos(HWND console)
{
    vec2d out;
    POINT p;
    GetCursorPos(&p);
    out.x = p.x; out.y = p.y;       
    return out;
}

int main()
{
    HWND console = GetConsoleWindow();
    HDC dc = GetDC(console);
    SelectObject(dc, CreatePen(PS_SOLID, 1, RGB(255, 255, 255)));

    while (1)
    {
        //BitBlt(dc, 0, 0, 1000, 1000, 0, 0, 0, BLACKNESS);        Flickering is much much bigger, because its faster
        system("cls");
        Line(dc, { 0, 0 }, GetMousePos(console));       
    }
}

谢谢,马克。

1 个答案:

答案 0 :(得分:1)

我认为您对控制台窗口的控制不如对自己的HWND的控制。通过将system("cls");替换为InvalidateRect(),我可以消除代码中的闪烁。

RECT client;
GetClientRect(console, &client);
while (1)
{
    InvalidateRect(console, &client, TRUE);
    Line(dc, console, { 0, 0 }, GetMousePos(console));
}

(您可以通过仅使绘制上一行的区域无效来改善此问题。)

此外,您可以进行的另一项更改(与闪烁无关)是添加:

ScreenToClient(console, &p);
呼叫GetMousePos()后,

GetCursorPos(&p);。这会将指针坐标映射到窗口而不是屏幕。

进一步了解如何创建自己的窗口:Creating a Window。不像使用控制台窗口那样简单,但是您拥有更大的控制权。