|
马上注册,结交更多好友,享用更多功能^_^
您需要 登录 才可以下载或查看,没有账号?立即注册
x
- #include <windows.h>
- #include <strsafe.h>
- #include "sysmets.h"
- LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
- int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstcance, PSTR lpCmdLine, int iCmdShow)
- {
- HWND hwnd;
- MSG msg;
- WNDCLASS wndclass;
- //窗口类名
- WCHAR szClassName[] = TEXT("FristWindow");
- //初始化窗口类
- wndclass.style = CS_HREDRAW | CS_VREDRAW;
- wndclass.lpfnWndProc = WndProc;
- wndclass.cbClsExtra = 0;
- wndclass.cbWndExtra = 0;
- wndclass.hIcon = LoadIcon(NULL, IDI_APPLICATION);
- wndclass.hCursor = LoadCursor(NULL, IDC_ARROW);
- wndclass.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
- wndclass.hInstance = hInstance;
- wndclass.lpszClassName = szClassName;
- wndclass.lpszMenuName = NULL;
- //注册窗口类
- if (!RegisterClass(&wndclass))
- {
- MessageBox(NULL, TEXT("本程序只能在 WINDOWS NT 框架上运行!!!"), TEXT("提示信息:"), MB_OK | MB_ICONERROR);
- return 0;
- }
- //创建窗口
- hwnd = CreateWindow(szClassName, TEXT("FristWindow"), WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, NULL, NULL, hInstance, NULL);
- //显示并更新窗口
- ShowWindow(hwnd, iCmdShow);
- UpdateWindow(hwnd);
- //消息循环
- while (GetMessage(&msg, NULL, 0, 0))
- {
- TranslateMessage(&msg);
- DispatchMessage(&msg);
- }
- return msg.wParam;
- }
- LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
- {
- HDC hdc;
- RECT rect;
- PAINTSTRUCT ps;
- TEXTMETRIC tm;
- SCROLLINFO si;
- static int xChar, yChar, xUpper;
- static int xClient, yClient;
- int iVertPos;
- int iBeginPaint, iEndPaint;
- WCHAR szBuffer[128];
- switch (msg)
- {
- case WM_CREATE:
- //获取设备环境句柄
- hdc = GetDC(hwnd);
- //获取字体信息
- GetTextMetrics(hdc, &tm);
- //获取字体大小
- xChar = tm.tmAveCharWidth;
- yChar = tm.tmHeight + tm.tmExternalLeading;
- xUpper = (int)(tm.tmPitchAndFamily&1?3:2)*xChar/2;
- //清楚设备环境句柄
- ReleaseDC(hwnd, hdc);
- return 0;
- case WM_SIZE:
- //获得客户区的大小
- xClient = LOWORD(lParam);
- yClient = HIWORD(lParam);
- //设置 SCROLLINFO 结构信息
- //滑块的位置就是客户区 首行的需要打印元素的索引值
- si.cbSize = sizeof(si);
- si.fMask = SIF_RANGE | SIF_PAGE;
- si.nMax = NUMLINES - 1;
- si.nMin = 0;
- si.nPage = yClient / yChar;
- SetScrollInfo(hwnd, SB_VERT, &si, TRUE);
- return 0;
- case WM_VSCROLL:
- //获取 SCROLLINFO 的信息
- si.cbSize = sizeof(si);
- si.fMask = SIF_POS | SIF_PAGE|SIF_TRACKPOS;
- GetScrollInfo(hwnd, SB_VERT, &si);
- //获得当前滚动条的位置信息
- iVertPos = si.nPos;
- //处理垂直滚动条的信息
- switch (LOWORD(wParam))
- {
- case SB_LINEUP:
- si.nPos -= 1;
- break;
- case SB_LINEDOWN:
- si.nPos += 1;
- break;
- case SB_PAGEUP:
- si.nPos -= si.nPage;
- break;
- case SB_PAGEDOWN:
- si.nPos += si.nPage;
- break;
- case SB_THUMBTRACK:
- si.nPos = si.nTrackPos;
- break;
- }
- //设置 SCROLLINFO 的位置信息
- SetScrollInfo(hwnd, SB_VERT, &si, TRUE);
- //矫正 nPos 的值 使其控制在有效范围内
- GetScrollInfo(hwnd, SB_VERT, &si);
- //判断iVertPos位置是否改变
- if (iVertPos != si.nPos)
- {
- ScrollWindow(hwnd, 0, (iVertPos-si.nPos)*yChar, 0, 0);
- UpdateWindow(hwnd);
- }
- return 0;
- case WM_PAINT:
- hdc = BeginPaint(hwnd, &ps);
- //更新iVertPos使其保持在有效范围内
- si.cbSize = sizeof(si);
- si.fMask = SIF_POS;
- GetScrollInfo(hwnd, SB_VERT, &si);
- iVertPos = si.nPos;
- //获得索引值
- iBeginPaint = max(0, iVertPos+ps.rcPaint.top/yChar);
- iEndPaint = min(NUMLINES-1, iVertPos + ps.rcPaint.bottom / yChar);
- /*
- iVretPos 一直指向 当前客户区 的 首行索引值
- 无效区域的顶部 除以 字体高度 获得 是无效区域到客户区 的行距(偏移)
- */
- for (int i = iBeginPaint; i <= iEndPaint; i++)
- {
- TextOut(hdc, 20, (i - iVertPos)*yChar, sysmetrics[i].szLabel, lstrlen(sysmetrics[i].szLabel));
- /*
- i 表示 当前需要 打印 滑块 的位置信息
- iVerPost 表示客户区首行的滑块位置信息
- i - iVertPos 表示 当前需要打印的 偏移行数
- 乘以 行距 就获得 当前距离 客户区 首行的偏移 距离
- */
- }
- EndPaint(hwnd, &ps);
- break;
- case WM_CLOSE:
- PostQuitMessage(0);
- break;
- }
- return DefWindowProc(hwnd, msg, wParam, lParam);
- }
复制代码
谢谢了!!! |
|