This tutorial is part of the C/C++ & Win32 Game Programming Tutorials series.
Updated Apr 29, 2021

C/C++ & Win32 - Drawing Pixels (Game Programming Tutorial)

How to draw pixels on the screen using Windows API.

Code (main.cpp)

#include <windows.h>
#include <stdint.h>

typedef uint32_t u32;

int running = 1;
int width = 0;
int height = 0;

void* memory;
BITMAPINFO bitmap_info;

LRESULT CALLBACK 
WindowProc(HWND window, 
           UINT message, 
           WPARAM w_param, 
           LPARAM l_param)
{
    LRESULT result;
    switch(message)
    {
        case WM_CLOSE:
        {
            running = 0;
        } break;
        
        default:
        {
            result = DefWindowProc(window,
                                   message, 
                                   w_param, 
                                   l_param);
        } break;
    }
    
    return result;
}

int WINAPI 
wWinMain(HINSTANCE instance, 
         HINSTANCE prev_instance, 
         PWSTR cmd_line, 
         int cmd_show)
{
    WNDCLASS window_class = {0};
    
    wchar_t class_name[] = L"GameWindowClass";
    
    window_class.lpfnWndProc = WindowProc;
    window_class.hInstance = instance;
    window_class.lpszClassName = class_name;
    
    RegisterClass(&window_class);
    
    HWND window = CreateWindowEx(0,
                                 class_name,
                                 L"Game",
                                 WS_OVERLAPPEDWINDOW|WS_VISIBLE,
                                 CW_USEDEFAULT,
                                 CW_USEDEFAULT,
                                 CW_USEDEFAULT,
                                 CW_USEDEFAULT,
                                 0,
                                 0,
                                 instance,
                                 0);
    
    RECT rect;
    GetClientRect(window, &rect);
    width = rect.right - rect.left;
    height = rect.bottom - rect.top;
    
    memory = VirtualAlloc(0,
                          width * height * 4,
                          MEM_RESERVE|MEM_COMMIT,
                          PAGE_READWRITE
                          );
    
    u32 *pixel = (u32 *)memory; 
    
    for(int pixel_number = 0;
        pixel_number < width * height;
        ++pixel_number)
    {
        *pixel++ = 0xFF0000;
    }
    
    u32 red = 0xFF0000;
    u32 green = 0x00FF00;
    u32 blue = 0x0000FF;
    
    bitmap_info.bmiHeader.biSize = sizeof(bitmap_info.bmiHeader);
    bitmap_info.bmiHeader.biWidth = width;
    bitmap_info.bmiHeader.biHeight = height;
    bitmap_info.bmiHeader.biPlanes = 1;
    bitmap_info.bmiHeader.biBitCount = 32;
    bitmap_info.bmiHeader.biCompression = BI_RGB;
    
    HDC hdc = GetDC(window);
    
    while(running)
    {
        MSG message;
        while(PeekMessage(&message, window, 0, 0, PM_REMOVE))
        {
            TranslateMessage(&message);
            DispatchMessage(&message);
        }
        StretchDIBits(hdc,
                      0,
                      0,
                      width,
                      height,
                      0,
                      0,
                      width,
                      height,
                      memory,
                      &bitmap_info,
                      DIB_RGB_COLORS,
                      SRCCOPY
                      );
    }
    
    return 0;
}

Build script (build.bat)

@echo off
cl main.cpp /Fegame.exe ^
/Zi /nologo ^
/DUNICODE /D_UNICODE ^
user32.lib gdi32.lib
Leave comments on YouTube