Fix recursion issue with show_menu and newmenus
This commit is contained in:
parent
af0042b71d
commit
e634e512c8
|
@ -1251,8 +1251,11 @@ static cell AMX_NATIVE_CALL show_menu(AMX *amx, cell *params) /* 3 param */
|
|||
pPlayer->menu = 0;
|
||||
|
||||
// Fire newmenu callback so closing it can be handled by the plugin
|
||||
if (Menu *pMenu = get_menu_by_id(pPlayer->newmenu))
|
||||
pMenu->Close(pPlayer->index);
|
||||
if (!CloseNewMenus(pPlayer))
|
||||
{
|
||||
LogError(amx, AMX_ERR_NATIVE, "Plugin called menu_display when item=MENU_EXIT");
|
||||
return 0;
|
||||
}
|
||||
|
||||
UTIL_FakeClientCommand(pPlayer->pEdict, "menuselect", "10", 0);
|
||||
}
|
||||
|
@ -1274,8 +1277,11 @@ static cell AMX_NATIVE_CALL show_menu(AMX *amx, cell *params) /* 3 param */
|
|||
pPlayer->menu = 0;
|
||||
|
||||
// Fire newmenu callback so closing it can be handled by the plugin
|
||||
if (Menu *pMenu = get_menu_by_id(pPlayer->newmenu))
|
||||
pMenu->Close(pPlayer->index);
|
||||
if (!CloseNewMenus(pPlayer))
|
||||
{
|
||||
LogError(amx, AMX_ERR_NATIVE, "Plugin called menu_display when item=MENU_EXIT");
|
||||
return 0;
|
||||
}
|
||||
|
||||
UTIL_FakeClientCommand(pPlayer->pEdict, "menuselect", "10", 0);
|
||||
}
|
||||
|
|
|
@ -68,6 +68,28 @@ Menu *get_menu_by_id(int id)
|
|||
return g_NewMenus[id];
|
||||
}
|
||||
|
||||
bool CloseNewMenus(CPlayer *pPlayer)
|
||||
{
|
||||
// If the stupid handler keeps drawing menus,
|
||||
// We need to keep cancelling them. But we put in a quick infinite loop
|
||||
// counter to prevent this from going nuts.
|
||||
|
||||
int loops = 0;
|
||||
Menu *pMenu;
|
||||
|
||||
while ((pMenu = get_menu_by_id(pPlayer->newmenu)))
|
||||
{
|
||||
pMenu->Close(pPlayer->index);
|
||||
|
||||
if (++loops >= 10)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
Menu::Menu(const char *title, AMX *amx, int fid) : m_Title(title), m_ItemColor("\\r"),
|
||||
m_NeverExit(false), m_AutoColors(g_coloredmenus), thisId(0), func(fid),
|
||||
isDestroying(false), items_per_page(7)
|
||||
|
@ -792,28 +814,10 @@ static cell AMX_NATIVE_CALL menu_display(AMX *amx, cell *params)
|
|||
int page = params[3];
|
||||
CPlayer* pPlayer = GET_PLAYER_POINTER_I(player);
|
||||
|
||||
/* If the stupid handler keeps drawing menus,
|
||||
* We need to keep cancelling them. But we put in a quick infinite loop
|
||||
* counter to prevent this from going nuts.
|
||||
*/
|
||||
int menu;
|
||||
int loops = 0;
|
||||
while ((menu = pPlayer->newmenu) >= 0)
|
||||
if (!CloseNewMenus(pPlayer))
|
||||
{
|
||||
if ((size_t)menu >= g_NewMenus.length() || !g_NewMenus[menu])
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
||||
Menu *pOther = g_NewMenus[menu];
|
||||
pOther->Close(pPlayer->index);
|
||||
|
||||
/* Infinite loop counter */
|
||||
if (++loops >= 10)
|
||||
{
|
||||
LogError(amx, AMX_ERR_NATIVE, "Plugin called menu_display when item=MENU_EXIT");
|
||||
return 0;
|
||||
}
|
||||
LogError(amx, AMX_ERR_NATIVE, "Plugin called menu_display when item=MENU_EXIT");
|
||||
return 0;
|
||||
}
|
||||
|
||||
int time = -1;
|
||||
|
|
|
@ -129,6 +129,7 @@ public:
|
|||
|
||||
void ClearMenus();
|
||||
Menu *get_menu_by_id(int id);
|
||||
bool CloseNewMenus(CPlayer *pPlayer);
|
||||
|
||||
extern ke::Vector<Menu *> g_NewMenus;
|
||||
extern AMX_NATIVE_INFO g_NewMenuNatives[];
|
||||
|
|
Loading…
Reference in New Issue
Block a user