Using Menus

Menu Basics

We use a Menu object to construct a menu. For the scribble program, our menu will considt of two options: Clear and Exit. Constructing a Menu object is a three-step process:

  1. Instantiating the Menu object
  2. Adding items to the Menu with Append and Insert
  3. Attching the menu to the window with Wnd::SetMenu

For the scribble program's menu, the code looks like the following:

    Menu menu;
    menu.Append("Clear", MENU_EDIT_CLEAR);
    menu.Append("Exit", MENU_FILE_CLOSE);

    wnd.SetMenu(menu);

Menu::Append takes two arguments: the name of the menu item, and an integer identifier. The idenfier can be any integer. LVT also provides some predefined constants for use.

We handle menu messages in the OnMenuMessage handler. The handler for scribble looks like this:

void ScribblerWnd::OnMenuCommand(int id)
{
    // Do default menu command processing.
    Wnd::OnMenuCommand(id);

    if (id == MENU_EDIT_CLEAR)
    {
        // Erase all the polylines in our list and redraw the window.
        m_lines.clear();
        Redraw();
    }
}

The parameter to OnMenuMessage is the integer identifier of the selected menu item. While it is not strictly necessary to do so, we call the base class's OnMenuCommand handler before processing the message ourselves. The default implementation handles the MENU_FILE_EXIT and MENU_FILE_CLOSE messages.

Popup Menus

Creating popup menus is simliar to creating basic menus. The process is:

  1. Instantiate a Menu object. This will be the "main" menu.
  2. For each popup menu in the main menu:
    1. Create a Menu object.
    2. Insert menu items into the popup menu with Append and Insert
    3. Attach the popup menu to the main menu with Append or Insert
  3. Attach the main menu to the window with Wnd::SetMenu.

In addition, we can create popup menus within popup menus, using the same procedure.

The mscribble program, which we will construct in the next chapter, has the following menu structure:

File        Clear
    New
    Close
    -----
    Exit

The code to construct the menu looks like this:

    Menu mainMenu, fileMenu;
    fileMenu.Append("New", MENU_FILE_NEW);
    fileMenu.Append("Close", MENU_FILE_CLOSE);
    fileMenu.AppendSeparator();
    fileMenu.Append("Exit", MENU_FILE_EXIT);

    mainMenu.Append("File", fileMenu);
    mainMenu.Append("Clear", MENU_EDIT_CLEAR);
    SetMenu(mainMenu);

As you can see from the code, Append is overloaded to take a reference to a Menu object to insert as a popup menu. We can also see AppendSeparator to attach a separator item to a menu.

See the boxes example program in the LVT source distribution for another example of using menus in an LVT application.

In the next chapter, we'll look at how an application can make use of multiple top-level windows.