/*----------------------------------------
BTNLOOK.C -- Button Look Program
(c) Charles Petzold, 1998
----------------------------------------*/#include <windows.h>struct
{
int iStyle ;
TCHAR * szText ;
}
button[] =
{
BS_PUSHBUTTON, TEXT ("PUSHBUTTON"),
BS_DEFPUSHBUTTON, TEXT ("DEFPUSHBUTTON"),
BS_CHECKBOX, TEXT ("CHECKBOX"),
BS_AUTOCHECKBOX, TEXT ("AUTOCHECKBOX"),
BS_RADIOBUTTON, TEXT ("RADIOBUTTON"),
BS_3STATE, TEXT ("3STATE"),
BS_AUTO3STATE, TEXT ("AUTO3STATE"),
BS_GROUPBOX, TEXT ("GROUPBOX"),
BS_AUTORADIOBUTTON, TEXT ("AUTORADIO"),
BS_OWNERDRAW, TEXT ("OWNERDRAW")
} ;#define NUM (sizeof button / sizeof button[0])LRESULT CALLBACK WndProc (HWND, UINT, WPARAM, LPARAM) ;int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance,
PSTR szCmdLine, int iCmdShow)
{
static TCHAR szAppName[] = TEXT ("BtnLook") ;
HWND hwnd ;
MSG msg ;
WNDCLASS wndclass ;
wndclass.style = CS_HREDRAW | CS_VREDRAW ;
wndclass.lpfnWndProc = WndProc ;
wndclass.cbClsExtra = 0 ;
wndclass.cbWndExtra = 0 ;
wndclass.hInstance = hInstance ;
wndclass.hIcon = LoadIcon (NULL, IDI_APPLICATION) ;
wndclass.hCursor = LoadCursor (NULL, IDC_ARROW) ;
wndclass.hbrBackground = (HBRUSH) GetStockObject (WHITE_BRUSH) ;
wndclass.lpszMenuName = NULL ;
wndclass.lpszClassName = szAppName ;
if (!RegisterClass (&wndclass))
{
MessageBox (NULL, TEXT ("This program requires Windows NT!"),
szAppName, MB_ICONERROR) ;
return 0 ;
}
hwnd = CreateWindow (szAppName, TEXT ("Button Look"),
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 message, WPARAM wParam, LPARAM lParam)
{
static HWND hwndButton[NUM] ;
static RECT rect ;
static TCHAR szTop[] = TEXT ("message wParam lParam"),
szUnd[] = TEXT ("_______ ______ ______"),
szFormat[] = TEXT ("%-16s%04X-%04X %04X-%04X"),
szBuffer[50] ;
static int cxChar, cyChar ;
HDC hdc ;
PAINTSTRUCT ps ;
int i ;
switch (message)
{
/*case WM_DRAWITEM : */ //屏幕狂闪 不出现WM_DRAWITEM
case WM_CREATE :
cxChar = LOWORD (GetDialogBaseUnits ()) ;
cyChar = HIWORD (GetDialogBaseUnits ()) ;
for (i = 0 ; i < NUM ; i++)
hwndButton[i] = CreateWindow ( TEXT("button"),
button[i].szText,
WS_CHILD | WS_VISIBLE | button[i].iStyle,
cxChar, cyChar * (1 + 2 * i),
20 * cxChar, 7 * cyChar / 4,
hwnd, (HMENU) i,
((LPCREATESTRUCT) lParam)->hInstance, NULL) ;
return 0 ;
/*case WM_DRAWITEM :*/ //在最上面出现记录 且记录不断覆盖 不出现WM_DRAWITEM
case WM_SIZE :
rect.left = 24 * cxChar ;
rect.top = 2 * cyChar ;
rect.right = LOWORD (lParam) ;
rect.bottom = HIWORD (lParam) ;
return 0 ;
/*case WM_DRAWITEM : */ //若在此处则点最后一个按钮就会重新开始记录,不出现WM_DRAWITEM
case WM_PAINT :
InvalidateRect (hwnd, &rect, TRUE) ;
hdc = BeginPaint (hwnd, &ps) ;
SelectObject (hdc, GetStockObject (SYSTEM_FIXED_FONT)) ;
SetBkMode (hdc, TRANSPARENT) ;
TextOut (hdc, 24 * cxChar, cyChar, szTop, lstrlen (szTop)) ;
TextOut (hdc, 24 * cxChar, cyChar, szUnd, lstrlen (szUnd)) ;
EndPaint (hwnd, &ps) ;
return 0 ;
case WM_DRAWITEM : //正常状况
case WM_COMMAND :
ScrollWindow (hwnd, 0, -cyChar, &rect, &rect) ;
hdc = GetDC (hwnd) ;
SelectObject (hdc, GetStockObject (SYSTEM_FIXED_FONT)) ;
TextOut (hdc, 24 * cxChar, cyChar * (rect.bottom / cyChar - 1),
szBuffer,
wsprintf (szBuffer, szFormat,
message == WM_DRAWITEM ? TEXT ("WM_DRAWITEM") :
TEXT ("WM_COMMAND"),
HIWORD (wParam), LOWORD (wParam),
HIWORD (lParam), LOWORD (lParam))) ;
ReleaseDC (hwnd, hdc) ;
ValidateRect (hwnd, &rect) ;
break ;
/*case WM_DRAWITEM : */ //窗口一闪而过
case WM_DESTROY :
PostQuitMessage (0) ;
/*case WM_DRAWITEM : */ //没有WM_DRAWITEM消息出现
return 0 ; }
return DefWindowProc (hwnd, message, wParam, lParam) ;
}可以帮我看看添加注释地方的原因吗?
为什么WM_DRAWITEM要放在那个地方才是正常的?
WM_DRAWITEM是干什么的?(看了MSDN上说这是一个传递给用户自画按钮 菜单的父窗口的消息 当按钮外挂改变时,还是不理解什么时候出现?是由于BS_OWNERDRAW吗?)
case WM_DRAWITEM : //窗口一闪而过
case WM_DESTROY :
PostQuitMessage (0) ;不是走的是PostQuitMessage(0);吗?程序退出
WM_DRAWITEM Notification--------------------------------------------------------------------------------
The WM_DRAWITEM message is sent to the parent window of an owner-drawn button, combo box, list box, or menu when a visual aspect of the button, combo box, list box, or menu has changed.A window receives this message through its WindowProc function.
SyntaxWM_DRAWITEM WPARAM wParam
lpDrawItem = (LPDRAWITEMSTRUCT) lParam;
ParameterswParam
Specifies the identifier of the control that sent the WM_DRAWITEM message. If the message was sent by a menu, this parameter is zero.
lpDrawItem
Pointer to a DRAWITEMSTRUCT structure containing information about the item to be drawn and the type of drawing required.
Return ValueIf an application processes this message, it should return TRUE. ResBy default, the DefWindowProc function draws the focus rectangle for an owner-drawn list box item. The itemAction member of the DRAWITEMSTRUCT structure specifies the drawing operation that an application should perform. Before returning from processing this message, an application should ensure that the device context identified by the hDC member of the DRAWITEMSTRUCT structure is in the default state. Notification RequirementsMinimum DLL Version None
Header Declared in Winuser.h, include Windows.h
Minimum operating systems Windows 95, Windows NT 3.1 See AlsoCombo Boxes Overview, DefWindowProc, DRAWITEMSTRUCT
break;
case WM_DESTROY :
PostQuitMessage (0) ;兄弟 添加break 如果不添加break 就会随便执行PostQuitMessage(0)
程序自动退出