win32 API编程之菜单

一、分类

二、创建菜单的函数

三、代码实例

四、通过资源创建菜单

五、创建右键弹出菜单

一、分类

  • 系统菜单
  • 顶层菜单
  • 弹出式菜单(右键菜单)

二、创建菜单的函数

AppendMenu函数:

CreatePopupMenu函数:

InsertMenu函数

SetMenu函数:

三、代码实例

#include<windows.h>
#include<CommCtrl.h> 


//自定义的窗口过程
LRESULT  CALLBACK    MyWindowProc(HWND hWnd, UINT Msg,
    WPARAM wParam, LPARAM lParam)
{
    switch (Msg)
    {

    case WM_DESTROY:
        PostQuitMessage(0);//可以使GetMessage返回0    
        return 0; 

    case  WM_CREATE:
    {
        //创建顶层菜单
        HMENU  hTop = CreateMenu();//空菜单
        AppendMenu(hTop, MF_STRING, 100, L"文件"); //添加第一项
        InsertMenu(hTop, 0, MF_STRING | MF_BYPOSITION, 200, L"工具"); //添加第二项

                                                                    //创建弹出菜单(子菜单)
        HMENU  hPopUp = CreatePopupMenu();//空菜单 
        AppendMenu(hPopUp, MF_SEPARATOR, NULL, NULL);//分隔条
        AppendMenu(hPopUp, MF_STRING, 301, L"打开");
        InsertMenu(hPopUp, 0, MF_STRING | MF_BYPOSITION, 302, L"新建");

        //添加第三项
        AppendMenu(hTop, MF_POPUP, (UINT_PTR)hPopUp, L"打开2");
    
         //设置窗口菜单
        SetMenu(hWnd, hTop);

        //释放菜单资源
        DestroyMenu(hTop);
        DestroyMenu(hPopUp);


    
    }break;

    case WM_COMMAND:
    { 
        //菜单ID
        WORD  menuId = LOWORD(wParam);
        switch (menuId)
        {
        case 100:
            MessageBox(hWnd, L"文件菜单点击", L"提示", MB_OK);
            break;
        case 200:
            MessageBox(hWnd, L"工具菜单点击", L"提示", MB_OK);
            break;
        case 301:
            MessageBox(hWnd, L"打开菜单点击", L"提示", MB_OK);
            break;
        case 302:
            MessageBox(hWnd, L"新建菜单点击", L"提示", MB_OK);
            break;
        } 

    }  break;

    }

    return DefWindowProc(hWnd, Msg, wParam, lParam);
}


int  WINAPI   WinMain(HINSTANCE  hInstance, HINSTANCE  hPrevInstance,
    LPSTR lpCmdLine, int  nShowCmd)
{

    //1.注册窗口类
    WNDCLASS  wnd;
    wnd.cbClsExtra = 0;
    wnd.cbWndExtra = 0;
    wnd.hbrBackground = (HBRUSH)(GetStockObject(GRAY_BRUSH));//背景色
    wnd.hCursor = LoadCursor(NULL, IDC_ARROW);//光标
    wnd.hIcon = LoadIcon(NULL, IDI_APPLICATION);//图标
                                                //wnd.lpfnWndProc = DefWindowProc;//默认窗口过程函数,用于处理消息
    wnd.lpfnWndProc = MyWindowProc;//自定义的窗口过程函数
    wnd.lpszClassName = L"MrHuang";//窗口类名
    wnd.lpszMenuName = NULL;//菜单资源名称
    wnd.style = CS_HREDRAW | CS_DBLCLKS;//窗口类、样式
    wnd.hInstance = hInstance;//实例句柄
    RegisterClass(&wnd);
     

    //创建窗口(返回之前发送WM_CREATE)
    HWND    hWnd = CreateWindow(L"MrHuang", L"第一个窗口程序",
        WS_OVERLAPPEDWINDOW, 100, 100, 400, 400, NULL, NULL, hInstance, NULL);

    //显示窗口
    ShowWindow(hWnd, nShowCmd);
    //更新窗口(发送WM_PAINT)
    UpdateWindow(hWnd);

    //消息循环(收到WM_QUIT消息退出)
    MSG  msg;
    while (GetMessage(&msg, NULL, 0, 0))
    {
        TranslateMessage(&msg);//翻译消息
        DispatchMessage(&msg);//分发消息到窗口过程
    }
}

四、通过资源创建菜单

1)LoadMenu函数:

2)GetMenu函数:

3)GetMenuItemInfo函数:

4)代码实例

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


//自定义的窗口过程
LRESULT  CALLBACK    MyWindowProc(HWND hWnd, UINT Msg,
    WPARAM wParam, LPARAM lParam)
{
    switch (Msg)
    {

    case WM_DESTROY:
        PostQuitMessage(0);//可以使GetMessage返回0    
        return 0;

    case  WM_CREATE:
    {
        //加载菜单资源
        HMENU  hTop=LoadMenu(GetModuleHandle(NULL),  MAKEINTRESOURCE( IDR_MENU1));
       
        //设置菜单到窗口
        SetMenu(hWnd,  hTop);


        //获取某个窗口的顶层菜单
        HMENU hMenuTop=  GetMenu(hWnd);
        //获取顶层菜单的弹出菜单
        HMENU  hPop = GetSubMenu(hMenuTop, 0);
        //获取菜单项中的内容
        MENUITEMINFO   mii = {0};
        mii.cbSize = sizeof(MENUITEMINFO);
        mii.fMask = MIIM_TYPE|MIIM_ID;
        mii.fType = MFT_STRING;
        mii.dwTypeData = new  TCHAR[64];
        mii.cch =64 ;
        GetMenuItemInfo(hPop, 2, true, &mii);
        MessageBox(hWnd, mii.dwTypeData, L"提示", MB_OK);


    }break;

    case WM_COMMAND:
    {
        //菜单ID
        WORD  menuId = LOWORD(wParam);
        switch (menuId)
        { 
        case ID_OPEN:
            MessageBox(hWnd, L"打开菜单点击", L"提示", MB_OK);
            break;
        case ID_NEW:
            MessageBox(hWnd, L"新建菜单点击", L"提示", MB_OK);
            break;
        case 2000:
            MessageBox(hWnd, L"工具菜单点击", L"提示", MB_OK);
            break;
        }

    }  break;

    }

    return DefWindowProc(hWnd, Msg, wParam, lParam);
}


int  WINAPI   WinMain(HINSTANCE  hInstance, HINSTANCE  hPrevInstance,
    LPSTR lpCmdLine, int  nShowCmd)
{

    //1.注册窗口类
    WNDCLASS  wnd;
    wnd.cbClsExtra = 0;
    wnd.cbWndExtra = 0;
    wnd.hbrBackground = (HBRUSH)(GetStockObject(GRAY_BRUSH));//背景色
    wnd.hCursor = LoadCursor(NULL, IDC_ARROW);//光标
    wnd.hIcon = LoadIcon(NULL, IDI_APPLICATION);//图标
                                                //wnd.lpfnWndProc = DefWindowProc;//默认窗口过程函数,用于处理消息
    wnd.lpfnWndProc = MyWindowProc;//自定义的窗口过程函数
    wnd.lpszClassName = L"MrHuang";//窗口类名
    wnd.lpszMenuName = NULL;//菜单资源名称
    wnd.style = CS_HREDRAW | CS_DBLCLKS;//窗口类、样式
    wnd.hInstance = hInstance;//实例句柄
    RegisterClass(&wnd);


    //创建窗口(返回之前发送WM_CREATE)
    HWND    hWnd = CreateWindow(L"MrHuang", L"第一个窗口程序",
        WS_OVERLAPPEDWINDOW, 100, 100, 400, 400, NULL, NULL, hInstance, NULL);

    //显示窗口
    ShowWindow(hWnd, nShowCmd);
    //更新窗口(发送WM_PAINT)
    UpdateWindow(hWnd);

    //消息循环(收到WM_QUIT消息退出)
    MSG  msg;
    while (GetMessage(&msg, NULL, 0, 0))
    {
        TranslateMessage(&msg);//翻译消息
        DispatchMessage(&msg);//分发消息到窗口过程
    }
}

五、创建右键弹出菜单

1)CreatePopupMenu函数

2)TrackPopupMenu函数

3)代码实例

#include<windows.h> 


//自定义的窗口过程
LRESULT  CALLBACK    MyWindowProc(HWND hWnd, UINT Msg,
    WPARAM wParam, LPARAM lParam)
{
    switch (Msg)
    {

    case WM_DESTROY:
        PostQuitMessage(0);//可以使GetMessage返回0    
        return 0;

    case WM_RBUTTONDOWN:
    {
        //创建弹出菜单
        HMENU  hPop=CreatePopupMenu();
        AppendMenu(hPop, MF_STRING, 111, L"新建");
        AppendMenu(hPop, MF_STRING, 222, L"打开");

        //转换坐标
        POINT pt = { LOWORD(lParam)  ,HIWORD(lParam) }; //自己窗口的客户区
        ClientToScreen(hWnd,&pt);

        //在指定位置弹出菜单(这里的x,y是相对于屏幕左上角的坐标)
        TrackPopupMenu(hPop, TPM_CENTERALIGN|TPM_BOTTOMALIGN, pt.x, pt.y, 0, hWnd, NULL);

        //释放菜单资源
        DestroyMenu(hPop);


    }break;

    case WM_COMMAND:
    {
        //菜单ID
        WORD  menuId = LOWORD(wParam);
        switch (menuId)
        {
        case 222:
            MessageBox(hWnd, L"打开菜单点击", L"提示", MB_OK);
            break;
        case 111:
            MessageBox(hWnd, L"新建菜单点击", L"提示", MB_OK);
            break; 
        }

    }  break;

    }

    return DefWindowProc(hWnd, Msg, wParam, lParam);
}


int  WINAPI   WinMain(HINSTANCE  hInstance, HINSTANCE  hPrevInstance,
    LPSTR lpCmdLine, int  nShowCmd)
{

    //1.注册窗口类
    WNDCLASS  wnd;
    wnd.cbClsExtra = 0;
    wnd.cbWndExtra = 0;
    wnd.hbrBackground = (HBRUSH)(GetStockObject(GRAY_BRUSH));//背景色
    wnd.hCursor = LoadCursor(NULL, IDC_ARROW);//光标
    wnd.hIcon = LoadIcon(NULL, IDI_APPLICATION);//图标
                                                //wnd.lpfnWndProc = DefWindowProc;//默认窗口过程函数,用于处理消息
    wnd.lpfnWndProc = MyWindowProc;//自定义的窗口过程函数
    wnd.lpszClassName = L"MrHuang";//窗口类名
    wnd.lpszMenuName = NULL;//菜单资源名称
    wnd.style = CS_HREDRAW | CS_DBLCLKS;//窗口类、样式
    wnd.hInstance = hInstance;//实例句柄
    RegisterClass(&wnd);


    //创建窗口(返回之前发送WM_CREATE)
    HWND    hWnd = CreateWindow(L"MrHuang", L"第一个窗口程序",
        WS_OVERLAPPEDWINDOW, 100, 100, 400, 400, NULL, NULL, hInstance, NULL);

    //显示窗口
    ShowWindow(hWnd, nShowCmd);
    //更新窗口(发送WM_PAINT)
    UpdateWindow(hWnd);

    //消息循环(收到WM_QUIT消息退出)
    MSG  msg;
    while (GetMessage(&msg, NULL, 0, 0))
    {
        TranslateMessage(&msg);//翻译消息
        DispatchMessage(&msg);//分发消息到窗口过程
    }
}

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

原文地址:https://www.cnblogs.com/mango1997/p/14631997.html