JunRoss

 

Windows API窗口绘图实验|鼠标点击绘制随机大小红色正方形

一、实验简介

本次实验基于 Win32 Windows API 编写窗口程序,使用GDI完成绘图功能。
实验需求:

  1. 创建Windows窗口,窗口背景设置为黑色
  2. 在窗口内按下鼠标左键,在点击位置绘制正方形
  3. 正方形边长在10~100之间随机生成
  4. 正方形内部使用红色填充

二、本次代码用到的GDI核心对象与函数

  1. HDC 设备上下文句柄(Device Context)
    设备上下文DC相当于一块画布。要绘图,必须先拿到窗口的DC。
    GetDC(hWnd):获取窗口客户区的DC画布
    ReleaseDC(hWnd,hdc):释放DC。必须释放,否则造成资源泄漏

  2. 画刷 HBRUSH
    画刷用来填充图形内部颜色。
    CreateSolidBrush(RGB(r,g,b)):创建纯色画刷。RGB(255,0,0)代表红色。
    SelectObject(hdc,对象):把GDI对象(画笔/画刷)选入画布DC,保存旧对象。
    DeleteObject():删除手动创建的GDI对象。自定义创建的GDI对象,用完必须删除!

  3. 绘图函数 Rectangle
    Rectangle(hdc, x1,y1,x2,y2):绘制矩形(正方形属于特殊矩形)
    x1,y1:左上角坐标
    x2,y2:右下角坐标

    然后我们使用其他系统自带库存对象:BLACK_BRUSH黑色画刷,直接拿来设置窗口背景。

三、实机演示

image

四、完整源代码

#include <windows.h>
#include <stdlib.h>
#include <time.h>

//窗口过程回调函数声明
LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam);

//WinMain:Windows窗口程序入口函数
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
{
    WNDCLASSEX wc;
    HWND hWnd;
    MSG msg;

    //1.填充窗口类结构体
    wc.cbSize        = sizeof(WNDCLASSEX);
    wc.lpfnWndProc   = WndProc;         //绑定窗口过程回调函数
    wc.hInstance     = hInstance;
    wc.lpszClassName = L"DrawSquareClass";
    wc.style         = 0;
    wc.hCursor       = LoadCursor(NULL, IDC_ARROW);
    wc.hbrBackground = (HBRUSH)GetStockObject(BLACK_BRUSH);  //窗口背景:黑色
    wc.lpszMenuName  = NULL;
    wc.cbClsExtra    = 0;
    wc.hWndExtra    = 0;
    wc.hIcon         = LoadIcon(NULL, IDI_APPLICATION);
    wc.hIconSm       = LoadIcon(NULL, IDI_APPLICATION);

    RegisterClassEx(&wc); //注册窗口类

    //2.创建窗口
    hWnd = CreateWindowEx(
        0,
        L"DrawSquareClass",
        L"鼠标点击绘制随机红色正方形",
        WS_OVERLAPPEDWINDOW,
        200, 100, 600, 450,
        NULL, NULL, hInstance, NULL
    );

    ShowWindow(hWnd, nCmdShow);  //显示窗口
    UpdateWindow(hWnd);

    srand((unsigned int)time(NULL)); //设置随机数种子

    //消息循环,不断接收窗口消息
    while(GetMessage(&msg, NULL, 0,0) >0)
    {
        TranslateMessage(&msg);
        DispatchMessage(&msg);
    }
    return msg.wParam;
}

//窗口回调过程:处理窗口各类消息
LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
    HDC hdc;
    HBRUSH hRedBrush, hOldBrush;
    int x,y,side;
    switch(msg)
    {
        //鼠标左键按下消息
        case WM_LBUTTONDOWN:
        {
            hdc = GetDC(hWnd); //获取窗口画布DC

            //lParam存储鼠标坐标,LOWORD取x,HIWORD取y
            x = LOWORD(lParam);
            y = HIWORD(lParam);

            //随机边长,范围:10 ~ 100
            side = rand() % 91 + 10; 

            //创建红色纯色画刷 RGB(红,绿,蓝)
            hRedBrush = CreateSolidBrush(RGB(255,0,0));
            //将红色画刷选入DC,保存原来的画刷
            hOldBrush = (HBRUSH)SelectObject(hdc, hRedBrush);

            //绘制正方形:左上角(x,y),右下角(x+side,y+side)
            Rectangle(hdc, x, y, x+side, y+side);

            //恢复旧画刷
            SelectObject(hdc, hOldBrush);
            DeleteObject(hRedBrush); //释放自定义画刷GDI资源!
            ReleaseDC(hWnd,hdc);     //释放画布DC
            break;
        }
        case WM_DESTROY:
            PostQuitMessage(0);
            break;
        default:
            return DefWindowProc(hWnd, msg, wParam, lParam);
    }
    return 0;
}

posted on 2026-09-24 16:48  00后留声机  阅读(8)  评论(0)    收藏  举报

导航