From cd7cb8c1a887bd332fd24ce8585935c36e984106 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Valentin=20Gr=C3=BCnbacher?= Date: Wed, 21 May 2014 18:17:09 +0200 Subject: [PATCH 01/10] Newmenus: Execute menu callback when old-style menu overwrites new menu show_menu simply resets CPlayer::newmenu. The menu callback is never fired and the plugin never informed that the menu has been closed. This can result in leaking menu handles. Using "menuselect 10" on the client is not an appropriate solution because it is possible to construct newmenus that contain 10 valid items. --- amxmodx/amxmodx.cpp | 26 ++++++++++++++++++++++++-- 1 file changed, 24 insertions(+), 2 deletions(-) diff --git a/amxmodx/amxmodx.cpp b/amxmodx/amxmodx.cpp index 8d0c644d..94b0e73a 100755 --- a/amxmodx/amxmodx.cpp +++ b/amxmodx/amxmodx.cpp @@ -32,6 +32,7 @@ #include #include "amxmodx.h" #include "CMenu.h" +#include "newmenus.h" #include "natives.h" #include "debugger.h" #include "binlog.h" @@ -1292,6 +1293,17 @@ static cell AMX_NATIVE_CALL show_menu(AMX *amx, cell *params) /* 3 param */ pPlayer->keys = 0; pPlayer->menu = 0; + // Fire newmenu callback so closing it can be handled by the plugin + int menu = pPlayer->newmenu; + if (menu >= 0 && menu < (int)g_NewMenus.size() && g_NewMenus[menu]) + { + Menu *pMenu = g_NewMenus[menu]; + + pPlayer->newmenu = -1; + + executeForwards(pMenu->func, static_cast(pPlayer->index), static_cast(menu), static_cast(MENU_EXIT)); + } + UTIL_FakeClientCommand(pPlayer->pEdict, "menuselect", "10", 0); pPlayer->keys = keys; @@ -1303,7 +1315,6 @@ static cell AMX_NATIVE_CALL show_menu(AMX *amx, cell *params) /* 3 param */ else pPlayer->menuexpire = gpGlobals->time + static_cast(time); - pPlayer->newmenu = -1; pPlayer->page = 0; UTIL_ShowMenu(pPlayer->pEdict, keys, time, sMenu, ilen); } @@ -1324,6 +1335,17 @@ static cell AMX_NATIVE_CALL show_menu(AMX *amx, cell *params) /* 3 param */ pPlayer->keys = 0; pPlayer->menu = 0; + // Fire newmenu callback so closing it can be handled by the plugin + int menu = pPlayer->newmenu; + if (menu >= 0 && menu < (int)g_NewMenus.size() && g_NewMenus[menu]) + { + Menu *pMenu = g_NewMenus[menu]; + + pPlayer->newmenu = -1; + + executeForwards(pMenu->func, static_cast(pPlayer->index), static_cast(menu), static_cast(MENU_EXIT)); + } + UTIL_FakeClientCommand(pPlayer->pEdict, "menuselect", "10", 0); pPlayer->keys = keys; @@ -1335,7 +1357,6 @@ static cell AMX_NATIVE_CALL show_menu(AMX *amx, cell *params) /* 3 param */ else pPlayer->menuexpire = gpGlobals->time + static_cast(time); - pPlayer->newmenu = -1; pPlayer->page = 0; UTIL_ShowMenu(pPlayer->pEdict, keys, time, sMenu, ilen); } @@ -2948,6 +2969,7 @@ static cell AMX_NATIVE_CALL get_user_menu(AMX *amx, cell *params) /* 3 param */ if (gpGlobals->time > pPlayer->menuexpire) { pPlayer->menu = 0; + *cpMenu = 0; *cpKeys = 0; From 2e8ce87c23f8c67eb215650114b19dcd3e88c1f4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Valentin=20Gr=C3=BCnbacher?= Date: Wed, 21 May 2014 18:45:40 +0200 Subject: [PATCH 02/10] Newmenus: Add MENU_TIMEOUT status code and pass it where necessary --- amxmodx/CMisc.cpp | 8 +++++++- amxmodx/amxmodx.cpp | 14 ++++++++++++-- amxmodx/newmenus.cpp | 27 ++++++++++++++++++++++----- amxmodx/newmenus.h | 1 + 4 files changed, 42 insertions(+), 8 deletions(-) diff --git a/amxmodx/CMisc.cpp b/amxmodx/CMisc.cpp index 3cf9957f..6309641b 100755 --- a/amxmodx/CMisc.cpp +++ b/amxmodx/CMisc.cpp @@ -70,13 +70,19 @@ void CPlayer::Disconnect() Menu *pMenu = g_NewMenus[newmenu]; if (pMenu) { + int status; + if (gpGlobals->time > menuexpire) + status = MENU_TIMEOUT; + else + status = MENU_EXIT; + //prevent recursion newmenu = -1; menu = 0; executeForwards(pMenu->func, static_cast(ENTINDEX(pEdict)), static_cast(pMenu->thisId), - static_cast(MENU_EXIT)); + static_cast(status)); } } diff --git a/amxmodx/amxmodx.cpp b/amxmodx/amxmodx.cpp index 94b0e73a..e44db859 100755 --- a/amxmodx/amxmodx.cpp +++ b/amxmodx/amxmodx.cpp @@ -1298,10 +1298,15 @@ static cell AMX_NATIVE_CALL show_menu(AMX *amx, cell *params) /* 3 param */ if (menu >= 0 && menu < (int)g_NewMenus.size() && g_NewMenus[menu]) { Menu *pMenu = g_NewMenus[menu]; + int status; + if (gpGlobals->time > pPlayer->menuexpire) + status = MENU_TIMEOUT; + else + status = MENU_EXIT; pPlayer->newmenu = -1; - executeForwards(pMenu->func, static_cast(pPlayer->index), static_cast(menu), static_cast(MENU_EXIT)); + executeForwards(pMenu->func, static_cast(pPlayer->index), static_cast(menu), static_cast(status)); } UTIL_FakeClientCommand(pPlayer->pEdict, "menuselect", "10", 0); @@ -1340,10 +1345,15 @@ static cell AMX_NATIVE_CALL show_menu(AMX *amx, cell *params) /* 3 param */ if (menu >= 0 && menu < (int)g_NewMenus.size() && g_NewMenus[menu]) { Menu *pMenu = g_NewMenus[menu]; + int status; + if (gpGlobals->time > pPlayer->menuexpire) + status = MENU_TIMEOUT; + else + status = MENU_EXIT; pPlayer->newmenu = -1; - executeForwards(pMenu->func, static_cast(pPlayer->index), static_cast(menu), static_cast(MENU_EXIT)); + executeForwards(pMenu->func, static_cast(pPlayer->index), static_cast(menu), static_cast(status)); } UTIL_FakeClientCommand(pPlayer->pEdict, "menuselect", "10", 0); diff --git a/amxmodx/newmenus.cpp b/amxmodx/newmenus.cpp index 26ceeef4..d94d6f45 100755 --- a/amxmodx/newmenus.cpp +++ b/amxmodx/newmenus.cpp @@ -794,14 +794,19 @@ static cell AMX_NATIVE_CALL menu_display(AMX *amx, cell *params) break; } - Menu *pOther = g_NewMenus[menu]; + Menu *pOther = g_NewMenus[menu]; + int status; + if (gpGlobals->time > pPlayer->menuexpire) + status = MENU_TIMEOUT; + else + status = MENU_EXIT; pPlayer->newmenu = -1; pPlayer->menu = 0; executeForwards(pOther->func, static_cast(player), static_cast(pOther->thisId), - static_cast(MENU_EXIT)); + static_cast(status)); /* Infinite loop counter */ if (++loops >= 10) @@ -1047,13 +1052,19 @@ static cell AMX_NATIVE_CALL menu_cancel(AMX *amx, cell *params) return 0; Menu *pMenu = g_NewMenus[menu]; + + int status; + if (gpGlobals->time > player->menuexpire) + status = MENU_TIMEOUT; + else + status = MENU_EXIT; player->newmenu = -1; player->menu = 0; executeForwards(pMenu->func, static_cast(index), static_cast(pMenu->thisId), - static_cast(MENU_EXIT)); + static_cast(status)); return 1; } @@ -1074,13 +1085,19 @@ static cell AMX_NATIVE_CALL menu_destroy(AMX *amx, cell *params) { player = GET_PLAYER_POINTER_I(i); if (player->newmenu == pMenu->thisId) - { + { + int status; + if (gpGlobals->time > player->menuexpire) + status = MENU_TIMEOUT; + else + status = MENU_EXIT; + player->newmenu = -1; player->menu = 0; executeForwards(pMenu->func, static_cast(i), static_cast(pMenu->thisId), - static_cast(MENU_EXIT)); + static_cast(status)); } } g_NewMenus[params[1]] = NULL; diff --git a/amxmodx/newmenus.h b/amxmodx/newmenus.h index d759dcf2..0e7f6579 100755 --- a/amxmodx/newmenus.h +++ b/amxmodx/newmenus.h @@ -32,6 +32,7 @@ #ifndef _INCLUDE_NEWMENUS_H #define _INCLUDE_NEWMENUS_H +#define MENU_TIMEOUT -4 #define MENU_EXIT -3 #define MENU_BACK -2 #define MENU_MORE -1 From 6a4c55de7da1e1facde60281487767a7ab0b9f0c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Valentin=20Gr=C3=BCnbacher?= Date: Wed, 21 May 2014 18:47:20 +0200 Subject: [PATCH 03/10] Newmenus: Fire MENU_TIMEOUT on menuselect client command --- amxmodx/meta_api.cpp | 26 ++++++++++++++++++++++---- 1 file changed, 22 insertions(+), 4 deletions(-) diff --git a/amxmodx/meta_api.cpp b/amxmodx/meta_api.cpp index f5fd25f5..061b922c 100755 --- a/amxmodx/meta_api.cpp +++ b/amxmodx/meta_api.cpp @@ -961,12 +961,30 @@ void C_ClientCommand(edict_t *pEntity) if (pPlayer->keys & bit_key) { - if ((pPlayer->menu > 0 && !pPlayer->vgui) && (gpGlobals->time > pPlayer->menuexpire)) + if (gpGlobals->time > pPlayer->menuexpire) { - pPlayer->menu = 0; - pPlayer->keys = 0; + int menu = pPlayer->newmenu; + if (menu >= 0 && menu < (int)g_NewMenus.size() && g_NewMenus[menu]) + { + Menu *pMenu = g_NewMenus[menu]; - RETURN_META(MRES_SUPERCEDE); + pPlayer->newmenu = -1; + pPlayer->menu = 0; + + executeForwards(pMenu->func, + static_cast(pPlayer->index), + static_cast(menu), + static_cast(MENU_TIMEOUT)); + + RETURN_META(MRES_SUPERCEDE); + } + else if (pPlayer->menu > 0 && !pPlayer->vgui) + { + pPlayer->menu = 0; + pPlayer->keys = 0; + + RETURN_META(MRES_SUPERCEDE); + } } int menuid = pPlayer->menu; From 34337fb95922d9d0a15dc353e2f64b86254f325a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Valentin=20Gr=C3=BCnbacher?= Date: Wed, 21 May 2014 18:51:55 +0200 Subject: [PATCH 04/10] Newmenus: Add Menu::Close to remove a bunch of redundant code --- amxmodx/newmenus.cpp | 20 ++++++++++++++++++++ amxmodx/newmenus.h | 3 ++- 2 files changed, 22 insertions(+), 1 deletion(-) diff --git a/amxmodx/newmenus.cpp b/amxmodx/newmenus.cpp index d94d6f45..c252bedd 100755 --- a/amxmodx/newmenus.cpp +++ b/amxmodx/newmenus.cpp @@ -321,6 +321,26 @@ bool Menu::Display(int player, page_t page) return true; } +void Menu::Close(int player) +{ + CPlayer *pPlayer = GET_PLAYER_POINTER_I(player); + + int status; + if (gpGlobals->time > pPlayer->menuexpire) + status = MENU_TIMEOUT; + else + status = MENU_EXIT; + + pPlayer->keys = 0; + pPlayer->menu = 0; + pPlayer->newmenu = -1; + + executeForwards(func, + static_cast(player), + static_cast(thisId), + static_cast(status)); +} + const char *Menu::GetTextString(int player, page_t page, int &keys) { page_t pages = GetPageCount(); diff --git a/amxmodx/newmenus.h b/amxmodx/newmenus.h index 0e7f6579..e90b807e 100755 --- a/amxmodx/newmenus.h +++ b/amxmodx/newmenus.h @@ -127,7 +127,8 @@ public: const char *GetTextString(int player, page_t page, int &keys); bool Display(int player, page_t page); - + void Close(int player); + int PagekeyToItem(page_t page, item_t key); int GetMenuMenuid(); public: From fa5336cade1d760b691bb83c5e6a4f919b520ea4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Valentin=20Gr=C3=BCnbacher?= Date: Wed, 21 May 2014 18:58:51 +0200 Subject: [PATCH 05/10] Newmenus: Use Menu::Close everywhere --- amxmodx/CMisc.cpp | 19 ++----------------- amxmodx/amxmodx.cpp | 20 ++------------------ amxmodx/meta_api.cpp | 9 +-------- amxmodx/newmenus.cpp | 40 +++------------------------------------- 4 files changed, 8 insertions(+), 80 deletions(-) diff --git a/amxmodx/CMisc.cpp b/amxmodx/CMisc.cpp index 6309641b..8f2e508b 100755 --- a/amxmodx/CMisc.cpp +++ b/amxmodx/CMisc.cpp @@ -65,25 +65,10 @@ void CPlayer::Disconnect() authorized = false; teamIdsInitialized = false; - if (newmenu != -1) + if (newmenu >= 0 && newmenu < (int)g_NewMenus.size() && g_NewMenus[newmenu]) { Menu *pMenu = g_NewMenus[newmenu]; - if (pMenu) - { - int status; - if (gpGlobals->time > menuexpire) - status = MENU_TIMEOUT; - else - status = MENU_EXIT; - - //prevent recursion - newmenu = -1; - menu = 0; - executeForwards(pMenu->func, - static_cast(ENTINDEX(pEdict)), - static_cast(pMenu->thisId), - static_cast(status)); - } + pMenu->Close(index); } List::iterator iter, end=queries.end(); diff --git a/amxmodx/amxmodx.cpp b/amxmodx/amxmodx.cpp index e44db859..fd09387b 100755 --- a/amxmodx/amxmodx.cpp +++ b/amxmodx/amxmodx.cpp @@ -1298,15 +1298,7 @@ static cell AMX_NATIVE_CALL show_menu(AMX *amx, cell *params) /* 3 param */ if (menu >= 0 && menu < (int)g_NewMenus.size() && g_NewMenus[menu]) { Menu *pMenu = g_NewMenus[menu]; - int status; - if (gpGlobals->time > pPlayer->menuexpire) - status = MENU_TIMEOUT; - else - status = MENU_EXIT; - - pPlayer->newmenu = -1; - - executeForwards(pMenu->func, static_cast(pPlayer->index), static_cast(menu), static_cast(status)); + pMenu->Close(pPlayer->index); } UTIL_FakeClientCommand(pPlayer->pEdict, "menuselect", "10", 0); @@ -1345,15 +1337,7 @@ static cell AMX_NATIVE_CALL show_menu(AMX *amx, cell *params) /* 3 param */ if (menu >= 0 && menu < (int)g_NewMenus.size() && g_NewMenus[menu]) { Menu *pMenu = g_NewMenus[menu]; - int status; - if (gpGlobals->time > pPlayer->menuexpire) - status = MENU_TIMEOUT; - else - status = MENU_EXIT; - - pPlayer->newmenu = -1; - - executeForwards(pMenu->func, static_cast(pPlayer->index), static_cast(menu), static_cast(status)); + pMenu->Close(pPlayer->index); } UTIL_FakeClientCommand(pPlayer->pEdict, "menuselect", "10", 0); diff --git a/amxmodx/meta_api.cpp b/amxmodx/meta_api.cpp index 061b922c..86e9b998 100755 --- a/amxmodx/meta_api.cpp +++ b/amxmodx/meta_api.cpp @@ -967,14 +967,7 @@ void C_ClientCommand(edict_t *pEntity) if (menu >= 0 && menu < (int)g_NewMenus.size() && g_NewMenus[menu]) { Menu *pMenu = g_NewMenus[menu]; - - pPlayer->newmenu = -1; - pPlayer->menu = 0; - - executeForwards(pMenu->func, - static_cast(pPlayer->index), - static_cast(menu), - static_cast(MENU_TIMEOUT)); + pMenu->Close(pPlayer->index); RETURN_META(MRES_SUPERCEDE); } diff --git a/amxmodx/newmenus.cpp b/amxmodx/newmenus.cpp index c252bedd..6b75394d 100755 --- a/amxmodx/newmenus.cpp +++ b/amxmodx/newmenus.cpp @@ -815,18 +815,7 @@ static cell AMX_NATIVE_CALL menu_display(AMX *amx, cell *params) } Menu *pOther = g_NewMenus[menu]; - int status; - if (gpGlobals->time > pPlayer->menuexpire) - status = MENU_TIMEOUT; - else - status = MENU_EXIT; - - pPlayer->newmenu = -1; - pPlayer->menu = 0; - executeForwards(pOther->func, - static_cast(player), - static_cast(pOther->thisId), - static_cast(status)); + pOther->Close(pPlayer->index); /* Infinite loop counter */ if (++loops >= 10) @@ -1072,19 +1061,7 @@ static cell AMX_NATIVE_CALL menu_cancel(AMX *amx, cell *params) return 0; Menu *pMenu = g_NewMenus[menu]; - - int status; - if (gpGlobals->time > player->menuexpire) - status = MENU_TIMEOUT; - else - status = MENU_EXIT; - - player->newmenu = -1; - player->menu = 0; - executeForwards(pMenu->func, - static_cast(index), - static_cast(pMenu->thisId), - static_cast(status)); + pMenu->Close(player->index); return 1; } @@ -1106,18 +1083,7 @@ static cell AMX_NATIVE_CALL menu_destroy(AMX *amx, cell *params) player = GET_PLAYER_POINTER_I(i); if (player->newmenu == pMenu->thisId) { - int status; - if (gpGlobals->time > player->menuexpire) - status = MENU_TIMEOUT; - else - status = MENU_EXIT; - - player->newmenu = -1; - player->menu = 0; - executeForwards(pMenu->func, - static_cast(i), - static_cast(pMenu->thisId), - static_cast(status)); + pMenu->Close(player->index); } } g_NewMenus[params[1]] = NULL; From c8b7a09028e4855861c52f453eb9b0bbcef26a4f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Valentin=20Gr=C3=BCnbacher?= Date: Wed, 21 May 2014 19:01:27 +0200 Subject: [PATCH 06/10] Newmenus: get_user_menu should also handle newmenu timeouts properly --- amxmodx/amxmodx.cpp | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/amxmodx/amxmodx.cpp b/amxmodx/amxmodx.cpp index fd09387b..d2ae3f13 100755 --- a/amxmodx/amxmodx.cpp +++ b/amxmodx/amxmodx.cpp @@ -2962,7 +2962,14 @@ static cell AMX_NATIVE_CALL get_user_menu(AMX *amx, cell *params) /* 3 param */ { if (gpGlobals->time > pPlayer->menuexpire) { - pPlayer->menu = 0; + int menu = pPlayer->newmenu; + if (menu >= 0 && menu < (int)g_NewMenus.size() && g_NewMenus[menu]) + { + Menu *pMenu = g_NewMenus[menu]; + pMenu->Close(pPlayer->index); + } + else + pPlayer->menu = 0; *cpMenu = 0; *cpKeys = 0; From 3b87c428dc1cfbd42bafc909bfb2880b61fd24c7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Valentin=20Gr=C3=BCnbacher?= Date: Wed, 21 May 2014 19:17:04 +0200 Subject: [PATCH 07/10] Newmenus: Add necessary API changes for newmenu timeouts --- amxmodx/newmenus.cpp | 10 ++++++++-- plugins/include/amxconst.inc | 7 ++++--- plugins/include/newmenus.inc | 9 ++++++++- 3 files changed, 20 insertions(+), 6 deletions(-) diff --git a/amxmodx/newmenus.cpp b/amxmodx/newmenus.cpp index 6b75394d..ee607ffe 100755 --- a/amxmodx/newmenus.cpp +++ b/amxmodx/newmenus.cpp @@ -825,8 +825,14 @@ static cell AMX_NATIVE_CALL menu_display(AMX *amx, cell *params) } } - // This will set the expire time of the menu to infinite - pPlayer->menuexpire = INFINITE; + int time = -1; + if (params[0] / sizeof(cell) >= 4) + time = params[4]; + + if (time < 0) + pPlayer->menuexpire = INFINITE; + else + pPlayer->menuexpire = gpGlobals->time + static_cast(time); return pMenu->Display(player, page); } diff --git a/plugins/include/amxconst.inc b/plugins/include/amxconst.inc index 1f902d34..2c0a298c 100755 --- a/plugins/include/amxconst.inc +++ b/plugins/include/amxconst.inc @@ -269,9 +269,10 @@ enum { #define INVALID_PLUGIN_ID -1 -#define MENU_EXIT -3 -#define MENU_BACK -2 -#define MENU_MORE -1 +#define MENU_TIMEOUT -4 +#define MENU_EXIT -3 +#define MENU_BACK -2 +#define MENU_MORE -1 #define ITEM_IGNORE 0 #define ITEM_ENABLED 1 #define ITEM_DISABLED 2 diff --git a/plugins/include/newmenus.inc b/plugins/include/newmenus.inc index 1da1ec76..829a8b1a 100644 --- a/plugins/include/newmenus.inc +++ b/plugins/include/newmenus.inc @@ -111,13 +111,20 @@ native menu_items(menu); * when the item is less than 0 (i.e. calling this from a cancelled menu will * result in an error). * + * Starting with 1.8.3 this allows to select a menu timeout similar to the + * show_menu native. If the menu exists on the client past the timeout *any* + * further action will send the MENU_TIMEOUT status code to the menu handler. + * That includes actions which would otherwise send MENU_EXIT, including + * client disconnect and calling menu_cancel or menu_destroy on a live menu. + * * @param id Client index. * @param menu Menu resource identifier. * @param page Page to start from (starting from 0). + * @param time If >=0 menu will timeout after this many seconds * @noreturn * @error Invalid menu resource or client index. */ -native menu_display(id, menu, page=0); +native menu_display(id, menu, page=0, time=-1); /** * Given a page on a menu and a keypress on that page, returns the item id selected. From c91d67912b062471bb3c2eb20fa46249c382312d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Valentin=20Gr=C3=BCnbacher?= Date: Tue, 27 May 2014 10:32:28 +0200 Subject: [PATCH 08/10] Newmenus: Update MENU_TIMEOUT doc --- plugins/include/newmenus.inc | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/plugins/include/newmenus.inc b/plugins/include/newmenus.inc index 829a8b1a..fe233b03 100644 --- a/plugins/include/newmenus.inc +++ b/plugins/include/newmenus.inc @@ -111,11 +111,12 @@ native menu_items(menu); * when the item is less than 0 (i.e. calling this from a cancelled menu will * result in an error). * - * Starting with 1.8.3 this allows to select a menu timeout similar to the + * Starting with 1.8.3 this allows to specify a menu timeout similar to the * show_menu native. If the menu exists on the client past the timeout *any* * further action will send the MENU_TIMEOUT status code to the menu handler. - * That includes actions which would otherwise send MENU_EXIT, including - * client disconnect and calling menu_cancel or menu_destroy on a live menu. + * That includes actions which would otherwise send MENU_EXIT, such as the + * client selecting an item or disconnecting and calling menu_cancel or + * menu_destroy on a live menu. * * @param id Client index. * @param menu Menu resource identifier. From a6ffae72f5afe37a4802a88a445694a313d2bd37 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Valentin=20Gr=C3=BCnbacher?= Date: Tue, 27 May 2014 10:33:53 +0200 Subject: [PATCH 09/10] Newmenus: Add get_menu_by_id and use it everywhere --- amxmodx/CMisc.cpp | 5 +---- amxmodx/amxmodx.cpp | 18 +++--------------- amxmodx/meta_api.cpp | 8 ++------ amxmodx/newmenus.cpp | 32 +++++++++++++++++++------------- amxmodx/newmenus.h | 1 + 5 files changed, 26 insertions(+), 38 deletions(-) diff --git a/amxmodx/CMisc.cpp b/amxmodx/CMisc.cpp index 8f2e508b..e1990618 100755 --- a/amxmodx/CMisc.cpp +++ b/amxmodx/CMisc.cpp @@ -65,11 +65,8 @@ void CPlayer::Disconnect() authorized = false; teamIdsInitialized = false; - if (newmenu >= 0 && newmenu < (int)g_NewMenus.size() && g_NewMenus[newmenu]) - { - Menu *pMenu = g_NewMenus[newmenu]; + if (Menu *pMenu = get_menu_by_id(newmenu)) pMenu->Close(index); - } List::iterator iter, end=queries.end(); for (iter=queries.begin(); iter!=end; iter++) diff --git a/amxmodx/amxmodx.cpp b/amxmodx/amxmodx.cpp index d2ae3f13..d491be17 100755 --- a/amxmodx/amxmodx.cpp +++ b/amxmodx/amxmodx.cpp @@ -1294,12 +1294,8 @@ 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 - int menu = pPlayer->newmenu; - if (menu >= 0 && menu < (int)g_NewMenus.size() && g_NewMenus[menu]) - { - Menu *pMenu = g_NewMenus[menu]; + if (Menu *pMenu = get_menu_by_id(pPlayer->newmenu)) pMenu->Close(pPlayer->index); - } UTIL_FakeClientCommand(pPlayer->pEdict, "menuselect", "10", 0); @@ -1333,12 +1329,8 @@ 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 - int menu = pPlayer->newmenu; - if (menu >= 0 && menu < (int)g_NewMenus.size() && g_NewMenus[menu]) - { - Menu *pMenu = g_NewMenus[menu]; + if (Menu *pMenu = get_menu_by_id(pPlayer->newmenu)) pMenu->Close(pPlayer->index); - } UTIL_FakeClientCommand(pPlayer->pEdict, "menuselect", "10", 0); @@ -2962,12 +2954,8 @@ static cell AMX_NATIVE_CALL get_user_menu(AMX *amx, cell *params) /* 3 param */ { if (gpGlobals->time > pPlayer->menuexpire) { - int menu = pPlayer->newmenu; - if (menu >= 0 && menu < (int)g_NewMenus.size() && g_NewMenus[menu]) - { - Menu *pMenu = g_NewMenus[menu]; + if (Menu *pMenu = get_menu_by_id(pPlayer->newmenu)) pMenu->Close(pPlayer->index); - } else pPlayer->menu = 0; diff --git a/amxmodx/meta_api.cpp b/amxmodx/meta_api.cpp index 86e9b998..67172920 100755 --- a/amxmodx/meta_api.cpp +++ b/amxmodx/meta_api.cpp @@ -963,10 +963,8 @@ void C_ClientCommand(edict_t *pEntity) { if (gpGlobals->time > pPlayer->menuexpire) { - int menu = pPlayer->newmenu; - if (menu >= 0 && menu < (int)g_NewMenus.size() && g_NewMenus[menu]) + if (Menu *pMenu = get_menu_by_id(pPlayer->newmenu)) { - Menu *pMenu = g_NewMenus[menu]; pMenu->Close(pPlayer->index); RETURN_META(MRES_SUPERCEDE); @@ -989,10 +987,8 @@ void C_ClientCommand(edict_t *pEntity) { int menu = pPlayer->newmenu; pPlayer->newmenu = -1; - - if (menu >= 0 && menu < (int)g_NewMenus.size() && g_NewMenus[menu]) + if (Menu *pMenu = get_menu_by_id(menu)) { - Menu *pMenu = g_NewMenus[menu]; int item = pMenu->PagekeyToItem(pPlayer->page, pressed_key+1); if (item == MENU_BACK) { diff --git a/amxmodx/newmenus.cpp b/amxmodx/newmenus.cpp index ee607ffe..691c3e6f 100755 --- a/amxmodx/newmenus.cpp +++ b/amxmodx/newmenus.cpp @@ -79,6 +79,14 @@ void validate_menu_text(char *str) *(str-offs) = '\0'; } } +} + +Menu *get_menu_by_id(int id) +{ + if (id < 0 || size_t(id) >= g_NewMenus.size() || !g_NewMenus[id]) + return NULL; + + return g_NewMenus[id]; } Menu::Menu(const char *title, AMX *amx, int fid) : m_Title(title), m_ItemColor("\\r"), @@ -606,10 +614,10 @@ const char *Menu::GetTextString(int player, page_t page, int &keys) return m_Text.c_str(); } -#define GETMENU(p) if (p >= (int)g_NewMenus.size() || p < 0 || !g_NewMenus[p] || g_NewMenus[p]->isDestroying) { \ +#define GETMENU(p) Menu *pMenu = get_menu_by_id(p); \ + if (pMenu == NULL || pMenu->isDestroying) { \ LogError(amx, AMX_ERR_NATIVE, "Invalid menu id %d(%d)", p, g_NewMenus.size()); \ - return 0; } \ - Menu *pMenu = g_NewMenus[p]; + return 0; } //Makes a new menu handle (-1 for failure) //native csdm_makemenu(title[]); @@ -1040,10 +1048,10 @@ static cell AMX_NATIVE_CALL menu_setprop(AMX *amx, cell *params) return 1; } -#define GETMENU_R(p) if (p >= (int)g_NewMenus.size() || p < 0 || !g_NewMenus[p]) { \ +#define GETMENU_R(p) Menu *pMenu = get_menu_by_id(p); \ + if (pMenu == NULL) { \ LogError(amx, AMX_ERR_NATIVE, "Invalid menu id %d(%d)", p, g_NewMenus.size()); \ - return 0; } \ - Menu *pMenu = g_NewMenus[p]; + return 0; } static cell AMX_NATIVE_CALL menu_cancel(AMX *amx, cell *params) { @@ -1062,14 +1070,12 @@ static cell AMX_NATIVE_CALL menu_cancel(AMX *amx, cell *params) return 0; } - int menu = player->newmenu; - if (menu < 0 || menu >= (int)g_NewMenus.size() || !g_NewMenus[menu]) - return 0; + if (Menu *pMenu = get_menu_by_id(player->newmenu)) { + pMenu->Close(player->index); + return 1; + } - Menu *pMenu = g_NewMenus[menu]; - pMenu->Close(player->index); - - return 1; + return 0; } static cell AMX_NATIVE_CALL menu_destroy(AMX *amx, cell *params) diff --git a/amxmodx/newmenus.h b/amxmodx/newmenus.h index e90b807e..c92e0069 100755 --- a/amxmodx/newmenus.h +++ b/amxmodx/newmenus.h @@ -151,6 +151,7 @@ public: }; void ClearMenus(); +Menu *get_menu_by_id(int id); extern CVector g_NewMenus; extern AMX_NATIVE_INFO g_NewMenuNatives[]; From dc3e68c507b1e443d11cf8c941f58bea53e29df1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Valentin=20Gr=C3=BCnbacher?= Date: Tue, 27 May 2014 10:38:25 +0200 Subject: [PATCH 10/10] Newmenus: Fix typo in error message --- amxmodx/newmenus.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/amxmodx/newmenus.cpp b/amxmodx/newmenus.cpp index 691c3e6f..028ebc76 100755 --- a/amxmodx/newmenus.cpp +++ b/amxmodx/newmenus.cpp @@ -1066,7 +1066,7 @@ static cell AMX_NATIVE_CALL menu_cancel(AMX *amx, cell *params) CPlayer *player = GET_PLAYER_POINTER_I(index); if (!player->ingame) { - LogError(amx, AMX_ERR_NATIVE, "Played %d is not in game", index); + LogError(amx, AMX_ERR_NATIVE, "Player %d is not in game", index); return 0; }