static cell_t SetVoteResultCallback(IPluginContext *pContext, const cell_t *params) { Handle_t hndl = (Handle_t)params[1]; HandleError err; IBaseMenu *menu; if ((err=g_Menus.ReadMenuHandle(params[1], &menu)) != HandleError_None) { return pContext->ThrowNativeError("Menu handle %x is invalid (error %d)", hndl, err); } IPluginFunction *pFunction = pContext->GetFunctionById(params[2]); if (!pFunction) { return pContext->ThrowNativeError("Invalid function %x", params[2]); } void *array[2]; array[0] = pFunction; array[1] = (void *)¶ms[2]; IMenuHandler *pHandler = menu->GetHandler(); if (!pHandler->OnSetHandlerOption("set_vote_results_handler", (const void *)array)) { return pContext->ThrowNativeError("The given menu does not support this option"); } return 1; }
static cell_t SetMenuNoVoteButton(IPluginContext *pContext, const cell_t *params) { Handle_t hndl = (Handle_t)params[1]; HandleError err; IBaseMenu *menu; if ((err=g_Menus.ReadMenuHandle(params[1], &menu)) != HandleError_None) { return pContext->ThrowNativeError("Menu handle %x is invalid (error %d)", hndl, err); } unsigned int flags = menu->GetMenuOptionFlags(); if (params[2]) { flags |= MENUFLAG_BUTTON_NOVOTE; } else { flags &= ~MENUFLAG_BUTTON_NOVOTE; } menu->SetMenuOptionFlags(flags); unsigned int new_flags = menu->GetMenuOptionFlags(); return (flags == new_flags); }
static cell_t GetMenuItem(IPluginContext *pContext, const cell_t *params) { Handle_t hndl = (Handle_t)params[1]; HandleError err; IBaseMenu *menu; if ((err=g_Menus.ReadMenuHandle(params[1], &menu)) != HandleError_None) { return pContext->ThrowNativeError("Menu handle %x is invalid (error %d)", hndl, err); } ItemDrawInfo dr; const char *info; if ((info=menu->GetItemInfo(params[2], &dr)) == NULL) { return 0; } pContext->StringToLocalUTF8(params[3], params[4], info, NULL); pContext->StringToLocalUTF8(params[6], params[7], dr.display ? dr.display : "", NULL); cell_t *addr; pContext->LocalToPhysAddr(params[5], &addr); *addr = dr.style; return 1; }
static cell_t CreateMenuEx(IPluginContext *pContext, const cell_t *params) { Handle_t hndl = (Handle_t)params[1]; HandleError err; IMenuStyle *style; if (hndl != 0) { if ((err=g_Menus.ReadStyleHandle(params[1], &style)) != HandleError_None) { return pContext->ThrowNativeError("MenuStyle handle %x is invalid (error %d)", hndl, err); } } else { style = g_Menus.GetDefaultStyle(); } IPluginFunction *pFunction; if ((pFunction=pContext->GetFunctionById(params[2])) == NULL) { return pContext->ThrowNativeError("Function id %x is invalid", params[2]); } CMenuHandler *handler = g_MenuHelpers.GetMenuHandler(pFunction, params[3]); IBaseMenu *pMenu = style->CreateMenu(handler, pContext->GetIdentity()); hndl = pMenu->GetHandle(); if (!hndl) { pMenu->Destroy(); return BAD_HANDLE; } return hndl; }
void MenuManager::OnHandleDestroy(HandleType_t type, void *object) { if (type == m_MenuType) { IBaseMenu *menu = (IBaseMenu *)object; menu->Destroy(false); } else if (type == m_StyleType) { /* Do nothing */ } }
static cell_t GetMenuExitBackButton(IPluginContext *pContext, const cell_t *params) { Handle_t hndl = (Handle_t)params[1]; HandleError err; IBaseMenu *menu; if ((err=g_Menus.ReadMenuHandle(params[1], &menu)) != HandleError_None) { return pContext->ThrowNativeError("Menu handle %x is invalid (error %d)", hndl, err); } return ((menu->GetMenuOptionFlags() & MENUFLAG_BUTTON_EXITBACK) == MENUFLAG_BUTTON_EXIT) ? 1 : 0; }
static cell_t DisplayMenuAtItem(IPluginContext *pContext, const cell_t *params) { Handle_t hndl = (Handle_t)params[1]; HandleError err; IBaseMenu *menu; if ((err=g_Menus.ReadMenuHandle(params[1], &menu)) != HandleError_None) { return pContext->ThrowNativeError("Menu handle %x is invalid (error %d)", hndl, err); } return menu->DisplayAtItem(params[2], params[4], params[3]) ? 1 : 0; }
static cell_t GetMenuItemCount(IPluginContext *pContext, const cell_t *params) { Handle_t hndl = (Handle_t)params[1]; HandleError err; IBaseMenu *menu; if ((err=g_Menus.ReadMenuHandle(params[1], &menu)) != HandleError_None) { return pContext->ThrowNativeError("Menu handle %x is invalid (error %d)", hndl, err); } return menu->GetItemCount(); }
void CRPGPlayer::ShowBaseMenu() { IMenuStyle *style = menus->GetDefaultStyle(); IBaseMenu *menu = style->CreateMenu(&g_RPGPlugin, myself->GetIdentity()); menu->SetDefaultTitle(MENU_BASE_TITLE); for (int i = 0; i < BASEMENUCHOICES; i++) { menu->AppendItem(BaseMenuChoices[i], ItemDrawInfo(BaseMenuChoices[i])); } //menu->SetMenuOptionFlags( menu->GetMenuOptionFlags() | MENUFLAG_BUTTON_EXIT ); menu->Display(this->GetIndex(), MENU_TIME_FOREVER); }
void CRPGPlayer::ShowChar() { IMenuStyle *style = menus->GetDefaultStyle(); IBaseMenu *menu = style->CreateMenu(&g_RPGPlugin, myself->GetIdentity()); IMenuPanel *panel = menu->CreatePanel(); menu->SetDefaultTitle(MENU_CHAR_TITLE); panel->DrawTitle(MENU_CHAR_TITLE); char text[255]; sprintf(text, "Player ID: %d", GetSQLIndex()); panel->DrawItem(ItemDrawInfo(text)); int classnum = GetCurrentClass(); if (classnum > RPG_CLASS_NONE) { int team = GetCachedTeam(); if ( team == TEAM_SURVIVORS) { sprintf(text, "Class: %s", HumanClasses[classnum]); } else if (team == TEAM_UNDEAD) { sprintf(text, "Class: %s", ZombieClasses[classnum]); } else { sprintf(text, "Class: None"); } panel->DrawItem(ItemDrawInfo(text)); // item 1 sprintf(text, "Level: %d", GetLevel()); panel->DrawItem(ItemDrawInfo(text)); // item 2 sprintf(text, "Experience: %d", GetExperience()); panel->DrawItem(ItemDrawInfo(text)); // item 3 for (int i = 0; i < MAX_SKILLS; i++) // item 4-7 { sprintf(text, "%s - (Level %d)", SkillNames[skills[i].iIndex], skills[i].iLevel); panel->DrawItem(ItemDrawInfo(text)); } } panel->SendDisplay(GetIndex(), &g_RPGPlugin, MENU_TIME_FOREVER ); }
static cell_t SetMenuOptionFlags(IPluginContext *pContext, const cell_t *params) { Handle_t hndl = (Handle_t)params[1]; HandleError err; IBaseMenu *menu; if ((err=g_Menus.ReadMenuHandle(params[1], &menu)) != HandleError_None) { return pContext->ThrowNativeError("Menu handle %x is invalid (error %d)", hndl, err); } menu->SetMenuOptionFlags(params[2]); return 1; }
static cell_t GetMenuTitle(IPluginContext *pContext, const cell_t *params) { Handle_t hndl = (Handle_t)params[1]; HandleError err; IBaseMenu *menu; if ((err=g_Menus.ReadMenuHandle(params[1], &menu)) != HandleError_None) { return pContext->ThrowNativeError("Menu handle %x is invalid (error %d)", hndl, err); } size_t written; const char *title = menu->GetDefaultTitle(); pContext->StringToLocalUTF8(params[2], params[3], title, &written); return (cell_t)written; }
static cell_t SetMenuTitle(IPluginContext *pContext, const cell_t *params) { Handle_t hndl = (Handle_t)params[1]; HandleError err; IBaseMenu *menu; if ((err=g_Menus.ReadMenuHandle(params[1], &menu)) != HandleError_None) { return pContext->ThrowNativeError("Menu handle %x is invalid (error %d)", hndl, err); } char buffer[1024]; g_SourceMod.FormatString(buffer, sizeof(buffer), pContext, params, 2); menu->SetDefaultTitle(buffer); return 1; }
static cell_t CreatePanelFromMenu(IPluginContext *pContext, const cell_t *params) { Handle_t hndl = (Handle_t)params[1]; HandleError err; IBaseMenu *menu; if ((err=g_Menus.ReadMenuHandle(params[1], &menu)) != HandleError_None) { return pContext->ThrowNativeError("Menu handle %x is invalid (error %d)", hndl, err); } IMenuPanel *panel = menu->CreatePanel(); hndl = MakePanelHandle(panel, pContext); if (!hndl) { panel->DeleteThis(); } return hndl; }
static cell_t InsertMenuItem(IPluginContext *pContext, const cell_t *params) { Handle_t hndl = (Handle_t)params[1]; HandleError err; IBaseMenu *menu; if ((err=g_Menus.ReadMenuHandle(params[1], &menu)) != HandleError_None) { return pContext->ThrowNativeError("Menu handle %x is invalid (error %d)", hndl, err); } char *info; ItemDrawInfo dr; pContext->LocalToString(params[3], &info); pContext->LocalToString(params[4], (char **)&dr.display); dr.style = params[5]; return menu->InsertItem(params[2], info, dr) ? 1 : 0; }
void CRPGPlayer::ShowClassMenu( int team ) { IMenuStyle *style = menus->GetDefaultStyle(); IBaseMenu *menu = style->CreateMenu(&g_RPGPlugin, myself->GetIdentity()); menu->SetDefaultTitle(MENU_CLASS_TITLE); switch (team) { case TEAM_SURVIVORS: for (int i = 0; i < NUM_HUMAN_CLASSES; i++) { menu->AppendItem(HumanClasses[i], ItemDrawInfo(HumanClasses[i])); } break; case TEAM_UNDEAD: for (int i = 0; i < NUM_ZOMBIE_CLASSES; i++) { menu->AppendItem(ZombieClasses[i], ItemDrawInfo(ZombieClasses[i])); } break; } menu->InsertItem(MENU_CHOICE_RETURN, MENU_ITEM_RETURN, ItemDrawInfo(MENU_ITEM_RETURN)); menu->Display(this->GetIndex(), MENU_TIME_FOREVER ); }
static cell_t CreateMenu(IPluginContext *pContext, const cell_t *params) { IMenuStyle *style = g_Menus.GetDefaultStyle(); IPluginFunction *pFunction; if ((pFunction=pContext->GetFunctionById(params[1])) == NULL) { return pContext->ThrowNativeError("Function id %x is invalid", params[1]); } CMenuHandler *handler = g_MenuHelpers.GetMenuHandler(pFunction, params[2]); IBaseMenu *menu = style->CreateMenu(handler, pContext->GetIdentity()); Handle_t hndl = menu->GetHandle(); if (!hndl) { menu->Destroy(); return BAD_HANDLE; } return hndl; }
void CRPGPlayer::ShowSkillMenu() { if (GetCurrentClass() == RPG_CLASS_NONE ) { ShowClassMenu( GetPlayerInfo()->GetTeamIndex()); return; } if (GetFreeSkills() < 0) { ResetAccount(); gamehelpers->TextMsg(GetIndex(), HUD_PRINTTALK, "[ZPS-RPG] Your skills have been reset because of an error.\n"); } IMenuStyle *style = menus->GetDefaultStyle(); IBaseMenu *menu = style->CreateMenu(&g_RPGPlugin, myself->GetIdentity()); menu->SetDefaultTitle(MENU_SKILL_TITLE); char skillname[64]; unsigned int menustyle = ITEMDRAW_DEFAULT; for (int i = 0; i < MAX_SKILLS; i++) { sprintf(skillname, "%s (Level %d)", SkillNames[skills[i].iIndex], skills[i].iLevel); menustyle = ITEMDRAW_DEFAULT; if ((skills[i].iLevel >= 3) || (GetFreeSkills() == 0)) menustyle = ITEMDRAW_DISABLED; if( i == 3 ) // ULTIMATE { if ((skills[i].iLevel >= 1) || (GetLevel() < 6) || (GetFreeSkills() == 0)) { menustyle = ITEMDRAW_DISABLED; } } menu->AppendItem(SkillNames[skills[i].iIndex], ItemDrawInfo(skillname, menustyle)); } menu->AppendItem(MENU_ITEM_RESET, ItemDrawInfo("Reset Skills")); menu->InsertItem(6, MENU_ITEM_RETURN, ItemDrawInfo(MENU_ITEM_RETURN)); menu->SetMenuOptionFlags( menu->GetMenuOptionFlags() | MENUFLAG_BUTTON_EXIT ); menu->Display(this->GetIndex(), MENU_TIME_FOREVER); }
void BaseMenuStyle::ClientPressedKey(int client, unsigned int key_press) { #if defined MENU_DEBUG g_Logger.LogMessage("[SM_MENU] ClientPressedKey() (client %d) (key_press %d)", client, key_press); #endif CBaseMenuPlayer *player = GetMenuPlayer(client); /* First question: Are we in a menu? */ if (!player->bInMenu) { return; } bool cancel = false; unsigned int item = 0; MenuCancelReason reason = MenuCancel_Exit; MenuEndReason end_reason = MenuEnd_Selected; menu_states_t &states = player->states; /* Save variables */ IMenuHandler *mh = states.mh; IBaseMenu *menu = states.menu; unsigned int item_on_page = states.item_on_page; assert(mh != NULL); if (menu == NULL) { item = key_press; } else if (key_press < 1 || key_press > GetMaxPageItems()) { cancel = true; } else { ItemSelection type = states.slots[key_press].type; /* Check if we should play a sound about the type */ if (g_Menus.MenuSoundsEnabled() && (!menu || (menu->GetMenuOptionFlags() & MENUFLAG_NO_SOUND) != MENUFLAG_NO_SOUND)) { CellRecipientFilter filter; cell_t clients[1]; clients[0] = client; filter.Initialize(clients, 1); const char *sound = g_Menus.GetMenuSound(type); if (sound != NULL) { edict_t *pEdict = PEntityOfEntIndex(client); if (pEdict) { ICollideable *pCollideable = pEdict->GetCollideable(); if (pCollideable) { const Vector & pos = pCollideable->GetCollisionOrigin(); enginesound->EmitSound(filter, client, CHAN_AUTO, #if SOURCE_ENGINE >= SE_PORTAL2 sound, -1, #endif sound, VOL_NORM, ATTN_NORM, #if SOURCE_ENGINE >= SE_PORTAL2 0, #endif 0, PITCH_NORM, #if SOURCE_ENGINE == SE_CSS || SOURCE_ENGINE == SE_HL2DM || SOURCE_ENGINE == SE_DODS \ || SOURCE_ENGINE == SE_SDK2013 || SOURCE_ENGINE == SE_BMS || SOURCE_ENGINE == SE_TF2 0, #endif &pos); } } } } /* For navigational items, we're going to redisplay */ if (type == ItemSel_Back) { if (!RedoClientMenu(client, ItemOrder_Descending)) { cancel = true; reason = MenuCancel_NoDisplay; end_reason = MenuEnd_Cancelled; } else { return; } } else if (type == ItemSel_Next) { if (!RedoClientMenu(client, ItemOrder_Ascending)) { cancel = true; /* I like Saltines. */ reason = MenuCancel_NoDisplay; end_reason = MenuEnd_Cancelled; } else { return; } } else if (type == ItemSel_Exit || type == ItemSel_None) { cancel = true; reason = MenuCancel_Exit; end_reason = MenuEnd_Exit; } else if (type == ItemSel_ExitBack) { cancel = true; reason = MenuCancel_ExitBack; end_reason = MenuEnd_ExitBack; } else { item = states.slots[key_press].item; } } /* Clear states */ player->bInMenu = false; if (player->menuHoldTime) { RemoveClientFromWatch(client); } Handle_t hndl = menu ? menu->GetHandle() : BAD_HANDLE; AutoHandleRooter ahr(hndl); if (cancel) { mh->OnMenuCancel(menu, client, reason); } else { mh->OnMenuSelect(menu, client, item); if (mh->GetMenuAPIVersion2() >= 13) { mh->OnMenuSelect2(menu, client, item, item_on_page); } } /* Only fire end for valid menus */ if (menu) { mh->OnMenuEnd(menu, end_reason); } }
IMenuPanel *MenuManager::RenderMenu(int client, menu_states_t &md, ItemOrder order) { IBaseMenu *menu = md.menu; if (!menu) { return NULL; } struct { unsigned int position; ItemDrawInfo draw; } drawItems[10]; /* Figure out how many items to draw */ IMenuStyle *style = menu->GetDrawStyle(); unsigned int pgn = menu->GetPagination(); unsigned int maxItems = style->GetMaxPageItems(); bool exitButton = (menu->GetMenuOptionFlags() & MENUFLAG_BUTTON_EXIT) == MENUFLAG_BUTTON_EXIT; bool novoteButton = (menu->GetMenuOptionFlags() & MENUFLAG_BUTTON_NOVOTE) == MENUFLAG_BUTTON_NOVOTE; if (pgn != MENU_NO_PAGINATION) { maxItems = pgn; } else if (exitButton) { maxItems--; } if (novoteButton) { maxItems--; } /* This is very not allowed! */ if (maxItems < 2) { return NULL; } unsigned int totalItems = menu->GetItemCount(); unsigned int startItem = 0; /* For pagination, find the starting point. */ if (pgn != MENU_NO_PAGINATION) { if (order == ItemOrder_Ascending) { startItem = md.lastItem; /* This shouldn't happen with well-coded menus. * If the item is out of bounds, switch the order to * Items_Descending and make us start from the top. */ if (startItem >= totalItems) { startItem = totalItems - 1; order = ItemOrder_Descending; } } else if (order == ItemOrder_Descending) { startItem = md.firstItem; /* This shouldn't happen with well-coded menus. * If searching backwards doesn't give us enough room, * start from the beginning and change to ascending. */ if (startItem <= maxItems) { startItem = 0; order = ItemOrder_Ascending; } } } /* Get our Display pointer and initialize some crap */ IMenuPanel *panel = menu->CreatePanel(); IMenuHandler *mh = md.mh; bool foundExtra = false; unsigned int extraItem = 0; if (panel == NULL) { return NULL; } /** * We keep searching until: * 1) There are no more items * 2) We reach one OVER the maximum number of slot items * 3) We have reached maxItems and pagination is MENU_NO_PAGINATION */ unsigned int i = startItem; unsigned int foundItems = 0; while (totalItems) { ItemDrawInfo &dr = drawItems[foundItems].draw; /* Is the item valid? */ if (menu->GetItemInfo(i, &dr) != NULL) { /* Ask the user to change the style, if necessary */ mh->OnMenuDrawItem(menu, client, i, dr.style); /* Check if it's renderable */ if (IsSlotItem(panel, dr.style)) { /* If we've already found the max number of items, * This means we should just cancel out and log our * "last item." */ if (foundItems >= maxItems) { foundExtra = true; extraItem = i; break; } drawItems[foundItems++].position = i; } } /* If there's no pagination, stop once the menu is full. */ if (pgn == MENU_NO_PAGINATION) { /* If we've filled up, then stop */ if (foundItems >= maxItems) { break; } } /* If we're descending and this is the first item, stop */ if (order == ItemOrder_Descending) { if (i == 0) { break; } i--; } /* If we're ascending and this is the last item, stop */ else if (order == ItemOrder_Ascending) { if (i >= totalItems - 1) { break; } i++; } } /* There were no items to draw! */ if (!foundItems) { panel->DeleteThis(); return NULL; } bool displayPrev = false; bool displayNext = false; /* This is an annoying process. * Skip it for non-paginated menus, which get special treatment. */ if (pgn != MENU_NO_PAGINATION) { if (foundExtra) { if (order == ItemOrder_Descending) { displayPrev = true; md.firstItem = extraItem; } else if (order == ItemOrder_Ascending) { displayNext = true; md.lastItem = extraItem; } } unsigned int lastItem = 0; ItemDrawInfo dr; /* Find the last feasible item to search from. */ if (order == ItemOrder_Descending) { lastItem = drawItems[0].position; if (lastItem >= totalItems - 1) { goto skip_search; } while (++lastItem < totalItems) { if (menu->GetItemInfo(lastItem, &dr) != NULL) { mh->OnMenuDrawItem(menu, client, lastItem, dr.style); if (IsSlotItem(panel, dr.style)) { displayNext = true; md.lastItem = lastItem; break; } } } } else if (order == ItemOrder_Ascending) { lastItem = drawItems[0].position; if (lastItem == 0) { goto skip_search; } lastItem--; while (lastItem != 0) { if (menu->GetItemInfo(lastItem, &dr) != NULL) { mh->OnMenuDrawItem(menu, client, lastItem, dr.style); if (IsSlotItem(panel, dr.style)) { displayPrev = true; md.firstItem = lastItem; break; } } lastItem--; } } } skip_search: /* Draw the item according to the order */ menu_slots_t *slots = md.slots; unsigned int position = 0; /* Keep track of the last position */ if (novoteButton) { char text[50]; if (!logicore.CoreTranslate(text, sizeof(text), "%T", 2, NULL, "No Vote", &client)) { UTIL_Format(text, sizeof(text), "No Vote"); } ItemDrawInfo dr(text, 0); position = panel->DrawItem(dr); slots[position].type = ItemSel_Exit; position++; } if (order == ItemOrder_Ascending) { md.item_on_page = drawItems[0].position; for (unsigned int i = 0; i < foundItems; i++) { ItemDrawInfo &dr = drawItems[i].draw; if ((position = mh->OnMenuDisplayItem(menu, client, panel, drawItems[i].position, dr)) == 0) { position = panel->DrawItem(dr); } if (position != 0) { slots[position].item = drawItems[i].position; if ((dr.style & ITEMDRAW_DISABLED) == ITEMDRAW_DISABLED) { slots[position].type = ItemSel_None; } else { slots[position].type = ItemSel_Item; } } } } else if (order == ItemOrder_Descending) { unsigned int i = foundItems; /* NOTE: There will always be at least one item because * of the check earlier. */ md.item_on_page = drawItems[foundItems - 1].position; while (i--) { ItemDrawInfo &dr = drawItems[i].draw; if ((position = mh->OnMenuDisplayItem(menu, client, panel, drawItems[i].position, dr)) == 0) { position = panel->DrawItem(dr); } if (position != 0) { slots[position].item = drawItems[i].position; if ((dr.style & ITEMDRAW_DISABLED) == ITEMDRAW_DISABLED) { slots[position].type = ItemSel_None; } else { slots[position].type = ItemSel_Item; } } } } /* Now, we need to check if we need to add anything extra */ if (pgn != MENU_NO_PAGINATION || exitButton) { bool canDrawDisabled = panel->CanDrawItem(ITEMDRAW_DISABLED|ITEMDRAW_CONTROL); bool exitBackButton = false; char text[50]; if (pgn != MENU_NO_PAGINATION && (menu->GetMenuOptionFlags() & MENUFLAG_BUTTON_EXITBACK) == MENUFLAG_BUTTON_EXITBACK) { exitBackButton = true; } /* Calculate how many items we are allowed for control stuff */ unsigned int padding = style->GetMaxPageItems() - maxItems; /* Add the number of available slots */ padding += (maxItems - foundItems); /* Someday, if we are able to re-enable this, we will be very lucky men. */ #if 0 if (!style->FeatureExists(MenuStyleFeature_ImplicitExit)) { #endif /* Even if we don't draw an exit button, we invalidate the slot. */ padding--; #if 0 } else { /* Otherwise, we don't draw anything and leave the slot available */ exitButton = false; } #endif if (pgn != MENU_NO_PAGINATION) { /* Subtract two slots for the displayNext/displayPrev padding */ padding -= 2; } /* If we have an "Exit Back" button and the space to draw it, do so. */ if (exitBackButton) { if (!displayPrev) { displayPrev = true; } else { exitBackButton = false; } } /** * We allow next/prev to be undrawn if neither exists. * Thus, we only need padding if one of them will be drawn, * or the exit button will be drawn. */ ItemDrawInfo padItem(NULL, ITEMDRAW_SPACER); if (exitButton || (displayNext || displayPrev)) { /* If there are no control options, * Instead just pad with invisible slots. */ if (!displayPrev && !displayPrev) { padItem.style = ITEMDRAW_NOTEXT; } /* Add spacers so we can pad to the end */ for (unsigned int i=0; i<padding; i++) { position = panel->DrawItem(padItem); slots[position].type = ItemSel_None; } } /* Put a fake spacer before control stuff, if possible */ if ((displayPrev || displayNext) || exitButton) { ItemDrawInfo draw("", ITEMDRAW_RAWLINE|ITEMDRAW_SPACER); panel->DrawItem(draw); } ItemDrawInfo dr(text, 0); /** * If we have one or the other, we need to have spacers for both. */ if (pgn != MENU_NO_PAGINATION) { if (displayPrev || displayNext) { /* PREVIOUS */ ItemDrawInfo padCtrlItem(NULL, ITEMDRAW_SPACER|ITEMDRAW_CONTROL); if (displayPrev || canDrawDisabled) { if (exitBackButton) { if (!logicore.CoreTranslate(text, sizeof(text), "%T", 2, NULL, "Back", &client)) { UTIL_Format(text, sizeof(text), "Back"); } dr.style = ITEMDRAW_CONTROL; position = panel->DrawItem(dr); slots[position].type = ItemSel_ExitBack; } else { if (!logicore.CoreTranslate(text, sizeof(text), "%T", 2, NULL, "Previous", &client)) { UTIL_Format(text, sizeof(text), "Previous"); } dr.style = (displayPrev ? 0 : ITEMDRAW_DISABLED)|ITEMDRAW_CONTROL; position = panel->DrawItem(dr); slots[position].type = ItemSel_Back; } } else if (displayNext || exitButton) { /* If we can't display this, and there is an exit button, * we need to pad! */ position = panel->DrawItem(padCtrlItem); slots[position].type = ItemSel_None; } /* NEXT */ if (displayNext || canDrawDisabled) { if (!logicore.CoreTranslate(text, sizeof(text), "%T", 2, NULL, "Next", &client)) { UTIL_Format(text, sizeof(text), "Next"); } dr.style = (displayNext ? 0 : ITEMDRAW_DISABLED)|ITEMDRAW_CONTROL; position = panel->DrawItem(dr); slots[position].type = ItemSel_Next; } else if (exitButton) { /* If we can't display this, * but there is an "exit" button, we need to pad! */ position = panel->DrawItem(padCtrlItem); slots[position].type = ItemSel_None; } } else { /* Otherwise, bump to two slots! */ ItemDrawInfo numBump(NULL, ITEMDRAW_NOTEXT); position = panel->DrawItem(numBump); slots[position].type = ItemSel_None; position = panel->DrawItem(numBump); slots[position].type = ItemSel_None; } } /* EXIT */ if (exitButton) { if (!logicore.CoreTranslate(text, sizeof(text), "%T", 2, NULL, "Exit", &client)) { UTIL_Format(text, sizeof(text), "Exit"); } dr.style = ITEMDRAW_CONTROL; position = panel->DrawItem(dr); slots[position].type = ItemSel_Exit; } } /* Lastly, fill in any slots we could have missed */ for (unsigned int i = position + 1; i < 10; i++) { slots[i].type = ItemSel_None; } /* Do title stuff */ mh->OnMenuDisplay(menu, client, panel); panel->DrawTitle(menu->GetDefaultTitle(), true); return panel; }