diff --git a/src/winmenu.c b/src/winmenu.c index bfba18e6..14cb2713 100644 --- a/src/winmenu.c +++ b/src/winmenu.c @@ -48,6 +48,18 @@ #include "xinerama.h" #include "winmenu.h" + +static WMenu *makeWorkspaceMenu(WScreen *scr); +static WMenu *makeOptionsMenu(WScreen *scr); +static WMenu *makeMaximizeMenu(WScreen *scr); + +/* + * Define the Menu entry that will be present in the Window menu + * + * The order of this list defines the order in which they will appear; + * make sure to keep the structure below aligned with the list because + * the constant index is used in many places. + */ enum { MC_MAXIMIZE, @@ -57,7 +69,7 @@ enum MC_HIDE, MC_MOVERESIZE, MC_SELECT, - MC_DUMMY_MOVETO, + MC_CHANGEWKSPC, MC_PROPERTIES, MC_OPTIONS, MC_RELAUNCH, @@ -65,6 +77,31 @@ enum MC_KILL }; +static const struct { + const char *label; + WMenu *(*generate_submenu)(WScreen *scr); +} window_menu_entries[] = { + [MC_MAXIMIZE] = { N_("Maximize"), NULL }, + [MC_OTHERMAX] = { N_("Other maximization"), makeMaximizeMenu }, + [MC_MINIATURIZE] = { N_("Miniaturize"), NULL }, + [MC_SHADE] = { N_("Shade"), NULL }, + [MC_HIDE] = { N_("Hide"), NULL }, + [MC_MOVERESIZE] = { N_("Resize/Move"), NULL }, + [MC_SELECT] = { N_("Select"), NULL }, + [MC_CHANGEWKSPC] = { N_("Move To"), makeWorkspaceMenu }, + [MC_PROPERTIES] = { N_("Attributes..."), NULL }, + [MC_OPTIONS] = { N_("Options"), makeOptionsMenu }, + [MC_RELAUNCH] = { N_("Launch"), NULL }, + [MC_CLOSE] = { N_("Close"), NULL }, + [MC_KILL] = { N_("Kill"), NULL } +}; + +/* + * Defines the menu entries for the Options sub-menu + * + * These options will be placed at the beginning of the menu, the rest will + * be populated with the Window Shortcut possibilities + */ enum { WO_KEEP_ON_TOP, @@ -478,19 +515,13 @@ static WMenu *makeWorkspaceMenu(WScreen * scr) updateWorkspaceMenu(menu); - return menu; -} - -static WMenu *makeMakeShortcutMenu(WMenu * menu) -{ - int i; - - for (i = 0; i < MAX_WINDOW_SHORTCUTS; i++) { - WMenuEntry *entry; - entry = wMenuAddCallback(menu, "", makeShortcutCommand, NULL); - - entry->flags.indicator = 1; - } + /* + * The Workspace Menu is made visible in the screen structure because + * it is updated when there is a change on workspaces. This was done + * to be efficient, avoiding re-generating completely the window menu + * and its sub-menus everytime it is needed. + */ + scr->workspace_submenu = menu; return menu; } @@ -499,6 +530,7 @@ static WMenu *makeOptionsMenu(WScreen * scr) { WMenu *menu; WMenuEntry *entry; + int i; menu = wMenuCreate(scr, NULL, False); if (!menu) { @@ -518,6 +550,11 @@ static WMenu *makeOptionsMenu(WScreen * scr) entry->flags.indicator = 1; entry->flags.indicator_type = MI_CHECK; + for (i = 0; i < MAX_WINDOW_SHORTCUTS; i++) { + entry = wMenuAddCallback(menu, "", makeShortcutCommand, NULL); + entry->flags.indicator = 1; + } + return menu; } @@ -541,49 +578,23 @@ static WMenu *makeMaximizeMenu(WScreen * scr) static WMenu *createWindowMenu(WScreen * scr) { WMenu *menu; - WMenuEntry *entry; + int i; menu = wMenuCreate(scr, NULL, False); - /* - * Warning: If you make some change that affects the order of the - * entries, you must update the command enum in the top of - * this file. - */ - entry = wMenuAddCallback(menu, _("Maximize"), execMenuCommand, NULL); - entry = wMenuAddCallback(menu, _("Other maximization"), NULL, NULL); - wMenuEntrySetCascade(menu, entry, makeMaximizeMenu(scr)); + for (i = 0; i < wlengthof(window_menu_entries); i++) { + WMenuEntry *entry; - entry = wMenuAddCallback(menu, _("Miniaturize"), execMenuCommand, NULL); + entry = wMenuAddCallback(menu, _(window_menu_entries[i].label), + (window_menu_entries[i].generate_submenu == NULL)?execMenuCommand:NULL, + NULL); + if (window_menu_entries[i].generate_submenu != NULL) { + WMenu *submenu; - entry = wMenuAddCallback(menu, _("Shade"), execMenuCommand, NULL); - - entry = wMenuAddCallback(menu, _("Hide"), execMenuCommand, NULL); - - entry = wMenuAddCallback(menu, _("Resize/Move"), execMenuCommand, NULL); - - entry = wMenuAddCallback(menu, _("Select"), execMenuCommand, NULL); - - entry = wMenuAddCallback(menu, _("Move To"), NULL, NULL); - scr->workspace_submenu = makeWorkspaceMenu(scr); - if (scr->workspace_submenu) - wMenuEntrySetCascade(menu, entry, scr->workspace_submenu); - - entry = wMenuAddCallback(menu, _("Attributes..."), execMenuCommand, NULL); - - entry = wMenuAddCallback(menu, _("Options"), NULL, NULL); - wMenuEntrySetCascade(menu, entry, makeMakeShortcutMenu(makeOptionsMenu(scr))); - - /* - entry = wMenuAddCallback(menu, _("Select Shortcut"), NULL, NULL); - wMenuEntrySetCascade(menu, entry, makeMakeShortcutMenu(scr)); - */ - - entry = wMenuAddCallback(menu, _("Launch"), execMenuCommand, NULL); - - entry = wMenuAddCallback(menu, _("Close"), execMenuCommand, NULL); - - entry = wMenuAddCallback(menu, _("Kill"), execMenuCommand, NULL); + submenu = window_menu_entries[i].generate_submenu(scr); + wMenuEntrySetCascade(menu, entry, submenu); + } + } return menu; } @@ -685,7 +696,7 @@ static void updateMenuForWindow(WMenu * menu, WWindow * wwin) menu->entries[MC_SELECT]->text = text; } - wMenuSetEnabled(menu, MC_DUMMY_MOVETO, !IS_OMNIPRESENT(wwin)); + wMenuSetEnabled(menu, MC_CHANGEWKSPC, !IS_OMNIPRESENT(wwin)); if (!wwin->flags.inspector_open) { wMenuSetEnabled(menu, MC_PROPERTIES, True);