Append Menu Item to Windows System Menu


So for my Installer app which doesn’t have (or require) a (real) menu… I use MenuBarModel::setMacMainMenu() to add the “About” option to the Apple Menu – so I thought it would be good to add the same option to the Windows System menu.

I looked through the forum and didn’t find any reference to anyone having done this before – I know it’s possible in MFC:

Anyone done this in JUCE?

I’m thinking I can use WIN32 calls otherwise:

GetSystemMenu () and InsertMenuItem() – I’ll just have to figure out how to interface it to MenuBarModel



It looks like I need to register a MESSAGE ID (WM_USER + nnnn) with MessageManager and have WindowClassHolder::peerWindowProc() call a method in MessageManager with any unhanded messages which could broadcast the message to an Listeners which registered the message.

Any hope of something like that being added?




Okay, I may as well post my solution in case it helps someone else:

in the app’s initialise():

     mainWindow = new MainWindow (getApplicationName());

    HMENU menu = GetSystemMenu ((HWND) mainWindow->getWindowHandle(), FALSE);
    std::string menuText = "About " + getApplicationName().toStdString();
    mi.cbSize = sizeof (mi);
    mi.fMask = MIIM_TYPE | MIIM_ID;
    mi.fType = MFT_STRING;
    mi.dwTypeData = (LPTSTR) menuText.c_str();
    mi.cch = static_cast<UINT>(menuText.length());
    mi.wID = ABOUT_ID;  // IDs are lower than 0xF000 and higher than zero
    InsertMenuItem (menu, 0, TRUE, &mi);
    mi.fMask = MIIM_FTYPE;
    mi.fType = MFT_SEPARATOR;
    mi.wID = 0;
    InsertMenuItem (menu, 1, TRUE, &mi);
    DrawMenuBar ((HWND) mainWindow->getWindowHandle());


and I added a private method:


void MessagePump()
    MSG msg;

    m_bFinished = false;

    while (! m_bFinished)
        if (PeekMessage (&msg, NULL, WM_SYSCOMMAND, WM_SYSCOMMAND, PM_NOREMOVE))
            if (msg.message == WM_SYSCOMMAND)
                if ((msg.wParam & 0xfff0) == ABOUT_ID)
                    menuItemSelected (ABOUT_ID, -1);


            if  (! MessageManager::getInstance()->runDispatchLoopUntil (20))