mirror of
https://github.com/ZDoom/raze-gles.git
synced 2024-12-29 13:00:43 +00:00
- it compiles again (with lots of code commented out.)
This commit is contained in:
parent
46a1fe3826
commit
82612a1330
62 changed files with 3946 additions and 6469 deletions
|
@ -980,17 +980,19 @@ set (PCH_SOURCES
|
||||||
|
|
||||||
core/music/s_advsound.cpp
|
core/music/s_advsound.cpp
|
||||||
|
|
||||||
core/menu/imagescroller.cpp
|
#core/menu/imagescroller.cpp
|
||||||
core/menu/joystickmenu.cpp
|
core/menu/joystickmenu.cpp
|
||||||
core/menu/listmenu.cpp
|
#core/menu/listmenu.cpp
|
||||||
core/menu/savegamemanager.cpp
|
#core/menu/savegamemanager.cpp
|
||||||
core/menu/loadsavemenu.cpp
|
core/menu/loadsavemenu.cpp
|
||||||
core/menu/menu.cpp
|
core/menu/menu.cpp
|
||||||
core/menu/menudef.cpp
|
core/menu/menudef.cpp
|
||||||
core/menu/menuinput.cpp
|
#core/menu/menuinput.cpp
|
||||||
core/menu/messagebox.cpp
|
core/menu/messagebox.cpp
|
||||||
core/menu/optionmenu.cpp
|
core/menu/optionmenu.cpp
|
||||||
|
core/menu/playermenu.cpp
|
||||||
core/menu/resolutionmenu.cpp
|
core/menu/resolutionmenu.cpp
|
||||||
|
core/menu/razemenu.cpp
|
||||||
)
|
)
|
||||||
|
|
||||||
if( ${HAVE_VM_JIT} )
|
if( ${HAVE_VM_JIT} )
|
||||||
|
|
|
@ -39,7 +39,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "view.h"
|
#include "view.h"
|
||||||
#include "nnexts.h"
|
#include "nnexts.h"
|
||||||
#include "zstring.h"
|
#include "zstring.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "gstrings.h"
|
#include "gstrings.h"
|
||||||
#include "v_2ddrawer.h"
|
#include "v_2ddrawer.h"
|
||||||
#include "v_video.h"
|
#include "v_video.h"
|
||||||
|
|
|
@ -51,7 +51,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "gamecontrol.h"
|
#include "gamecontrol.h"
|
||||||
#include "m_argv.h"
|
#include "m_argv.h"
|
||||||
#include "statistics.h"
|
#include "statistics.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "raze_sound.h"
|
#include "raze_sound.h"
|
||||||
#include "nnexts.h"
|
#include "nnexts.h"
|
||||||
#include "secrets.h"
|
#include "secrets.h"
|
||||||
|
@ -61,6 +61,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "choke.h"
|
#include "choke.h"
|
||||||
#include "d_net.h"
|
#include "d_net.h"
|
||||||
#include "v_video.h"
|
#include "v_video.h"
|
||||||
|
#include "v_draw.h"
|
||||||
#include "statusbar.h"
|
#include "statusbar.h"
|
||||||
|
|
||||||
BEGIN_BLD_NS
|
BEGIN_BLD_NS
|
||||||
|
|
|
@ -26,7 +26,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "mmulti.h"
|
#include "mmulti.h"
|
||||||
#include "view.h"
|
#include "view.h"
|
||||||
#include "gamestate.h"
|
#include "gamestate.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
|
|
||||||
BEGIN_BLD_NS
|
BEGIN_BLD_NS
|
||||||
|
|
||||||
|
|
|
@ -38,7 +38,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "screenjob.h"
|
#include "screenjob.h"
|
||||||
#include "gamestate.h"
|
#include "gamestate.h"
|
||||||
#include "seq.h"
|
#include "seq.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
|
|
||||||
BEGIN_BLD_NS
|
BEGIN_BLD_NS
|
||||||
|
|
||||||
|
|
|
@ -27,7 +27,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "compat.h"
|
#include "compat.h"
|
||||||
#include "mmulti.h"
|
#include "mmulti.h"
|
||||||
#include "c_bind.h"
|
#include "c_bind.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "gamestate.h"
|
#include "gamestate.h"
|
||||||
|
|
||||||
#include "blood.h"
|
#include "blood.h"
|
||||||
|
@ -36,6 +36,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "view.h"
|
#include "view.h"
|
||||||
#include "sound.h"
|
#include "sound.h"
|
||||||
#include "v_video.h"
|
#include "v_video.h"
|
||||||
|
#include "v_draw.h"
|
||||||
|
|
||||||
bool ShowOptionMenu();
|
bool ShowOptionMenu();
|
||||||
|
|
||||||
|
@ -124,6 +125,7 @@ static std::unique_ptr<CGameMenuItemQAV> itemBloodQAV; // This must be global to
|
||||||
|
|
||||||
void UpdateNetworkMenus(void)
|
void UpdateNetworkMenus(void)
|
||||||
{
|
{
|
||||||
|
#if 0
|
||||||
// For now disable the network menu item as it is not yet functional.
|
// For now disable the network menu item as it is not yet functional.
|
||||||
for (auto name : { NAME_Mainmenu, NAME_IngameMenu })
|
for (auto name : { NAME_Mainmenu, NAME_IngameMenu })
|
||||||
{
|
{
|
||||||
|
@ -140,8 +142,11 @@ void UpdateNetworkMenus(void)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#if 0
|
||||||
//----------------------------------------------------------------------------
|
//----------------------------------------------------------------------------
|
||||||
//
|
//
|
||||||
// Implements the native looking menu used for the main menu
|
// Implements the native looking menu used for the main menu
|
||||||
|
@ -196,6 +201,7 @@ class DBloodImageScrollerMenu : public DImageScrollerMenu
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
//----------------------------------------------------------------------------
|
//----------------------------------------------------------------------------
|
||||||
//
|
//
|
||||||
|
@ -205,6 +211,7 @@ class DBloodImageScrollerMenu : public DImageScrollerMenu
|
||||||
|
|
||||||
void GameInterface::DrawNativeMenuText(int fontnum, int state, double xpos, double ypos, float fontscale, const char* text, int flags)
|
void GameInterface::DrawNativeMenuText(int fontnum, int state, double xpos, double ypos, float fontscale, const char* text, int flags)
|
||||||
{
|
{
|
||||||
|
#if 0
|
||||||
if (!text) return;
|
if (!text) return;
|
||||||
int shade = (state != NIT_InactiveState) ? 32 : 48;
|
int shade = (state != NIT_InactiveState) ? 32 : 48;
|
||||||
int pal = (state != NIT_InactiveState) ? 5 : 5;
|
int pal = (state != NIT_InactiveState) ? 5 : 5;
|
||||||
|
@ -221,6 +228,7 @@ void GameInterface::DrawNativeMenuText(int fontnum, int state, double xpos, doub
|
||||||
|
|
||||||
DrawText(twod, gamefont, CR_UNDEFINED, xpos, ypos, text, DTA_TranslationIndex, TRANSLATION(Translation_Remap, pal), DTA_Color, shadeToLight(shade),
|
DrawText(twod, gamefont, CR_UNDEFINED, xpos, ypos, text, DTA_TranslationIndex, TRANSLATION(Translation_Remap, pal), DTA_Color, shadeToLight(shade),
|
||||||
DTA_FullscreenScale, FSMode_Fit320x200, TAG_DONE);
|
DTA_FullscreenScale, FSMode_Fit320x200, TAG_DONE);
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -245,7 +253,7 @@ bool GameInterface::StartGame(FNewGameStartup& gs)
|
||||||
{
|
{
|
||||||
if (g_gameType & GAMEFLAG_SHAREWARE)
|
if (g_gameType & GAMEFLAG_SHAREWARE)
|
||||||
{
|
{
|
||||||
M_StartMessage(GStrings("BUYBLOOD"), 1, -1); // unreachable because we do not support Blood SW versions yet.
|
M_StartMessage(GStrings("BUYBLOOD"), 1, NAME_None); // unreachable because we do not support Blood SW versions yet.
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -304,20 +312,3 @@ void GameInterface::QuitToTitle()
|
||||||
|
|
||||||
END_BLD_NS
|
END_BLD_NS
|
||||||
|
|
||||||
//----------------------------------------------------------------------------
|
|
||||||
//
|
|
||||||
// Class registration
|
|
||||||
//
|
|
||||||
//----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
|
|
||||||
static TMenuClassDescriptor<Blood::BloodListMenu> _lm("Blood.ListMenu");
|
|
||||||
static TMenuClassDescriptor<Blood::BloodListMenu> _mm("Blood.MainMenu");
|
|
||||||
static TMenuClassDescriptor<Blood::DBloodImageScrollerMenu> _im("Blood.ImageScrollerMenu");
|
|
||||||
|
|
||||||
void RegisterBloodMenus()
|
|
||||||
{
|
|
||||||
menuClasses.Push(&_lm);
|
|
||||||
menuClasses.Push(&_mm);
|
|
||||||
menuClasses.Push(&_im);
|
|
||||||
}
|
|
||||||
|
|
|
@ -39,7 +39,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "view.h"
|
#include "view.h"
|
||||||
#include "nnexts.h"
|
#include "nnexts.h"
|
||||||
#include "zstring.h"
|
#include "zstring.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "gstrings.h"
|
#include "gstrings.h"
|
||||||
#include "v_2ddrawer.h"
|
#include "v_2ddrawer.h"
|
||||||
#include "v_video.h"
|
#include "v_video.h"
|
||||||
|
|
|
@ -38,7 +38,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "sound.h"
|
#include "sound.h"
|
||||||
#include "view.h"
|
#include "view.h"
|
||||||
#include "eventq.h"
|
#include "eventq.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
|
|
||||||
BEGIN_BLD_NS
|
BEGIN_BLD_NS
|
||||||
|
|
||||||
|
|
|
@ -39,7 +39,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "view.h"
|
#include "view.h"
|
||||||
#include "nnexts.h"
|
#include "nnexts.h"
|
||||||
#include "zstring.h"
|
#include "zstring.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "gstrings.h"
|
#include "gstrings.h"
|
||||||
#include "v_2ddrawer.h"
|
#include "v_2ddrawer.h"
|
||||||
#include "v_video.h"
|
#include "v_video.h"
|
||||||
|
|
|
@ -39,7 +39,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "view.h"
|
#include "view.h"
|
||||||
#include "nnexts.h"
|
#include "nnexts.h"
|
||||||
#include "zstring.h"
|
#include "zstring.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "gstrings.h"
|
#include "gstrings.h"
|
||||||
#include "v_2ddrawer.h"
|
#include "v_2ddrawer.h"
|
||||||
#include "v_video.h"
|
#include "v_video.h"
|
||||||
|
@ -47,6 +47,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "glbackend/glbackend.h"
|
#include "glbackend/glbackend.h"
|
||||||
#include "statusbar.h"
|
#include "statusbar.h"
|
||||||
#include "automap.h"
|
#include "automap.h"
|
||||||
|
#include "v_draw.h"
|
||||||
|
|
||||||
CVARD(Bool, hud_powerupduration, true, CVAR_ARCHIVE/*|CVAR_FRONTEND_BLOOD*/, "enable/disable displaying the remaining seconds for power-ups")
|
CVARD(Bool, hud_powerupduration, true, CVAR_ARCHIVE/*|CVAR_FRONTEND_BLOOD*/, "enable/disable displaying the remaining seconds for power-ups")
|
||||||
|
|
||||||
|
|
|
@ -39,13 +39,14 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "view.h"
|
#include "view.h"
|
||||||
#include "nnexts.h"
|
#include "nnexts.h"
|
||||||
#include "zstring.h"
|
#include "zstring.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "gstrings.h"
|
#include "gstrings.h"
|
||||||
#include "v_2ddrawer.h"
|
#include "v_2ddrawer.h"
|
||||||
#include "v_video.h"
|
#include "v_video.h"
|
||||||
#include "v_font.h"
|
#include "v_font.h"
|
||||||
#include "statusbar.h"
|
#include "statusbar.h"
|
||||||
#include "automap.h"
|
#include "automap.h"
|
||||||
|
#include "v_draw.h"
|
||||||
#include "glbackend/glbackend.h"
|
#include "glbackend/glbackend.h"
|
||||||
|
|
||||||
BEGIN_BLD_NS
|
BEGIN_BLD_NS
|
||||||
|
|
|
@ -23,7 +23,7 @@
|
||||||
#include "v_2ddrawer.h"
|
#include "v_2ddrawer.h"
|
||||||
#include "v_draw.h"
|
#include "v_draw.h"
|
||||||
#include "stats.h"
|
#include "stats.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "version.h"
|
#include "version.h"
|
||||||
#include "earcut.hpp"
|
#include "earcut.hpp"
|
||||||
#include "gamestate.h"
|
#include "gamestate.h"
|
||||||
|
|
|
@ -35,7 +35,7 @@
|
||||||
#include "c_dispatch.h"
|
#include "c_dispatch.h"
|
||||||
|
|
||||||
#include "v_text.h"
|
#include "v_text.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include <zmusic.h>
|
#include <zmusic.h>
|
||||||
#include "s_music.h"
|
#include "s_music.h"
|
||||||
#include "c_cvars.h"
|
#include "c_cvars.h"
|
||||||
|
|
|
@ -2078,7 +2078,7 @@ FSoundChan *OpenALSoundRenderer::FindLowestChannel()
|
||||||
|
|
||||||
#endif // NO_OPENAL
|
#endif // NO_OPENAL
|
||||||
|
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
|
|
||||||
void I_BuildALDeviceList(FOptionValues* opt)
|
void I_BuildALDeviceList(FOptionValues* opt)
|
||||||
{
|
{
|
||||||
|
|
|
@ -37,7 +37,7 @@
|
||||||
#include "d_eventbase.h"
|
#include "d_eventbase.h"
|
||||||
#include "c_console.h"
|
#include "c_console.h"
|
||||||
#include "d_gui.h"
|
#include "d_gui.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "utf8.h"
|
#include "utf8.h"
|
||||||
#include "m_joy.h"
|
#include "m_joy.h"
|
||||||
#include "vm.h"
|
#include "vm.h"
|
||||||
|
|
|
@ -59,7 +59,7 @@
|
||||||
#include "dobject.h"
|
#include "dobject.h"
|
||||||
#include "templates.h"
|
#include "templates.h"
|
||||||
#include "c_dispatch.h"
|
#include "c_dispatch.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "stats.h"
|
#include "stats.h"
|
||||||
#include "printf.h"
|
#include "printf.h"
|
||||||
|
|
||||||
|
|
|
@ -42,7 +42,7 @@
|
||||||
#include "d_eventbase.h"
|
#include "d_eventbase.h"
|
||||||
#include "d_gui.h"
|
#include "d_gui.h"
|
||||||
#include "hardware.h"
|
#include "hardware.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "menustate.h"
|
#include "menustate.h"
|
||||||
#include "keydef.h"
|
#include "keydef.h"
|
||||||
#include "i_interface.h"
|
#include "i_interface.h"
|
||||||
|
|
|
@ -40,7 +40,7 @@
|
||||||
#include "c_dispatch.h"
|
#include "c_dispatch.h"
|
||||||
#include "v_video.h"
|
#include "v_video.h"
|
||||||
#include "hw_cvars.h"
|
#include "hw_cvars.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "printf.h"
|
#include "printf.h"
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -53,7 +53,7 @@
|
||||||
#include "cmdlib.h"
|
#include "cmdlib.h"
|
||||||
#include "hardware.h"
|
#include "hardware.h"
|
||||||
#include "m_png.h"
|
#include "m_png.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "vm.h"
|
#include "vm.h"
|
||||||
#include "r_videoscale.h"
|
#include "r_videoscale.h"
|
||||||
#include "i_time.h"
|
#include "i_time.h"
|
||||||
|
|
|
@ -36,7 +36,7 @@
|
||||||
|
|
||||||
#include "gstrings.h"
|
#include "gstrings.h"
|
||||||
#include "v_font.h"
|
#include "v_font.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "types.h"
|
#include "types.h"
|
||||||
#include "dictionary.h"
|
#include "dictionary.h"
|
||||||
#include "vm.h"
|
#include "vm.h"
|
||||||
|
|
|
@ -42,7 +42,7 @@
|
||||||
#include "c_bind.h"
|
#include "c_bind.h"
|
||||||
#include "c_dispatch.h"
|
#include "c_dispatch.h"
|
||||||
#include "templates.h"
|
#include "templates.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "vm.h"
|
#include "vm.h"
|
||||||
#include "gstrings.h"
|
#include "gstrings.h"
|
||||||
#include "printf.h"
|
#include "printf.h"
|
||||||
|
|
|
@ -62,9 +62,10 @@
|
||||||
#include "v_video.h"
|
#include "v_video.h"
|
||||||
#include "v_draw.h"
|
#include "v_draw.h"
|
||||||
#include "g_input.h"
|
#include "g_input.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "raze_music.h"
|
#include "raze_music.h"
|
||||||
#include "gstrings.h"
|
#include "gstrings.h"
|
||||||
|
#include "menustate.h"
|
||||||
|
|
||||||
#define LEFTMARGIN 8
|
#define LEFTMARGIN 8
|
||||||
#define RIGHTMARGIN 8
|
#define RIGHTMARGIN 8
|
||||||
|
|
|
@ -38,7 +38,7 @@
|
||||||
#include "c_console.h"
|
#include "c_console.h"
|
||||||
#include "d_gui.h"
|
#include "d_gui.h"
|
||||||
#include "inputstate.h"
|
#include "inputstate.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "gamestate.h"
|
#include "gamestate.h"
|
||||||
#include "gamecontrol.h"
|
#include "gamecontrol.h"
|
||||||
#include "uiinput.h"
|
#include "uiinput.h"
|
||||||
|
|
|
@ -36,9 +36,10 @@
|
||||||
#include "vm.h"
|
#include "vm.h"
|
||||||
#include "c_buttons.h"
|
#include "c_buttons.h"
|
||||||
#include "v_draw.h"
|
#include "v_draw.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "gamestruct.h"
|
#include "gamestruct.h"
|
||||||
#include "gamecvars.h"
|
#include "gamecvars.h"
|
||||||
|
#include "menustate.h"
|
||||||
|
|
||||||
enum
|
enum
|
||||||
{
|
{
|
||||||
|
|
|
@ -46,7 +46,7 @@
|
||||||
#include <inttypes.h>
|
#include <inttypes.h>
|
||||||
|
|
||||||
#include "version.h"
|
#include "version.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "i_video.h"
|
#include "i_video.h"
|
||||||
#include "c_console.h"
|
#include "c_console.h"
|
||||||
#include "d_net.h"
|
#include "d_net.h"
|
||||||
|
|
|
@ -41,7 +41,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "i_specialpaths.h"
|
#include "i_specialpaths.h"
|
||||||
#include "raze_music.h"
|
#include "raze_music.h"
|
||||||
#include "statistics.h"
|
#include "statistics.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "gstrings.h"
|
#include "gstrings.h"
|
||||||
#include "quotemgr.h"
|
#include "quotemgr.h"
|
||||||
#include "mapinfo.h"
|
#include "mapinfo.h"
|
||||||
|
@ -71,6 +71,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "uiinput.h"
|
#include "uiinput.h"
|
||||||
#include "d_net.h"
|
#include "d_net.h"
|
||||||
#include "automap.h"
|
#include "automap.h"
|
||||||
|
#include "v_draw.h"
|
||||||
|
|
||||||
CVAR(Bool, autoloadlights, true, CVAR_ARCHIVE|CVAR_GLOBALCONFIG)
|
CVAR(Bool, autoloadlights, true, CVAR_ARCHIVE|CVAR_GLOBALCONFIG)
|
||||||
CVAR(Bool, autoloadbrightmaps, true, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
CVAR(Bool, autoloadbrightmaps, true, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
||||||
|
@ -533,7 +534,7 @@ int GameMain()
|
||||||
r = -1;
|
r = -1;
|
||||||
}
|
}
|
||||||
DeleteScreenJob();
|
DeleteScreenJob();
|
||||||
M_ClearMenus(true);
|
M_ClearMenus();
|
||||||
if (gi)
|
if (gi)
|
||||||
{
|
{
|
||||||
gi->FreeGameData(); // Must be done before taking down any subsystems.
|
gi->FreeGameData(); // Must be done before taking down any subsystems.
|
||||||
|
@ -551,7 +552,6 @@ int GameMain()
|
||||||
TileFiles.CloseAll(); // delete the texture data before shutting down graphics.
|
TileFiles.CloseAll(); // delete the texture data before shutting down graphics.
|
||||||
GLInterface.Deinit();
|
GLInterface.Deinit();
|
||||||
I_ShutdownGraphics();
|
I_ShutdownGraphics();
|
||||||
M_DeinitMenus();
|
|
||||||
engineUnInit();
|
engineUnInit();
|
||||||
if (gi)
|
if (gi)
|
||||||
{
|
{
|
||||||
|
@ -1791,3 +1791,63 @@ void playerProcessHelpers(fixed_t* q16ang, double* angAdjust, fixed_t* angTarget
|
||||||
*q16horiz += FloatToFixed(scaleAdjust * *horizAdjust);
|
*q16horiz += FloatToFixed(scaleAdjust * *horizAdjust);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void GameInterface::DrawCenteredTextScreen(const DVector2& origin, const char* text, int position, bool bg)
|
||||||
|
{
|
||||||
|
double scale = SmallFontScale();
|
||||||
|
int formatwidth = int(320 / scale);
|
||||||
|
auto lines = V_BreakLines(SmallFont, formatwidth, text, true);
|
||||||
|
auto fheight = bg ? 10 : SmallFont->GetHeight() * scale; // Fixme: Get spacing for text pages from elsewhere.
|
||||||
|
if (!bg)
|
||||||
|
{
|
||||||
|
auto totaltextheight = lines.Size() * fheight;
|
||||||
|
position -= totaltextheight / 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
double y = origin.Y + position;
|
||||||
|
for (auto& line : lines)
|
||||||
|
{
|
||||||
|
double x = origin.X + 160 - line.Width * scale * 0.5;
|
||||||
|
DrawText(twod, SmallFont, CR_UNTRANSLATED, x, y, line.Text, DTA_FullscreenScale, FSMode_Fit320x200, DTA_ScaleX, scale, DTA_ScaleY, scale, TAG_DONE);
|
||||||
|
y += fheight;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
bool M_Active()
|
||||||
|
{
|
||||||
|
return CurrentMenu != nullptr || ConsoleState == c_down || ConsoleState == c_falling;
|
||||||
|
}
|
||||||
|
|
||||||
|
struct gamefilter
|
||||||
|
{
|
||||||
|
const char* gamename;
|
||||||
|
int gameflag;
|
||||||
|
};
|
||||||
|
|
||||||
|
static const gamefilter games[] = {
|
||||||
|
{ "Duke", GAMEFLAG_DUKE},
|
||||||
|
{ "Nam", GAMEFLAG_NAM | GAMEFLAG_NAPALM},
|
||||||
|
{ "NamOnly", GAMEFLAG_NAM}, // for cases where the difference matters.
|
||||||
|
{ "Napalm", GAMEFLAG_NAPALM},
|
||||||
|
{ "WW2GI", GAMEFLAG_WW2GI},
|
||||||
|
{ "Redneck", GAMEFLAG_RR},
|
||||||
|
{ "RedneckRides", GAMEFLAG_RRRA},
|
||||||
|
{ "Deer", GAMEFLAG_DEER},
|
||||||
|
{ "Blood", GAMEFLAG_BLOOD},
|
||||||
|
{ "ShadowWarrior", GAMEFLAG_SW},
|
||||||
|
{ "Exhumed", GAMEFLAG_POWERSLAVE | GAMEFLAG_EXHUMED},
|
||||||
|
{ "Worldtour", GAMEFLAG_WORLDTOUR},
|
||||||
|
};
|
||||||
|
|
||||||
|
// for other parts that need to filter by game name.
|
||||||
|
bool validFilter(const char* str)
|
||||||
|
{
|
||||||
|
for (auto& gf : games)
|
||||||
|
{
|
||||||
|
if (g_gameType & gf.gameflag)
|
||||||
|
{
|
||||||
|
if (!stricmp(str, gf.gamename)) return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
|
@ -67,7 +67,7 @@
|
||||||
#include "d_net.h"
|
#include "d_net.h"
|
||||||
#include "gamecontrol.h"
|
#include "gamecontrol.h"
|
||||||
#include "c_console.h"
|
#include "c_console.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "i_system.h"
|
#include "i_system.h"
|
||||||
#include "raze_sound.h"
|
#include "raze_sound.h"
|
||||||
#include "raze_music.h"
|
#include "raze_music.h"
|
||||||
|
@ -76,7 +76,6 @@
|
||||||
#include "screenjob.h"
|
#include "screenjob.h"
|
||||||
#include "mmulti.h"
|
#include "mmulti.h"
|
||||||
#include "c_console.h"
|
#include "c_console.h"
|
||||||
#include "menu.h"
|
|
||||||
#include "uiinput.h"
|
#include "uiinput.h"
|
||||||
#include "v_video.h"
|
#include "v_video.h"
|
||||||
#include "glbackend/glbackend.h"
|
#include "glbackend/glbackend.h"
|
||||||
|
@ -86,6 +85,8 @@
|
||||||
#include "mapinfo.h"
|
#include "mapinfo.h"
|
||||||
#include "automap.h"
|
#include "automap.h"
|
||||||
#include "statusbar.h"
|
#include "statusbar.h"
|
||||||
|
#include "gamestruct.h"
|
||||||
|
#include "savegamehelp.h"
|
||||||
|
|
||||||
CVAR(Bool, vid_activeinbackground, false, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
CVAR(Bool, vid_activeinbackground, false, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
||||||
CVAR(Bool, r_ticstability, true, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
CVAR(Bool, r_ticstability, true, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
||||||
|
@ -103,7 +104,7 @@ int entertic;
|
||||||
int oldentertics;
|
int oldentertics;
|
||||||
int gametic;
|
int gametic;
|
||||||
|
|
||||||
extern FString BackupSaveGame;
|
FString BackupSaveGame;
|
||||||
|
|
||||||
void DoLoadGame(const char* name);
|
void DoLoadGame(const char* name);
|
||||||
|
|
||||||
|
@ -146,7 +147,9 @@ static void GameTicker()
|
||||||
C_ClearMessages();
|
C_ClearMessages();
|
||||||
if (BackupSaveGame.IsNotEmpty() && cl_resumesavegame)
|
if (BackupSaveGame.IsNotEmpty() && cl_resumesavegame)
|
||||||
{
|
{
|
||||||
|
#if 0
|
||||||
DoLoadGame(BackupSaveGame);
|
DoLoadGame(BackupSaveGame);
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
|
|
@ -38,6 +38,12 @@
|
||||||
#include "filesystem.h"
|
#include "filesystem.h"
|
||||||
#include "printf.h"
|
#include "printf.h"
|
||||||
|
|
||||||
|
FString gSkillNames[MAXSKILLS];
|
||||||
|
FString gVolumeNames[MAXVOLUMES];
|
||||||
|
FString gVolumeSubtitles[MAXVOLUMES];
|
||||||
|
int32_t gVolumeFlags[MAXVOLUMES];
|
||||||
|
int gDefaultVolume = 0, gDefaultSkill = 1;
|
||||||
|
|
||||||
MapRecord mapList[512]; // Due to how this gets used it needs to be static. EDuke defines 7 episode plus one spare episode with 64 potential levels each and relies on the static array which is freely accessible by scripts.
|
MapRecord mapList[512]; // Due to how this gets used it needs to be static. EDuke defines 7 episode plus one spare episode with 64 potential levels each and relies on the static array which is freely accessible by scripts.
|
||||||
MapRecord *currentLevel; // level that is currently played. (The real level, not what script hacks modfifying the current level index can pretend.)
|
MapRecord *currentLevel; // level that is currently played. (The real level, not what script hacks modfifying the current level index can pretend.)
|
||||||
MapRecord* lastLevel; // Same here, for the last level.
|
MapRecord* lastLevel; // Same here, for the last level.
|
||||||
|
|
|
@ -7,6 +7,22 @@
|
||||||
#undef GetMessage // Windows strikes...
|
#undef GetMessage // Windows strikes...
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
enum EMax
|
||||||
|
{
|
||||||
|
MAXSKILLS = 7,
|
||||||
|
MAXVOLUMES = 7,
|
||||||
|
MAXMENUGAMEPLAYENTRIES = 7,
|
||||||
|
};
|
||||||
|
|
||||||
|
// These get filled in by the map definition parsers of the front ends.
|
||||||
|
extern FString gSkillNames[MAXSKILLS];
|
||||||
|
extern FString gVolumeNames[MAXVOLUMES];
|
||||||
|
extern FString gVolumeSubtitles[MAXVOLUMES];
|
||||||
|
extern int32_t gVolumeFlags[MAXVOLUMES];
|
||||||
|
extern int gDefaultVolume, gDefaultSkill;
|
||||||
|
|
||||||
|
|
||||||
// Localization capable replacement of the game specific solutions.
|
// Localization capable replacement of the game specific solutions.
|
||||||
|
|
||||||
inline void MakeStringLocalizable(FString "e)
|
inline void MakeStringLocalizable(FString "e)
|
||||||
|
|
|
@ -1,182 +0,0 @@
|
||||||
/*
|
|
||||||
** imagescroller.cpp
|
|
||||||
** Scrolls through multiple fullscreen image pages,
|
|
||||||
**
|
|
||||||
**---------------------------------------------------------------------------
|
|
||||||
** Copyright 2019 Christoph Oelckers
|
|
||||||
** All rights reserved.
|
|
||||||
**
|
|
||||||
** Redistribution and use in source and binary forms, with or without
|
|
||||||
** modification, are permitted provided that the following conditions
|
|
||||||
** are met:
|
|
||||||
**
|
|
||||||
** 1. Redistributions of source code must retain the above copyright
|
|
||||||
** notice, this list of conditions and the following disclaimer.
|
|
||||||
** 2. Redistributions in binary form must reproduce the above copyright
|
|
||||||
** notice, this list of conditions and the following disclaimer in the
|
|
||||||
** documentation and/or other materials provided with the distribution.
|
|
||||||
** 3. The name of the author may not be used to endorse or promote products
|
|
||||||
** derived from this software without specific prior written permission.
|
|
||||||
**
|
|
||||||
** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
|
|
||||||
** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
|
||||||
** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
|
||||||
** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
|
|
||||||
** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
|
||||||
** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
|
||||||
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
|
||||||
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
||||||
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
|
||||||
** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
||||||
**---------------------------------------------------------------------------
|
|
||||||
**
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "v_font.h"
|
|
||||||
#include "cmdlib.h"
|
|
||||||
#include "gstrings.h"
|
|
||||||
#include "d_gui.h"
|
|
||||||
#include "d_event.h"
|
|
||||||
#include "menu.h"
|
|
||||||
#include "v_draw.h"
|
|
||||||
#include "gamecontrol.h"
|
|
||||||
#include "build.h"
|
|
||||||
#include "zstring.h"
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
// Fullscreen image drawer (move to its own source file!)
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void ImageScreen::Drawer()
|
|
||||||
{
|
|
||||||
if (mDesc == nullptr)
|
|
||||||
{
|
|
||||||
// don't let bogus definitions crash this.
|
|
||||||
}
|
|
||||||
else if (mDesc->type == 0)
|
|
||||||
{
|
|
||||||
auto tileindexp = NameToTileIndex.CheckKey(FName(mDesc->text, true));
|
|
||||||
int tileindex = 0;
|
|
||||||
if (tileindexp == nullptr)
|
|
||||||
{
|
|
||||||
// If this isn't a name, try a literal tile index;
|
|
||||||
auto c = mDesc->text.GetChars();
|
|
||||||
if (*c == '#') tileindex = (int)strtoll(c + 1, nullptr, 0);
|
|
||||||
// Error out if the screen cannot be found, this is always a definition error that needs to be reported.
|
|
||||||
else I_Error("Invalid menu screen '%s'", mDesc->text.GetChars());
|
|
||||||
}
|
|
||||||
else tileindex = *tileindexp;
|
|
||||||
if (!gi->DrawSpecialScreen(origin, tileindex)) // allows the front end to do custom handling for a given image.
|
|
||||||
{
|
|
||||||
DrawTexture(twod, tileGetTexture(tileindex), origin.X, origin.Y, DTA_FullscreenScale, FSMode_Fit320x200, DTA_TopLeft, true, DTA_LegacyRenderStyle, STYLE_Normal, TAG_DONE);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (mDesc->type > 0)
|
|
||||||
{
|
|
||||||
gi->DrawCenteredTextScreen(origin, mDesc->text, mDesc->type);
|
|
||||||
}
|
|
||||||
// QAVs are handled in the Blood frontend. Maybe they should be moved out? Stuff for later, but this is a feature where it is feasible.
|
|
||||||
}
|
|
||||||
|
|
||||||
ImageScreen* DImageScrollerMenu::newImageScreen(FImageScrollerDescriptor::ScrollerItem* desc)
|
|
||||||
{
|
|
||||||
return new ImageScreen(desc);
|
|
||||||
}
|
|
||||||
|
|
||||||
void DImageScrollerMenu::Init(DMenu* parent, FImageScrollerDescriptor* desc)
|
|
||||||
{
|
|
||||||
mParentMenu = parent;
|
|
||||||
index = 0;
|
|
||||||
mDesc = desc;
|
|
||||||
canAnimate = !!(mDesc->mFlags & LMF_Animate);
|
|
||||||
|
|
||||||
mCurrent = newImageScreen(&mDesc->mItems[0]);
|
|
||||||
mCurrent->canAnimate = canAnimate;
|
|
||||||
isAnimated = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool DImageScrollerMenu::MenuEvent(int mkey, bool fromcontroller)
|
|
||||||
{
|
|
||||||
if (mDesc->mItems.Size() <= 1)
|
|
||||||
{
|
|
||||||
if (mkey == MKEY_Enter) mkey = MKEY_Back;
|
|
||||||
else if (mkey == MKEY_Right || mkey == MKEY_Left) return true;
|
|
||||||
}
|
|
||||||
switch (mkey)
|
|
||||||
{
|
|
||||||
case MKEY_Back:
|
|
||||||
// Before going back the currently running transition must be terminated.
|
|
||||||
pageTransition.previous = nullptr;
|
|
||||||
if (pageTransition.current) pageTransition.current->origin = { 0,0 };
|
|
||||||
return DMenu::MenuEvent(mkey, fromcontroller);
|
|
||||||
|
|
||||||
|
|
||||||
case MKEY_Left:
|
|
||||||
if (pageTransition.previous == nullptr)
|
|
||||||
{
|
|
||||||
if (--index < 0) index = mDesc->mItems.Size() - 1;
|
|
||||||
auto next = newImageScreen(&mDesc->mItems[index]);
|
|
||||||
next->canAnimate = canAnimate;
|
|
||||||
if (!pageTransition.StartTransition(mCurrent, next, MA_Return))
|
|
||||||
{
|
|
||||||
delete mCurrent;
|
|
||||||
}
|
|
||||||
mCurrent = next;
|
|
||||||
gi->MenuSound(ChooseSound);
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
|
|
||||||
case MKEY_Right:
|
|
||||||
case MKEY_Enter:
|
|
||||||
if (pageTransition.previous == nullptr)
|
|
||||||
{
|
|
||||||
int oldindex = index;
|
|
||||||
if (++index >= (int)mDesc->mItems.Size()) index = 0;
|
|
||||||
|
|
||||||
auto next = newImageScreen(&mDesc->mItems[index]);
|
|
||||||
next->canAnimate = canAnimate;
|
|
||||||
if (!pageTransition.StartTransition(mCurrent, next, MA_Advance))
|
|
||||||
{
|
|
||||||
delete mCurrent;
|
|
||||||
}
|
|
||||||
mCurrent = next;
|
|
||||||
gi->MenuSound(ChooseSound);
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
|
|
||||||
default:
|
|
||||||
return DMenu::MenuEvent(mkey, fromcontroller);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
bool DImageScrollerMenu::MouseEvent(int type, int x, int y)
|
|
||||||
{
|
|
||||||
// Todo: Implement some form of drag event to switch between pages.
|
|
||||||
if (type == MOUSE_Release)
|
|
||||||
{
|
|
||||||
return MenuEvent(MKEY_Enter, false);
|
|
||||||
}
|
|
||||||
|
|
||||||
return DMenu::MouseEvent(type, x, y);
|
|
||||||
}
|
|
||||||
|
|
||||||
void DImageScrollerMenu::Ticker()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void DImageScrollerMenu::Drawer()
|
|
||||||
{
|
|
||||||
if (pageTransition.previous != nullptr)
|
|
||||||
{
|
|
||||||
auto res = pageTransition.Draw();
|
|
||||||
if (res) return;
|
|
||||||
delete pageTransition.previous;
|
|
||||||
pageTransition.previous = nullptr;
|
|
||||||
}
|
|
||||||
mCurrent->origin = origin;
|
|
||||||
mCurrent->Drawer();
|
|
||||||
mCurrent->origin = {};
|
|
||||||
}
|
|
||||||
|
|
|
@ -32,313 +32,105 @@
|
||||||
**
|
**
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <float.h>
|
|
||||||
|
|
||||||
#include "menu.h"
|
#include "menu.h"
|
||||||
#include "c_dispatch.h"
|
|
||||||
#include "filesystem.h"
|
|
||||||
#include "sc_man.h"
|
|
||||||
#include "v_font.h"
|
|
||||||
#include "c_bind.h"
|
|
||||||
#include "d_event.h"
|
|
||||||
#include "d_gui.h"
|
|
||||||
#include "m_joy.h"
|
#include "m_joy.h"
|
||||||
#include "v_video.h"
|
#include "vm.h"
|
||||||
|
|
||||||
#define NO_IMP
|
|
||||||
#include "optionmenuitems.h"
|
|
||||||
|
|
||||||
|
|
||||||
static TArray<IJoystickConfig *> Joysticks;
|
static TArray<IJoystickConfig *> Joysticks;
|
||||||
IJoystickConfig *SELECTED_JOYSTICK;
|
|
||||||
|
|
||||||
FOptionMenuDescriptor *UpdateJoystickConfigMenu(IJoystickConfig *joy);
|
DEFINE_ACTION_FUNCTION(IJoystickConfig, GetSensitivity)
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
class FOptionMenuSliderJoySensitivity : public FOptionMenuSliderBase
|
|
||||||
{
|
{
|
||||||
public:
|
PARAM_SELF_STRUCT_PROLOGUE(IJoystickConfig);
|
||||||
FOptionMenuSliderJoySensitivity(const char *label, double min, double max, double step, int showval)
|
ACTION_RETURN_FLOAT(self->GetSensitivity());
|
||||||
: FOptionMenuSliderBase(label, min, max, step, showval)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
double GetSliderValue()
|
|
||||||
{
|
|
||||||
return SELECTED_JOYSTICK->GetSensitivity();
|
|
||||||
}
|
|
||||||
|
|
||||||
void SetSliderValue(double val)
|
|
||||||
{
|
|
||||||
SELECTED_JOYSTICK->SetSensitivity(float(val));
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
class FOptionMenuSliderJoyScale : public FOptionMenuSliderBase
|
|
||||||
{
|
|
||||||
int mAxis;
|
|
||||||
int mNeg;
|
|
||||||
|
|
||||||
public:
|
|
||||||
FOptionMenuSliderJoyScale(const char *label, int axis, double min, double max, double step, int showval)
|
|
||||||
: FOptionMenuSliderBase(label, min, max, step, showval)
|
|
||||||
{
|
|
||||||
mAxis = axis;
|
|
||||||
mNeg = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
double GetSliderValue()
|
|
||||||
{
|
|
||||||
double d = SELECTED_JOYSTICK->GetAxisScale(mAxis);
|
|
||||||
mNeg = d < 0? -1:1;
|
|
||||||
return d;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SetSliderValue(double val)
|
|
||||||
{
|
|
||||||
SELECTED_JOYSTICK->SetAxisScale(mAxis, float(val * mNeg));
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
class FOptionMenuSliderJoyDeadZone : public FOptionMenuSliderBase
|
|
||||||
{
|
|
||||||
int mAxis;
|
|
||||||
int mNeg;
|
|
||||||
|
|
||||||
public:
|
|
||||||
FOptionMenuSliderJoyDeadZone(const char *label, int axis, double min, double max, double step, int showval)
|
|
||||||
: FOptionMenuSliderBase(label, min, max, step, showval)
|
|
||||||
{
|
|
||||||
mAxis = axis;
|
|
||||||
mNeg = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
double GetSliderValue()
|
|
||||||
{
|
|
||||||
double d = SELECTED_JOYSTICK->GetAxisDeadZone(mAxis);
|
|
||||||
mNeg = d < 0? -1:1;
|
|
||||||
return d;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SetSliderValue(double val)
|
|
||||||
{
|
|
||||||
SELECTED_JOYSTICK->SetAxisDeadZone(mAxis, float(val * mNeg));
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
class FOptionMenuItemJoyMap : public FOptionMenuItemOptionBase
|
|
||||||
{
|
|
||||||
int mAxis;
|
|
||||||
public:
|
|
||||||
|
|
||||||
FOptionMenuItemJoyMap(const char *label, int axis, const char *values, int center)
|
|
||||||
: FOptionMenuItemOptionBase(label, "none", values, NULL, center)
|
|
||||||
{
|
|
||||||
mAxis = axis;
|
|
||||||
}
|
|
||||||
|
|
||||||
int GetSelection()
|
|
||||||
{
|
|
||||||
double f = SELECTED_JOYSTICK->GetAxisMap(mAxis);
|
|
||||||
FOptionValues **opt = OptionValues.CheckKey(mValues);
|
|
||||||
if (opt != NULL && *opt != NULL)
|
|
||||||
{
|
|
||||||
// Map from joystick axis to menu selection.
|
|
||||||
for(unsigned i = 0; i < (*opt)->mValues.Size(); i++)
|
|
||||||
{
|
|
||||||
if (fabs(f - (*opt)->mValues[i].Value) < FLT_EPSILON)
|
|
||||||
{
|
|
||||||
return i;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SetSelection(int selection)
|
|
||||||
{
|
|
||||||
FOptionValues **opt = OptionValues.CheckKey(mValues);
|
|
||||||
// Map from menu selection to joystick axis.
|
|
||||||
if (opt == NULL || *opt == NULL || (unsigned)selection >= (*opt)->mValues.Size())
|
|
||||||
{
|
|
||||||
selection = JOYAXIS_None;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
selection = (int)(*opt)->mValues[selection].Value;
|
|
||||||
}
|
|
||||||
SELECTED_JOYSTICK->SetAxisMap(mAxis, (EJoyAxis)selection);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
class FOptionMenuItemInverter : public FOptionMenuItemOptionBase
|
|
||||||
{
|
|
||||||
int mAxis;
|
|
||||||
public:
|
|
||||||
|
|
||||||
FOptionMenuItemInverter(const char *label, int axis, int center)
|
|
||||||
: FOptionMenuItemOptionBase(label, "none", "YesNo", NULL, center)
|
|
||||||
{
|
|
||||||
mAxis = axis;
|
|
||||||
}
|
|
||||||
|
|
||||||
int GetSelection()
|
|
||||||
{
|
|
||||||
float f = SELECTED_JOYSTICK->GetAxisScale(mAxis);
|
|
||||||
return f > 0? 0:1;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SetSelection(int Selection)
|
|
||||||
{
|
|
||||||
float f = fabs(SELECTED_JOYSTICK->GetAxisScale(mAxis));
|
|
||||||
if (Selection) f*=-1;
|
|
||||||
SELECTED_JOYSTICK->SetAxisScale(mAxis, f);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
class DJoystickConfigMenu : public DOptionMenu
|
|
||||||
{
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
// Executes a CCMD, action is a CCMD name
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
class FOptionMenuItemJoyConfigMenu : public FOptionMenuItemSubmenu
|
|
||||||
{
|
|
||||||
IJoystickConfig *mJoy;
|
|
||||||
public:
|
|
||||||
FOptionMenuItemJoyConfigMenu(const char *label, IJoystickConfig *joy)
|
|
||||||
: FOptionMenuItemSubmenu(label, "JoystickConfigMenu")
|
|
||||||
{
|
|
||||||
mJoy = joy;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool Activate(FName caller) override
|
|
||||||
{
|
|
||||||
UpdateJoystickConfigMenu(mJoy);
|
|
||||||
return FOptionMenuItemSubmenu::Activate(caller);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
/*=======================================
|
|
||||||
*
|
|
||||||
* Joystick Menu
|
|
||||||
*
|
|
||||||
*=======================================*/
|
|
||||||
|
|
||||||
FOptionMenuDescriptor *UpdateJoystickConfigMenu(IJoystickConfig *joy)
|
|
||||||
{
|
|
||||||
FMenuDescriptor **desc = MenuDescriptors.CheckKey(NAME_JoystickConfigMenu);
|
|
||||||
if (desc != NULL && (*desc)->mType == MDESC_OptionsMenu)
|
|
||||||
{
|
|
||||||
FOptionMenuDescriptor *opt = (FOptionMenuDescriptor *)*desc;
|
|
||||||
FOptionMenuItem *it;
|
|
||||||
for(unsigned i=0;i<opt->mItems.Size();i++)
|
|
||||||
{
|
|
||||||
delete opt->mItems[i];
|
|
||||||
opt->mItems.Clear();
|
|
||||||
}
|
|
||||||
if (joy == NULL)
|
|
||||||
{
|
|
||||||
opt->mTitle = "$JOYMNU_TITLE";
|
|
||||||
it = new FOptionMenuItemStaticText("$JOYMNU_INVALID");
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
opt->mTitle.Format("%s", joy->GetName().GetChars());
|
|
||||||
|
|
||||||
SELECTED_JOYSTICK = joy;
|
|
||||||
|
|
||||||
it = new FOptionMenuSliderJoySensitivity("$JOYMNU_OVRSENS", 0, 2, 0.1, 3);
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
it = new FOptionMenuItemStaticText(" ");
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
|
|
||||||
if (joy->GetNumAxes() > 0)
|
|
||||||
{
|
|
||||||
it = new FOptionMenuItemStaticText("$JOYMNU_AXIS");
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
|
|
||||||
for (int i = 0; i < joy->GetNumAxes(); ++i)
|
|
||||||
{
|
|
||||||
it = new FOptionMenuItemStaticText(" ");
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
|
|
||||||
it = new FOptionMenuItemJoyMap(joy->GetAxisName(i), i, "JoyAxisMapNames", false);
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
it = new FOptionMenuSliderJoyScale("$JOYMNU_OVRSENS", i, 0, 4, 0.1, 3);
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
it = new FOptionMenuItemInverter("$JOYMNU_INVERT", i, false);
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
it = new FOptionMenuSliderJoyDeadZone("$JOYMNU_DEADZONE", i, 0, 0.9, 0.05, 3);
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
it = new FOptionMenuItemStaticText("$JOYMNU_NOAXES");
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
opt->mScrollPos = 0;
|
|
||||||
opt->mSelectedItem = -1;
|
|
||||||
opt->mIndent = 0;
|
|
||||||
opt->CalcIndent();
|
|
||||||
return opt;
|
|
||||||
}
|
|
||||||
return NULL;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DEFINE_ACTION_FUNCTION(IJoystickConfig, SetSensitivity)
|
||||||
|
{
|
||||||
|
PARAM_SELF_STRUCT_PROLOGUE(IJoystickConfig);
|
||||||
|
PARAM_FLOAT(sens);
|
||||||
|
self->SetSensitivity((float)sens);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
DEFINE_ACTION_FUNCTION(IJoystickConfig, GetAxisScale)
|
||||||
|
{
|
||||||
|
PARAM_SELF_STRUCT_PROLOGUE(IJoystickConfig);
|
||||||
|
PARAM_INT(axis);
|
||||||
|
ACTION_RETURN_FLOAT(self->GetAxisScale(axis));
|
||||||
|
}
|
||||||
|
|
||||||
|
DEFINE_ACTION_FUNCTION(IJoystickConfig, SetAxisScale)
|
||||||
|
{
|
||||||
|
PARAM_SELF_STRUCT_PROLOGUE(IJoystickConfig);
|
||||||
|
PARAM_INT(axis);
|
||||||
|
PARAM_FLOAT(sens);
|
||||||
|
self->SetAxisScale(axis, (float)sens);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
DEFINE_ACTION_FUNCTION(IJoystickConfig, GetAxisDeadZone)
|
||||||
|
{
|
||||||
|
PARAM_SELF_STRUCT_PROLOGUE(IJoystickConfig);
|
||||||
|
PARAM_INT(axis);
|
||||||
|
ACTION_RETURN_FLOAT(self->GetAxisDeadZone(axis));
|
||||||
|
}
|
||||||
|
|
||||||
|
DEFINE_ACTION_FUNCTION(IJoystickConfig, SetAxisDeadZone)
|
||||||
|
{
|
||||||
|
PARAM_SELF_STRUCT_PROLOGUE(IJoystickConfig);
|
||||||
|
PARAM_INT(axis);
|
||||||
|
PARAM_FLOAT(dz);
|
||||||
|
self->SetAxisDeadZone(axis, (float)dz);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
DEFINE_ACTION_FUNCTION(IJoystickConfig, GetAxisMap)
|
||||||
|
{
|
||||||
|
PARAM_SELF_STRUCT_PROLOGUE(IJoystickConfig);
|
||||||
|
PARAM_INT(axis);
|
||||||
|
ACTION_RETURN_INT(self->GetAxisMap(axis));
|
||||||
|
}
|
||||||
|
|
||||||
|
DEFINE_ACTION_FUNCTION(IJoystickConfig, SetAxisMap)
|
||||||
|
{
|
||||||
|
PARAM_SELF_STRUCT_PROLOGUE(IJoystickConfig);
|
||||||
|
PARAM_INT(axis);
|
||||||
|
PARAM_INT(map);
|
||||||
|
self->SetAxisMap(axis, (EJoyAxis)map);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
DEFINE_ACTION_FUNCTION(IJoystickConfig, GetName)
|
||||||
|
{
|
||||||
|
PARAM_SELF_STRUCT_PROLOGUE(IJoystickConfig);
|
||||||
|
ACTION_RETURN_STRING(self->GetName());
|
||||||
|
}
|
||||||
|
|
||||||
|
DEFINE_ACTION_FUNCTION(IJoystickConfig, GetAxisName)
|
||||||
|
{
|
||||||
|
PARAM_SELF_STRUCT_PROLOGUE(IJoystickConfig);
|
||||||
|
PARAM_INT(axis);
|
||||||
|
ACTION_RETURN_STRING(self->GetAxisName(axis));
|
||||||
|
}
|
||||||
|
|
||||||
|
DEFINE_ACTION_FUNCTION(IJoystickConfig, GetNumAxes)
|
||||||
|
{
|
||||||
|
PARAM_SELF_STRUCT_PROLOGUE(IJoystickConfig);
|
||||||
|
ACTION_RETURN_INT(self->GetNumAxes());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void UpdateJoystickMenu(IJoystickConfig *selected)
|
void UpdateJoystickMenu(IJoystickConfig *selected)
|
||||||
{
|
{
|
||||||
FMenuDescriptor **desc = MenuDescriptors.CheckKey(NAME_JoystickOptions);
|
DMenuDescriptor **desc = MenuDescriptors.CheckKey(NAME_JoystickOptions);
|
||||||
if (desc != NULL && (*desc)->mType == MDESC_OptionsMenu)
|
DMenuDescriptor **ddesc = MenuDescriptors.CheckKey("JoystickOptionsDefaults");
|
||||||
|
if (ddesc == nullptr) return; // without any data the menu cannot be set up and must remain empty.
|
||||||
|
if (desc != NULL && (*desc)->IsKindOf(RUNTIME_CLASS(DOptionMenuDescriptor)))
|
||||||
{
|
{
|
||||||
FOptionMenuDescriptor *opt = (FOptionMenuDescriptor *)*desc;
|
DOptionMenuDescriptor *opt = (DOptionMenuDescriptor *)*desc;
|
||||||
FOptionMenuItem *it;
|
DOptionMenuDescriptor *dopt = (DOptionMenuDescriptor *)*ddesc;
|
||||||
|
if (dopt == nullptr) return;
|
||||||
for(unsigned i=0;i<opt->mItems.Size();i++)
|
DMenuItemBase *it;
|
||||||
{
|
|
||||||
delete opt->mItems[i];
|
|
||||||
}
|
|
||||||
opt->mItems.Clear();
|
|
||||||
|
|
||||||
int i;
|
int i;
|
||||||
int itemnum = -1;
|
int itemnum = -1;
|
||||||
|
@ -359,76 +151,48 @@ void UpdateJoystickMenu(IJoystickConfig *selected)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
opt->mItems = dopt->mItems;
|
||||||
|
|
||||||
// Todo: Block joystick for changing this one.
|
it = opt->GetItem("ConfigureMessage");
|
||||||
it = new FOptionMenuItemOption("$JOYMNU_ENABLE", "use_joystick", "YesNo", NULL, false);
|
if (it != nullptr) it->SetValue(0, !!Joysticks.Size());
|
||||||
opt->mItems.Push(it);
|
it = opt->GetItem("ConnectMessage1");
|
||||||
#if 0//def _WIN32
|
if (it != nullptr) it->SetValue(0, !use_joystick);
|
||||||
it = new FOptionMenuItemOption("Enable DirectInput controllers", "joy_dinput", "YesNo", NULL, false);
|
it = opt->GetItem("ConnectMessage2");
|
||||||
opt->mItems.Push(it);
|
if (it != nullptr) it->SetValue(0, !use_joystick);
|
||||||
it = new FOptionMenuItemOption("Enable XInput controllers", "joy_xinput", "YesNo", NULL, false);
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
it = new FOptionMenuItemOption("Enable raw PlayStation 2 adapters", "joy_ps2raw", "YesNo", NULL, false);
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
it = new FOptionMenuItemStaticText(" ");
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
|
|
||||||
if (Joysticks.Size() == 0)
|
|
||||||
{
|
|
||||||
it = new FOptionMenuItemStaticText("$JOYMNU_NOCON");
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
if (!use_joystick)
|
|
||||||
{
|
|
||||||
it = new FOptionMenuItemStaticText("$JOYMNU_DISABLED1");
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
it = new FOptionMenuItemStaticText("$JOYMNU_DISABLED2");
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
it = new FOptionMenuItemStaticText("$JOYMNU_CONFIG");
|
|
||||||
opt->mItems.Push(it);
|
|
||||||
|
|
||||||
for (int i = 0; i < (int)Joysticks.Size(); ++i)
|
for (int i = 0; i < (int)Joysticks.Size(); ++i)
|
||||||
{
|
{
|
||||||
it = new FOptionMenuItemJoyConfigMenu(Joysticks[i]->GetName(), Joysticks[i]);
|
it = CreateOptionMenuItemJoyConfigMenu(Joysticks[i]->GetName(), Joysticks[i]);
|
||||||
|
GC::WriteBarrier(opt, it);
|
||||||
opt->mItems.Push(it);
|
opt->mItems.Push(it);
|
||||||
if (i == itemnum) opt->mSelectedItem = opt->mItems.Size();
|
if (i == itemnum) opt->mSelectedItem = opt->mItems.Size();
|
||||||
}
|
}
|
||||||
}
|
|
||||||
if (opt->mSelectedItem >= (int)opt->mItems.Size())
|
if (opt->mSelectedItem >= (int)opt->mItems.Size())
|
||||||
{
|
{
|
||||||
opt->mSelectedItem = opt->mItems.Size() - 1;
|
opt->mSelectedItem = opt->mItems.Size() - 1;
|
||||||
}
|
}
|
||||||
|
//opt->CalcIndent();
|
||||||
|
|
||||||
opt->CalcIndent();
|
// If the joystick config menu is open, close it if the device it's open for is gone.
|
||||||
|
if (CurrentMenu != nullptr && (CurrentMenu->IsKindOf("JoystickConfigMenu")))
|
||||||
// If the joystick config menu is open, close it if the device it's
|
|
||||||
// open for is gone.
|
|
||||||
for (i = 0; (unsigned)i < Joysticks.Size(); ++i)
|
|
||||||
{
|
{
|
||||||
if (Joysticks[i] == SELECTED_JOYSTICK)
|
auto p = CurrentMenu->PointerVar<IJoystickConfig>("mJoy");
|
||||||
|
if (p != nullptr)
|
||||||
|
{
|
||||||
|
unsigned i;
|
||||||
|
for (i = 0; i < Joysticks.Size(); ++i)
|
||||||
|
{
|
||||||
|
if (Joysticks[i] == p)
|
||||||
{
|
{
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (i == (int)Joysticks.Size())
|
if (i == Joysticks.Size())
|
||||||
{
|
|
||||||
SELECTED_JOYSTICK = NULL;
|
|
||||||
if (CurrentMenu != NULL && dynamic_cast<DJoystickConfigMenu*>(CurrentMenu))
|
|
||||||
{
|
{
|
||||||
CurrentMenu->Close();
|
CurrentMenu->Close();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static TMenuClassDescriptor<DJoystickConfigMenu> _im("JoystickConfigMenu");
|
|
||||||
|
|
||||||
void RegisterJoystickMenus()
|
|
||||||
{
|
|
||||||
menuClasses.Push(&_im);
|
|
||||||
}
|
|
||||||
|
|
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
|
@ -4,108 +4,21 @@
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
#include "v_font.h"
|
#include "dobject.h"
|
||||||
#include "c_cvars.h"
|
#include "c_cvars.h"
|
||||||
#include "version.h"
|
#include "v_font.h"
|
||||||
#include "textures.h"
|
#include "textures.h"
|
||||||
#include "zstring.h"
|
|
||||||
#include "v_draw.h"
|
|
||||||
#include "menustate.h"
|
|
||||||
#include "gamestruct.h"
|
|
||||||
|
|
||||||
EXTERN_CVAR(Float, snd_menuvolume)
|
EXTERN_CVAR(Float, snd_menuvolume)
|
||||||
EXTERN_CVAR(Int, m_use_mouse);
|
EXTERN_CVAR(Int, m_use_mouse);
|
||||||
|
|
||||||
enum EMax
|
|
||||||
{
|
|
||||||
MAXSKILLS = 7,
|
|
||||||
MAXVOLUMES = 7,
|
|
||||||
MAXMENUGAMEPLAYENTRIES = 7,
|
|
||||||
};
|
|
||||||
|
|
||||||
// These get filled in by the map definition parsers of the front ends.
|
|
||||||
extern FString gSkillNames[MAXSKILLS];
|
|
||||||
extern FString gVolumeNames[MAXVOLUMES];
|
|
||||||
extern FString gVolumeSubtitles[MAXVOLUMES];
|
|
||||||
extern int32_t gVolumeFlags[MAXVOLUMES];
|
|
||||||
extern int gDefaultVolume, gDefaultSkill;
|
|
||||||
|
|
||||||
const int MENU_TICRATE = 30;
|
|
||||||
extern bool help_disabled, credits_disabled;
|
|
||||||
extern int g_currentMenu;
|
|
||||||
|
|
||||||
enum MenuTransitionType
|
|
||||||
{ // Note: This enum is for logical categories, not visual types.
|
|
||||||
MA_None,
|
|
||||||
MA_Return,
|
|
||||||
MA_Advance,
|
|
||||||
};
|
|
||||||
|
|
||||||
class DMenu;
|
|
||||||
|
|
||||||
struct MenuTransition
|
|
||||||
{
|
|
||||||
DMenu* previous;
|
|
||||||
DMenu* current;
|
|
||||||
|
|
||||||
double start;
|
|
||||||
int32_t length;
|
|
||||||
int32_t dir;
|
|
||||||
|
|
||||||
bool StartTransition(DMenu* from, DMenu* to, MenuTransitionType animtype);
|
|
||||||
bool Draw();
|
|
||||||
|
|
||||||
};
|
|
||||||
|
|
||||||
enum
|
|
||||||
{
|
|
||||||
EF_HIDEFROMSP = 1 << 0,
|
|
||||||
};
|
|
||||||
|
|
||||||
enum MenuGameplayEntryFlags
|
|
||||||
{
|
|
||||||
MGE_Locked = 1u << 0u,
|
|
||||||
MGE_Hidden = 1u << 1u,
|
|
||||||
MGE_UserContent = 1u << 2u,
|
|
||||||
};
|
|
||||||
|
|
||||||
typedef struct MenuGameplayEntry
|
|
||||||
{
|
|
||||||
char name[64];
|
|
||||||
uint8_t flags;
|
|
||||||
|
|
||||||
bool isValid() const { return name[0] != '\0'; }
|
|
||||||
} MenuGameplayEntry;
|
|
||||||
|
|
||||||
typedef struct MenuGameplayStemEntry
|
|
||||||
{
|
|
||||||
MenuGameplayEntry entry;
|
|
||||||
MenuGameplayEntry subentries[MAXMENUGAMEPLAYENTRIES];
|
|
||||||
} MenuGameplayStemEntry;
|
|
||||||
|
|
||||||
extern MenuGameplayStemEntry g_MenuGameplayEntries[MAXMENUGAMEPLAYENTRIES];
|
|
||||||
|
|
||||||
|
|
||||||
enum EMenuSounds : int
|
|
||||||
{
|
|
||||||
ActivateSound,
|
|
||||||
CursorSound,
|
|
||||||
AdvanceSound,
|
|
||||||
BackSound,
|
|
||||||
CloseSound,
|
|
||||||
PageSound,
|
|
||||||
ChangeSound,
|
|
||||||
ChooseSound
|
|
||||||
};
|
|
||||||
|
|
||||||
EXTERN_CVAR(Bool, menu_sounds)
|
|
||||||
|
|
||||||
struct event_t;
|
struct event_t;
|
||||||
class FGameTexture;
|
class FTexture;
|
||||||
class FFont;
|
class FFont;
|
||||||
enum EColorRange : int;
|
enum EColorRange : int;
|
||||||
class FPlayerClass;
|
|
||||||
class FKeyBindings;
|
class FKeyBindings;
|
||||||
|
struct FBrokenLines;
|
||||||
|
|
||||||
enum EMenuKey
|
enum EMenuKey
|
||||||
{
|
{
|
||||||
|
@ -129,24 +42,11 @@ enum EMenuKey
|
||||||
MKEY_MBNo,
|
MKEY_MBNo,
|
||||||
};
|
};
|
||||||
|
|
||||||
enum ENativeFontValues
|
|
||||||
{
|
|
||||||
NIT_BigFont,
|
|
||||||
NIT_SmallFont,
|
|
||||||
|
|
||||||
NIT_ActiveColor = -1,
|
|
||||||
NIT_InactiveColor = -2,
|
|
||||||
NIT_SelectedColor = -3,
|
|
||||||
|
|
||||||
NIT_ActiveState = 1,
|
|
||||||
NIT_InactiveState = 2,
|
|
||||||
NIT_SelectedState = 3
|
|
||||||
// positive values for color are direct palswap indices.
|
|
||||||
};
|
|
||||||
|
|
||||||
extern FNewGameStartup NewGameStartupInfo;
|
|
||||||
extern EMenuState menuactive;
|
|
||||||
|
|
||||||
|
class DMenu;
|
||||||
|
extern DMenu *CurrentMenu;
|
||||||
|
extern int MenuTime;
|
||||||
|
class DMenuItemBase;
|
||||||
|
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
//
|
//
|
||||||
|
@ -155,63 +55,44 @@ extern EMenuState menuactive;
|
||||||
//
|
//
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
|
|
||||||
enum EMenuDescriptorType
|
class DMenuDescriptor : public DObject
|
||||||
{
|
{
|
||||||
MDESC_ListMenu,
|
DECLARE_CLASS(DMenuDescriptor, DObject)
|
||||||
MDESC_OptionsMenu,
|
public:
|
||||||
MDESC_ImageScroller,
|
FName mMenuName = NAME_None;
|
||||||
};
|
|
||||||
|
|
||||||
struct FMenuDescriptor
|
|
||||||
{
|
|
||||||
FName mMenuName;
|
|
||||||
FString mNetgameMessage;
|
FString mNetgameMessage;
|
||||||
int mType;
|
PClass *mClass = nullptr;
|
||||||
FName mClass;
|
bool mProtected = false;
|
||||||
|
TArray<DMenuItemBase *> mItems;
|
||||||
|
|
||||||
virtual ~FMenuDescriptor() {}
|
virtual size_t PropagateMark() { return 0; }
|
||||||
};
|
};
|
||||||
|
|
||||||
class FListMenuItem;
|
|
||||||
class FOptionMenuItem;
|
|
||||||
|
|
||||||
enum ListMenuFlags
|
class DListMenuDescriptor : public DMenuDescriptor
|
||||||
{
|
{
|
||||||
LMF_Centered = 1,
|
DECLARE_CLASS(DListMenuDescriptor, DMenuDescriptor)
|
||||||
LMF_DontSpace = 2,
|
|
||||||
LMF_Animate = 4,
|
|
||||||
};
|
|
||||||
|
|
||||||
struct FListMenuDescriptor : public FMenuDescriptor
|
public:
|
||||||
{
|
|
||||||
TDeletingArray<FListMenuItem *> mItems;
|
|
||||||
FString mCaption;
|
|
||||||
int mSelectedItem;
|
int mSelectedItem;
|
||||||
int mSelectOfsX;
|
double mSelectOfsX;
|
||||||
int mSelectOfsY;
|
double mSelectOfsY;
|
||||||
FGameTexture *mSelector;
|
FTextureID mSelector;
|
||||||
int mDisplayTop;
|
int mDisplayTop;
|
||||||
int mXpos, mYpos, mYbotton;
|
double mXpos, mYpos;
|
||||||
int mWLeft, mWRight;
|
int mWLeft, mWRight;
|
||||||
int mLinespacing; // needs to be stored for dynamically created menus
|
int mLinespacing; // needs to be stored for dynamically created menus
|
||||||
int mAutoselect; // this can only be set by internal menu creation functions
|
int mAutoselect; // this can only be set by internal menu creation functions
|
||||||
int mScriptId;
|
|
||||||
int mSecondaryId;
|
|
||||||
int mNativeFontNum, mNativePalNum;
|
|
||||||
float mNativeFontScale;
|
|
||||||
FFont *mFont;
|
FFont *mFont;
|
||||||
EColorRange mFontColor;
|
EColorRange mFontColor;
|
||||||
EColorRange mFontColor2;
|
EColorRange mFontColor2;
|
||||||
FMenuDescriptor *mRedirect; // used to redirect overlong skill and episode menus to option menu based alternatives
|
bool mCenter;
|
||||||
int mFlags;
|
bool mFromEngine;
|
||||||
int mSpacing;
|
int mVirtWidth;
|
||||||
|
int mVirtHeight;
|
||||||
FListMenuDescriptor()
|
|
||||||
{
|
|
||||||
Reset();
|
|
||||||
}
|
|
||||||
|
|
||||||
void Reset();
|
void Reset();
|
||||||
|
size_t PropagateMark() override;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct FOptionMenuSettings
|
struct FOptionMenuSettings
|
||||||
|
@ -226,9 +107,11 @@ struct FOptionMenuSettings
|
||||||
int mLinespacing;
|
int mLinespacing;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct FOptionMenuDescriptor : public FMenuDescriptor
|
class DOptionMenuDescriptor : public DMenuDescriptor
|
||||||
{
|
{
|
||||||
TDeletingArray<FOptionMenuItem *> mItems;
|
DECLARE_CLASS(DOptionMenuDescriptor, DMenuDescriptor)
|
||||||
|
|
||||||
|
public:
|
||||||
FString mTitle;
|
FString mTitle;
|
||||||
int mSelectedItem;
|
int mSelectedItem;
|
||||||
int mDrawTop;
|
int mDrawTop;
|
||||||
|
@ -237,36 +120,17 @@ struct FOptionMenuDescriptor : public FMenuDescriptor
|
||||||
int mIndent;
|
int mIndent;
|
||||||
int mPosition;
|
int mPosition;
|
||||||
bool mDontDim;
|
bool mDontDim;
|
||||||
|
FFont *mFont;
|
||||||
|
|
||||||
void CalcIndent();
|
void CalcIndent();
|
||||||
FOptionMenuItem *GetItem(FName name);
|
DMenuItemBase *GetItem(FName name);
|
||||||
void Reset()
|
void Reset();
|
||||||
{
|
size_t PropagateMark() override;
|
||||||
// Reset the default settings (ignore all other values in the struct)
|
~DOptionMenuDescriptor() = default;
|
||||||
mPosition = 0;
|
|
||||||
mScrollTop = 0;
|
|
||||||
mIndent = 0;
|
|
||||||
mDontDim = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
};
|
|
||||||
|
|
||||||
struct FImageScrollerDescriptor : public FMenuDescriptor
|
|
||||||
{
|
|
||||||
struct ScrollerItem
|
|
||||||
{
|
|
||||||
int type; // 0: fullscreen image; 1: centered text
|
|
||||||
int scriptID;
|
|
||||||
FString text;
|
|
||||||
};
|
|
||||||
int mFlags = 0;
|
|
||||||
|
|
||||||
TArray<ScrollerItem> mItems;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
typedef TMap<FName, DMenuDescriptor *> MenuDescriptorList;
|
||||||
typedef TMap<FName, FMenuDescriptor *> MenuDescriptorList;
|
|
||||||
|
|
||||||
extern FOptionMenuSettings OptionSettings;
|
extern FOptionMenuSettings OptionSettings;
|
||||||
extern MenuDescriptorList MenuDescriptors;
|
extern MenuDescriptorList MenuDescriptors;
|
||||||
|
@ -300,11 +164,12 @@ struct FMenuRect
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
class DMenu
|
class DMenu : public DObject
|
||||||
{
|
{
|
||||||
protected:
|
DECLARE_CLASS (DMenu, DObject)
|
||||||
bool mMouseCapture;
|
HAS_OBJECT_POINTERS
|
||||||
bool mBackbuttonSelected;
|
|
||||||
|
|
||||||
|
|
||||||
public:
|
public:
|
||||||
enum
|
enum
|
||||||
|
@ -314,41 +179,21 @@ public:
|
||||||
MOUSE_Release
|
MOUSE_Release
|
||||||
};
|
};
|
||||||
|
|
||||||
enum
|
TObjPtr<DMenu*> mParentMenu;
|
||||||
{
|
bool mMouseCapture;
|
||||||
BACKBUTTON_TIME = 4*MENU_TICRATE
|
bool mBackbuttonSelected;
|
||||||
};
|
bool DontDim;
|
||||||
|
bool DontBlur;
|
||||||
static bool InMenu;
|
static int InMenu;
|
||||||
|
|
||||||
DMenu *mParentMenu;
|
|
||||||
DVector2 origin = { 0,0 };
|
|
||||||
int scriptID = INT_MAX;
|
|
||||||
bool canAnimate = false;
|
|
||||||
bool isAnimated = false; // set to true when uncapped frame rate is needed.
|
|
||||||
|
|
||||||
DMenu(DMenu *parent = NULL);
|
DMenu(DMenu *parent = NULL);
|
||||||
virtual ~DMenu() = default;
|
bool TranslateKeyboardEvents();
|
||||||
virtual bool Responder (event_t *ev);
|
|
||||||
virtual bool MenuEvent (int mkey, bool fromcontroller);
|
|
||||||
virtual void Ticker ();
|
|
||||||
virtual void PreDraw() {}
|
|
||||||
virtual void PostDraw() {}
|
|
||||||
virtual void Drawer ();
|
|
||||||
virtual bool DimAllowed ();
|
|
||||||
virtual bool TranslateKeyboardEvents();
|
|
||||||
virtual void Close();
|
virtual void Close();
|
||||||
virtual bool MouseEvent(int type, int x, int y);
|
|
||||||
virtual void Destroy() {}
|
bool CallResponder(event_t *ev);
|
||||||
bool IsAnimated() const { return isAnimated; }
|
bool CallMenuEvent(int mkey, bool fromcontroller);
|
||||||
bool MouseEventBack(int type, int x, int y);
|
void CallTicker();
|
||||||
void SetCapture();
|
void CallDrawer();
|
||||||
void ReleaseCapture();
|
|
||||||
void SetOrigin();
|
|
||||||
bool HasCapture()
|
|
||||||
{
|
|
||||||
return mMouseCapture;
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
|
@ -357,229 +202,21 @@ public:
|
||||||
//
|
//
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
|
|
||||||
class DListMenu;
|
class DMenuItemBase : public DObject
|
||||||
|
|
||||||
class FListMenuItem
|
|
||||||
{
|
{
|
||||||
protected:
|
DECLARE_CLASS(DMenuItemBase, DObject)
|
||||||
int mXpos, mYpos;
|
public:
|
||||||
int mHeight;
|
double mXpos, mYpos;
|
||||||
FName mAction;
|
FName mAction;
|
||||||
|
bool mEnabled;
|
||||||
|
|
||||||
public:
|
bool Activate();
|
||||||
bool mEnabled, mHidden;
|
bool SetString(int i, const char *s);
|
||||||
|
bool GetString(int i, char *s, int len);
|
||||||
FListMenuItem(int xpos = 0, int ypos = 0, FName action = NAME_None)
|
bool SetValue(int i, int value);
|
||||||
{
|
bool GetValue(int i, int *pvalue);
|
||||||
mXpos = xpos;
|
|
||||||
mYpos = ypos;
|
|
||||||
mAction = action;
|
|
||||||
mEnabled = true;
|
|
||||||
mHidden = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual ~FListMenuItem();
|
|
||||||
|
|
||||||
virtual bool CheckCoordinate(int x, int y);
|
|
||||||
virtual void Ticker();
|
|
||||||
virtual void Drawer(DListMenu *menu, const DVector2& origin, bool selected);
|
|
||||||
virtual bool Selectable();
|
|
||||||
virtual bool Activate(FName caller);
|
|
||||||
virtual FName GetAction(int *pparam);
|
|
||||||
virtual bool SetString(int i, const char *s);
|
|
||||||
virtual bool GetString(int i, char *s, int len);
|
|
||||||
virtual bool SetValue(int i, int value);
|
|
||||||
virtual bool GetValue(int i, int *pvalue);
|
|
||||||
virtual void Enable(bool on);
|
|
||||||
virtual bool MenuEvent (int mkey, bool fromcontroller);
|
|
||||||
virtual bool MouseEvent(int type, int x, int y);
|
|
||||||
virtual bool CheckHotkey(int c);
|
|
||||||
virtual int GetWidth();
|
|
||||||
virtual void DrawSelector(int xofs, int yofs, FGameTexture *tex);
|
|
||||||
void OffsetPositionY(int ydelta) { mYpos += ydelta; }
|
void OffsetPositionY(int ydelta) { mYpos += ydelta; }
|
||||||
int GetY() { return mYpos; }
|
double GetY() { return mYpos; }
|
||||||
int GetX() { return mXpos; }
|
|
||||||
void SetX(int x) { mXpos = x; }
|
|
||||||
void SetY(int x) { mYpos = x; }
|
|
||||||
void SetHeight(int x) { mHeight = x; }
|
|
||||||
void SetAction(FName action) { mAction = action; }
|
|
||||||
};
|
|
||||||
|
|
||||||
class FListMenuItemStaticPatch : public FListMenuItem
|
|
||||||
{
|
|
||||||
protected:
|
|
||||||
FGameTexture *mTexture;
|
|
||||||
bool mCentered;
|
|
||||||
|
|
||||||
public:
|
|
||||||
FListMenuItemStaticPatch(int x, int y, FGameTexture *patch, bool centered);
|
|
||||||
void Drawer(DListMenu* menu, const DVector2& origin, bool selected);
|
|
||||||
};
|
|
||||||
|
|
||||||
class FListMenuItemStaticText : public FListMenuItem
|
|
||||||
{
|
|
||||||
protected:
|
|
||||||
const char *mText;
|
|
||||||
FFont *mFont;
|
|
||||||
EColorRange mColor;
|
|
||||||
bool mCentered;
|
|
||||||
|
|
||||||
public:
|
|
||||||
FListMenuItemStaticText(int x, int y, const char *text, FFont *font, EColorRange color, bool centered);
|
|
||||||
~FListMenuItemStaticText();
|
|
||||||
void Drawer(DListMenu* menu, const DVector2& origin, bool selected) override;
|
|
||||||
};
|
|
||||||
|
|
||||||
class FListMenuItemNativeStaticText : public FListMenuItem
|
|
||||||
{
|
|
||||||
protected:
|
|
||||||
FString mText;
|
|
||||||
int mFontnum;
|
|
||||||
int mPalnum;
|
|
||||||
bool mCentered;
|
|
||||||
|
|
||||||
public:
|
|
||||||
FListMenuItemNativeStaticText(int x, int y, const FString & text, int fontnum, int palnum, bool centered);
|
|
||||||
void Drawer(DListMenu* menu, const DVector2& origin, bool selected) override;
|
|
||||||
};
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
// selectable items
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
class FListMenuItemSelectable : public FListMenuItem
|
|
||||||
{
|
|
||||||
protected:
|
|
||||||
int mHotkey;
|
|
||||||
int mParam;
|
|
||||||
|
|
||||||
public:
|
|
||||||
FListMenuItemSelectable(int x, int y, int height, FName childmenu, int mParam = -1);
|
|
||||||
bool CheckCoordinate(int x, int y) override;
|
|
||||||
bool Selectable() override;
|
|
||||||
bool CheckHotkey(int c) override;
|
|
||||||
bool Activate(FName caller) override;
|
|
||||||
bool MouseEvent(int type, int x, int y) override;
|
|
||||||
FName GetAction(int *pparam) override;
|
|
||||||
};
|
|
||||||
|
|
||||||
class FListMenuItemText : public FListMenuItemSelectable
|
|
||||||
{
|
|
||||||
FString mText;
|
|
||||||
FFont *mFont;
|
|
||||||
EColorRange mColor;
|
|
||||||
EColorRange mColorSelected;
|
|
||||||
public:
|
|
||||||
FListMenuItemText(int x, int y, int height, int hotkey, const FString &text, FFont *font, EColorRange color, EColorRange color2, FName child, int param = 0);
|
|
||||||
~FListMenuItemText();
|
|
||||||
void Drawer(DListMenu* menu, const DVector2& origin, bool selected) override;
|
|
||||||
int GetWidth() override;
|
|
||||||
};
|
|
||||||
|
|
||||||
class FListMenuItemNativeText : public FListMenuItemSelectable
|
|
||||||
{
|
|
||||||
// This draws the item with the game frontend's native text drawer and uses a front end defined font, it takes only symbolic constants as parameters.
|
|
||||||
FString mText;
|
|
||||||
int mFontnum;
|
|
||||||
int mPalnum;
|
|
||||||
float mFontscale;
|
|
||||||
public:
|
|
||||||
FListMenuItemNativeText(int x, int y, int height, int hotkey, const FString& text, int fontnum, int palnum, float fontscale, FName child, int param = 0);
|
|
||||||
~FListMenuItemNativeText();
|
|
||||||
void Drawer(DListMenu* menu, const DVector2& origin, bool selected) override;
|
|
||||||
int GetWidth() override;
|
|
||||||
void DrawSelector(int xofs, int yofs, FGameTexture* tex) override { } // The text drawer handles this itself.
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
class FListMenuItemPatch : public FListMenuItemSelectable
|
|
||||||
{
|
|
||||||
FGameTexture* mTexture;
|
|
||||||
public:
|
|
||||||
FListMenuItemPatch(int x, int y, int height, int hotkey, FGameTexture* patch, FName child, int param = 0);
|
|
||||||
void Drawer(DListMenu* menu, const DVector2& origin, bool selected) override;
|
|
||||||
int GetWidth() override;
|
|
||||||
};
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
// list menu class runs a menu described by a FListMenuDescriptor
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
class DListMenu : public DMenu
|
|
||||||
{
|
|
||||||
typedef DMenu Super;
|
|
||||||
protected:
|
|
||||||
FListMenuDescriptor *mDesc = nullptr;
|
|
||||||
FListMenuItem *mFocusControl = nullptr;
|
|
||||||
|
|
||||||
public:
|
|
||||||
DListMenu(DMenu *parent = NULL, FListMenuDescriptor *desc = NULL);
|
|
||||||
virtual void Init(DMenu *parent = NULL, FListMenuDescriptor *desc = NULL);
|
|
||||||
FListMenuItem *GetItem(FName name);
|
|
||||||
bool Responder (event_t *ev) override;
|
|
||||||
bool MenuEvent (int mkey, bool fromcontroller) override;
|
|
||||||
bool MouseEvent(int type, int x, int y) override;
|
|
||||||
void Ticker () override;
|
|
||||||
void Drawer () override;
|
|
||||||
void PreDraw() override;
|
|
||||||
virtual void SelectionChanged() {}
|
|
||||||
void SetFocus(FListMenuItem *fc)
|
|
||||||
{
|
|
||||||
mFocusControl = fc;
|
|
||||||
}
|
|
||||||
bool CheckFocus(FListMenuItem *fc)
|
|
||||||
{
|
|
||||||
return mFocusControl == fc;
|
|
||||||
}
|
|
||||||
void ReleaseFocus()
|
|
||||||
{
|
|
||||||
mFocusControl = NULL;
|
|
||||||
}
|
|
||||||
const FListMenuDescriptor* Descriptor() const
|
|
||||||
{
|
|
||||||
return mDesc;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
// base class for menu items
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
class FOptionMenuItem : public FListMenuItem
|
|
||||||
{
|
|
||||||
protected:
|
|
||||||
FString mLabel;
|
|
||||||
bool mCentered = false;
|
|
||||||
|
|
||||||
void drawText(int x, int y, int color, const char * text, bool grayed = false);
|
|
||||||
|
|
||||||
int drawLabel(int indent, int y, EColorRange color, bool grayed = false);
|
|
||||||
void drawValue(int indent, int y, int color, const char *text, bool grayed = false);
|
|
||||||
|
|
||||||
int CursorSpace();
|
|
||||||
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
FOptionMenuItem(const char *text, FName action = NAME_None, bool center = false)
|
|
||||||
: FListMenuItem(0, 0, action)
|
|
||||||
{
|
|
||||||
mLabel = text;
|
|
||||||
mCentered = center;
|
|
||||||
}
|
|
||||||
|
|
||||||
~FOptionMenuItem();
|
|
||||||
virtual int Draw(FOptionMenuDescriptor *desc, int y, int indent, bool selected);
|
|
||||||
virtual bool Selectable();
|
|
||||||
virtual int GetIndent();
|
|
||||||
virtual bool MouseEvent(int type, int x, int y);
|
|
||||||
};
|
};
|
||||||
|
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
|
@ -606,239 +243,41 @@ extern FOptionMap OptionValues;
|
||||||
|
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
//
|
//
|
||||||
// Option menu class runs a menu described by a FOptionMenuDescriptor
|
//
|
||||||
//
|
//
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
|
|
||||||
class DOptionMenu : public DMenu
|
|
||||||
{
|
|
||||||
using Super = DMenu;
|
|
||||||
bool CanScrollUp;
|
|
||||||
bool CanScrollDown;
|
|
||||||
int VisBottom;
|
|
||||||
FOptionMenuItem *mFocusControl;
|
|
||||||
|
|
||||||
protected:
|
|
||||||
FOptionMenuDescriptor *mDesc;
|
|
||||||
|
|
||||||
int GetPosition();
|
|
||||||
|
|
||||||
public:
|
|
||||||
FOptionMenuItem *GetItem(FName name);
|
|
||||||
DOptionMenu(DMenu *parent = NULL, FOptionMenuDescriptor *desc = NULL);
|
|
||||||
virtual void Init(DMenu *parent = NULL, FOptionMenuDescriptor *desc = NULL);
|
|
||||||
int FirstSelectable();
|
|
||||||
bool Responder (event_t *ev);
|
|
||||||
bool MenuEvent (int mkey, bool fromcontroller);
|
|
||||||
bool MouseEvent(int type, int x, int y);
|
|
||||||
void Ticker ();
|
|
||||||
void Drawer ();
|
|
||||||
virtual int GetIndent();
|
|
||||||
const FOptionMenuDescriptor *GetDescriptor() const { return mDesc; }
|
|
||||||
void SetFocus(FOptionMenuItem *fc)
|
|
||||||
{
|
|
||||||
mFocusControl = fc;
|
|
||||||
}
|
|
||||||
bool CheckFocus(FOptionMenuItem *fc)
|
|
||||||
{
|
|
||||||
return mFocusControl == fc;
|
|
||||||
}
|
|
||||||
void ReleaseFocus()
|
|
||||||
{
|
|
||||||
mFocusControl = NULL;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
FFont *OptionFont();
|
|
||||||
int OptionHeight();
|
|
||||||
int OptionWidth(const char * s);
|
|
||||||
void DrawOptionText(int x, int y, int color, const char *text, bool grayed = false);
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
// ImageScroller
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
class ImageScreen;
|
|
||||||
|
|
||||||
class DImageScrollerMenu : public DMenu
|
|
||||||
{
|
|
||||||
DMenu* mCurrent = nullptr;
|
|
||||||
FImageScrollerDescriptor* mDesc = nullptr;
|
|
||||||
int index = 0;
|
|
||||||
MenuTransition pageTransition = {};
|
|
||||||
|
|
||||||
protected:
|
|
||||||
virtual ImageScreen* newImageScreen(FImageScrollerDescriptor::ScrollerItem* desc);
|
|
||||||
|
|
||||||
public:
|
|
||||||
void Init(DMenu* parent = nullptr, FImageScrollerDescriptor* desc = nullptr);
|
|
||||||
bool MenuEvent(int mkey, bool fromcontroller);
|
|
||||||
bool MouseEvent(int type, int x, int y);
|
|
||||||
void Ticker();
|
|
||||||
void Drawer();
|
|
||||||
};
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
// Input some text
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
class DTextEnterMenu : public DMenu
|
|
||||||
{
|
|
||||||
using Super = DMenu;
|
|
||||||
|
|
||||||
FString mEnterString;
|
|
||||||
int mEnterSize;
|
|
||||||
bool mInputGridOkay;
|
|
||||||
int InputGridX;
|
|
||||||
int InputGridY;
|
|
||||||
int CursorSize;
|
|
||||||
bool AllowColors;
|
|
||||||
FFont *displayFont;
|
|
||||||
|
|
||||||
|
|
||||||
void AppendChar(int ch);
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
// [TP] Added allowcolors
|
|
||||||
DTextEnterMenu(DMenu *parent, FFont *dpf, FString textbuffer, int maxlen, bool showgrid, bool allowcolors = false);
|
|
||||||
|
|
||||||
void Drawer ();
|
|
||||||
bool MenuEvent (int mkey, bool fromcontroller);
|
|
||||||
bool Responder(event_t *ev);
|
|
||||||
bool TranslateKeyboardEvents();
|
|
||||||
bool MouseEvent(int type, int x, int y);
|
|
||||||
const char* GetText() { return mEnterString.GetChars(); }
|
|
||||||
|
|
||||||
};
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
// Show a fullscreen image / centered text screen for an image scroller
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
class ImageScreen : public DMenu
|
|
||||||
{
|
|
||||||
protected:
|
|
||||||
const FImageScrollerDescriptor::ScrollerItem* mDesc;
|
|
||||||
public:
|
|
||||||
ImageScreen(const FImageScrollerDescriptor::ScrollerItem* it)
|
|
||||||
{
|
|
||||||
mDesc = it;
|
|
||||||
}
|
|
||||||
void Drawer() override;
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
struct event_t;
|
struct event_t;
|
||||||
void M_EnableMenu (bool on) ;
|
void M_EnableMenu (bool on) ;
|
||||||
bool M_Responder (event_t *ev);
|
bool M_Responder (event_t *ev);
|
||||||
void M_Ticker (void);
|
void M_Ticker (void);
|
||||||
void M_Drawer (void);
|
void M_Drawer (void);
|
||||||
void M_PreviousMenu();
|
|
||||||
void M_Init (void);
|
void M_Init (void);
|
||||||
void M_CreateMenus();
|
void M_CreateMenus();
|
||||||
void M_ActivateMenu(DMenu *menu);
|
void M_ActivateMenu(DMenu *menu);
|
||||||
void M_ClearMenus (bool final = false);
|
void M_ClearMenus ();
|
||||||
|
void M_PreviousMenu ();
|
||||||
void M_ParseMenuDefs();
|
void M_ParseMenuDefs();
|
||||||
void M_StartupSkillMenu(FNewGameStartup *gs);
|
void M_DoStartControlPanel(bool scaleoverride);
|
||||||
int M_GetDefaultSkill();
|
void M_SetMenu(FName menu, int param = -1);
|
||||||
void M_StartControlPanel (bool makeSound);
|
void M_StartMessage(const char *message, int messagemode, FName action = NAME_None);
|
||||||
bool M_SetMenu(FName menu, int param = -1, FName callingMenu = NAME_None);
|
DMenu *StartPickerMenu(DMenu *parent, const char *name, FColorCVar *cvar);
|
||||||
void M_NotifyNewSave (const char *file, const char *title, bool okForQuicksave);
|
void M_MarkMenus();
|
||||||
void M_StartMessage(const char *message, int messagemode, int scriptId, FName action = NAME_None);
|
FTextureID GetMenuTexture(const char* const name);
|
||||||
void M_UnhideCustomMenu(int menu, int itemmask);
|
void DeinitMenus();
|
||||||
void M_MenuSound(EMenuSounds snd);
|
|
||||||
void M_Autosave();
|
|
||||||
bool M_Active();
|
bool M_Active();
|
||||||
void M_DeinitMenus();
|
inline bool M_IsAnimated() { return false; }
|
||||||
void M_UnpauseSound();
|
|
||||||
|
|
||||||
|
|
||||||
void I_SetMouseCapture();
|
struct IJoystickConfig;
|
||||||
void I_ReleaseMouseCapture();
|
DMenuItemBase * CreateOptionMenuItemStaticText(const char *name, int v = -1);
|
||||||
|
DMenuItemBase * CreateOptionMenuItemSubmenu(const char *label, FName cmd, int center);
|
||||||
struct MenuClassDescriptor;
|
DMenuItemBase * CreateOptionMenuItemControl(const char *label, FName cmd, FKeyBindings *bindings);
|
||||||
extern TArray<MenuClassDescriptor*> menuClasses;
|
DMenuItemBase * CreateOptionMenuItemJoyConfigMenu(const char *label, IJoystickConfig *joy);
|
||||||
|
DMenuItemBase * CreateListMenuItemPatch(double x, double y, int height, int hotkey, FTextureID tex, FName command, int param);
|
||||||
using hFunc = std::function<bool(bool)>;
|
DMenuItemBase * CreateListMenuItemText(double x, double y, int height, int hotkey, const char *text, FFont *font, PalEntry color1, PalEntry color2, FName command, int param);
|
||||||
DMenu* CreateMessageBoxMenu(DMenu* parent, const char* message, int messagemode, int scriptID, bool playsound, FName action = NAME_None, hFunc handler = nullptr);
|
DMenuItemBase * CreateOptionMenuItemCommand(const char *label, FName cmd, bool centered = false);
|
||||||
|
|
||||||
|
|
||||||
struct MenuClassDescriptor
|
|
||||||
{
|
|
||||||
FName mName;
|
|
||||||
MenuClassDescriptor(const char* name) : mName(name)
|
|
||||||
{
|
|
||||||
//menuClasses.Push(this);
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual DMenu* CreateNew() = 0;
|
|
||||||
};
|
|
||||||
|
|
||||||
template<class Menu> struct TMenuClassDescriptor : public MenuClassDescriptor
|
|
||||||
{
|
|
||||||
TMenuClassDescriptor(const char* name) : MenuClassDescriptor(name)
|
|
||||||
{}
|
|
||||||
DMenu* CreateNew()
|
|
||||||
{
|
|
||||||
return new Menu;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
struct FSavegameManager
|
|
||||||
{
|
|
||||||
private:
|
|
||||||
TArray<FSaveGameNode*> SaveGames;
|
|
||||||
FSaveGameNode NewSaveNode;
|
|
||||||
int LastSaved = -1;
|
|
||||||
int LastAccessed = -1;
|
|
||||||
TArray<char> SavePicData;
|
|
||||||
FGameTexture *SavePic = nullptr;
|
|
||||||
|
|
||||||
public:
|
|
||||||
int WindowSize = 0;
|
|
||||||
FString SaveCommentString;
|
|
||||||
FSaveGameNode *quickSaveSlot = nullptr;
|
|
||||||
~FSavegameManager();
|
|
||||||
|
|
||||||
private:
|
|
||||||
int InsertSaveNode(FSaveGameNode *node);
|
|
||||||
public:
|
|
||||||
void NotifyNewSave(const FString &file, const FString &title, bool okForQuicksave, bool forceQuicksave);
|
|
||||||
void ClearSaveGames();
|
|
||||||
|
|
||||||
void ReadSaveStrings();
|
|
||||||
void UnloadSaveData();
|
|
||||||
|
|
||||||
int RemoveSaveSlot(int index);
|
|
||||||
void LoadSavegame(int Selected);
|
|
||||||
void DoSave(int Selected, const char *savegamestring);
|
|
||||||
unsigned ExtractSaveData(int index);
|
|
||||||
void ClearSaveStuff();
|
|
||||||
bool DrawSavePic(int x, int y, int w, int h);
|
|
||||||
void DrawSaveComment(FFont *font, int cr, int x, int y, int scalefactor);
|
|
||||||
void SetFileInfo(int Selected);
|
|
||||||
unsigned SavegameCount();
|
|
||||||
FSaveGameNode *GetSavegame(int i);
|
|
||||||
void InsertNewSaveNode();
|
|
||||||
bool RemoveNewSaveNode();
|
|
||||||
|
|
||||||
void LoadGame(FSaveGameNode* node);
|
|
||||||
void SaveGame(FSaveGameNode* node, bool ok4q, bool forceq);
|
|
||||||
|
|
||||||
};
|
|
||||||
|
|
||||||
extern FSavegameManager savegameManager;
|
|
||||||
extern DMenu* CurrentMenu;
|
|
||||||
|
|
||||||
bool M_IsAnimated();
|
|
||||||
|
|
||||||
|
void UpdateVRModes(bool considerQuadBuffered=true);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -1,374 +0,0 @@
|
||||||
/*
|
|
||||||
** menuinput.cpp
|
|
||||||
** The string input code
|
|
||||||
**
|
|
||||||
**---------------------------------------------------------------------------
|
|
||||||
** Copyright 2001-2010 Randy Heit
|
|
||||||
** Copyright 2010 Christoph Oelckers
|
|
||||||
** All rights reserved.
|
|
||||||
**
|
|
||||||
** Redistribution and use in source and binary forms, with or without
|
|
||||||
** modification, are permitted provided that the following conditions
|
|
||||||
** are met:
|
|
||||||
**
|
|
||||||
** 1. Redistributions of source code must retain the above copyright
|
|
||||||
** notice, this list of conditions and the following disclaimer.
|
|
||||||
** 2. Redistributions in binary form must reproduce the above copyright
|
|
||||||
** notice, this list of conditions and the following disclaimer in the
|
|
||||||
** documentation and/or other materials provided with the distribution.
|
|
||||||
** 3. The name of the author may not be used to endorse or promote products
|
|
||||||
** derived from this software without specific prior written permission.
|
|
||||||
**
|
|
||||||
** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
|
|
||||||
** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
|
||||||
** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
|
||||||
** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
|
|
||||||
** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
|
||||||
** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
|
||||||
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
|
||||||
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
||||||
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
|
||||||
** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
||||||
**---------------------------------------------------------------------------
|
|
||||||
**
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "menu.h"
|
|
||||||
#include "c_cvars.h"
|
|
||||||
#include "d_event.h"
|
|
||||||
#include "d_gui.h"
|
|
||||||
#include "v_font.h"
|
|
||||||
#include "v_text.h"
|
|
||||||
#include "v_draw.h"
|
|
||||||
#include "v_video.h"
|
|
||||||
|
|
||||||
#define INPUTGRID_WIDTH 13
|
|
||||||
#define INPUTGRID_HEIGHT 5
|
|
||||||
|
|
||||||
// Heretic and Hexen do not, by default, come with glyphs for all of these
|
|
||||||
// characters. Oh well. Doom and Strife do.
|
|
||||||
static const char InputGridChars[INPUTGRID_WIDTH * INPUTGRID_HEIGHT] =
|
|
||||||
"ABCDEFGHIJKLM"
|
|
||||||
"NOPQRSTUVWXYZ"
|
|
||||||
"0123456789+-="
|
|
||||||
".,!?@'\":;[]()"
|
|
||||||
"<>^#$%&*/_ \b";
|
|
||||||
|
|
||||||
|
|
||||||
CVAR(Bool, m_showinputgrid, false, CVAR_ARCHIVE|CVAR_GLOBALCONFIG)
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
// [TP] Added allowcolors
|
|
||||||
DTextEnterMenu::DTextEnterMenu(DMenu *parent, FFont *dpf, FString textbuffer, int maxlen, bool showgrid, bool allowcolors)
|
|
||||||
: DMenu(parent)
|
|
||||||
{
|
|
||||||
mEnterString = textbuffer;
|
|
||||||
mEnterSize = maxlen;
|
|
||||||
mInputGridOkay = (showgrid && (m_showinputgrid == 0)) || (m_showinputgrid >= 1);
|
|
||||||
if (mEnterString.Len() > 0)
|
|
||||||
{
|
|
||||||
InputGridX = INPUTGRID_WIDTH - 1;
|
|
||||||
InputGridY = INPUTGRID_HEIGHT - 1;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
// If we are naming a new save, don't start the cursor on "end".
|
|
||||||
InputGridX = 0;
|
|
||||||
InputGridY = 0;
|
|
||||||
}
|
|
||||||
AllowColors = allowcolors; // [TP]
|
|
||||||
displayFont = dpf;
|
|
||||||
CursorSize = displayFont->StringWidth(displayFont->GetCursor());
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
bool DTextEnterMenu::TranslateKeyboardEvents()
|
|
||||||
{
|
|
||||||
return mInputGridOkay;
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
bool DTextEnterMenu::Responder(event_t *ev)
|
|
||||||
{
|
|
||||||
if (ev->type == EV_GUI_Event)
|
|
||||||
{
|
|
||||||
// Save game and player name string input
|
|
||||||
if (ev->subtype == EV_GUI_Char)
|
|
||||||
{
|
|
||||||
mInputGridOkay = false;
|
|
||||||
AppendChar(ev->data1);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
char ch = (char)ev->data1;
|
|
||||||
if ((ev->subtype == EV_GUI_KeyDown || ev->subtype == EV_GUI_KeyRepeat) && ch == '\b')
|
|
||||||
{
|
|
||||||
if (mEnterString.Len() > 0)
|
|
||||||
{
|
|
||||||
mEnterString.DeleteLastCharacter();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (ev->subtype == EV_GUI_KeyDown)
|
|
||||||
{
|
|
||||||
if (ch == GK_ESCAPE)
|
|
||||||
{
|
|
||||||
DMenu *parent = mParentMenu;
|
|
||||||
parent->MenuEvent(MKEY_Abort, false);
|
|
||||||
Close();
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
else if (ch == '\r')
|
|
||||||
{
|
|
||||||
if (mEnterString.Len() > 0)
|
|
||||||
{
|
|
||||||
// [TP] If we allow color codes, colorize the string now.
|
|
||||||
//if (AllowColors)
|
|
||||||
//mEnterString = mEnterString.Filter();
|
|
||||||
|
|
||||||
DMenu *parent = mParentMenu;
|
|
||||||
parent->MenuEvent(MKEY_Input, false);
|
|
||||||
Close();
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (ev->subtype == EV_GUI_KeyDown || ev->subtype == EV_GUI_KeyRepeat)
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return Super::Responder(ev);
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
bool DTextEnterMenu::MouseEvent(int type, int x, int y)
|
|
||||||
{
|
|
||||||
const int cell_width = 18 * CleanXfac_1;
|
|
||||||
const int cell_height = 16 * CleanYfac_1;
|
|
||||||
const int screen_y = screen->GetHeight() - INPUTGRID_HEIGHT * cell_height;
|
|
||||||
const int screen_x = (screen->GetWidth() - INPUTGRID_WIDTH * cell_width) / 2;
|
|
||||||
|
|
||||||
if (x >= screen_x && x < screen_x + INPUTGRID_WIDTH * cell_width && y >= screen_y)
|
|
||||||
{
|
|
||||||
InputGridX = (x - screen_x) / cell_width;
|
|
||||||
InputGridY = (y - screen_y) / cell_height;
|
|
||||||
if (type == DMenu::MOUSE_Release)
|
|
||||||
{
|
|
||||||
if (MenuEvent(MKEY_Enter, true))
|
|
||||||
{
|
|
||||||
//M_MenuSound(CursorSound);
|
|
||||||
if (m_use_mouse == 2) InputGridX = InputGridY = -1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
InputGridX = InputGridY = -1;
|
|
||||||
}
|
|
||||||
return Super::MouseEvent(type, x, y);
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void DTextEnterMenu::AppendChar(int ch)
|
|
||||||
{
|
|
||||||
FStringf newstring("%s%c%c", mEnterString.GetChars(), ch, displayFont->GetCursor());
|
|
||||||
if (mEnterSize < 0 || displayFont->StringWidth(newstring) < mEnterSize)
|
|
||||||
{
|
|
||||||
mEnterString.AppendCharacter(ch);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
bool DTextEnterMenu::MenuEvent (int key, bool fromcontroller)
|
|
||||||
{
|
|
||||||
if (key == MKEY_Back)
|
|
||||||
{
|
|
||||||
mParentMenu->MenuEvent(MKEY_Abort, false);
|
|
||||||
return Super::MenuEvent(key, fromcontroller);
|
|
||||||
}
|
|
||||||
if (fromcontroller)
|
|
||||||
{
|
|
||||||
mInputGridOkay = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mInputGridOkay)
|
|
||||||
{
|
|
||||||
int ch;
|
|
||||||
|
|
||||||
if (InputGridX == -1 || InputGridY == -1)
|
|
||||||
{
|
|
||||||
InputGridX = InputGridY = 0;
|
|
||||||
}
|
|
||||||
switch (key)
|
|
||||||
{
|
|
||||||
case MKEY_Down:
|
|
||||||
InputGridY = (InputGridY + 1) % INPUTGRID_HEIGHT;
|
|
||||||
return true;
|
|
||||||
|
|
||||||
case MKEY_Up:
|
|
||||||
InputGridY = (InputGridY + INPUTGRID_HEIGHT - 1) % INPUTGRID_HEIGHT;
|
|
||||||
return true;
|
|
||||||
|
|
||||||
case MKEY_Right:
|
|
||||||
InputGridX = (InputGridX + 1) % INPUTGRID_WIDTH;
|
|
||||||
return true;
|
|
||||||
|
|
||||||
case MKEY_Left:
|
|
||||||
InputGridX = (InputGridX + INPUTGRID_WIDTH - 1) % INPUTGRID_WIDTH;
|
|
||||||
return true;
|
|
||||||
|
|
||||||
case MKEY_Clear:
|
|
||||||
if (mEnterString.Len() > 0)
|
|
||||||
{
|
|
||||||
mEnterString.DeleteLastCharacter();
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
|
|
||||||
case MKEY_Enter:
|
|
||||||
assert(unsigned(InputGridX) < INPUTGRID_WIDTH && unsigned(InputGridY) < INPUTGRID_HEIGHT);
|
|
||||||
if (mInputGridOkay)
|
|
||||||
{
|
|
||||||
ch = InputGridChars[InputGridX + InputGridY * INPUTGRID_WIDTH];
|
|
||||||
if (ch == 0) // end
|
|
||||||
{
|
|
||||||
if (mEnterString.Len() > 0)
|
|
||||||
{
|
|
||||||
DMenu *parent = mParentMenu;
|
|
||||||
parent->MenuEvent(MKEY_Input, false);
|
|
||||||
Close();
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (ch == '\b') // bs
|
|
||||||
{
|
|
||||||
if (mEnterString.Len() > 0)
|
|
||||||
{
|
|
||||||
mEnterString.DeleteLastCharacter();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
AppendChar(ch);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
|
|
||||||
default:
|
|
||||||
break; // Keep GCC quiet
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void DTextEnterMenu::Drawer ()
|
|
||||||
{
|
|
||||||
mParentMenu->Drawer();
|
|
||||||
if (mInputGridOkay)
|
|
||||||
{
|
|
||||||
const int cell_width = 18 * CleanXfac;
|
|
||||||
const int cell_height = 12 * CleanYfac;
|
|
||||||
const int top_padding = cell_height / 2 - displayFont->GetHeight() * CleanYfac / 2;
|
|
||||||
|
|
||||||
// Darken the background behind the character grid.
|
|
||||||
// Unless we frame it with a border, I think it looks better to extend the
|
|
||||||
// background across the full width of the screen.
|
|
||||||
twod->AddColorOnlyQuad(0 /*screen->GetWidth()/2 - 13 * cell_width / 2*/,
|
|
||||||
screen->GetHeight() - INPUTGRID_HEIGHT * cell_height,
|
|
||||||
screen->GetWidth() /*13 * cell_width*/,
|
|
||||||
INPUTGRID_HEIGHT * cell_height, 0xc8000000);
|
|
||||||
|
|
||||||
if (InputGridX >= 0 && InputGridY >= 0)
|
|
||||||
{
|
|
||||||
// Highlight the background behind the selected character.
|
|
||||||
twod->AddColorOnlyQuad(
|
|
||||||
InputGridX * cell_width - INPUTGRID_WIDTH * cell_width / 2 + screen->GetWidth() / 2,
|
|
||||||
InputGridY * cell_height - INPUTGRID_HEIGHT * cell_height + screen->GetHeight(),
|
|
||||||
cell_width, cell_height, PalEntry(255, 255, 248, 220));
|
|
||||||
}
|
|
||||||
|
|
||||||
for (int y = 0; y < INPUTGRID_HEIGHT; ++y)
|
|
||||||
{
|
|
||||||
const int yy = y * cell_height - INPUTGRID_HEIGHT * cell_height + screen->GetHeight();
|
|
||||||
for (int x = 0; x < INPUTGRID_WIDTH; ++x)
|
|
||||||
{
|
|
||||||
int width;
|
|
||||||
const int xx = x * cell_width - INPUTGRID_WIDTH * cell_width / 2 + screen->GetWidth() / 2;
|
|
||||||
const int ch = InputGridChars[y * INPUTGRID_WIDTH + x];
|
|
||||||
auto pic = displayFont->GetChar(ch, CR_DARKGRAY, &width);
|
|
||||||
EColorRange color;
|
|
||||||
int remap;
|
|
||||||
|
|
||||||
// The highlighted character is yellow; the rest are dark gray.
|
|
||||||
color = (x == InputGridX && y == InputGridY) ? CR_YELLOW : CR_DARKGRAY;
|
|
||||||
remap = displayFont->GetColorTranslation(color);
|
|
||||||
|
|
||||||
if (pic != NULL)
|
|
||||||
{
|
|
||||||
// Draw a normal character.
|
|
||||||
DrawTexture(twod, pic, xx + cell_width/2 - width*CleanXfac_1/2, yy + top_padding,
|
|
||||||
DTA_TranslationIndex, remap,
|
|
||||||
DTA_CleanNoMove_1, true,
|
|
||||||
TAG_DONE);
|
|
||||||
}
|
|
||||||
else if (ch == ' ')
|
|
||||||
{
|
|
||||||
// Draw the space as a box outline. We also draw it 50% wider than it really is.
|
|
||||||
const int x1 = xx + cell_width/2 - width * CleanXfac_1 * 3 / 4;
|
|
||||||
const int x2 = x1 + width * 3 * CleanXfac_1 / 2;
|
|
||||||
const int y1 = yy + top_padding;
|
|
||||||
const int y2 = y1 + displayFont->GetHeight() * CleanYfac_1;
|
|
||||||
auto palcolor = PalEntry(255, 160, 160, 160);
|
|
||||||
twod->AddColorOnlyQuad(x1, y1, x2 - x1, CleanYfac_1, palcolor); // top
|
|
||||||
twod->AddColorOnlyQuad(x1, y2, x2 - x1, CleanYfac_1, palcolor); // bottom
|
|
||||||
twod->AddColorOnlyQuad(x1, y1+CleanYfac_1, CleanXfac_1, y2 - y1, palcolor); // left
|
|
||||||
twod->AddColorOnlyQuad(x2-CleanXfac_1, y1+CleanYfac_1, CleanXfac_1, CleanYfac_1, palcolor); // right
|
|
||||||
}
|
|
||||||
else if (ch == '\b' || ch == 0)
|
|
||||||
{
|
|
||||||
// Draw the backspace and end "characters".
|
|
||||||
const char *const str = ch == '\b' ? "BS" : "ED";
|
|
||||||
DrawText(twod, NewSmallFont, color,
|
|
||||||
xx + cell_width/2 - displayFont->StringWidth(str)*CleanXfac_1/2,
|
|
||||||
yy + top_padding, str, DTA_CleanNoMove_1, true, TAG_DONE);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Super::Drawer();
|
|
||||||
}
|
|
|
@ -32,87 +32,26 @@
|
||||||
**
|
**
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include <ctype.h>
|
||||||
#include "menu.h"
|
#include "menu.h"
|
||||||
#include "d_event.h"
|
|
||||||
#include "d_gui.h"
|
|
||||||
#include "v_text.h"
|
|
||||||
#include "v_draw.h"
|
|
||||||
#include "gstrings.h"
|
#include "gstrings.h"
|
||||||
|
#include "i_video.h"
|
||||||
#include "c_dispatch.h"
|
#include "c_dispatch.h"
|
||||||
#include "statistics.h"
|
#include "vm.h"
|
||||||
#include "v_2ddrawer.h"
|
#include "menustate.h"
|
||||||
#include "v_video.h"
|
|
||||||
#include "i_time.h"
|
|
||||||
#include "engineerrors.h"
|
|
||||||
|
|
||||||
extern FSaveGameNode *quickSaveSlot;
|
void M_StartControlPanel(bool makeSound, bool scaleoverride = false);
|
||||||
|
FName MessageBoxClass = NAME_MessageBoxMenu;
|
||||||
|
|
||||||
|
CVAR(Bool, m_quickexit, false, CVAR_ARCHIVE)
|
||||||
|
|
||||||
void GameInterface::DrawCenteredTextScreen(const DVector2& origin, const char* text, int position, bool bg)
|
typedef void(*hfunc)();
|
||||||
|
DEFINE_ACTION_FUNCTION(DMessageBoxMenu, CallHandler)
|
||||||
{
|
{
|
||||||
double scale = SmallFontScale();
|
PARAM_PROLOGUE;
|
||||||
int formatwidth = int(320 / scale);
|
PARAM_POINTERTYPE(Handler, hfunc);
|
||||||
auto lines = V_BreakLines(SmallFont, formatwidth, text, true);
|
Handler();
|
||||||
auto fheight = bg? 10 : SmallFont->GetHeight()* scale; // Fixme: Get spacing for text pages from elsewhere.
|
return 0;
|
||||||
if (!bg)
|
|
||||||
{
|
|
||||||
auto totaltextheight = lines.Size() * fheight;
|
|
||||||
position -= totaltextheight / 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
double y = origin.Y + position;
|
|
||||||
for (auto& line : lines)
|
|
||||||
{
|
|
||||||
double x = origin.X + 160 - line.Width * scale * 0.5;
|
|
||||||
DrawText(twod, SmallFont, CR_UNTRANSLATED, x, y, line.Text, DTA_FullscreenScale, FSMode_Fit320x200, DTA_ScaleX, scale, DTA_ScaleY, scale, TAG_DONE);
|
|
||||||
y += fheight;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
class DMessageBoxMenu : public DMenu
|
|
||||||
{
|
|
||||||
using Super = DMenu;
|
|
||||||
FString mFullMessage;
|
|
||||||
TArray<FBrokenLines> mMessage;
|
|
||||||
int mMessageMode;
|
|
||||||
int messageSelection;
|
|
||||||
int mMouseLeft, mMouseRight, mMouseY;
|
|
||||||
FName mAction;
|
|
||||||
std::function<bool(bool)> mActionFunc;
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
DMessageBoxMenu(DMenu *parent = NULL, const char *message = NULL, int messagemode = 0, bool playsound = false, FName action = NAME_None, hFunc handler = nullptr);
|
|
||||||
void Destroy();
|
|
||||||
void Init(DMenu *parent, const char *message, int messagemode, bool playsound = false);
|
|
||||||
void Drawer();
|
|
||||||
bool Responder(event_t *ev);
|
|
||||||
bool MenuEvent(int mkey, bool fromcontroller);
|
|
||||||
bool MouseEvent(int type, int x, int y);
|
|
||||||
void CloseSound();
|
|
||||||
virtual void HandleResult(bool res);
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
DMessageBoxMenu::DMessageBoxMenu(DMenu *parent, const char *message, int messagemode, bool playsound, FName action, hFunc handler)
|
|
||||||
: DMenu(parent)
|
|
||||||
{
|
|
||||||
mAction = action;
|
|
||||||
mActionFunc = handler;
|
|
||||||
messageSelection = 0;
|
|
||||||
mMouseLeft = 140;
|
|
||||||
mMouseY = INT_MIN;
|
|
||||||
int mr1 = 170 + SmallFont->StringWidth(GStrings["TXT_YES"]);
|
|
||||||
int mr2 = 170 + SmallFont->StringWidth(GStrings["TXT_NO"]);
|
|
||||||
mMouseRight = std::max(mr1, mr2);
|
|
||||||
|
|
||||||
Init(parent, message, messagemode, playsound);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
|
@ -121,20 +60,20 @@ DMessageBoxMenu::DMessageBoxMenu(DMenu *parent, const char *message, int message
|
||||||
//
|
//
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
|
|
||||||
void DMessageBoxMenu::Init(DMenu *parent, const char *message, int messagemode, bool playsound)
|
DMenu *CreateMessageBoxMenu(DMenu *parent, const char *message, int messagemode, bool playsound, FName action = NAME_None, hfunc handler = nullptr)
|
||||||
{
|
{
|
||||||
mParentMenu = parent;
|
auto c = PClass::FindClass(MessageBoxClass);
|
||||||
if (message != NULL)
|
if (!c->IsDescendantOf(NAME_MessageBoxMenu)) c = PClass::FindClass(NAME_MessageBoxMenu);
|
||||||
|
auto p = c->CreateNew();
|
||||||
|
FString namestr = message;
|
||||||
|
|
||||||
|
IFVIRTUALPTRNAME(p, NAME_MessageBoxMenu, Init)
|
||||||
{
|
{
|
||||||
mFullMessage = message;
|
VMValue params[] = { p, parent, &namestr, messagemode, playsound, action.GetIndex(), reinterpret_cast<void*>(handler) };
|
||||||
mMessage = V_BreakLines(SmallFont, 300, GStrings.localize(message));
|
VMCall(func, params, countof(params), nullptr, 0);
|
||||||
}
|
return (DMenu*)p;
|
||||||
mMessageMode = messagemode;
|
|
||||||
if (playsound)
|
|
||||||
{
|
|
||||||
//S_StopSound (CHAN_VOICE);
|
|
||||||
//S_Sound (CHAN_VOICE | CHANF_UI, "menu/prompt", snd_menuvolume, ATTN_NONE);
|
|
||||||
}
|
}
|
||||||
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
|
@ -143,326 +82,24 @@ void DMessageBoxMenu::Init(DMenu *parent, const char *message, int messagemode,
|
||||||
//
|
//
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
|
|
||||||
void DMessageBoxMenu::Destroy()
|
void M_StartMessage(const char *message, int messagemode, FName action)
|
||||||
{
|
|
||||||
mMessage.Reset();
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void DMessageBoxMenu::CloseSound()
|
|
||||||
{
|
|
||||||
M_MenuSound(CurrentMenu ? BackSound : ::CloseSound);
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void DMessageBoxMenu::HandleResult(bool res)
|
|
||||||
{
|
|
||||||
if (mMessageMode == 0)
|
|
||||||
{
|
|
||||||
if (mActionFunc)
|
|
||||||
{
|
|
||||||
if (mActionFunc(res)) Close();
|
|
||||||
}
|
|
||||||
else if (mAction == NAME_None && mParentMenu)
|
|
||||||
{
|
|
||||||
mParentMenu->MenuEvent(res ? MKEY_MBYes : MKEY_MBNo, false);
|
|
||||||
Close();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
Close();
|
|
||||||
if (res) M_SetMenu(mAction, -1);
|
|
||||||
}
|
|
||||||
CloseSound();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
CVAR(Bool, m_generic_messagebox, false, CVAR_ARCHIVE)
|
|
||||||
|
|
||||||
void DMessageBoxMenu::Drawer()
|
|
||||||
{
|
|
||||||
int y;
|
|
||||||
PalEntry fade = 0;
|
|
||||||
|
|
||||||
int fontheight = SmallFont->GetHeight();
|
|
||||||
//V_SetBorderNeedRefresh();
|
|
||||||
//ST_SetNeedRefresh();
|
|
||||||
|
|
||||||
y = 100;
|
|
||||||
|
|
||||||
if (m_generic_messagebox)
|
|
||||||
{
|
|
||||||
if (mMessage.Size())
|
|
||||||
{
|
|
||||||
for (unsigned i = 0; i < mMessage.Size(); i++)
|
|
||||||
y -= SmallFont->GetHeight() / 2;
|
|
||||||
|
|
||||||
for (unsigned i = 0; i < mMessage.Size(); i++)
|
|
||||||
{
|
|
||||||
DrawText(twod, SmallFont, CR_UNTRANSLATED, 160 - mMessage[i].Width / 2, y, mMessage[i].Text,
|
|
||||||
DTA_Clean, true, TAG_DONE);
|
|
||||||
y += fontheight;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mMessageMode == 0)
|
|
||||||
{
|
|
||||||
y += fontheight;
|
|
||||||
mMouseY = y;
|
|
||||||
DrawText(twod, SmallFont,
|
|
||||||
messageSelection == 0 ? OptionSettings.mFontColorSelection : OptionSettings.mFontColor,
|
|
||||||
160, y, GStrings["TXT_YES"], DTA_Clean, true, TAG_DONE);
|
|
||||||
DrawText(twod, SmallFont,
|
|
||||||
messageSelection == 1 ? OptionSettings.mFontColorSelection : OptionSettings.mFontColor,
|
|
||||||
160, y + fontheight + 1, GStrings["TXT_NO"], DTA_Clean, true, TAG_DONE);
|
|
||||||
|
|
||||||
if (messageSelection >= 0)
|
|
||||||
{
|
|
||||||
auto time = I_msTime() / 30;
|
|
||||||
if (((time >> 2) % 8) < 6)
|
|
||||||
{
|
|
||||||
DrawText(twod, SmallFont, OptionSettings.mFontColorSelection,
|
|
||||||
(150 - 160) * CleanXfac + screen->GetWidth() / 2,
|
|
||||||
(y + (fontheight + 1) * messageSelection - 100 + fontheight / 2 - 5) * CleanYfac + screen->GetHeight() / 2,
|
|
||||||
"\xd",
|
|
||||||
DTA_CellX, 8 * CleanXfac,
|
|
||||||
DTA_CellY, 8 * CleanYfac,
|
|
||||||
TAG_DONE);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
twod->ClearScreen(0xa0000000);
|
|
||||||
gi->DrawCenteredTextScreen(origin, mFullMessage, 100, false);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
bool DMessageBoxMenu::Responder(event_t *ev)
|
|
||||||
{
|
|
||||||
if (ev->type == EV_GUI_Event && ev->subtype == EV_GUI_KeyDown)
|
|
||||||
{
|
|
||||||
if (mMessageMode == 0)
|
|
||||||
{
|
|
||||||
int ch = tolower(ev->data1);
|
|
||||||
if (ch == 'n' || ch == ' ')
|
|
||||||
{
|
|
||||||
HandleResult(false);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
else if (ch == 'y')
|
|
||||||
{
|
|
||||||
HandleResult(true);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
Close();
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
else if (ev->type == EV_KeyDown)
|
|
||||||
{
|
|
||||||
Close();
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
return Super::Responder(ev);
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
bool DMessageBoxMenu::MenuEvent(int mkey, bool fromcontroller)
|
|
||||||
{
|
|
||||||
if (mMessageMode == 0)
|
|
||||||
{
|
|
||||||
if ((mkey == MKEY_Up || mkey == MKEY_Down) && m_generic_messagebox)
|
|
||||||
{
|
|
||||||
//S_Sound (CHAN_VOICE | CHANF_UI, "menu/cursor", snd_menuvolume, ATTN_NONE);
|
|
||||||
messageSelection = !messageSelection;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
else if (mkey == MKEY_Enter)
|
|
||||||
{
|
|
||||||
// 0 is yes, 1 is no
|
|
||||||
HandleResult(!messageSelection);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
else if (mkey == MKEY_Back)
|
|
||||||
{
|
|
||||||
HandleResult(false);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
Close();
|
|
||||||
CloseSound();
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
bool DMessageBoxMenu::MouseEvent(int type, int x, int y)
|
|
||||||
{
|
|
||||||
if (mMessageMode == 1 || m_generic_messagebox)
|
|
||||||
{
|
|
||||||
if (type == MOUSE_Click)
|
|
||||||
{
|
|
||||||
return MenuEvent(MKEY_Enter, true);
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
int sel = -1;
|
|
||||||
int fh = SmallFont->GetHeight() + 1;
|
|
||||||
|
|
||||||
// convert x/y from screen to virtual coordinates, according to CleanX/Yfac use in DrawTexture
|
|
||||||
x = ((x - (screen->GetWidth() / 2)) / CleanXfac) + 160;
|
|
||||||
y = ((y - (screen->GetHeight() / 2)) / CleanYfac) + 100;
|
|
||||||
|
|
||||||
if (x >= mMouseLeft && x <= mMouseRight && y >= mMouseY && y < mMouseY + 2 * fh)
|
|
||||||
{
|
|
||||||
sel = y >= mMouseY + fh;
|
|
||||||
}
|
|
||||||
if (sel != -1 && sel != messageSelection)
|
|
||||||
{
|
|
||||||
M_MenuSound(CursorSound);
|
|
||||||
}
|
|
||||||
messageSelection = sel;
|
|
||||||
if (type == MOUSE_Release)
|
|
||||||
{
|
|
||||||
return MenuEvent(MKEY_Enter, true);
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void M_StartMessage(const char *message, int messagemode, int scriptId, FName action)
|
|
||||||
{
|
{
|
||||||
if (CurrentMenu == NULL)
|
if (CurrentMenu == NULL)
|
||||||
{
|
{
|
||||||
// only play a sound if no menu was active before
|
// only play a sound if no menu was active before
|
||||||
M_StartControlPanel(menuactive == MENU_Off);
|
M_StartControlPanel(menuactive == MENU_Off);
|
||||||
}
|
}
|
||||||
DMenu *newmenu = new DMessageBoxMenu(CurrentMenu, message, messagemode, false, action);
|
DMenu *newmenu = CreateMessageBoxMenu(CurrentMenu, message, messagemode, false, action);
|
||||||
newmenu->mParentMenu = CurrentMenu;
|
newmenu->mParentMenu = CurrentMenu;
|
||||||
newmenu->scriptID = scriptId;
|
|
||||||
M_ActivateMenu(newmenu);
|
M_ActivateMenu(newmenu);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DEFINE_ACTION_FUNCTION(DMenu, StartMessage)
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
DMenu* CreateMessageBoxMenu(DMenu* parent, const char* message, int messagemode, int scriptId, bool playsound, FName action, hFunc handler)
|
|
||||||
{
|
{
|
||||||
auto newmenu = new DMessageBoxMenu(CurrentMenu, message, messagemode, false, action, handler);
|
PARAM_PROLOGUE;
|
||||||
newmenu->scriptID = scriptId;
|
PARAM_STRING(msg);
|
||||||
return newmenu;
|
PARAM_INT(mode);
|
||||||
|
PARAM_NAME(action);
|
||||||
|
M_StartMessage(msg, mode, action);
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void ActivateEndGameMenu()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
CCMD (menu_endgame)
|
|
||||||
{ // F7
|
|
||||||
if (!gi->CanSave())
|
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
M_StartControlPanel (true);
|
|
||||||
FString tempstring;
|
|
||||||
tempstring << GStrings("ENDGAME") << "\n\n" << GStrings("PRESSYN");
|
|
||||||
DMenu* newmenu = CreateMessageBoxMenu(CurrentMenu, tempstring, 0, 501, false, NAME_None, [](bool res)
|
|
||||||
{
|
|
||||||
if (res)
|
|
||||||
{
|
|
||||||
STAT_Cancel();
|
|
||||||
M_ClearMenus();
|
|
||||||
gi->QuitToTitle();
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
});
|
|
||||||
|
|
||||||
M_ActivateMenu(newmenu);
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
CCMD (menu_quit)
|
|
||||||
{ // F10
|
|
||||||
|
|
||||||
M_StartControlPanel (true);
|
|
||||||
|
|
||||||
FString EndString;
|
|
||||||
EndString << GStrings("CONFIRM_QUITMSG") << "\n\n" << GStrings("PRESSYN");
|
|
||||||
|
|
||||||
DMenu *newmenu = CreateMessageBoxMenu(CurrentMenu, EndString, 0, 500, false, NAME_None, [](bool res)
|
|
||||||
{
|
|
||||||
if (res) gi->ExitFromMenu();
|
|
||||||
return true;
|
|
||||||
});
|
|
||||||
|
|
||||||
M_ActivateMenu(newmenu);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
** Handler class for the option menus and associated items
|
** Handler class for the option menus and associated items
|
||||||
**
|
**
|
||||||
**---------------------------------------------------------------------------
|
**---------------------------------------------------------------------------
|
||||||
** Copyright 2010 Christoph Oelckers
|
** Copyright 2010-2017 Christoph Oelckers
|
||||||
** All rights reserved.
|
** All rights reserved.
|
||||||
**
|
**
|
||||||
** Redistribution and use in source and binary forms, with or without
|
** Redistribution and use in source and binary forms, with or without
|
||||||
|
@ -32,54 +32,10 @@
|
||||||
**
|
**
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "v_font.h"
|
|
||||||
#include "cmdlib.h"
|
|
||||||
#include "gstrings.h"
|
|
||||||
#include "d_gui.h"
|
|
||||||
#include "d_event.h"
|
|
||||||
#include "c_dispatch.h"
|
|
||||||
#include "c_console.h"
|
|
||||||
#include "c_cvars.h"
|
|
||||||
#include "c_bind.h"
|
|
||||||
#include "gameconfigfile.h"
|
|
||||||
#include "menu.h"
|
|
||||||
#include "v_draw.h"
|
|
||||||
#include "v_2ddrawer.h"
|
|
||||||
#include "v_video.h"
|
#include "v_video.h"
|
||||||
#include "i_time.h"
|
#include "menu.h"
|
||||||
|
#include "vm.h"
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
// Draws a string in the console font, scaled to the 8x8 cells
|
|
||||||
// used by the default console font.
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
FFont *OptionFont()
|
|
||||||
{
|
|
||||||
return NewSmallFont;
|
|
||||||
}
|
|
||||||
|
|
||||||
int OptionHeight()
|
|
||||||
{
|
|
||||||
return OptionFont()->GetHeight();
|
|
||||||
}
|
|
||||||
|
|
||||||
int OptionWidth(const char * s)
|
|
||||||
{
|
|
||||||
return OptionFont()->StringWidth(s);
|
|
||||||
}
|
|
||||||
|
|
||||||
void DrawOptionText(int x, int y, int color, const char *text, bool grayed)
|
|
||||||
{
|
|
||||||
PalEntry overlay = grayed? PalEntry(96,48,0,0) : PalEntry(0,0,0);
|
|
||||||
DrawText (twod, OptionFont(), color, x, y, text, DTA_CleanNoMove_1, true, DTA_ColorOverlay, overlay, TAG_END);
|
|
||||||
}
|
|
||||||
|
|
||||||
int DOptionMenu::GetPosition()
|
|
||||||
{
|
|
||||||
return mDesc->mPosition * screen->GetHeight() * 2 / CleanYfac_1 / 1080; // y position uses a 1920x1080 screen as reference but has to adjust to scaled 320x200 content.
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
//
|
//
|
||||||
|
@ -87,483 +43,26 @@ int DOptionMenu::GetPosition()
|
||||||
//
|
//
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
|
|
||||||
DOptionMenu::DOptionMenu(DMenu *parent, FOptionMenuDescriptor *desc)
|
DMenuItemBase *DOptionMenuDescriptor::GetItem(FName name)
|
||||||
: DMenu(parent)
|
|
||||||
{
|
|
||||||
CanScrollUp = false;
|
|
||||||
CanScrollDown = false;
|
|
||||||
VisBottom = 0;
|
|
||||||
mFocusControl = NULL;
|
|
||||||
Init(parent, desc);
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void DOptionMenu::Init(DMenu *parent, FOptionMenuDescriptor *desc)
|
|
||||||
{
|
|
||||||
mParentMenu = parent;
|
|
||||||
mDesc = desc;
|
|
||||||
if (mDesc != NULL && mDesc->mSelectedItem == -1) mDesc->mSelectedItem = FirstSelectable();
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
int DOptionMenu::FirstSelectable()
|
|
||||||
{
|
|
||||||
if (mDesc != NULL)
|
|
||||||
{
|
|
||||||
// Go down to the first selectable item
|
|
||||||
int i = -1;
|
|
||||||
do
|
|
||||||
{
|
|
||||||
i++;
|
|
||||||
}
|
|
||||||
while (i < (int)mDesc->mItems.Size() && !mDesc->mItems[i]->Selectable());
|
|
||||||
if (i>=0 && i < (int)mDesc->mItems.Size()) return i;
|
|
||||||
}
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
FOptionMenuItem *DOptionMenu::GetItem(FName name)
|
|
||||||
{
|
|
||||||
for(unsigned i=0;i<mDesc->mItems.Size(); i++)
|
|
||||||
{
|
|
||||||
FName nm = mDesc->mItems[i]->GetAction(NULL);
|
|
||||||
if (nm == name) return mDesc->mItems[i];
|
|
||||||
}
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
bool DOptionMenu::Responder (event_t *ev)
|
|
||||||
{
|
|
||||||
if (ev->type == EV_GUI_Event)
|
|
||||||
{
|
|
||||||
if (ev->subtype == EV_GUI_WheelUp)
|
|
||||||
{
|
|
||||||
int scrollamt = std::min(2, mDesc->mScrollPos);
|
|
||||||
mDesc->mScrollPos -= scrollamt;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
else if (ev->subtype == EV_GUI_WheelDown)
|
|
||||||
{
|
|
||||||
if (CanScrollDown)
|
|
||||||
{
|
|
||||||
if (VisBottom < (int)(mDesc->mItems.Size()-2))
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos += 2;
|
|
||||||
VisBottom += 2;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos++;
|
|
||||||
VisBottom++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return Super::Responder(ev);
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
bool DOptionMenu::MenuEvent (int mkey, bool fromcontroller)
|
|
||||||
{
|
|
||||||
int startedAt = mDesc->mSelectedItem;
|
|
||||||
|
|
||||||
switch (mkey)
|
|
||||||
{
|
|
||||||
case MKEY_Up:
|
|
||||||
if (mDesc->mSelectedItem == -1)
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = FirstSelectable();
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
do
|
|
||||||
{
|
|
||||||
--mDesc->mSelectedItem;
|
|
||||||
|
|
||||||
if (mDesc->mScrollPos > 0 &&
|
|
||||||
mDesc->mSelectedItem <= mDesc->mScrollTop + mDesc->mScrollPos)
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos = std::max(mDesc->mSelectedItem - mDesc->mScrollTop - 1, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mDesc->mSelectedItem < 0)
|
|
||||||
{
|
|
||||||
// Figure out how many lines of text fit on the menu
|
|
||||||
int y = GetPosition();
|
|
||||||
|
|
||||||
y *= CleanYfac_1;
|
|
||||||
int rowheight = OptionSettings.mLinespacing * CleanYfac_1;
|
|
||||||
int maxitems = (screen->GetHeight() - rowheight - y) / rowheight + 1;
|
|
||||||
|
|
||||||
mDesc->mScrollPos = std::max(0, (int)mDesc->mItems.Size() - maxitems + mDesc->mScrollTop);
|
|
||||||
mDesc->mSelectedItem = mDesc->mItems.Size()-1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
while (!mDesc->mItems[mDesc->mSelectedItem]->Selectable() && mDesc->mSelectedItem != startedAt);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case MKEY_Down:
|
|
||||||
if (mDesc->mSelectedItem == -1)
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = FirstSelectable();
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
do
|
|
||||||
{
|
|
||||||
++mDesc->mSelectedItem;
|
|
||||||
|
|
||||||
if (CanScrollDown && mDesc->mSelectedItem == VisBottom)
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos++;
|
|
||||||
VisBottom++;
|
|
||||||
}
|
|
||||||
if (mDesc->mSelectedItem >= (int)mDesc->mItems.Size())
|
|
||||||
{
|
|
||||||
if (startedAt == -1)
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = -1;
|
|
||||||
mDesc->mScrollPos = -1;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = 0;
|
|
||||||
mDesc->mScrollPos = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
while (!mDesc->mItems[mDesc->mSelectedItem]->Selectable() && mDesc->mSelectedItem != startedAt);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case MKEY_PageUp:
|
|
||||||
if (mDesc->mScrollPos > 0)
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos -= VisBottom - mDesc->mScrollPos - mDesc->mScrollTop;
|
|
||||||
if (mDesc->mScrollPos < 0)
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos = 0;
|
|
||||||
}
|
|
||||||
if (mDesc->mSelectedItem != -1)
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = mDesc->mScrollTop + mDesc->mScrollPos + 1;
|
|
||||||
while (!mDesc->mItems[mDesc->mSelectedItem]->Selectable())
|
|
||||||
{
|
|
||||||
if (++mDesc->mSelectedItem >= (int)mDesc->mItems.Size())
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (mDesc->mScrollPos > mDesc->mSelectedItem)
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos = mDesc->mSelectedItem;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
|
|
||||||
case MKEY_PageDown:
|
|
||||||
if (CanScrollDown)
|
|
||||||
{
|
|
||||||
int pagesize = VisBottom - mDesc->mScrollPos - mDesc->mScrollTop;
|
|
||||||
mDesc->mScrollPos += pagesize;
|
|
||||||
if (mDesc->mScrollPos + mDesc->mScrollTop + pagesize > (int)mDesc->mItems.Size())
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos = mDesc->mItems.Size() - mDesc->mScrollTop - pagesize;
|
|
||||||
}
|
|
||||||
if (mDesc->mSelectedItem != -1)
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = mDesc->mScrollTop + mDesc->mScrollPos;
|
|
||||||
while (!mDesc->mItems[mDesc->mSelectedItem]->Selectable())
|
|
||||||
{
|
|
||||||
if (++mDesc->mSelectedItem >= (int)mDesc->mItems.Size())
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (mDesc->mScrollPos > mDesc->mSelectedItem)
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos = mDesc->mSelectedItem;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
|
|
||||||
case MKEY_Enter:
|
|
||||||
if (mDesc->mSelectedItem >= 0 && mDesc->mItems[mDesc->mSelectedItem]->Activate(mDesc->mMenuName))
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
// fall through to default
|
|
||||||
default:
|
|
||||||
if (mDesc->mSelectedItem >= 0 &&
|
|
||||||
mDesc->mItems[mDesc->mSelectedItem]->MenuEvent(mkey, fromcontroller)) return true;
|
|
||||||
return Super::MenuEvent(mkey, fromcontroller);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mDesc->mSelectedItem != startedAt)
|
|
||||||
{
|
|
||||||
M_MenuSound(CursorSound);
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
bool DOptionMenu::MouseEvent(int type, int x, int y)
|
|
||||||
{
|
|
||||||
y = (y / CleanYfac_1) - mDesc->mDrawTop;
|
|
||||||
|
|
||||||
if (mFocusControl)
|
|
||||||
{
|
|
||||||
mFocusControl->MouseEvent(type, x, y);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
int yline = (y / OptionSettings.mLinespacing);
|
|
||||||
if (yline >= mDesc->mScrollTop)
|
|
||||||
{
|
|
||||||
yline += mDesc->mScrollPos;
|
|
||||||
}
|
|
||||||
if ((unsigned)yline < mDesc->mItems.Size() && mDesc->mItems[yline]->Selectable())
|
|
||||||
{
|
|
||||||
if (yline != mDesc->mSelectedItem)
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = yline;
|
|
||||||
//M_MenuSound(CursorSound); too noisy
|
|
||||||
|
|
||||||
}
|
|
||||||
mDesc->mItems[yline]->MouseEvent(type, x, y);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
mDesc->mSelectedItem = -1;
|
|
||||||
return Super::MouseEvent(type, x, y);
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void DOptionMenu::Ticker ()
|
|
||||||
{
|
|
||||||
Super::Ticker();
|
|
||||||
for(unsigned i=0;i<mDesc->mItems.Size(); i++)
|
|
||||||
{
|
|
||||||
mDesc->mItems[i]->Ticker();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
int DOptionMenu::GetIndent()
|
|
||||||
{
|
|
||||||
int indent = std::max(0, (mDesc->mIndent + 40) - CleanWidth_1 / 2);
|
|
||||||
return screen->GetWidth() / 2 + indent * CleanXfac_1;
|
|
||||||
}
|
|
||||||
|
|
||||||
void DOptionMenu::Drawer ()
|
|
||||||
{
|
|
||||||
int y = GetPosition();
|
|
||||||
|
|
||||||
if (mDesc->mTitle.IsNotEmpty())
|
|
||||||
{
|
|
||||||
gi->DrawMenuCaption(origin, GStrings.localize(mDesc->mTitle));
|
|
||||||
}
|
|
||||||
mDesc->mDrawTop = y;
|
|
||||||
int fontheight = OptionSettings.mLinespacing * CleanYfac_1;
|
|
||||||
y *= CleanYfac_1;
|
|
||||||
|
|
||||||
int indent = GetIndent();
|
|
||||||
|
|
||||||
int ytop = y + mDesc->mScrollTop * 8 * CleanYfac_1;
|
|
||||||
int lastrow = screen->GetHeight() - OptionFont()->GetHeight() * CleanYfac_1;
|
|
||||||
|
|
||||||
unsigned i;
|
|
||||||
for (i = 0; i < mDesc->mItems.Size() && y <= lastrow; i++, y += fontheight)
|
|
||||||
{
|
|
||||||
// Don't scroll the uppermost items
|
|
||||||
if ((int)i == mDesc->mScrollTop)
|
|
||||||
{
|
|
||||||
i += mDesc->mScrollPos;
|
|
||||||
if (i >= mDesc->mItems.Size()) break; // skipped beyond end of menu
|
|
||||||
}
|
|
||||||
bool isSelected = mDesc->mSelectedItem == (int)i;
|
|
||||||
int cur_indent = mDesc->mItems[i]->Draw(mDesc, y, indent, isSelected);
|
|
||||||
if (cur_indent >= 0 && isSelected && mDesc->mItems[i]->Selectable())
|
|
||||||
{
|
|
||||||
auto time = I_msTime() / 30;
|
|
||||||
if ((((time>>2)%8) < 6) || CurrentMenu != this)
|
|
||||||
{
|
|
||||||
DrawOptionText(cur_indent + 3 * CleanXfac_1, y, OptionSettings.mFontColorSelection, "◄");
|
|
||||||
//M_DrawConText(OptionSettings.mFontColorSelection, cur_indent + 3 * CleanXfac_1, y+fontheight-9*CleanYfac_1, "\xd");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
CanScrollUp = (mDesc->mScrollPos > 0);
|
|
||||||
CanScrollDown = (i < mDesc->mItems.Size());
|
|
||||||
VisBottom = i - 1;
|
|
||||||
|
|
||||||
if (CanScrollUp)
|
|
||||||
{
|
|
||||||
DrawOptionText(screen->GetWidth() - 11 * CleanXfac_1, ytop, OptionSettings.mFontColorSelection, "▲");
|
|
||||||
//M_DrawConText(CR_ORANGE, 3 * CleanXfac_1, ytop, "\x1a");
|
|
||||||
}
|
|
||||||
if (CanScrollDown)
|
|
||||||
{
|
|
||||||
DrawOptionText(screen->GetWidth() - 11 * CleanXfac_1 , y - 8*CleanYfac_1, OptionSettings.mFontColorSelection, "▼");
|
|
||||||
//M_DrawConText(CR_ORANGE, 3 * CleanXfac_1, y - 8*CleanYfac_1, "\x1b");
|
|
||||||
}
|
|
||||||
Super::Drawer();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
// base class for menu items
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
FOptionMenuItem::~FOptionMenuItem()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
int FOptionMenuItem::Draw(FOptionMenuDescriptor *desc, int y, int indent, bool selected)
|
|
||||||
{
|
|
||||||
return indent;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool FOptionMenuItem::Selectable()
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool FOptionMenuItem::MouseEvent(int type, int x, int y)
|
|
||||||
{
|
|
||||||
if (Selectable() && type == DMenu::MOUSE_Release)
|
|
||||||
{
|
|
||||||
return CurrentMenu->MenuEvent(MKEY_Enter, true);
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int FOptionMenuItem::GetIndent()
|
|
||||||
{
|
|
||||||
if (mCentered) return 0;
|
|
||||||
if (screen->GetWidth() < 640) return screen->GetWidth() / 2;
|
|
||||||
return OptionWidth(GStrings.localize(mLabel));
|
|
||||||
}
|
|
||||||
|
|
||||||
void FOptionMenuItem::drawText(int x, int y, int color, const char * text, bool grayed)
|
|
||||||
{
|
|
||||||
DrawOptionText(x, y, color, text, grayed);
|
|
||||||
}
|
|
||||||
|
|
||||||
int FOptionMenuItem::drawLabel(int indent, int y, EColorRange color, bool grayed)
|
|
||||||
{
|
|
||||||
const char *label = GStrings.localize(mLabel);
|
|
||||||
int x;
|
|
||||||
int w = OptionWidth(label) * CleanXfac_1;
|
|
||||||
if (!mCentered) x = indent - w;
|
|
||||||
else x = (screen->GetWidth() - w) / 2;
|
|
||||||
DrawOptionText(x, y, color, label, grayed);
|
|
||||||
return x;
|
|
||||||
}
|
|
||||||
|
|
||||||
void FOptionMenuItem::drawValue(int indent, int y, int color, const char *text, bool grayed)
|
|
||||||
{
|
|
||||||
DrawOptionText(indent + CursorSpace(), y, color, text, grayed);
|
|
||||||
}
|
|
||||||
|
|
||||||
int FOptionMenuItem::CursorSpace()
|
|
||||||
{
|
|
||||||
return (14 * CleanXfac_1);
|
|
||||||
}
|
|
||||||
|
|
||||||
void FOptionMenuDescriptor::CalcIndent()
|
|
||||||
{
|
|
||||||
// calculate the menu indent
|
|
||||||
int widest = 0, thiswidth;
|
|
||||||
|
|
||||||
for (unsigned i = 0; i < mItems.Size(); i++)
|
|
||||||
{
|
|
||||||
thiswidth = mItems[i]->GetIndent();
|
|
||||||
if (thiswidth > widest) widest = thiswidth;
|
|
||||||
}
|
|
||||||
mIndent = widest + 4;
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
FOptionMenuItem *FOptionMenuDescriptor::GetItem(FName name)
|
|
||||||
{
|
{
|
||||||
for(unsigned i=0;i<mItems.Size(); i++)
|
for(unsigned i=0;i<mItems.Size(); i++)
|
||||||
{
|
{
|
||||||
FName nm = mItems[i]->GetAction(NULL);
|
FName nm = mItems[i]->mAction;
|
||||||
if (nm == name) return mItems[i];
|
if (nm == name) return mItems[i];
|
||||||
}
|
}
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
class PlayerMenu : public DOptionMenu
|
void SetCVarDescription(FBaseCVar* cvar, const FString* label)
|
||||||
{
|
{
|
||||||
using Super = DOptionMenu;
|
cvar->AddDescription(*label);
|
||||||
|
}
|
||||||
public:
|
|
||||||
void Drawer()
|
DEFINE_ACTION_FUNCTION_NATIVE(_OptionMenuItemOption, SetCVarDescription, SetCVarDescription)
|
||||||
{
|
{
|
||||||
// Hack: The team item is #3. This part doesn't work properly yet.
|
PARAM_PROLOGUE;
|
||||||
gi->DrawPlayerSprite(origin, (mDesc->mSelectedItem == 3));
|
PARAM_POINTER(cv, FBaseCVar);
|
||||||
Super::Drawer();
|
PARAM_STRING(label);
|
||||||
}
|
SetCVarDescription(cv, &label);
|
||||||
};
|
return 0;
|
||||||
|
|
||||||
static TMenuClassDescriptor<PlayerMenu> _ppm("NewPlayerMenu");
|
|
||||||
|
|
||||||
void RegisterOptionMenus()
|
|
||||||
{
|
|
||||||
menuClasses.Push(&_ppm);
|
|
||||||
}
|
}
|
File diff suppressed because it is too large
Load diff
257
source/core/menu/playermenu.cpp
Normal file
257
source/core/menu/playermenu.cpp
Normal file
|
@ -0,0 +1,257 @@
|
||||||
|
/*
|
||||||
|
** playermenu.cpp
|
||||||
|
** The player setup menu's setters. These are native for security purposes.
|
||||||
|
**
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
** Copyright 2001-2010 Randy Heit
|
||||||
|
** Copyright 2010 Christoph Oelckers
|
||||||
|
** All rights reserved.
|
||||||
|
**
|
||||||
|
** Redistribution and use in source and binary forms, with or without
|
||||||
|
** modification, are permitted provided that the following conditions
|
||||||
|
** are met:
|
||||||
|
**
|
||||||
|
** 1. Redistributions of source code must retain the above copyright
|
||||||
|
** notice, this list of conditions and the following disclaimer.
|
||||||
|
** 2. Redistributions in binary form must reproduce the above copyright
|
||||||
|
** notice, this list of conditions and the following disclaimer in the
|
||||||
|
** documentation and/or other materials provided with the distribution.
|
||||||
|
** 3. The name of the author may not be used to endorse or promote products
|
||||||
|
** derived from this software without specific prior written permission.
|
||||||
|
**
|
||||||
|
** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
|
||||||
|
** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
||||||
|
** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||||
|
** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
|
||||||
|
** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
||||||
|
** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||||
|
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||||
|
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||||
|
** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
**
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "menu.h"
|
||||||
|
#include "c_dispatch.h"
|
||||||
|
#include "vm.h"
|
||||||
|
|
||||||
|
EXTERN_CVAR(Int, team)
|
||||||
|
EXTERN_CVAR(Float, autoaim)
|
||||||
|
EXTERN_CVAR(Bool, neverswitchonpickup)
|
||||||
|
EXTERN_CVAR(Bool, cl_run)
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
#if 0
|
||||||
|
DEFINE_ACTION_FUNCTION(DPlayerMenu, ColorChanged)
|
||||||
|
{
|
||||||
|
PARAM_PROLOGUE;
|
||||||
|
PARAM_INT(r);
|
||||||
|
PARAM_INT(g);
|
||||||
|
PARAM_INT(b);
|
||||||
|
// only allow if the menu is active to prevent abuse.
|
||||||
|
if (DMenu::InMenu)
|
||||||
|
{
|
||||||
|
char command[24];
|
||||||
|
players[consoleplayer].userinfo.ColorChanged(MAKERGB(r, g, b));
|
||||||
|
mysnprintf(command, countof(command), "color \"%02x %02x %02x\"", r, g, b);
|
||||||
|
C_DoCommand(command);
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
// access to the player config is done natively, so that broader access
|
||||||
|
// functions do not need to be exported.
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
DEFINE_ACTION_FUNCTION(DPlayerMenu, PlayerNameChanged)
|
||||||
|
{
|
||||||
|
#if 0
|
||||||
|
PARAM_PROLOGUE;
|
||||||
|
PARAM_STRING(s);
|
||||||
|
const char *pp = s;
|
||||||
|
FString command("name \"");
|
||||||
|
|
||||||
|
if (DMenu::InMenu)
|
||||||
|
{
|
||||||
|
// Escape any backslashes or quotation marks before sending the name to the console.
|
||||||
|
for (auto p = pp; *p != '\0'; ++p)
|
||||||
|
{
|
||||||
|
if (*p == '"' || *p == '\\')
|
||||||
|
{
|
||||||
|
command << '\\';
|
||||||
|
}
|
||||||
|
command << *p;
|
||||||
|
}
|
||||||
|
command << '"';
|
||||||
|
C_DoCommand(command);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
#if 0
|
||||||
|
DEFINE_ACTION_FUNCTION(DPlayerMenu, ColorSetChanged)
|
||||||
|
{
|
||||||
|
PARAM_PROLOGUE;
|
||||||
|
PARAM_INT(sel);
|
||||||
|
if (DMenu::InMenu)
|
||||||
|
{
|
||||||
|
players[consoleplayer].userinfo.ColorSetChanged(sel);
|
||||||
|
char command[24];
|
||||||
|
mysnprintf(command, countof(command), "colorset %d", sel);
|
||||||
|
C_DoCommand(command);
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
#if 0
|
||||||
|
DEFINE_ACTION_FUNCTION(DPlayerMenu, ClassChanged)
|
||||||
|
{
|
||||||
|
PARAM_PROLOGUE;
|
||||||
|
PARAM_INT(sel);
|
||||||
|
PARAM_POINTER(cls, FPlayerClass);
|
||||||
|
if (DMenu::InMenu)
|
||||||
|
{
|
||||||
|
const char *pclass = sel == -1 ? "Random" : GetPrintableDisplayName(cls->Type).GetChars();
|
||||||
|
players[consoleplayer].userinfo.PlayerClassChanged(pclass);
|
||||||
|
cvar_set("playerclass", pclass);
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
#if 0
|
||||||
|
DEFINE_ACTION_FUNCTION(DPlayerMenu, SkinChanged)
|
||||||
|
{
|
||||||
|
PARAM_PROLOGUE;
|
||||||
|
PARAM_INT(sel);
|
||||||
|
if (DMenu::InMenu)
|
||||||
|
{
|
||||||
|
players[consoleplayer].userinfo.SkinNumChanged(sel);
|
||||||
|
cvar_set("skin", Skins[sel].Name);
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
#if 0
|
||||||
|
DEFINE_ACTION_FUNCTION(DPlayerMenu, AutoaimChanged)
|
||||||
|
{
|
||||||
|
PARAM_PROLOGUE;
|
||||||
|
PARAM_FLOAT(val);
|
||||||
|
// only allow if the menu is active to prevent abuse.
|
||||||
|
if (DMenu::InMenu)
|
||||||
|
{
|
||||||
|
autoaim = float(val);
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
#if 0
|
||||||
|
DEFINE_ACTION_FUNCTION(DPlayerMenu, TeamChanged)
|
||||||
|
{
|
||||||
|
PARAM_PROLOGUE;
|
||||||
|
PARAM_INT(val);
|
||||||
|
// only allow if the menu is active to prevent abuse.
|
||||||
|
if (DMenu::InMenu)
|
||||||
|
{
|
||||||
|
team = val == 0 ? TEAM_NONE : val - 1;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
DEFINE_ACTION_FUNCTION(DPlayerMenu, GenderChanged)
|
||||||
|
{
|
||||||
|
PARAM_PROLOGUE;
|
||||||
|
PARAM_INT(v);
|
||||||
|
// only allow if the menu is active to prevent abuse.
|
||||||
|
if (DMenu::InMenu)
|
||||||
|
{
|
||||||
|
switch(v)
|
||||||
|
{
|
||||||
|
case 0: cvar_set("gender", "male"); break;
|
||||||
|
case 1: cvar_set("gender", "female"); break;
|
||||||
|
case 2: cvar_set("gender", "neutral"); break;
|
||||||
|
case 3: cvar_set("gender", "other"); break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
#if 0
|
||||||
|
DEFINE_ACTION_FUNCTION(DPlayerMenu, SwitchOnPickupChanged)
|
||||||
|
{
|
||||||
|
PARAM_PROLOGUE;
|
||||||
|
PARAM_INT(v);
|
||||||
|
// only allow if the menu is active to prevent abuse.
|
||||||
|
if (DMenu::InMenu)
|
||||||
|
{
|
||||||
|
neverswitchonpickup = !!v;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
#if 0
|
||||||
|
DEFINE_ACTION_FUNCTION(DPlayerMenu, AlwaysRunChanged)
|
||||||
|
{
|
||||||
|
PARAM_PROLOGUE;
|
||||||
|
PARAM_INT(v);
|
||||||
|
// only allow if the menu is active to prevent abuse.
|
||||||
|
if (DMenu::InMenu)
|
||||||
|
{
|
||||||
|
cl_run = !!v;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
#endif
|
1119
source/core/menu/razemenu.cpp
Normal file
1119
source/core/menu/razemenu.cpp
Normal file
File diff suppressed because it is too large
Load diff
69
source/core/menu/razemenu.h
Normal file
69
source/core/menu/razemenu.h
Normal file
|
@ -0,0 +1,69 @@
|
||||||
|
#pragma once
|
||||||
|
#include "menu.h"
|
||||||
|
#include "gamestruct.h"
|
||||||
|
#include "c_cvars.h"
|
||||||
|
|
||||||
|
void M_StartControlPanel (bool makeSound, bool scaleoverride = false);
|
||||||
|
|
||||||
|
|
||||||
|
extern FNewGameStartup NewGameStartupInfo;
|
||||||
|
void M_StartupEpisodeMenu(FNewGameStartup *gs);
|
||||||
|
void M_StartupSkillMenu(FNewGameStartup *gs);
|
||||||
|
void M_CreateGameMenus();
|
||||||
|
|
||||||
|
// The savegame manager contains too much code that is game specific. Parts are shareable but need more work first.
|
||||||
|
|
||||||
|
struct FSavegameManager
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
TArray<FSaveGameNode*> SaveGames;
|
||||||
|
FSaveGameNode NewSaveNode;
|
||||||
|
int LastSaved = -1;
|
||||||
|
int LastAccessed = -1;
|
||||||
|
FGameTexture *SavePic = nullptr;
|
||||||
|
|
||||||
|
public:
|
||||||
|
int WindowSize = 0;
|
||||||
|
FString SaveCommentString;
|
||||||
|
FSaveGameNode *quickSaveSlot = nullptr;
|
||||||
|
~FSavegameManager();
|
||||||
|
|
||||||
|
private:
|
||||||
|
int InsertSaveNode(FSaveGameNode *node);
|
||||||
|
public:
|
||||||
|
void NotifyNewSave(const FString &file, const FString &title, bool okForQuicksave, bool forceQuicksave);
|
||||||
|
void ClearSaveGames();
|
||||||
|
|
||||||
|
void ReadSaveStrings();
|
||||||
|
void UnloadSaveData();
|
||||||
|
|
||||||
|
int RemoveSaveSlot(int index);
|
||||||
|
void LoadSavegame(int Selected);
|
||||||
|
void DoSave(int Selected, const char *savegamestring);
|
||||||
|
unsigned ExtractSaveData(int index);
|
||||||
|
void ClearSaveStuff();
|
||||||
|
bool DrawSavePic(int x, int y, int w, int h);
|
||||||
|
void DrawSaveComment(FFont *font, int cr, int x, int y, int scalefactor);
|
||||||
|
void SetFileInfo(int Selected);
|
||||||
|
unsigned SavegameCount();
|
||||||
|
FSaveGameNode *GetSavegame(int i);
|
||||||
|
void InsertNewSaveNode();
|
||||||
|
bool RemoveNewSaveNode();
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
extern FSavegameManager savegameManager;
|
||||||
|
|
||||||
|
enum EMenuSounds : int
|
||||||
|
{
|
||||||
|
ActivateSound,
|
||||||
|
CursorSound,
|
||||||
|
AdvanceSound,
|
||||||
|
BackSound,
|
||||||
|
CloseSound,
|
||||||
|
PageSound,
|
||||||
|
ChangeSound,
|
||||||
|
ChooseSound
|
||||||
|
};
|
||||||
|
|
||||||
|
EXTERN_CVAR(Bool, menu_sounds)
|
|
@ -1,739 +0,0 @@
|
||||||
/*
|
|
||||||
** loadsavemenu.cpp
|
|
||||||
** The load game and save game menus
|
|
||||||
**
|
|
||||||
**---------------------------------------------------------------------------
|
|
||||||
** Copyright 2001-2010 Randy Heit
|
|
||||||
** Copyright 2010 Christoph Oelckers
|
|
||||||
** All rights reserved.
|
|
||||||
**
|
|
||||||
** Redistribution and use in source and binary forms, with or without
|
|
||||||
** modification, are permitted provided that the following conditions
|
|
||||||
** are met:
|
|
||||||
**
|
|
||||||
** 1. Redistributions of source code must retain the above copyright
|
|
||||||
** notice, this list of conditions and the following disclaimer.
|
|
||||||
** 2. Redistributions in binary form must reproduce the above copyright
|
|
||||||
** notice, this list of conditions and the following disclaimer in the
|
|
||||||
** documentation and/or other materials provided with the distribution.
|
|
||||||
** 3. The name of the author may not be used to endorse or promote products
|
|
||||||
** derived from this software without specific prior written permission.
|
|
||||||
**
|
|
||||||
** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
|
|
||||||
** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
|
||||||
** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
|
||||||
** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
|
|
||||||
** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
|
||||||
** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
|
||||||
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
|
||||||
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
||||||
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
|
||||||
** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
||||||
**---------------------------------------------------------------------------
|
|
||||||
**
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "menu.h"
|
|
||||||
#include "version.h"
|
|
||||||
#include "m_png.h"
|
|
||||||
#include "filesystem.h"
|
|
||||||
#include "v_text.h"
|
|
||||||
#include "d_event.h"
|
|
||||||
#include "gstrings.h"
|
|
||||||
#include "d_gui.h"
|
|
||||||
#include "v_draw.h"
|
|
||||||
#include "files.h"
|
|
||||||
#include "resourcefile.h"
|
|
||||||
#include "cmdlib.h"
|
|
||||||
#include "files.h"
|
|
||||||
#include "savegamehelp.h"
|
|
||||||
#include "i_specialpaths.h"
|
|
||||||
#include "c_dispatch.h"
|
|
||||||
#include "build.h"
|
|
||||||
#include "serializer.h"
|
|
||||||
#include "findfile.h"
|
|
||||||
#include "inputstate.h"
|
|
||||||
#include "gamestate.h"
|
|
||||||
|
|
||||||
|
|
||||||
FSavegameManager savegameManager;
|
|
||||||
FString BackupSaveGame;
|
|
||||||
|
|
||||||
void DoLoadGame(const char* name)
|
|
||||||
{
|
|
||||||
if (OpenSaveGameForRead(name))
|
|
||||||
{
|
|
||||||
if (gi->LoadGame(nullptr))
|
|
||||||
{
|
|
||||||
gameaction = ga_level;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
I_Error("%s: Failed to load savegame", name);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
I_Error("%s: Failed to open savegame", name);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void FSavegameManager::LoadGame(FSaveGameNode* node)
|
|
||||||
{
|
|
||||||
inputState.ClearAllInput();
|
|
||||||
gi->FreeLevelData();
|
|
||||||
DoLoadGame(node->Filename);
|
|
||||||
BackupSaveGame = node->Filename;
|
|
||||||
}
|
|
||||||
|
|
||||||
void FSavegameManager::SaveGame(FSaveGameNode* node, bool ok4q, bool forceq)
|
|
||||||
{
|
|
||||||
if (OpenSaveGameForWrite(node->Filename, node->SaveTitle))
|
|
||||||
{
|
|
||||||
if (gi->SaveGame(node) && FinishSavegameWrite())
|
|
||||||
{
|
|
||||||
FString fn = node->Filename;
|
|
||||||
FString desc = node->SaveTitle;
|
|
||||||
NotifyNewSave(fn, desc, ok4q, forceq);
|
|
||||||
Printf(PRINT_NOTIFY, "%s\n", GStrings("GAME SAVED"));
|
|
||||||
BackupSaveGame = node->Filename;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
// Save data maintenance
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void FSavegameManager::ClearSaveGames()
|
|
||||||
{
|
|
||||||
for (unsigned i = 0; i<SaveGames.Size(); i++)
|
|
||||||
{
|
|
||||||
if (!SaveGames[i]->bNoDelete)
|
|
||||||
delete SaveGames[i];
|
|
||||||
}
|
|
||||||
SaveGames.Clear();
|
|
||||||
}
|
|
||||||
|
|
||||||
FSavegameManager::~FSavegameManager()
|
|
||||||
{
|
|
||||||
ClearSaveGames();
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
// Save data maintenance
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
int FSavegameManager::RemoveSaveSlot(int index)
|
|
||||||
{
|
|
||||||
int listindex = SaveGames[0]->bNoDelete ? index - 1 : index;
|
|
||||||
if (listindex < 0) return index;
|
|
||||||
|
|
||||||
remove(SaveGames[index]->Filename.GetChars());
|
|
||||||
UnloadSaveData();
|
|
||||||
|
|
||||||
FSaveGameNode *file = SaveGames[index];
|
|
||||||
|
|
||||||
if (quickSaveSlot == SaveGames[index])
|
|
||||||
{
|
|
||||||
quickSaveSlot = nullptr;
|
|
||||||
}
|
|
||||||
if (!file->bNoDelete) delete file;
|
|
||||||
|
|
||||||
if (LastSaved == listindex) LastSaved = -1;
|
|
||||||
else if (LastSaved > listindex) LastSaved--;
|
|
||||||
if (LastAccessed == listindex) LastAccessed = -1;
|
|
||||||
else if (LastAccessed > listindex) LastAccessed--;
|
|
||||||
|
|
||||||
SaveGames.Delete(index);
|
|
||||||
if ((unsigned)index >= SaveGames.Size()) index--;
|
|
||||||
ExtractSaveData(index);
|
|
||||||
return index;
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
int FSavegameManager::InsertSaveNode(FSaveGameNode *node)
|
|
||||||
{
|
|
||||||
if (SaveGames.Size() == 0)
|
|
||||||
{
|
|
||||||
return SaveGames.Push(node);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (node->bOldVersion)
|
|
||||||
{ // Add node at bottom of list
|
|
||||||
return SaveGames.Push(node);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{ // Add node at top of list
|
|
||||||
unsigned int i = 0;
|
|
||||||
if (SaveGames[0] == &NewSaveNode) i++; // To not insert above the "new savegame" dummy entry.
|
|
||||||
for (; i < SaveGames.Size(); i++)
|
|
||||||
{
|
|
||||||
if (SaveGames[i]->bOldVersion || node->SaveTitle.CompareNoCase(SaveGames[i]->SaveTitle) <= 0)
|
|
||||||
{
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
SaveGames.Insert(i, node);
|
|
||||||
return i;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
// M_ReadSaveStrings
|
|
||||||
//
|
|
||||||
// Find savegames and read their titles
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void FSavegameManager::ReadSaveStrings()
|
|
||||||
{
|
|
||||||
if (SaveGames.Size() == 0)
|
|
||||||
{
|
|
||||||
void *filefirst;
|
|
||||||
findstate_t c_file;
|
|
||||||
FString filter;
|
|
||||||
|
|
||||||
LastSaved = LastAccessed = -1;
|
|
||||||
quickSaveSlot = nullptr;
|
|
||||||
filter = G_BuildSaveName("*");
|
|
||||||
filefirst = I_FindFirst(filter.GetChars(), &c_file);
|
|
||||||
if (filefirst != ((void *)(-1)))
|
|
||||||
{
|
|
||||||
do
|
|
||||||
{
|
|
||||||
// I_FindName only returns the file's name and not its full path
|
|
||||||
FString filepath = G_BuildSaveName(I_FindName(&c_file));
|
|
||||||
|
|
||||||
FResourceFile *savegame = FResourceFile::OpenResourceFile(filepath, true, true);
|
|
||||||
if (savegame != nullptr)
|
|
||||||
{
|
|
||||||
FResourceLump *info = savegame->FindLump("info.json");
|
|
||||||
if (info == nullptr)
|
|
||||||
{
|
|
||||||
// savegame info not found. This is not a savegame so leave it alone.
|
|
||||||
delete savegame;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
auto fr = info->NewReader();
|
|
||||||
FString title;
|
|
||||||
int check = G_ValidateSavegame(fr, &title, true);
|
|
||||||
fr.Close();
|
|
||||||
delete savegame;
|
|
||||||
if (check != 0)
|
|
||||||
{
|
|
||||||
FSaveGameNode *node = new FSaveGameNode;
|
|
||||||
node->Filename = filepath;
|
|
||||||
node->bOldVersion = check == -1;
|
|
||||||
node->bMissingWads = check == -2;
|
|
||||||
node->SaveTitle = title;
|
|
||||||
InsertSaveNode(node);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} while (I_FindNext (filefirst, &c_file) == 0);
|
|
||||||
I_FindClose (filefirst);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void FSavegameManager::NotifyNewSave(const FString &file, const FString &title, bool okForQuicksave, bool forceQuicksave)
|
|
||||||
{
|
|
||||||
FSaveGameNode *node;
|
|
||||||
|
|
||||||
if (file.IsEmpty())
|
|
||||||
return;
|
|
||||||
|
|
||||||
ReadSaveStrings();
|
|
||||||
|
|
||||||
// See if the file is already in our list
|
|
||||||
for (unsigned i = 0; i<SaveGames.Size(); i++)
|
|
||||||
{
|
|
||||||
FSaveGameNode *node = SaveGames[i];
|
|
||||||
#ifdef __unix__
|
|
||||||
if (node->Filename.Compare(file) == 0)
|
|
||||||
#else
|
|
||||||
if (node->Filename.CompareNoCase(file) == 0)
|
|
||||||
#endif
|
|
||||||
{
|
|
||||||
node->SaveTitle = title;
|
|
||||||
node->bOldVersion = false;
|
|
||||||
node->bMissingWads = false;
|
|
||||||
if (okForQuicksave)
|
|
||||||
{
|
|
||||||
if (quickSaveSlot == nullptr || quickSaveSlot == (FSaveGameNode*)1 || forceQuicksave) quickSaveSlot = node;
|
|
||||||
LastAccessed = LastSaved = i - 1; // without <new save> item
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
node = new FSaveGameNode;
|
|
||||||
node->SaveTitle = title;
|
|
||||||
node->Filename = file;
|
|
||||||
node->bOldVersion = false;
|
|
||||||
node->bMissingWads = false;
|
|
||||||
int index = InsertSaveNode(node);
|
|
||||||
|
|
||||||
if (okForQuicksave)
|
|
||||||
{
|
|
||||||
if (quickSaveSlot == nullptr || quickSaveSlot == (FSaveGameNode*)1 || forceQuicksave) quickSaveSlot = node;
|
|
||||||
LastAccessed = LastSaved = index - 1; // without <new save> item
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
LastAccessed = ++LastSaved;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
// Loads the savegame
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void FSavegameManager::LoadSavegame(int Selected)
|
|
||||||
{
|
|
||||||
auto sel = savegameManager.GetSavegame(Selected);
|
|
||||||
if (sel && !sel->bOldVersion && !sel->bMissingWads)
|
|
||||||
{
|
|
||||||
savegameManager.LoadGame(SaveGames[Selected]);
|
|
||||||
if (quickSaveSlot == (FSaveGameNode*)1)
|
|
||||||
{
|
|
||||||
quickSaveSlot = SaveGames[Selected];
|
|
||||||
}
|
|
||||||
M_ClearMenus();
|
|
||||||
LastAccessed = Selected;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void FSavegameManager::DoSave(int Selected, const char *savegamestring)
|
|
||||||
{
|
|
||||||
if (Selected != 0)
|
|
||||||
{
|
|
||||||
auto node = *SaveGames[Selected];
|
|
||||||
node.SaveTitle = savegamestring;
|
|
||||||
savegameManager.SaveGame(&node, true, false);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
// Find an unused filename and save as that
|
|
||||||
FString filename;
|
|
||||||
int i;
|
|
||||||
|
|
||||||
for (i = 0;; ++i)
|
|
||||||
{
|
|
||||||
filename = G_BuildSaveName(FStringf("save%04d", i));
|
|
||||||
if (!FileExists(filename))
|
|
||||||
{
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
FSaveGameNode sg{ savegamestring, filename };
|
|
||||||
savegameManager.SaveGame(&sg, true, false);
|
|
||||||
}
|
|
||||||
M_ClearMenus();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
unsigned FSavegameManager::ExtractSaveData(int index)
|
|
||||||
{
|
|
||||||
FResourceFile *resf;
|
|
||||||
FSaveGameNode *node;
|
|
||||||
|
|
||||||
if (index == -1)
|
|
||||||
{
|
|
||||||
if (SaveGames.Size() > 0 && SaveGames[0]->bNoDelete)
|
|
||||||
{
|
|
||||||
index = LastSaved + 1;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
index = LastAccessed < 0? 0 : LastAccessed;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
UnloadSaveData();
|
|
||||||
|
|
||||||
if ((unsigned)index < SaveGames.Size() &&
|
|
||||||
(node = SaveGames[index]) &&
|
|
||||||
!node->Filename.IsEmpty() &&
|
|
||||||
!node->bOldVersion &&
|
|
||||||
(resf = FResourceFile::OpenResourceFile(node->Filename.GetChars(), true)) != nullptr)
|
|
||||||
{
|
|
||||||
FResourceLump *info = resf->FindLump("info.json");
|
|
||||||
if (info == nullptr)
|
|
||||||
{
|
|
||||||
// this should not happen because the file has already been verified.
|
|
||||||
return index;
|
|
||||||
}
|
|
||||||
|
|
||||||
void* data = info->Lock();
|
|
||||||
FSerializer arc;
|
|
||||||
if (!arc.OpenReader((const char*)data, info->LumpSize))
|
|
||||||
{
|
|
||||||
info->Unlock();
|
|
||||||
return index;
|
|
||||||
}
|
|
||||||
info->Unlock();
|
|
||||||
|
|
||||||
FString comment, fcomment, ncomment, mtime;
|
|
||||||
|
|
||||||
arc("Creation Time", comment)
|
|
||||||
("Map Label", fcomment)
|
|
||||||
("Map Name", ncomment)
|
|
||||||
("Map Time", mtime);
|
|
||||||
|
|
||||||
comment.AppendFormat("\n%s - %s\n%s", fcomment.GetChars(), ncomment.GetChars(), mtime.GetChars());
|
|
||||||
SaveCommentString = comment;
|
|
||||||
|
|
||||||
FResourceLump *pic = resf->FindLump("savepic.png");
|
|
||||||
if (pic != nullptr)
|
|
||||||
{
|
|
||||||
FileReader picreader;
|
|
||||||
|
|
||||||
picreader.OpenMemoryArray([=](TArray<uint8_t> &array)
|
|
||||||
{
|
|
||||||
auto cache = pic->Lock();
|
|
||||||
array.Resize(pic->LumpSize);
|
|
||||||
memcpy(&array[0], cache, pic->LumpSize);
|
|
||||||
pic->Unlock();
|
|
||||||
return true;
|
|
||||||
});
|
|
||||||
PNGHandle *png = M_VerifyPNG(picreader);
|
|
||||||
if (png != nullptr)
|
|
||||||
{
|
|
||||||
SavePic = PNGTexture_CreateFromFile(png, node->Filename);
|
|
||||||
delete png;
|
|
||||||
if (SavePic && SavePic->GetDisplayWidth() == 1 && SavePic->GetDisplayHeight() == 1)
|
|
||||||
{
|
|
||||||
delete SavePic;
|
|
||||||
SavePic = nullptr;
|
|
||||||
SavePicData.Clear();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
delete resf;
|
|
||||||
}
|
|
||||||
return index;
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void FSavegameManager::UnloadSaveData()
|
|
||||||
{
|
|
||||||
if (SavePic != nullptr)
|
|
||||||
{
|
|
||||||
delete SavePic;
|
|
||||||
}
|
|
||||||
|
|
||||||
SaveCommentString = "";
|
|
||||||
SavePic = nullptr;
|
|
||||||
SavePicData.Clear();
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void FSavegameManager::ClearSaveStuff()
|
|
||||||
{
|
|
||||||
UnloadSaveData();
|
|
||||||
if (quickSaveSlot == (FSaveGameNode*)1)
|
|
||||||
{
|
|
||||||
quickSaveSlot = nullptr;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
bool FSavegameManager::DrawSavePic(int x, int y, int w, int h)
|
|
||||||
{
|
|
||||||
if (SavePic == nullptr) return false;
|
|
||||||
DrawTexture(twod, SavePic, x, y, DTA_DestWidth, w, DTA_DestHeight, h, DTA_Masked, false, TAG_DONE);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void FSavegameManager::SetFileInfo(int Selected)
|
|
||||||
{
|
|
||||||
if (!SaveGames[Selected]->Filename.IsEmpty())
|
|
||||||
{
|
|
||||||
SaveCommentString.Format("File on disk:\n%s", SaveGames[Selected]->Filename.GetChars());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
unsigned FSavegameManager::SavegameCount()
|
|
||||||
{
|
|
||||||
return SaveGames.Size();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
FSaveGameNode *FSavegameManager::GetSavegame(int i)
|
|
||||||
{
|
|
||||||
return SaveGames[i];
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void FSavegameManager::InsertNewSaveNode()
|
|
||||||
{
|
|
||||||
NewSaveNode.SaveTitle = GStrings("NEWSAVE");
|
|
||||||
NewSaveNode.bNoDelete = true;
|
|
||||||
SaveGames.Insert(0, &NewSaveNode);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
bool FSavegameManager::RemoveNewSaveNode()
|
|
||||||
{
|
|
||||||
if (SaveGames[0] == &NewSaveNode)
|
|
||||||
{
|
|
||||||
SaveGames.Delete(0);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
CVAR(Bool, saveloadconfirmation, true, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
|
||||||
|
|
||||||
CVAR(Int, autosavenum, 0, CVAR_NOSET | CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
|
||||||
static int nextautosave = -1;
|
|
||||||
CVAR(Int, disableautosave, 0, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
|
||||||
CUSTOM_CVAR(Int, autosavecount, 4, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
|
||||||
{
|
|
||||||
if (self < 1)
|
|
||||||
self = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
CVAR(Int, quicksavenum, 0, CVAR_NOSET | CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
|
||||||
static int nextquicksave = -1;
|
|
||||||
CUSTOM_CVAR(Int, quicksavecount, 4, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
|
||||||
{
|
|
||||||
if (self < 1)
|
|
||||||
self = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
void M_Autosave()
|
|
||||||
{
|
|
||||||
if (disableautosave) return;
|
|
||||||
if (!gi->CanSave()) return;
|
|
||||||
FString description;
|
|
||||||
FString file;
|
|
||||||
// Keep a rotating sets of autosaves
|
|
||||||
UCVarValue num;
|
|
||||||
const char* readableTime;
|
|
||||||
int count = autosavecount != 0 ? autosavecount : 1;
|
|
||||||
|
|
||||||
if (nextautosave == -1)
|
|
||||||
{
|
|
||||||
nextautosave = (autosavenum + 1) % count;
|
|
||||||
}
|
|
||||||
|
|
||||||
num.Int = nextautosave;
|
|
||||||
autosavenum.ForceSet(num, CVAR_Int);
|
|
||||||
|
|
||||||
FSaveGameNode sg;
|
|
||||||
sg.Filename = G_BuildSaveName(FStringf("auto%04d", nextautosave));
|
|
||||||
readableTime = myasctime();
|
|
||||||
sg.SaveTitle.Format("Autosave %s", readableTime);
|
|
||||||
nextautosave = (nextautosave + 1) % count;
|
|
||||||
savegameManager.SaveGame(&sg, false, false);
|
|
||||||
}
|
|
||||||
|
|
||||||
CCMD(autosave)
|
|
||||||
{
|
|
||||||
gameaction = ga_autosave;
|
|
||||||
}
|
|
||||||
|
|
||||||
CCMD(rotatingquicksave)
|
|
||||||
{
|
|
||||||
if (!gi->CanSave()) return;
|
|
||||||
FString description;
|
|
||||||
FString file;
|
|
||||||
// Keep a rotating sets of quicksaves
|
|
||||||
UCVarValue num;
|
|
||||||
const char* readableTime;
|
|
||||||
int count = quicksavecount != 0 ? quicksavecount : 1;
|
|
||||||
|
|
||||||
if (nextquicksave == -1)
|
|
||||||
{
|
|
||||||
nextquicksave = (quicksavenum + 1) % count;
|
|
||||||
}
|
|
||||||
|
|
||||||
num.Int = nextquicksave;
|
|
||||||
quicksavenum.ForceSet(num, CVAR_Int);
|
|
||||||
|
|
||||||
FSaveGameNode sg;
|
|
||||||
sg.Filename = G_BuildSaveName(FStringf("quick%04d", nextquicksave));
|
|
||||||
readableTime = myasctime();
|
|
||||||
sg.SaveTitle.Format("Quicksave %s", readableTime);
|
|
||||||
nextquicksave = (nextquicksave + 1) % count;
|
|
||||||
savegameManager.SaveGame(&sg, false, false);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
CCMD(quicksave)
|
|
||||||
{ // F6
|
|
||||||
if (!gi->CanSave()) return;
|
|
||||||
|
|
||||||
if (savegameManager.quickSaveSlot == NULL || savegameManager.quickSaveSlot == (FSaveGameNode*)1)
|
|
||||||
{
|
|
||||||
M_StartControlPanel(true);
|
|
||||||
M_SetMenu(NAME_Savegamemenu);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
auto slot = savegameManager.quickSaveSlot;
|
|
||||||
|
|
||||||
// [mxd]. Just save the game, no questions asked.
|
|
||||||
if (!saveloadconfirmation)
|
|
||||||
{
|
|
||||||
savegameManager.SaveGame(savegameManager.quickSaveSlot, true, true);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
FString tempstring = GStrings("QSPROMPT");
|
|
||||||
tempstring.Substitute("%s", slot->SaveTitle.GetChars());
|
|
||||||
M_StartControlPanel(true);
|
|
||||||
|
|
||||||
DMenu* newmenu = CreateMessageBoxMenu(CurrentMenu, tempstring, 0, INT_MAX, false, NAME_None, [](bool res)
|
|
||||||
{
|
|
||||||
if (res)
|
|
||||||
{
|
|
||||||
savegameManager.SaveGame(savegameManager.quickSaveSlot, true, true);
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
});
|
|
||||||
|
|
||||||
M_ActivateMenu(newmenu);
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
CCMD(quickload)
|
|
||||||
{ // F9
|
|
||||||
#if 0
|
|
||||||
if (netgame)
|
|
||||||
{
|
|
||||||
M_StartControlPanel(true);
|
|
||||||
M_StartMessage(GStrings("QLOADNET"), 1);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
if (savegameManager.quickSaveSlot == nullptr || savegameManager.quickSaveSlot == (FSaveGameNode*)1)
|
|
||||||
{
|
|
||||||
M_StartControlPanel(true);
|
|
||||||
// signal that whatever gets loaded should be the new quicksave
|
|
||||||
savegameManager.quickSaveSlot = (FSaveGameNode*)1;
|
|
||||||
M_SetMenu(NAME_Loadgamemenu);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// [mxd]. Just load the game, no questions asked.
|
|
||||||
if (!saveloadconfirmation)
|
|
||||||
{
|
|
||||||
savegameManager.LoadGame(savegameManager.quickSaveSlot);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
FString tempstring = GStrings("QLPROMPT");
|
|
||||||
tempstring.Substitute("%s", savegameManager.quickSaveSlot->SaveTitle.GetChars());
|
|
||||||
|
|
||||||
M_StartControlPanel(true);
|
|
||||||
|
|
||||||
DMenu* newmenu = CreateMessageBoxMenu(CurrentMenu, tempstring, 0, INT_MAX, false, NAME_None, [](bool res)
|
|
||||||
{
|
|
||||||
if (res)
|
|
||||||
{
|
|
||||||
savegameManager.LoadGame(savegameManager.quickSaveSlot);
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
});
|
|
||||||
M_ActivateMenu(newmenu);
|
|
||||||
}
|
|
|
@ -53,6 +53,8 @@
|
||||||
#include "gamestruct.h"
|
#include "gamestruct.h"
|
||||||
#include "automap.h"
|
#include "automap.h"
|
||||||
#include "statusbar.h"
|
#include "statusbar.h"
|
||||||
|
#include "gamestate.h"
|
||||||
|
#include "razemenu.h"
|
||||||
|
|
||||||
static CompositeSavegameWriter savewriter;
|
static CompositeSavegameWriter savewriter;
|
||||||
static FResourceFile *savereader;
|
static FResourceFile *savereader;
|
||||||
|
@ -564,3 +566,88 @@ void LoadEngineState()
|
||||||
fr.Close();
|
fr.Close();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
CVAR(Bool, saveloadconfirmation, true, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
||||||
|
|
||||||
|
CVAR(Int, autosavenum, 0, CVAR_NOSET | CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
||||||
|
static int nextautosave = -1;
|
||||||
|
CVAR(Int, disableautosave, 0, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
||||||
|
CUSTOM_CVAR(Int, autosavecount, 4, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
||||||
|
{
|
||||||
|
if (self < 1)
|
||||||
|
self = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
CVAR(Int, quicksavenum, 0, CVAR_NOSET | CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
||||||
|
static int nextquicksave = -1;
|
||||||
|
CUSTOM_CVAR(Int, quicksavecount, 4, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
||||||
|
{
|
||||||
|
if (self < 1)
|
||||||
|
self = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
void M_Autosave()
|
||||||
|
{
|
||||||
|
if (disableautosave) return;
|
||||||
|
if (!gi->CanSave()) return;
|
||||||
|
FString description;
|
||||||
|
FString file;
|
||||||
|
// Keep a rotating sets of autosaves
|
||||||
|
UCVarValue num;
|
||||||
|
const char* readableTime;
|
||||||
|
int count = autosavecount != 0 ? autosavecount : 1;
|
||||||
|
|
||||||
|
if (nextautosave == -1)
|
||||||
|
{
|
||||||
|
nextautosave = (autosavenum + 1) % count;
|
||||||
|
}
|
||||||
|
|
||||||
|
num.Int = nextautosave;
|
||||||
|
autosavenum.ForceSet(num, CVAR_Int);
|
||||||
|
|
||||||
|
FSaveGameNode sg;
|
||||||
|
sg.Filename = G_BuildSaveName(FStringf("auto%04d", nextautosave));
|
||||||
|
readableTime = myasctime();
|
||||||
|
sg.SaveTitle.Format("Autosave %s", readableTime);
|
||||||
|
nextautosave = (nextautosave + 1) % count;
|
||||||
|
//savegameManager.SaveGame(&sg, false, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
CCMD(autosave)
|
||||||
|
{
|
||||||
|
gameaction = ga_autosave;
|
||||||
|
}
|
||||||
|
|
||||||
|
CCMD(rotatingquicksave)
|
||||||
|
{
|
||||||
|
if (!gi->CanSave()) return;
|
||||||
|
FString description;
|
||||||
|
FString file;
|
||||||
|
// Keep a rotating sets of quicksaves
|
||||||
|
UCVarValue num;
|
||||||
|
const char* readableTime;
|
||||||
|
int count = quicksavecount != 0 ? quicksavecount : 1;
|
||||||
|
|
||||||
|
if (nextquicksave == -1)
|
||||||
|
{
|
||||||
|
nextquicksave = (quicksavenum + 1) % count;
|
||||||
|
}
|
||||||
|
|
||||||
|
num.Int = nextquicksave;
|
||||||
|
quicksavenum.ForceSet(num, CVAR_Int);
|
||||||
|
|
||||||
|
FSaveGameNode sg;
|
||||||
|
sg.Filename = G_BuildSaveName(FStringf("quick%04d", nextquicksave));
|
||||||
|
readableTime = myasctime();
|
||||||
|
sg.SaveTitle.Format("Quicksave %s", readableTime);
|
||||||
|
nextquicksave = (nextquicksave + 1) % count;
|
||||||
|
//savegameManager.SaveGame(&sg, false, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -19,6 +19,7 @@ int G_ValidateSavegame(FileReader &fr, FString *savetitle, bool formenu);
|
||||||
|
|
||||||
void SaveEngineState();
|
void SaveEngineState();
|
||||||
void LoadEngineState();
|
void LoadEngineState();
|
||||||
|
void M_Autosave();
|
||||||
|
|
||||||
#define SAVEGAME_EXT ".dsave"
|
#define SAVEGAME_EXT ".dsave"
|
||||||
|
|
||||||
|
|
|
@ -43,7 +43,7 @@
|
||||||
#include "s_soundinternal.h"
|
#include "s_soundinternal.h"
|
||||||
#include "animtexture.h"
|
#include "animtexture.h"
|
||||||
#include "gamestate.h"
|
#include "gamestate.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "raze_sound.h"
|
#include "raze_sound.h"
|
||||||
#include "SmackerDecoder.h"
|
#include "SmackerDecoder.h"
|
||||||
#include "movie/playmve.h"
|
#include "movie/playmve.h"
|
||||||
|
|
|
@ -59,7 +59,7 @@
|
||||||
#include "m_fixed.h"
|
#include "m_fixed.h"
|
||||||
#include "gamecontrol.h"
|
#include "gamecontrol.h"
|
||||||
#include "gamestruct.h"
|
#include "gamestruct.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "mapinfo.h"
|
#include "mapinfo.h"
|
||||||
|
|
||||||
#include "../version.h"
|
#include "../version.h"
|
||||||
|
|
|
@ -30,9 +30,10 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "gamestate.h"
|
#include "gamestate.h"
|
||||||
#include "mapinfo.h"
|
#include "mapinfo.h"
|
||||||
#include "gamecontrol.h"
|
#include "gamecontrol.h"
|
||||||
|
#include "v_draw.h"
|
||||||
|
|
||||||
|
|
||||||
#include "menu/menu.h" // to override the local menu.h
|
#include "razemenu.h" // to override the local menu.h
|
||||||
|
|
||||||
#include "../../glbackend/glbackend.h"
|
#include "../../glbackend/glbackend.h"
|
||||||
|
|
||||||
|
@ -49,6 +50,7 @@ BEGIN_PS_NS
|
||||||
void menu_DoPlasma();
|
void menu_DoPlasma();
|
||||||
double zoomsize = 0;
|
double zoomsize = 0;
|
||||||
|
|
||||||
|
#if 0
|
||||||
class PSMainMenu : public DListMenu
|
class PSMainMenu : public DListMenu
|
||||||
{
|
{
|
||||||
|
|
||||||
|
@ -81,6 +83,7 @@ class PSMainMenu : public DListMenu
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
//----------------------------------------------------------------------------
|
//----------------------------------------------------------------------------
|
||||||
|
@ -91,6 +94,7 @@ class PSMainMenu : public DListMenu
|
||||||
|
|
||||||
void GameInterface::DrawNativeMenuText(int fontnum, int state, double xpos, double ypos, float fontscale, const char* text, int flags)
|
void GameInterface::DrawNativeMenuText(int fontnum, int state, double xpos, double ypos, float fontscale, const char* text, int flags)
|
||||||
{
|
{
|
||||||
|
#if 0
|
||||||
int tilenum = (int)strtoll(text, nullptr, 0);
|
int tilenum = (int)strtoll(text, nullptr, 0);
|
||||||
double y = ypos - tilesiz[tilenum].y / 2;
|
double y = ypos - tilesiz[tilenum].y / 2;
|
||||||
|
|
||||||
|
@ -122,6 +126,7 @@ void GameInterface::DrawNativeMenuText(int fontnum, int state, double xpos, doub
|
||||||
DrawTexture(twod, tex, 62, ypos - 12, DTA_FullscreenScale, FSMode_Fit320x200, DTA_TopLeft, true, TAG_DONE);
|
DrawTexture(twod, tex, 62, ypos - 12, DTA_FullscreenScale, FSMode_Fit320x200, DTA_TopLeft, true, TAG_DONE);
|
||||||
DrawTexture(twod, tex, 207, ypos - 12, DTA_FullscreenScale, FSMode_Fit320x200, DTA_TopLeft, true, DTA_FlipX, true, TAG_DONE);
|
DrawTexture(twod, tex, 207, ypos - 12, DTA_FullscreenScale, FSMode_Fit320x200, DTA_TopLeft, true, DTA_FlipX, true, TAG_DONE);
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -183,17 +188,3 @@ void GameInterface::DrawMenuCaption(const DVector2& origin, const char* text)
|
||||||
|
|
||||||
|
|
||||||
END_PS_NS
|
END_PS_NS
|
||||||
|
|
||||||
//----------------------------------------------------------------------------
|
|
||||||
//
|
|
||||||
// Class registration
|
|
||||||
//
|
|
||||||
//----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
|
|
||||||
static TMenuClassDescriptor<Powerslave::PSMainMenu> _mm("Exhumed.MainMenu");
|
|
||||||
|
|
||||||
void RegisterPSMenus()
|
|
||||||
{
|
|
||||||
menuClasses.Push(&_mm);
|
|
||||||
}
|
|
||||||
|
|
|
@ -46,7 +46,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "cheathandler.h"
|
#include "cheathandler.h"
|
||||||
#include "inputstate.h"
|
#include "inputstate.h"
|
||||||
#include "d_protocol.h"
|
#include "d_protocol.h"
|
||||||
#include "core/menu/menu.h"
|
#include "razemenu.h"
|
||||||
|
|
||||||
BEGIN_PS_NS
|
BEGIN_PS_NS
|
||||||
|
|
||||||
|
@ -481,7 +481,9 @@ void GameInterface::app_init()
|
||||||
//int esi = 1;
|
//int esi = 1;
|
||||||
//int edi = esi;
|
//int edi = esi;
|
||||||
|
|
||||||
|
#if 0
|
||||||
help_disabled = true;
|
help_disabled = true;
|
||||||
|
#endif
|
||||||
// Create the global level table. Parts of the engine need it, even though the game itself does not.
|
// Create the global level table. Parts of the engine need it, even though the game itself does not.
|
||||||
for (int i = 0; i <= 32; i++)
|
for (int i = 0; i <= 32; i++)
|
||||||
{
|
{
|
||||||
|
|
|
@ -44,10 +44,11 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "cheathandler.h"
|
#include "cheathandler.h"
|
||||||
#include "statistics.h"
|
#include "statistics.h"
|
||||||
#include "g_input.h"
|
#include "g_input.h"
|
||||||
#include "core/menu/menu.h"
|
#include "razemenu.h"
|
||||||
#include "d_net.h"
|
#include "d_net.h"
|
||||||
#include "automap.h"
|
#include "automap.h"
|
||||||
#include "raze_music.h"
|
#include "raze_music.h"
|
||||||
|
#include "v_draw.h"
|
||||||
|
|
||||||
BEGIN_PS_NS
|
BEGIN_PS_NS
|
||||||
|
|
||||||
|
|
|
@ -21,7 +21,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "player.h"
|
#include "player.h"
|
||||||
#include "status.h"
|
#include "status.h"
|
||||||
#include "view.h"
|
#include "view.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
|
|
||||||
BEGIN_PS_NS
|
BEGIN_PS_NS
|
||||||
|
|
||||||
|
|
|
@ -35,7 +35,7 @@ Prepared for public release: 03/21/2003 - Charlie Wiederhold, 3D Realms
|
||||||
#include "gamecvars.h"
|
#include "gamecvars.h"
|
||||||
#include "gamecontrol.h"
|
#include "gamecontrol.h"
|
||||||
#include "c_bind.h"
|
#include "c_bind.h"
|
||||||
#include "menu/menu.h"
|
#include "razemenu.h"
|
||||||
#include "gstrings.h"
|
#include "gstrings.h"
|
||||||
#include "version.h"
|
#include "version.h"
|
||||||
#include "names.h"
|
#include "names.h"
|
||||||
|
@ -83,6 +83,7 @@ static void Menu_DrawCursor(double x, double y, double scale, bool right)
|
||||||
//
|
//
|
||||||
//----------------------------------------------------------------------------
|
//----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
#if 0
|
||||||
class DukeListMenu : public DListMenu
|
class DukeListMenu : public DListMenu
|
||||||
{
|
{
|
||||||
using Super = DListMenu;
|
using Super = DListMenu;
|
||||||
|
@ -163,7 +164,7 @@ class DukeMainMenu : public DukeListMenu
|
||||||
|
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
#endif
|
||||||
|
|
||||||
//----------------------------------------------------------------------------
|
//----------------------------------------------------------------------------
|
||||||
//
|
//
|
||||||
|
@ -173,6 +174,7 @@ class DukeMainMenu : public DukeListMenu
|
||||||
|
|
||||||
void GameInterface::DrawNativeMenuText(int fontnum, int state, double oxpos, double ypos, float fontscale, const char* text, int flags)
|
void GameInterface::DrawNativeMenuText(int fontnum, int state, double oxpos, double ypos, float fontscale, const char* text, int flags)
|
||||||
{
|
{
|
||||||
|
#if 0
|
||||||
double xpos = oxpos;
|
double xpos = oxpos;
|
||||||
int trans;
|
int trans;
|
||||||
PalEntry pe;
|
PalEntry pe;
|
||||||
|
@ -214,7 +216,7 @@ void GameInterface::DrawNativeMenuText(int fontnum, int state, double oxpos, dou
|
||||||
else
|
else
|
||||||
Menu_DrawCursor(oxpos - cursorOffset, ymid, cursorScale, false);
|
Menu_DrawCursor(oxpos - cursorOffset, ymid, cursorScale, false);
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
void GameInterface::MenuOpened()
|
void GameInterface::MenuOpened()
|
||||||
|
@ -270,7 +272,7 @@ bool GameInterface::StartGame(FNewGameStartup& gs)
|
||||||
{
|
{
|
||||||
if (g_gameType & GAMEFLAG_SHAREWARE)
|
if (g_gameType & GAMEFLAG_SHAREWARE)
|
||||||
{
|
{
|
||||||
M_StartMessage(GStrings("BUYDUKE"), 1, -1);
|
M_StartMessage(GStrings("BUYDUKE"), 1, NAME_None);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -283,6 +285,7 @@ bool GameInterface::StartGame(FNewGameStartup& gs)
|
||||||
static const short sounds_r[] = { 427, 428, 196, 195, 197 };
|
static const short sounds_r[] = { 427, 428, 196, 195, 197 };
|
||||||
if (gs.Skill >=0 && gs.Skill <= 5) skillsound = isRR()? sounds_r[gs.Skill] : sounds_d[gs.Skill];
|
if (gs.Skill >=0 && gs.Skill <= 5) skillsound = isRR()? sounds_r[gs.Skill] : sounds_d[gs.Skill];
|
||||||
|
|
||||||
|
#if 0
|
||||||
if (menu_sounds && skillsound >= 0 && SoundEnabled() && !netgame)
|
if (menu_sounds && skillsound >= 0 && SoundEnabled() && !netgame)
|
||||||
{
|
{
|
||||||
S_PlaySound(skillsound, CHAN_AUTO, CHANF_UI);
|
S_PlaySound(skillsound, CHAN_AUTO, CHANF_UI);
|
||||||
|
@ -295,6 +298,7 @@ bool GameInterface::StartGame(FNewGameStartup& gs)
|
||||||
}
|
}
|
||||||
Net_ClearFifo();
|
Net_ClearFifo();
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
auto map = FindMapByLevelNum(levelnum(gs.Episode, gs.Level));
|
auto map = FindMapByLevelNum(levelnum(gs.Episode, gs.Level));
|
||||||
if (map)
|
if (map)
|
||||||
{
|
{
|
||||||
|
@ -520,22 +524,3 @@ bool GameInterface::DrawSpecialScreen(const DVector2& origin, int tilenum)
|
||||||
}
|
}
|
||||||
|
|
||||||
END_DUKE_NS
|
END_DUKE_NS
|
||||||
|
|
||||||
//----------------------------------------------------------------------------
|
|
||||||
//
|
|
||||||
// Class registration
|
|
||||||
//
|
|
||||||
//----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
|
|
||||||
static TMenuClassDescriptor<Duke3d::DukeMainMenu> _mm("Duke.MainMenu");
|
|
||||||
static TMenuClassDescriptor<Duke3d::DukeListMenu> _lm("Duke.ListMenu");
|
|
||||||
|
|
||||||
static TMenuClassDescriptor<DImageScrollerMenu> _ism("Duke.ImageScrollerMenu"); // does not implement a new class, we only need the descriptor.
|
|
||||||
|
|
||||||
void RegisterDuke3dMenus()
|
|
||||||
{
|
|
||||||
menuClasses.Push(&_mm);
|
|
||||||
menuClasses.Push(&_lm);
|
|
||||||
menuClasses.Push(&_ism);
|
|
||||||
}
|
|
||||||
|
|
|
@ -9,7 +9,7 @@
|
||||||
|
|
||||||
#include "polymost.h"
|
#include "polymost.h"
|
||||||
#include "gamecvars.h"
|
#include "gamecvars.h"
|
||||||
#include "menu/menu.h"
|
#include "razemenu.h"
|
||||||
#include "funct.h"
|
#include "funct.h"
|
||||||
#include "gamecontrol.h"
|
#include "gamecontrol.h"
|
||||||
#include "gamevar.h"
|
#include "gamevar.h"
|
||||||
|
@ -20,6 +20,8 @@
|
||||||
#include "sounds.h"
|
#include "sounds.h"
|
||||||
#include "soundefs.h"
|
#include "soundefs.h"
|
||||||
#include "binaryangle.h"
|
#include "binaryangle.h"
|
||||||
|
#include "gamestruct.h"
|
||||||
|
#include "v_draw.h"
|
||||||
|
|
||||||
BEGIN_DUKE_NS
|
BEGIN_DUKE_NS
|
||||||
|
|
||||||
|
|
|
@ -40,7 +40,7 @@ Modifications for JonoF's port by Jonathon Fowler (jf@jonof.id.au)
|
||||||
#include "printf.h"
|
#include "printf.h"
|
||||||
#include "filesystem.h"
|
#include "filesystem.h"
|
||||||
#include "mapinfo.h"
|
#include "mapinfo.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "global.h"
|
#include "global.h"
|
||||||
#include "m_argv.h"
|
#include "m_argv.h"
|
||||||
#include "sounds.h"
|
#include "sounds.h"
|
||||||
|
|
|
@ -43,11 +43,12 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
#include "network.h"
|
#include "network.h"
|
||||||
|
|
||||||
#include "misc.h"
|
#include "misc.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "raze_sound.h"
|
#include "raze_sound.h"
|
||||||
#include "sounds.h"
|
#include "sounds.h"
|
||||||
#include "gamestate.h"
|
#include "gamestate.h"
|
||||||
#include "raze_music.h"
|
#include "raze_music.h"
|
||||||
|
#include "v_draw.h"
|
||||||
|
|
||||||
#include "../../glbackend/glbackend.h"
|
#include "../../glbackend/glbackend.h"
|
||||||
|
|
||||||
|
@ -62,6 +63,7 @@ BEGIN_SW_NS
|
||||||
//
|
//
|
||||||
//----------------------------------------------------------------------------
|
//----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
#if 0
|
||||||
class SWMainMenu : public DListMenu
|
class SWMainMenu : public DListMenu
|
||||||
{
|
{
|
||||||
void Ticker() override
|
void Ticker() override
|
||||||
|
@ -102,6 +104,7 @@ public:
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
#endif
|
||||||
|
|
||||||
//----------------------------------------------------------------------------
|
//----------------------------------------------------------------------------
|
||||||
//
|
//
|
||||||
|
@ -111,6 +114,7 @@ public:
|
||||||
|
|
||||||
void GameInterface::DrawNativeMenuText(int fontnum, int state, double xpos, double ypos, float fontscale, const char* text, int flags)
|
void GameInterface::DrawNativeMenuText(int fontnum, int state, double xpos, double ypos, float fontscale, const char* text, int flags)
|
||||||
{
|
{
|
||||||
|
#if 0
|
||||||
switch (fontnum)
|
switch (fontnum)
|
||||||
{
|
{
|
||||||
case NIT_BigFont:
|
case NIT_BigFont:
|
||||||
|
@ -144,6 +148,7 @@ void GameInterface::DrawNativeMenuText(int fontnum, int state, double xpos, doub
|
||||||
DrawTexture(twod, tileGetTexture(pic_yinyang, true), x, y, DTA_FullscreenScale, FSMode_Fit320x200,
|
DrawTexture(twod, tileGetTexture(pic_yinyang, true), x, y, DTA_FullscreenScale, FSMode_Fit320x200,
|
||||||
DTA_CenterOffset, true, DTA_Color, 0xfff0f0f0, DTA_ScaleX, scale / 65536., DTA_ScaleY, scale / 65536., TAG_DONE);
|
DTA_CenterOffset, true, DTA_Color, 0xfff0f0f0, DTA_ScaleX, scale / 65536., DTA_ScaleY, scale / 65536., TAG_DONE);
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
void GameInterface::QuitToTitle()
|
void GameInterface::QuitToTitle()
|
||||||
|
@ -200,7 +205,7 @@ bool GameInterface::StartGame(FNewGameStartup& gs)
|
||||||
{
|
{
|
||||||
if (g_gameType & GAMEFLAG_SHAREWARE)
|
if (g_gameType & GAMEFLAG_SHAREWARE)
|
||||||
{
|
{
|
||||||
M_StartMessage(GStrings("BUYSW"), 1, -1);
|
M_StartMessage(GStrings("BUYSW"), 1, NAME_None);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
map = FindMapByLevelNum(5);
|
map = FindMapByLevelNum(5);
|
||||||
|
@ -251,19 +256,3 @@ void GameInterface::DrawMenuCaption(const DVector2& origin, const char* text)
|
||||||
|
|
||||||
|
|
||||||
END_SW_NS
|
END_SW_NS
|
||||||
|
|
||||||
//----------------------------------------------------------------------------
|
|
||||||
//
|
|
||||||
// Class registration
|
|
||||||
//
|
|
||||||
//----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
|
|
||||||
static TMenuClassDescriptor<ShadowWarrior::SWMainMenu> _mm("ShadowWarrior.MainMenu");
|
|
||||||
static TMenuClassDescriptor<ShadowWarrior::SWOrderMenu> _so("ShadowWarrior.OrderMenu");
|
|
||||||
|
|
||||||
void RegisterSWMenus()
|
|
||||||
{
|
|
||||||
menuClasses.Push(&_mm);
|
|
||||||
menuClasses.Push(&_so);
|
|
||||||
}
|
|
||||||
|
|
|
@ -51,9 +51,10 @@ Prepared for public release: 03/28/2005 - Charlie Wiederhold, 3D Realms
|
||||||
#include "interp.h"
|
#include "interp.h"
|
||||||
#include "interpso.h"
|
#include "interpso.h"
|
||||||
#include "sector.h"
|
#include "sector.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "v_2ddrawer.h"
|
#include "v_2ddrawer.h"
|
||||||
#include "v_video.h"
|
#include "v_video.h"
|
||||||
|
#include "v_draw.h"
|
||||||
#include "glbackend/glbackend.h"
|
#include "glbackend/glbackend.h"
|
||||||
|
|
||||||
BEGIN_SW_NS
|
BEGIN_SW_NS
|
||||||
|
|
|
@ -64,7 +64,7 @@ Prepared for public release: 03/28/2005 - Charlie Wiederhold, 3D Realms
|
||||||
#include "printf.h"
|
#include "printf.h"
|
||||||
#include "m_argv.h"
|
#include "m_argv.h"
|
||||||
#include "debugbreak.h"
|
#include "debugbreak.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "raze_music.h"
|
#include "raze_music.h"
|
||||||
#include "statistics.h"
|
#include "statistics.h"
|
||||||
#include "gstrings.h"
|
#include "gstrings.h"
|
||||||
|
@ -77,6 +77,7 @@ Prepared for public release: 03/28/2005 - Charlie Wiederhold, 3D Realms
|
||||||
#include "inputstate.h"
|
#include "inputstate.h"
|
||||||
#include "gamestate.h"
|
#include "gamestate.h"
|
||||||
#include "d_net.h"
|
#include "d_net.h"
|
||||||
|
#include "v_draw.h"
|
||||||
|
|
||||||
//#include "crc32.h"
|
//#include "crc32.h"
|
||||||
|
|
||||||
|
|
|
@ -29,7 +29,7 @@ Prepared for public release: 03/28/2005 - Charlie Wiederhold, 3D Realms
|
||||||
#include "network.h"
|
#include "network.h"
|
||||||
#include "gamecontrol.h"
|
#include "gamecontrol.h"
|
||||||
#include "player.h"
|
#include "player.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
|
|
||||||
|
|
||||||
BEGIN_SW_NS
|
BEGIN_SW_NS
|
||||||
|
|
|
@ -39,7 +39,7 @@ Prepared for public release: 03/28/2005 - Charlie Wiederhold, 3D Realms
|
||||||
#include "v_2ddrawer.h"
|
#include "v_2ddrawer.h"
|
||||||
|
|
||||||
#include "weapon.h"
|
#include "weapon.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "raze_sound.h"
|
#include "raze_sound.h"
|
||||||
#include "glbackend/glbackend.h"
|
#include "glbackend/glbackend.h"
|
||||||
|
|
||||||
|
|
|
@ -50,9 +50,10 @@ Prepared for public release: 03/28/2005 - Charlie Wiederhold, 3D Realms
|
||||||
#include "misc.h"
|
#include "misc.h"
|
||||||
#include "interp.h"
|
#include "interp.h"
|
||||||
#include "interpso.h"
|
#include "interpso.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "gstrings.h"
|
#include "gstrings.h"
|
||||||
#include "raze_music.h"
|
#include "raze_music.h"
|
||||||
|
#include "v_draw.h"
|
||||||
#include "gamestate.h"
|
#include "gamestate.h"
|
||||||
|
|
||||||
BEGIN_SW_NS
|
BEGIN_SW_NS
|
||||||
|
|
|
@ -37,7 +37,7 @@ Prepared for public release: 03/28/2005 - Charlie Wiederhold, 3D Realms
|
||||||
#include "jsector.h"
|
#include "jsector.h"
|
||||||
#include "parent.h"
|
#include "parent.h"
|
||||||
#include "sc_man.h"
|
#include "sc_man.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "quotemgr.h"
|
#include "quotemgr.h"
|
||||||
#include "mapinfo.h"
|
#include "mapinfo.h"
|
||||||
|
|
||||||
|
|
|
@ -41,7 +41,7 @@ Prepared for public release: 03/28/2005 - Charlie Wiederhold, 3D Realms
|
||||||
#include "misc.h"
|
#include "misc.h"
|
||||||
#include "rts.h"
|
#include "rts.h"
|
||||||
#include "menus.h"
|
#include "menus.h"
|
||||||
#include "menu.h"
|
#include "razemenu.h"
|
||||||
#include "raze_music.h"
|
#include "raze_music.h"
|
||||||
#include "raze_sound.h"
|
#include "raze_sound.h"
|
||||||
#include "filesystem.h"
|
#include "filesystem.h"
|
||||||
|
|
Loading…
Reference in a new issue