/* Relay -- a tool to record and play Quake2 demos Copyright (C) 2000 Conor Davis This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. Conor Davis cedavis@planetquake.com */ #include "sv_local.h" // generic menu functions void UpdateLayout(client_t *client) { if (client->curmenu) Menu_Display(client->curmenu, client->layout, sizeof(client->layout)); else if (client->player != -1 && client->flags & RC_LAYOUT) strcpy(client->layout, dm2in.players[client->player].layout); else client->layout[0] = 0; client->layout_modified = true; } void OpenMenu(client_t *client, void (*Show)(menu_t *)) { Menu_Open(client, &client->curmenu, Show, ""); UpdateLayout(client); } void CloseMenu(client_t *client) { Menu_Close(&client->curmenu); UpdateLayout(client); } void CloseAllMenus(client_t *client) { Menu_CloseAll(&client->curmenu); UpdateLayout(client); } void Select_OpenMenu(menu_t *menu, menuitem_t *item, int key) { client_t *client; client = menu->client; Menu_Open(client, &client->curmenu, (void (*)(menu_t *))item->param[0], ""); UpdateLayout(client); } // // Demo Menu // void DemoMenu_Show(menu_t *menu) { char buf[256]; int i, count; Menu_Start(menu); if (!menu->title) menu->title = Z_Strdup("Demo Info"); if (!menu->id) menu->id = MENU_DEMO; count = 0; for (i = 0; i < dm2in.maxclients; i++) { if (ISBITSET(server.current_connected, i)) count++; } switch(dm2in.svd.isdemo) { case RECORD_NETWORK: strcpy(buf, "Type: Network"); break; case RECORD_CLIENT: strcpy(buf, "Type: Client"); break; case RECORD_SERVER: strcpy(buf, "Type: Server"); break; case RECORD_RELAY: strcpy(buf, "Type: Relay"); break; default: strcpy(buf, "Type: Unknown"); } Menu_AddItem(buf, ""); Menu_AddItem(va("Game: %s", (dm2in.svd.game[0] ? dm2in.svd.game : "baseq2")), ""); COM_FileBase(dm2in.configstrings[CS_MODELS+1], buf); Menu_AddItem(va("Map: %s", buf), ""); Menu_AddItem(va("Desc: %.32s", dm2in.svd.mapname), ""); Menu_AddItem(va("Maxclients: %d", dm2in.maxclients), ""); Menu_AddItem(va("Active players: %d", count), ""); Menu_Finish(menu); } // // Players Menu // void PlayersMenu_Select(menu_t *menu, menuitem_t *item, int key) { client_t *client; client = menu->client; if (CL_ChangePlayer(client, item->param[0])) CL_cprintf(&client->unreliable, PRINT_HIGH, "Unable to switch to player %s\n", item->text); } void PlayersMenu_Show(menu_t *menu) { int i, num, index; // if menu is newly opened (cur == -1), put cursor on currently // tracked player, otherwise try to keep the cursor on the same // player after the menu changes if (menu->cur == -1 || !menu->items) num = ((client_t *)menu->client)->player; else num = menu->items[menu->cur].param[0]; Menu_Start(menu); if (!menu->title) menu->title = Z_Strdup("Players"); if (!menu->id) menu->id = MENU_PLAYERS; Menu_AddItem("No player", "S1", PlayersMenu_Select, -1); if (dm2in.svd.isdemo == RECORD_RELAY) { for (i = 0; i < dm2in.maxclients; i++) { if (ISBITSET(server.current_connected, i)) { index = Menu_AddItem(PlayerName(dm2in.configstrings[CS_PLAYERSKINS+i]), "S1", PlayersMenu_Select, i); if (i == num) menu->cur = index; } } } else Menu_AddItem(PlayerName(dm2in.configstrings[CS_PLAYERSKINS]), "S1", PlayersMenu_Select, 0); Menu_Finish(menu); } // // Settings Menu // void SettingsMenu_Select(menu_t *menu, menuitem_t *item, int key) { client_t *client; client = menu->client; client->flags ^= item->param[0]; if (item->param[0] & RC_STATUSBAR) { if (client->flags & RC_STATUSBAR) { if (client->player != -1) { WriteByte(&client->nextreliable, SVC_CONFIGSTRING); DM2_WriteConfigstring(&client->nextreliable, CS_STATUSBAR, dm2in.configstrings[CS_STATUSBAR]); } } else { WriteByte(&client->nextreliable, SVC_CONFIGSTRING); DM2_WriteConfigstring(&client->nextreliable, CS_STATUSBAR, ""); } } Menu_Update(&client->curmenu, client->layout, sizeof(client->layout), MENU_SETTINGS); UpdateLayout(client); } void SettingsMenu_Show(menu_t *menu) { int flags; flags = ((client_t *)menu->client)->flags; Menu_Start(menu); if (!menu->title) menu->title = Z_Strdup("Settings"); if (!menu->id) menu->id = MENU_SETTINGS; Menu_AddItem(va("Lock position: %s", (flags & RC_LOCKPOS ? "On" : "Off")), "S1", SettingsMenu_Select, RC_LOCKPOS); Menu_AddItem(va("Lock view: %s", (flags & RC_LOCKVIEW ? "On" : "Off")), "S1", SettingsMenu_Select, RC_LOCKVIEW); Menu_AddItem(va("Chase view: %s", (flags & RC_CHASEVIEW ? "On" : "Off")), "S1", SettingsMenu_Select, RC_CHASEVIEW); Menu_AddItem(va("Statusbar: %s", (flags & RC_STATUSBAR ? "On" : "Off")), "S1", SettingsMenu_Select, RC_STATUSBAR); Menu_AddItem(va("Layout: %s", (flags & RC_LAYOUT ? "On" : "Off")), "S1", SettingsMenu_Select, RC_LAYOUT); Menu_AddItem(va("Tinting: %s", (flags & RC_TINT ? "On" : "Off")), "S1", SettingsMenu_Select, RC_TINT); Menu_Finish(menu); } // // Main Menu // void MainMenu_Show(menu_t *menu) { Menu_Start(menu); if (!menu->title) menu->title = Z_Strdup("Main Menu"); if (!menu->id) menu->id = MENU_MAIN; Menu_AddItem("Demo Info", "S1", Select_OpenMenu, DemoMenu_Show); Menu_AddItem("Players", "S1", Select_OpenMenu, PlayersMenu_Show); Menu_AddItem("Settings", "S1", Select_OpenMenu, SettingsMenu_Show); Menu_Finish(menu); }