windows程序设计第八章计时器中的一个小程序
虽然小,但是读起来收获颇大
上代码:
1 /*----------------------------------------- 2 DIGCLOCK.c -- Digital Clock 3 (c) Charles Petzold, 1998 4 -----------------------------------------*/ 5 6 #include <windows.h> 7 8 #define ID_TIMER 1 9 10 LRESULT CALLBACK WndProc (HWND, UINT, WPARAM, LPARAM) ; 11 12 int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance, 13 PSTR szCmdLine, int iCmdShow) 14 { 15 static TCHAR szAppName[] = TEXT ("DigClock") ; 16 HWND hwnd ; 17 MSG msg ; 18 WNDCLASS wndclass ; 19 20 wndclass.style = CS_HREDRAW | CS_VREDRAW ; 21 wndclass.lpfnWndProc = WndProc ; 22 wndclass.cbClsExtra = 0 ; 23 wndclass.cbWndExtra = 0 ; 24 wndclass.hInstance = hInstance ; 25 wndclass.hIcon = LoadIcon (NULL, IDI_APPLICATION) ; 26 wndclass.hCursor = LoadCursor (NULL, IDC_ARROW) ; 27 wndclass.hbrBackground = (HBRUSH) GetStockObject (WHITE_BRUSH) ; 28 wndclass.lpszMenuName = NULL ; 29 wndclass.lpszClassName = szAppName ; 30 31 if (!RegisterClass (&wndclass)) 32 { 33 MessageBox (NULL, TEXT ("Program requires Windows NT!"), 34 szAppName, MB_ICONERROR) ; 35 return 0 ; 36 } 37 38 hwnd = CreateWindow (szAppName, TEXT ("Digital Clock"), 39 WS_OVERLAPPEDWINDOW, 40 CW_USEDEFAULT, CW_USEDEFAULT, 41 CW_USEDEFAULT, CW_USEDEFAULT, 42 NULL, NULL, hInstance, NULL) ; 43 44 ShowWindow (hwnd, iCmdShow) ; 45 UpdateWindow (hwnd) ; 46 47 while (GetMessage (&msg, NULL, 0, 0)) 48 { 49 TranslateMessage (&msg) ; 50 DispatchMessage (&msg) ; 51 } 52 return msg.wParam ; 53 } 54 55 void DisplayDigit (HDC hdc, int iNumber) 56 { 57 static BOOL fSevenSegment [10][7] = { 58 1, 1, 1, 0, 1, 1, 1, // 0 59 0, 0, 1, 0, 0, 1, 0, // 1 60 1, 0, 1, 1, 1, 0, 1, // 2 61 1, 0, 1, 1, 0, 1, 1, // 3 62 0, 1, 1, 1, 0, 1, 0, // 4 63 1, 1, 0, 1, 0, 1, 1, // 5 64 1, 1, 0, 1, 1, 1, 1, // 6 65 1, 0, 1, 0, 0, 1, 0, // 7 66 1, 1, 1, 1, 1, 1, 1, // 8 67 1, 1, 1, 1, 0, 1, 1 } ; // 9 68 static POINT ptSegment [7][6] = { 69 7, 6, 11, 2, 31, 2, 35, 6, 31, 10, 11, 10, 70 6, 7, 10, 11, 10, 31, 6, 35, 2, 31, 2, 11, 71 36, 7, 40, 11, 40, 31, 36, 35, 32, 31, 32, 11, 72 7, 36, 11, 32, 31, 32, 35, 36, 31, 40, 11, 40, 73 6, 37, 10, 41, 10, 61, 6, 65, 2, 61, 2, 41, 74 36, 37, 40, 41, 40, 61, 36, 65, 32, 61, 32, 41, 75 7, 66, 11, 62, 31, 62, 35, 66, 31, 70, 11, 70 } ; 76 int iSeg ; 77 78 for (iSeg = 0 ; iSeg < 7 ; iSeg++) 79 if (fSevenSegment [iNumber][iSeg]) 80 Polygon (hdc, ptSegment [iSeg], 6) ; 81 } 82 83 void DisplayTwoDigits (HDC hdc, int iNumber, BOOL fSuppress) 84 { 85 if (!fSuppress || (iNumber / 10 != 0)) 86 DisplayDigit (hdc, iNumber / 10) ; 87 88 OffsetWindowOrgEx (hdc, -42, 0, NULL) ; 89 DisplayDigit (hdc, iNumber % 10) ; 90 OffsetWindowOrgEx (hdc, -42, 0, NULL) ; 91 } 92 93 void DisplayColon (HDC hdc) 94 { 95 POINT ptColon [2][4] = { 2, 21, 6, 17, 10, 21, 6, 25, 96 2, 51, 6, 47, 10, 51, 6, 55 } ; 97 98 Polygon (hdc, ptColon [0], 4) ; 99 Polygon (hdc, ptColon [1], 4) ; 100 101 OffsetWindowOrgEx (hdc, -12, 0, NULL) ; 102 } 103 104 void DisplayTime (HDC hdc, BOOL f24Hour, BOOL fSuppress) 105 { 106 SYSTEMTIME st ; 107 108 GetLocalTime (&st) ; 109 110 if (f24Hour) //小时 111 DisplayTwoDigits (hdc, st.wHour, fSuppress) ; 112 else 113 DisplayTwoDigits (hdc, (st.wHour %= 12) ? st.wHour : 12, fSuppress) ; 114 115 DisplayColon (hdc) ; //冒号 116 DisplayTwoDigits (hdc, st.wMinute, FALSE) ;//分钟 117 DisplayColon (hdc) ; //冒号 118 DisplayTwoDigits (hdc, st.wSecond, FALSE) ;//秒 119 } 120 121 LRESULT CALLBACK WndProc (HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) 122 { 123 static BOOL f24Hour, fSuppress ; 124 static HBRUSH hBrushRed ; 125 static int cxClient, cyClient ; 126 HDC hdc ; 127 PAINTSTRUCT ps ; 128 TCHAR szBuffer [2] ; 129 130 switch (message) 131 { 132 case WM_CREATE: 133 hBrushRed = CreateSolidBrush (RGB (255, 0, 0)) ; 134 SetTimer (hwnd, ID_TIMER, 1000, NULL) ; 135 136 // fall through 137 138 case WM_SETTINGCHANGE: 139 GetLocaleInfo (LOCALE_USER_DEFAULT, LOCALE_ITIME, szBuffer, 2) ; 140 f24Hour = (szBuffer[0] == '1') ; 141 142 GetLocaleInfo (LOCALE_USER_DEFAULT, LOCALE_ITLZERO, szBuffer, 2) ; 143 fSuppress = (szBuffer[0] == '0') ; 144 145 InvalidateRect (hwnd, NULL, TRUE) ; 146 return 0 ; 147 148 case WM_SIZE: 149 cxClient = LOWORD (lParam) ; 150 cyClient = HIWORD (lParam) ; 151 return 0 ; 152 153 case WM_TIMER: 154 InvalidateRect (hwnd, NULL, TRUE) ; 155 return 0 ; 156 157 case WM_PAINT: 158 hdc = BeginPaint (hwnd, &ps) ; 159 160 SetMapMode (hdc, MM_ISOTROPIC) ; 161 SetWindowExtEx (hdc, 276, 72, NULL) ; 162 SetViewportExtEx (hdc, cxClient, cyClient, NULL) ; 163 164 SetWindowOrgEx (hdc, 138, 36, NULL) ; 165 SetViewportOrgEx (hdc, cxClient / 2, cyClient / 2, NULL) ; 166 167 SelectObject (hdc, GetStockObject (NULL_PEN)) ; 168 SelectObject (hdc, hBrushRed) ; 169 170 DisplayTime (hdc, f24Hour, fSuppress) ; 171 172 EndPaint (hwnd, &ps) ; 173 return 0 ; 174 175 case WM_DESTROY: 176 KillTimer (hwnd, ID_TIMER) ; 177 DeleteObject (hBrushRed) ; 178 PostQuitMessage (0) ; 179 return 0 ; 180 } 181 return DefWindowProc (hwnd, message, wParam, lParam) ; 182 }
此程序显示一个数字时钟,用红色的画刷,设置好坐标系,计算出点的坐标,每秒钟更新一次。
我觉得其中的结构设置得非常好,各个子函数功能一目了然
如果我来写,估计又是一个又臭又长的子函数,修改过来修改过去,最后功能垃圾代码自己都看不下去
慎思之……