您的位置:首页 > 其它

第十章 菜单及其它资源part2

2010-04-14 17:06 225 查看
10.2菜单

当使用者选择一个菜单项时,Windows给您的程序发送包含该ID的WM_COMMAND消息。

菜单概念

窗口的菜单列紧接在标题列的下方显示,这个菜单列有时被称为「主菜单」或「顶层菜单」。

菜单结构

顶层菜单有一个菜单句柄,在顶层菜单中的每一个弹出式菜单也有它自己的菜单句柄。

系统菜单(也是一个弹出式菜单)也有菜单句柄。

菜单中的每一项都有三个特性

1.菜单中显示什么,它可以是字符串或位图

2.第二个特性是WM_COMMAND消息中Windows发送给程序的菜单ID,或者是在使用者选择
菜单项时Windows显示的弹出式菜单的句柄。

3.是菜单项的属性,包括是否被禁用、无效化或被选中。

定义菜单

为菜单中的项目键入文字时,可以键入一个「&」符号,指出后面一个字符在Windows显示菜单时要加底线。

Checked选项在菜单项边上放置一个选中标记。Separator选项在弹出式菜单上产生一个分栏的横线。

Grayed选项,菜单项是否启动的时候灰掉。 ID值是Windows发送给窗口消息处理程序中菜单消息中的数值。

在菜单中ID值应该是唯一的。按照惯例,我使用以IDM( 「ID for a Menu」 )开头的标识符。

在程序中引用菜单

如果在资源描述档中为菜单使用了名称,叙述如下:hMenu = LoadMenu (hInstance, TEXT ("MyMenu")) ;

如果使用了数值,那么LoadMenu呼叫采用如下的形式:hMenu = LoadMenu (hInstance, MAKEINTRESOURCE (ID_MENU)) ; 可以将这个菜单句柄作为CreateWindow的第九个参数

窗口被建立后再给窗口指定一个菜单SetMenu (hwnd, hMenu);

当窗口被清除时,与窗口相关的所有菜单都将被清除。

菜单和消息

WM_INITMENU这一类的消息,wParam值是您的主菜单句柄.WM_MENUSELECT是一个菜单追踪消息

HIWORD (wParam):选择旗标. wParam的高字组中的「选择旗标」可以是下列这些旗标的组合:MF_GRAYED、MF_DISABLED、MF_CHECKED、MF_BITMAP、MF_POPUP、MF_HELP、MF_SYSMENU和MF_MOUSESELECT。

当Windows准备显示一个弹出式菜单时,它给窗口消息处理程序发送一个WM_INITMENUPOPUP消息

最重要的菜单消息是WM_COMMAND, 它表示使用者已经从菜单中选中了一个被启用的菜单项。

WM_MENUCHAR:如果使用者按下Alt和一个与菜单项不匹配的字符时或者在显示弹出式菜单而使用者按下一个与弹出式菜
单里的项目不匹配的字符键时。 Windows会把这个消息发送到窗口消息处理程序。

#include <windows.h>
#include "resource.h"

#define ID_TIMER 1

LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);

TCHAR szAppName[] = TEXT("MenuDemo");

int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance,
PSTR  szCmdLine,  int
iCmdShow)
{
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 = szAppName;
//程序在窗口的定义中为菜单引用该名称
wndclass.lpszClassName = szAppName;
if (!RegisterClass (&wndclass))
{
MessageBox (NULL, TEXT ("This program requires Windows NT!"),
szAppName,
MB_ICONERROR);
return 0;
}
//这个菜单句柄作为CreateWindow的第九个参数
//您也可以在窗口类别中指定NULL菜单,并且在CreateWindow呼叫中也指定NULL菜单
//然后在窗口被建立后再给窗口指定一个菜单SetMenu(hwnd, hMenu);
HMENU hMenu = LoadMenu(hInstance, MAKEINTRESOURCE (IDR_MENU2)) ;

hwnd = CreateWindow ( szAppName, TEXT ("Menu Demonstration"),
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT, CW_USEDEFAULT,
CW_USEDEFAULT, CW_USEDEFAULT,
NULL, hMenu, 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 int idColor [5] = { WHITE_BRUSH,
LTGRAY_BRUSH,
GRAY_BRUSH,
DKGRAY_BRUSH,
BLACK_BRUSH
};

static int iSelection = IDM_BKGND_WHITE;
HMENU hMenu;

switch (message)
{
case WM_COMMAND:
//得到菜单句柄
hMenu = GetMenu(hwnd);
//LOWORD (wParam)
//被选中项目:菜单ID或者弹出式菜单句柄
//lParam: 包含被选中项目的菜单句柄
switch (LOWORD (wParam))
{
case IDM_FILE_NEW:
case IDM_FILE_OPEN:
case IDM_FILE_SAVE:
case IDM_FILE_SAVE_AS:
MessageBeep(0);
return 0;

case   IDM_APP_EXIT:
SendMessage(hwnd, WM_CLOSE, 0, 0);
return 0;

case IDM_EDIT_UNDO:
case IDM_EDIT_CUT:
case IDM_EDIT_COPY:
case IDM_EDIT_PASTE:
case IDM_EDIT_CLEAR:
MessageBeep (0);
return 0 ;

case IDM_BKGND_WHITE:              // Note:  Logic below
case IDM_BKGND_LTGRAY:             // assumes  that IDM_WHITE
case IDM_BKGND_GRAY:               // through IDM_BLACK are
case IDM_BKGND_DKGRAY:             // consecutive numbers in
case IDM_BKGND_BLACK:              // the order shown here.
//CheckMenuItem函数用来取消目前被选中的项目
CheckMenuItem(hMenu,  iSelection, MF_UNCHECKED);
//iSelection的值被设定为wParam的值,新的背景颜色被选中
iSelection = LOWORD(wParam);
CheckMenuItem(hMenu, iSelection, MF_CHECKED) ;
//弹出式菜单上的五项之一时,
//它必须从先前选中的背景颜色中除掉选中标记,
//并把标记加到新的背景颜色上。

//GetStockObject:该函数检索预定义的备用笔、刷子、字体或者调色板的句柄。
//SetClassLong该函数替换在额外类存储空间的指定偏移地址的32位长整型值,
//   或替换指定窗口所属类的WNDCLASSEX结构
//GCL_HBRBACKGROUND:替换与类有关的背景刷子的句柄
SetClassLong(hwnd,  GCL_HBRBACKGROUND,
(LONG)GetStockObject(idColor[LOWORD(wParam) - IDM_BKGND_WHITE]));
//HIWORD (wParam):选择旗标
//wParam的高字组中的「选择旗标」可以是下列这些旗标的组合
//MF_GRAYED、MF_DISABLED、MF_CHECKED、MF_BITMAP、MF_POPUP、
//MF_HELP、MF_SYSMENU和MF_MOUSESELECT

//窗口显示的区域变成无效状态
InvalidateRect(hwnd, NULL, TRUE);
return 0 ;

case IDM_TIMER_START:
if (SetTimer(hwnd, ID_TIMER, 1000, NULL))
{
//无效化「Start」选项,并启用「Stop」选项
EnableMenuItem(hMenu, IDM_TIMER_START, MF_GRAYED);
EnableMenuItem(hMenu, IDM_TIMER_STOP, MF_ENABLED);
}
return 0;

case IDM_TIMER_STOP:
KillTimer(hwnd, ID_TIMER);
EnableMenuItem(hMenu, IDM_TIMER_START, MF_ENABLED);
EnableMenuItem(hMenu, IDM_TIMER_STOP, MF_GRAYED);
return 0;

case IDM_APP_HELP:
MessageBox(hwnd, TEXT("Help not yet implemented!"),
szAppName, MB_ICONEXCLAMATION | MB_OK) ;
return 0;

case IDM_APP_ABOUT:
MessageBox (hwnd,TEXT("Menu Demonstration Program/n")
TEXT ("(c) Charles Petzold, 1998"),
szAppName, MB_ICONINFORMATION | MB_OK);
return 0 ;
}
break;
case WM_TIMER:
MessageBeep(0);
return 0;
case WM_DESTROY:
PostQuitMessage(0);
return 0;
}
return DefWindowProc(hwnd, message, wParam, lParam) ;
}


MENUDEMO.rc

/////////////////////////////////////////////////////////////////////////////
// 中国語 (P.R.C.) resources

#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_CHS)
#ifdef _WIN32
LANGUAGE LANG_CHINESE, SUBLANG_CHINESE_SIMPLIFIED
#pragma code_page(936)
#endif //_WIN32

/////////////////////////////////////////////////////////////////////////////
//
// Menu
//

#endif    // 中国語 (P.R.C.) resources
/////////////////////////////////////////////////////////////////////////////

#ifndef APSTUDIO_INVOKED
/////////////////////////////////////////////////////////////////////////////
//
// Generated from the TEXTINCLUDE 3 resource.
//
IDR_MENU2 MENU DISCARDABLE
BEGIN
POPUP "&File"
BEGIN
MENUITEM  "&New"  IDM_FILE_NEW
MENUITEM  "&Open" IDM_FILE_OPEN
MENUITEM  "&Save" IDM_FILE_SAVE
MENUITEM "Save &As..." IDM_FILE_SAVE_AS
MENUITEM SEPARATOR
MENUITEM  "E&xit" IDM_APP_EXIT
END

POPUP "&Edit"
BEGIN
MENUITEM  "&Undo", IDM_EDIT_UNDO
MENUITEM SEPARATOR
MENUITEM  "C&ut",  IDM_EDIT_CUT
MENUITEM  "&Copy", IDM_EDIT_COPY
MENUITEM  "&Paste",IDM_EDIT_PASTE
MENUITEM "De&lete",IDM_EDIT_CLEAR
END

POPUP "&Background"
BEGIN
MENUITEM "&White",      IDM_BKGND_WHITE, CHECKED
MENUITEM "&Light Gray", IDM_BKGND_LTGRAY
MENUITEM "&Gray",       IDM_BKGND_GRAY
MENUITEM "&Dark Gray",  IDM_BKGND_DKGRAY
MENUITEM "&Black",      IDM_BKGND_BLACK
END

POPUP "&Timer"
BEGIN
MENUITEM "&Start",      IDM_TIMER_START
MENUITEM "S&top",       IDM_TIMER_STOP, GRAYED
END

POPUP "&Help"
BEGIN
MENUITEM "&Help...",                IDM_APP_HELP
MENUITEM "&About MenuDemo...",      IDM_APP_ABOUT
END
END

/////////////////////////////////////////////////////////////////////////////
#endif    // not APSTUDIO_INVOKED
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: