1
0
mirror of https://github.com/TerryCavanagh/VVVVVV.git synced 2024-06-03 03:23:33 +02:00
VVVVVV/desktop_version/src/Input.cpp
Misa b528f25e3a Disable switching languages during cutscene tests
Not gonna lie, I am a bit disappointed at having to do this, because it
actually worked pretty well despite a few bugs depending on which
language you entered with. But that's only because I'm working with
the official translation files, which are in sync with each other.

With translation files that are completely arbitrary, it would be
apparent that switching languages during the cutscene test doesn't
really make sense. Like, at all. That's because the list of cutscenes is
populated entirely from language-specific XML and the cutscenes in them
are also from language-specific XML. So keeping the same position in the
menu doesn't really make sense, and keeping the same position in a
cutscene definitely doesn't make sense.
2024-02-02 15:05:10 -08:00

3567 lines
113 KiB
C++

#include <tinyxml2.h>
#include <vector>
#include "ButtonGlyphs.h"
#include "Credits.h"
#include "CustomLevels.h"
#include "Editor.h"
#include "Entity.h"
#include "Enums.h"
#include "FileSystemUtils.h"
#include "Game.h"
#include "GlitchrunnerMode.h"
#include "Graphics.h"
#include "GraphicsUtil.h"
#include "KeyPoll.h"
#include "LevelDebugger.h"
#include "Localization.h"
#include "LocalizationMaint.h"
#include "LocalizationStorage.h"
#include "MakeAndPlay.h"
#include "Map.h"
#include "Music.h"
#include "RoomnameTranslator.h"
#include "Screen.h"
#include "Script.h"
#include "UtilityClass.h"
#include "Vlogging.h"
static void updatebuttonmappings(int bind)
{
for (
SDL_GameControllerButton i = SDL_CONTROLLER_BUTTON_A;
i < SDL_CONTROLLER_BUTTON_DPAD_UP;
i = (SDL_GameControllerButton) (i + 1)
) {
if (key.isDown(i))
{
bool dupe = false;
switch (bind)
{
case 1:
{
size_t j;
for (j = 0; j < game.controllerButton_flip.size(); j += 1)
{
if (i == game.controllerButton_flip[j])
{
dupe = true;
}
}
if (!dupe)
{
game.controllerButton_flip.push_back(i);
music.playef(Sound_VIRIDIAN);
}
for (j = 0; j < game.controllerButton_map.size(); j += 1)
{
if (i == game.controllerButton_map[j])
{
game.controllerButton_map.erase(game.controllerButton_map.begin() + j);
}
}
for (j = 0; j < game.controllerButton_esc.size(); j += 1)
{
if (i == game.controllerButton_esc[j])
{
game.controllerButton_esc.erase(game.controllerButton_esc.begin() + j);
}
}
for (j = 0; j < game.controllerButton_restart.size(); j += 1)
{
if (i == game.controllerButton_restart[j])
{
game.controllerButton_restart.erase(game.controllerButton_restart.begin() + j);
}
}
for (j = 0; j < game.controllerButton_interact.size(); j += 1)
{
if (i == game.controllerButton_interact[j])
{
game.controllerButton_interact.erase(game.controllerButton_interact.begin() + j);
}
}
break;
}
case 2:
{
size_t j;
for (j = 0; j < game.controllerButton_map.size(); j += 1)
{
if (i == game.controllerButton_map[j])
{
dupe = true;
}
}
if (!dupe)
{
game.controllerButton_map.push_back(i);
music.playef(Sound_VIRIDIAN);
}
for (j = 0; j < game.controllerButton_flip.size(); j += 1)
{
if (i == game.controllerButton_flip[j])
{
game.controllerButton_flip.erase(game.controllerButton_flip.begin() + j);
}
}
for (j = 0; j < game.controllerButton_esc.size(); j += 1)
{
if (i == game.controllerButton_esc[j])
{
game.controllerButton_esc.erase(game.controllerButton_esc.begin() + j);
}
}
for (j = 0; j < game.controllerButton_restart.size(); j += 1)
{
if (i == game.controllerButton_restart[j])
{
game.controllerButton_restart.erase(game.controllerButton_restart.begin() + j);
}
}
for (j = 0; j < game.controllerButton_interact.size(); j += 1)
{
if (i == game.controllerButton_interact[j])
{
game.controllerButton_interact.erase(game.controllerButton_interact.begin() + j);
}
}
break;
}
case 3:
{
size_t j;
for (j = 0; j < game.controllerButton_esc.size(); j += 1)
{
if (i == game.controllerButton_esc[j])
{
dupe = true;
}
}
if (!dupe)
{
game.controllerButton_esc.push_back(i);
music.playef(Sound_VIRIDIAN);
}
for (j = 0; j < game.controllerButton_flip.size(); j += 1)
{
if (i == game.controllerButton_flip[j])
{
game.controllerButton_flip.erase(game.controllerButton_flip.begin() + j);
}
}
for (j = 0; j < game.controllerButton_map.size(); j += 1)
{
if (i == game.controllerButton_map[j])
{
game.controllerButton_map.erase(game.controllerButton_map.begin() + j);
}
}
for (j = 0; j < game.controllerButton_restart.size(); j += 1)
{
if (i == game.controllerButton_restart[j])
{
game.controllerButton_restart.erase(game.controllerButton_restart.begin() + j);
}
}
for (j = 0; j < game.controllerButton_interact.size(); j += 1)
{
if (i == game.controllerButton_interact[j])
{
game.controllerButton_interact.erase(game.controllerButton_interact.begin() + j);
}
}
break;
}
case 4:
{
size_t j;
for (j = 0; j < game.controllerButton_restart.size(); j += 1)
{
if (i == game.controllerButton_restart[j])
{
dupe = true;
}
}
if (!dupe)
{
game.controllerButton_restart.push_back(i);
music.playef(Sound_VIRIDIAN);
}
for (j = 0; j < game.controllerButton_flip.size(); j += 1)
{
if (i == game.controllerButton_flip[j])
{
game.controllerButton_flip.erase(game.controllerButton_flip.begin() + j);
}
}
for (j = 0; j < game.controllerButton_map.size(); j += 1)
{
if (i == game.controllerButton_map[j])
{
game.controllerButton_map.erase(game.controllerButton_map.begin() + j);
}
}
for (j = 0; j < game.controllerButton_esc.size(); j += 1)
{
if (i == game.controllerButton_esc[j])
{
game.controllerButton_esc.erase(game.controllerButton_esc.begin() + j);
}
}
for (j = 0; j < game.controllerButton_interact.size(); j += 1)
{
if (i == game.controllerButton_interact[j])
{
game.controllerButton_interact.erase(game.controllerButton_interact.begin() + j);
}
}
break;
}
case 5:
{
size_t j;
for (j = 0; j < game.controllerButton_interact.size(); j += 1)
{
if (i == game.controllerButton_interact[j])
{
dupe = true;
}
}
if (!dupe)
{
game.controllerButton_interact.push_back(i);
music.playef(Sound_VIRIDIAN);
}
for (j = 0; j < game.controllerButton_flip.size(); j += 1)
{
if (i == game.controllerButton_flip[j])
{
game.controllerButton_flip.erase(game.controllerButton_flip.begin() + j);
}
}
for (j = 0; j < game.controllerButton_map.size(); j += 1)
{
if (i == game.controllerButton_map[j])
{
game.controllerButton_map.erase(game.controllerButton_map.begin() + j);
}
}
for (j = 0; j < game.controllerButton_esc.size(); j += 1)
{
if (i == game.controllerButton_esc[j])
{
game.controllerButton_esc.erase(game.controllerButton_esc.begin() + j);
}
}
for (j = 0; j < game.controllerButton_restart.size(); j += 1)
{
if (i == game.controllerButton_restart[j])
{
game.controllerButton_restart.erase(game.controllerButton_restart.begin() + j);
}
}
break;
}
}
}
}
}
/* Also used in KeyPoll.cpp. */
void recomputetextboxes(void)
{
/* Retranslate and reposition all text boxes.
* WARNING: Needs to update in linear order, starting from 0. */
for (size_t i = 0; i < graphics.textboxes.size(); i++)
{
graphics.textboxes[i].updatetext();
graphics.textboxes[i].applyposition();
}
}
static void toggleflipmode(void)
{
graphics.setflipmode = !graphics.setflipmode;
game.savestatsandsettings_menu();
if (graphics.setflipmode)
{
music.playef(Sound_GAMESAVED);
game.screenshake = 10;
game.flashlight = 5;
}
else
{
music.playef(Sound_VIRIDIAN);
}
/* Some text boxes change depending on Flip Mode, so update text boxes. */
const bool temp = graphics.flipmode;
graphics.flipmode = graphics.setflipmode;
recomputetextboxes();
graphics.flipmode = temp;
}
static bool fadetomode = false;
static int fadetomodedelay = 0;
static enum StartMode gotomode = Start_MAINGAME;
static void startmode(const enum StartMode mode)
{
gotomode = mode;
graphics.fademode = FADE_START_FADEOUT;
fadetomode = true;
fadetomodedelay = 19;
}
static void handlefadetomode(void)
{
if (game.ingame_titlemode)
{
/* We shouldn't be here! */
SDL_assert(0 && "Loading a mode from in-game options!");
return;
}
if (fadetomodedelay > 0)
{
--fadetomodedelay;
}
else
{
fadetomode = false;
script.startgamemode(gotomode);
}
}
static int* user_changing_volume = NULL;
static int previous_volume = 0;
static void initvolumeslider(const int menuoption)
{
switch (menuoption)
{
case 0:
game.slidermode = SLIDER_MUSICVOLUME;
user_changing_volume = &music.user_music_volume;
break;
case 1:
game.slidermode = SLIDER_SOUNDVOLUME;
user_changing_volume = &music.user_sound_volume;
break;
default:
SDL_assert(0 && "Unhandled volume slider option!");
game.slidermode = SLIDER_NONE;
user_changing_volume = NULL;
return;
}
previous_volume = *user_changing_volume;
}
static void deinitvolumeslider(void)
{
user_changing_volume = NULL;
game.savestatsandsettings_menu();
game.slidermode = SLIDER_NONE;
}
static void slidermodeinput(void)
{
if (user_changing_volume == NULL)
{
SDL_assert(0 && "user_changing_volume is NULL!");
return;
}
if (game.press_left)
{
*user_changing_volume -= USER_VOLUME_STEP;
}
else if (game.press_right)
{
*user_changing_volume += USER_VOLUME_STEP;
}
*user_changing_volume = SDL_clamp(*user_changing_volume, 0, USER_VOLUME_MAX);
}
static void menuactionpress(void)
{
if (game.menutestmode)
{
music.playef(Sound_CRUMBLE);
Menu::MenuName nextmenu = (Menu::MenuName) (game.currentmenuname + 1);
game.returnmenu();
game.createmenu(nextmenu);
return;
}
switch (game.currentmenuname)
{
case Menu::mainmenu:
{
int option_id = -1;
int option_seq = 0; /* option number in YOUR configuration */
#define OPTION_ID(id) \
if (option_seq == game.currentmenuoption) \
{ \
option_id = id; \
} \
option_seq++;
#if !defined(MAKEANDPLAY)
OPTION_ID(0) /* play */
#endif
OPTION_ID(1) /* levels */
OPTION_ID(2) /* options */
if (loc::show_translator_menu)
{
OPTION_ID(3) /* translator */
}
OPTION_ID(4) /* credits */
OPTION_ID(5) /* quit */
#undef OPTION_ID
switch (option_id)
{
#if !defined(MAKEANDPLAY)
case 0:
//Play
if (!game.save_exists() && !game.anything_unlocked())
{
//No saves exist, just start a new game
music.playef(Sound_VIRIDIAN);
startmode(Start_MAINGAME);
}
else
{
//Bring you to the normal playmenu
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::play);
map.nexttowercolour();
}
break;
#endif
case 1:
//Bring you to the normal playmenu
music.playef(Sound_VIRIDIAN);
game.editor_disabled = !BUTTONGLYPHS_keyboard_is_available();
game.createmenu(Menu::playerworlds);
map.nexttowercolour();
break;
case 2:
//Options
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::options);
map.nexttowercolour();
break;
case 3:
//Translator
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::translator_main);
map.nexttowercolour();
break;
case 4:
//Credits
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::credits);
map.nexttowercolour();
break;
case 5:
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::youwannaquit);
map.nexttowercolour();
break;
}
break;
}
case Menu::levellist:
{
const bool nextlastoptions = cl.ListOfMetaData.size() > 8;
if(game.currentmenuoption==(int)game.menuoptions.size()-1){
//go back to menu
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
}else if(nextlastoptions && game.currentmenuoption==(int)game.menuoptions.size()-2){
//previous page
music.playef(Sound_VIRIDIAN);
if(game.levelpage==0){
game.levelpage=(cl.ListOfMetaData.size()-1)/8;
}else{
game.levelpage--;
}
game.createmenu(Menu::levellist, true);
game.currentmenuoption=game.menuoptions.size()-2;
map.nexttowercolour();
}else if(nextlastoptions && game.currentmenuoption==(int)game.menuoptions.size()-3){
//next page
music.playef(Sound_VIRIDIAN);
if((size_t) ((game.levelpage*8)+8) >= cl.ListOfMetaData.size()){
game.levelpage=0;
}else{
game.levelpage++;
}
game.createmenu(Menu::levellist, true);
game.currentmenuoption=game.menuoptions.size()-3;
map.nexttowercolour();
}else{
//Ok, launch the level!
//PLAY CUSTOM LEVEL HOOK
music.playef(Sound_VIRIDIAN);
game.playcustomlevel=(game.levelpage*8)+game.currentmenuoption;
game.customleveltitle=cl.ListOfMetaData[game.playcustomlevel].title;
game.customlevelfilename=cl.ListOfMetaData[game.playcustomlevel].filename;
std::string name = "saves/" + cl.ListOfMetaData[game.playcustomlevel].filename.substr(7) + ".vvv";
tinyxml2::XMLDocument doc;
if (!FILESYSTEM_loadTiXml2Document(name.c_str(), doc)){
startmode(Start_CUSTOM);
}else{
game.createmenu(Menu::quickloadlevel);
map.nexttowercolour();
}
}
break;
}
case Menu::quickloadlevel:
switch (game.currentmenuoption)
{
case 0: //continue save
music.playef(Sound_VIRIDIAN);
startmode(Start_CUSTOM_QUICKSAVE);
break;
case 1:
music.playef(Sound_VIRIDIAN);
startmode(Start_CUSTOM);
break;
case 2:
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::deletequicklevel);
map.nexttowercolour();
break;
default:
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::deletequicklevel:
switch (game.currentmenuoption)
{
default:
music.playef(Sound_VIRIDIAN);
game.returnmenu();
break;
case 1:
game.customdeletequick(cl.ListOfMetaData[game.playcustomlevel].filename);
game.returntomenu(Menu::levellist);
game.flashlight = 5;
game.screenshake = 15;
music.playef(Sound_DESTROY);
break;
}
map.nexttowercolour();
break;
case Menu::playerworlds:
if (game.currentmenuoption == 0)
{
music.playef(Sound_VIRIDIAN);
game.levelpage = 0;
cl.getDirectoryData();
game.loadcustomlevelstats(); //Should only load a file if it's needed
game.createmenu(Menu::levellist);
if (FILESYSTEM_levelDirHasError())
{
game.createmenu(Menu::warninglevellist);
}
map.nexttowercolour();
}
else if (game.currentmenuoption == 1)
{
// LEVEL EDITOR HOOK
if (game.editor_disabled)
{
music.playef(Sound_CRY);
}
else
{
music.playef(Sound_VIRIDIAN);
startmode(Start_EDITOR);
ed.filename = "";
}
}
else if (!game.editor_disabled && game.currentmenuoption == 2)
{
//"OPENFOLDERHOOK"
if (FILESYSTEM_openDirectoryEnabled()
&& FILESYSTEM_openDirectory(FILESYSTEM_getUserLevelDirectory()))
{
music.playef(Sound_VIRIDIAN);
SDL_MinimizeWindow(gameScreen.m_window);
}
else
{
music.playef(Sound_CRY);
}
}
else if (!game.editor_disabled && game.currentmenuoption == 3)
{
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::confirmshowlevelspath);
map.nexttowercolour();
}
else if (game.currentmenuoption == 4 || (game.editor_disabled && game.currentmenuoption == 2))
{
// back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
}
break;
case Menu::confirmshowlevelspath:
{
int prevmenuoption = game.currentmenuoption; /* returnmenu destroys this */
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
if (prevmenuoption == 1)
{
game.createmenu(Menu::showlevelspath);
}
break;
}
case Menu::showlevelspath:
music.playef(Sound_VIRIDIAN);
game.editor_disabled = !BUTTONGLYPHS_keyboard_is_available();
game.returntomenu(Menu::playerworlds);
map.nexttowercolour();
break;
case Menu::errornostart:
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::mainmenu);
map.nexttowercolour();
break;
case Menu::graphicoptions:
{
int offset = 0;
bool processed = false;
if (game.currentmenuoption == offset + 0 && !gameScreen.isForcedFullscreen())
{
processed = true;
music.playef(Sound_VIRIDIAN);
gameScreen.toggleFullScreen();
}
if (gameScreen.isForcedFullscreen())
{
--offset;
}
if (game.currentmenuoption == offset + 1)
{
processed = true;
music.playef(Sound_VIRIDIAN);
gameScreen.toggleScalingMode();
game.savestatsandsettings_menu();
}
if (game.currentmenuoption == offset + 2 && !gameScreen.isForcedFullscreen())
{
processed = true;
// resize to nearest multiple
if (gameScreen.isWindowed)
{
music.playef(Sound_VIRIDIAN);
gameScreen.ResizeToNearestMultiple();
game.savestatsandsettings_menu();
}
else
{
music.playef(Sound_CRY);
}
}
if (gameScreen.isForcedFullscreen())
{
--offset;
}
if (game.currentmenuoption == offset + 3)
{
processed = true;
music.playef(Sound_VIRIDIAN);
gameScreen.toggleLinearFilter();
game.savestatsandsettings_menu();
}
if (game.currentmenuoption == offset + 4)
{
processed = true;
//change smoothing
music.playef(Sound_VIRIDIAN);
gameScreen.badSignalEffect= !gameScreen.badSignalEffect;
game.savestatsandsettings_menu();
}
if (game.currentmenuoption == offset + 5)
{
processed = true;
//toggle vsync
music.playef(Sound_VIRIDIAN);
gameScreen.toggleVSync();
game.savestatsandsettings_menu();
}
if (!processed)
{
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
}
break;
}
case Menu::youwannaquit:
switch (game.currentmenuoption)
{
case 0:
//bye!
music.playef(Sound_CRY);
startmode(Start_QUIT);
break;
default:
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
}
break;
case Menu::setinvincibility:
switch (game.currentmenuoption)
{
case 0:
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
default:
map.invincibility = !map.invincibility;
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
game.savestatsandsettings_menu();
break;
}
break;
case Menu::setslowdown:
switch (game.currentmenuoption)
{
case 0:
//back
game.slowdown = 30;
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
game.savestatsandsettings_menu();
break;
case 1:
game.slowdown = 24;
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
game.savestatsandsettings_menu();
break;
case 2:
game.slowdown = 18;
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
game.savestatsandsettings_menu();
break;
case 3:
game.slowdown = 12;
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
game.savestatsandsettings_menu();
break;
}
break;
case Menu::speedrunneroptions:
switch (game.currentmenuoption)
{
case 0:
// Glitchrunner mode
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::setglitchrunner);
game.currentmenuoption = GlitchrunnerMode_get();
map.nexttowercolour();
break;
case 1:
/* Input delay */
music.playef(Sound_VIRIDIAN);
game.inputdelay = !game.inputdelay;
game.savestatsandsettings_menu();
break;
case 2:
/* Interact button toggle */
music.playef(Sound_VIRIDIAN);
game.separate_interact = !game.separate_interact;
game.savestatsandsettings_menu();
break;
case 3:
// toggle fake load screen
game.skipfakeload = !game.skipfakeload;
game.savestatsandsettings_menu();
music.playef(Sound_VIRIDIAN);
break;
case 4:
// toggle in game timer
game.showingametimer = !game.showingametimer;
game.savestatsandsettings_menu();
music.playef(Sound_VIRIDIAN);
break;
case 5:
// english sprites
loc::english_sprites = !loc::english_sprites;
if (!loc::english_sprites)
{
graphics.grphx.init_translations();
}
game.savestatsandsettings_menu();
music.playef(Sound_VIRIDIAN);
break;
default:
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::setglitchrunner:
GlitchrunnerMode_set((enum GlitchrunnerMode) game.currentmenuoption);
music.playef(Sound_VIRIDIAN);
game.returnmenu();
game.savestatsandsettings_menu();
map.nexttowercolour();
break;
case Menu::advancedoptions:
switch (game.currentmenuoption)
{
case 0:
// toggle unfocus pause
game.disablepause = !game.disablepause;
game.savestatsandsettings_menu();
music.playef(Sound_VIRIDIAN);
break;
case 1:
/* toggle unfocus music pause */
game.disableaudiopause = !game.disableaudiopause;
game.savestatsandsettings_menu();
music.playef(Sound_VIRIDIAN);
break;
case 2:
// toggle translucent roomname BG
graphics.translucentroomname = !graphics.translucentroomname;
game.savestatsandsettings_menu();
music.playef(Sound_VIRIDIAN);
break;
default:
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::accessibility:
{
int accessibilityoffset = 0;
#if !defined(MAKEANDPLAY)
accessibilityoffset = 1;
if (game.currentmenuoption == 0) {
//unlock play options
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::unlockmenu);
map.nexttowercolour();
}
#endif
if (game.currentmenuoption == accessibilityoffset + 0) {
//invincibility
if (!game.ingame_titlemode || !game.incompetitive())
{
if (!map.invincibility)
{
game.createmenu(Menu::setinvincibility);
map.nexttowercolour();
}
else
{
map.invincibility = !map.invincibility;
game.savestatsandsettings_menu();
}
music.playef(Sound_VIRIDIAN);
}
else
{
music.playef(Sound_CRY);
map.invincibility = false;
}
}
else if (game.currentmenuoption == accessibilityoffset + 1) {
//change game speed
if (!game.ingame_titlemode || !game.incompetitive())
{
game.createmenu(Menu::setslowdown);
map.nexttowercolour();
music.playef(Sound_VIRIDIAN);
}
else
{
music.playef(Sound_CRY);
game.slowdown = 30;
}
}
else if (game.currentmenuoption == accessibilityoffset + 2) {
//disable animated backgrounds
game.colourblindmode = !game.colourblindmode;
game.savestatsandsettings_menu();
graphics.towerbg.tdrawback = true;
graphics.titlebg.tdrawback = true;
music.playef(Sound_VIRIDIAN);
}
else if (game.currentmenuoption == accessibilityoffset + 3) {
//disable screeneffects
game.noflashingmode = !game.noflashingmode;
game.savestatsandsettings_menu();
if (!game.noflashingmode)
{
music.playef(Sound_GAMESAVED);
game.screenshake = 10;
game.flashlight = 5;
}
else {
music.playef(Sound_VIRIDIAN);
}
}
else if (game.currentmenuoption == accessibilityoffset + 4) {
//disable text outline
graphics.notextoutline = !graphics.notextoutline;
game.savestatsandsettings_menu();
music.playef(Sound_VIRIDIAN);
}
else if (game.currentmenuoption == accessibilityoffset + 5) {
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
}
break;
}
case Menu::gameplayoptions:
{
int gameplayoptionsoffset = 0;
#if !defined(MAKEANDPLAY)
if (game.ingame_titlemode && game.unlock[Unlock_FLIPMODE])
#endif
{
gameplayoptionsoffset = 1;
if (game.currentmenuoption == 0) {
toggleflipmode();
// Fix wrong area music in Tower (Positive Force vs. ecroF evitisoP)
if (map.custommode)
{
break;
}
int area = map.area(game.roomx, game.roomy);
if (area == 3 || area == 11)
{
if (graphics.setflipmode)
{
music.play(Music_POSITIVEFORCEREVERSED);
}
else
{
music.play(Music_POSITIVEFORCE);
}
}
}
}
if (game.currentmenuoption == gameplayoptionsoffset + 0)
{
//Toggle 30+ FPS
music.playef(Sound_VIRIDIAN);
game.over30mode = !game.over30mode;
game.savestatsandsettings_menu();
}
else if (game.currentmenuoption == gameplayoptionsoffset + 1)
{
//Speedrunner options
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::speedrunneroptions);
map.nexttowercolour();
}
else if (game.currentmenuoption == gameplayoptionsoffset + 2)
{
//Advanced options
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::advancedoptions);
map.nexttowercolour();
}
else if (game.currentmenuoption == gameplayoptionsoffset + 3)
{
//Clear Data
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::cleardatamenu);
map.nexttowercolour();
}
else if (game.currentmenuoption == gameplayoptionsoffset + 4)
{
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::clearcustomdatamenu);
map.nexttowercolour();
}
else if (game.currentmenuoption == gameplayoptionsoffset + 5) {
//return to previous menu
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
}
break;
}
case Menu::options:
switch (game.currentmenuoption)
{
case 0:
//gameplay options
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::gameplayoptions);
map.nexttowercolour();
break;
case 1:
//graphic options
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::graphicoptions);
map.nexttowercolour();
break;
case 2:
/* Audio options */
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::audiooptions);
map.nexttowercolour();
break;
case 3:
//gamepad options
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::controller);
map.nexttowercolour();
break;
case 4:
//accessibility options
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::accessibility);
map.nexttowercolour();
break;
case 5:
//language options
if (game.translator_cutscene_test)
{
music.playef(Sound_CRY);
break;
}
music.playef(Sound_VIRIDIAN);
loc::loadlanguagelist();
loc::pre_title_lang_menu = false;
game.createmenu(Menu::language);
game.currentmenuoption = loc::languagelist_curlang;
map.nexttowercolour();
break;
default:
/* Return */
music.playef(Sound_VIRIDIAN);
if (game.ingame_titlemode)
{
game.returntoingame();
}
else
{
game.returnmenu();
map.nexttowercolour();
}
break;
}
break;
case Menu::audiooptions:
switch (game.currentmenuoption)
{
case 0:
case 1:
music.playef(Sound_VIRIDIAN);
if (game.slidermode == SLIDER_NONE)
{
initvolumeslider(game.currentmenuoption);
}
else
{
deinitvolumeslider();
}
break;
case 2:
if (!music.mmmmmm)
{
break;
}
/* Toggle MMMMMM */
music.usingmmmmmm = !music.usingmmmmmm;
music.playef(Sound_VIRIDIAN);
if (music.currentsong > -1)
{
music.play(music.currentsong);
}
game.savestatsandsettings_menu();
break;
}
if (game.currentmenuoption == 2 + (int) music.mmmmmm)
{
/* Return */
game.returnmenu();
map.nexttowercolour();
music.playef(Sound_VIRIDIAN);
}
break;
case Menu::language:
{
std::string prev_lang = std::string(loc::lang);
music.playef(Sound_VIRIDIAN);
if (loc::languagelist.size() != 0 && (unsigned)game.currentmenuoption < loc::languagelist.size())
{
/* Update code also used in KeyPoll.cpp. */
loc::languagelist_curlang = game.currentmenuoption;
loc::lang = loc::languagelist[game.currentmenuoption].code;
loc::loadtext(false);
loc::lang_set = true;
graphics.grphx.init_translations();
}
if (loc::pre_title_lang_menu)
{
/* Make the title screen appear, we haven't seen it yet.
* game.returnmenu() works because Menu::mainmenu
* is created before the language menu. */
game.menustart = false;
loc::pre_title_lang_menu = false;
}
if (prev_lang != loc::lang)
{
recomputetextboxes();
}
game.returnmenu();
map.nexttowercolour();
game.savestatsandsettings_menu();
break;
}
case Menu::translator_main:
switch (game.currentmenuoption)
{
case 0:
// translator options
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::translator_options);
map.nexttowercolour();
break;
case 1:
// maintenance
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::translator_maintenance);
map.nexttowercolour();
break;
case 2:
// open lang folder
if (FILESYSTEM_openDirectoryEnabled()
&& FILESYSTEM_openDirectory(FILESYSTEM_getUserMainLangDirectory()))
{
music.playef(Sound_VIRIDIAN);
SDL_MinimizeWindow(gameScreen.m_window);
}
else
{
music.playef(Sound_CRY);
}
break;
default:
// return
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::translator_options:
switch (game.currentmenuoption)
{
case 0:
// language statistics
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::translator_options_stats);
map.nexttowercolour();
break;
case 1:
// translate room names
music.playef(Sound_VIRIDIAN);
roomname_translator::set_enabled(!roomname_translator::enabled);
game.savestatsandsettings_menu();
break;
case 2:
// explore game
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::translator_options_exploregame);
map.nexttowercolour();
break;
case 3:
// menu test
music.playef(Sound_GAMESAVED);
game.menutestmode = true;
game.createmenu((Menu::MenuName) 0);
map.nexttowercolour();
break;
case 4:
// cutscene test
if (loc::lang == "en")
{
music.playef(Sound_CRY);
}
else
{
music.playef(Sound_VIRIDIAN);
game.cutscenetest_menu_page = 0;
loc::populate_testable_script_ids();
game.createmenu(Menu::translator_options_cutscenetest);
map.nexttowercolour();
}
break;
case 5:
// limits check
music.playef(Sound_VIRIDIAN);
loc::local_limits_check();
game.createmenu(Menu::translator_options_limitscheck);
map.nexttowercolour();
break;
default:
// return
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::translator_options_limitscheck:
switch (game.currentmenuoption)
{
case 0:
// next
if (loc::limitscheck_current_overflow < loc::text_overflows.size())
{
music.playef(Sound_VIRIDIAN);
loc::limitscheck_current_overflow++;
}
break;
default:
// return
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::translator_options_stats:
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
case Menu::translator_options_exploregame:
music.playef(Sound_VIRIDIAN);
switch (game.currentmenuoption)
{
case 0:
game.start_translator_exploring = true;
startmode(Start_TIMETRIAL_SPACESTATION1);
break;
case 1:
game.start_translator_exploring = true;
startmode(Start_TIMETRIAL_LABORATORY);
break;
case 2:
game.start_translator_exploring = true;
startmode(Start_TIMETRIAL_TOWER);
break;
case 3:
game.start_translator_exploring = true;
startmode(Start_TIMETRIAL_SPACESTATION2);
break;
case 4:
game.start_translator_exploring = true;
startmode(Start_TIMETRIAL_WARPZONE);
break;
case 5:
game.createmenu(Menu::playint1);
game.start_translator_exploring = true;
map.nexttowercolour();
break;
case 6:
game.createmenu(Menu::playint2);
game.start_translator_exploring = true;
map.nexttowercolour();
break;
case 7:
game.start_translator_exploring = true;
startmode(Start_TIMETRIAL_FINALLEVEL);
break;
default:
// return
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::translator_options_cutscenetest:
if (game.currentmenuoption == (int)game.menuoptions.size()-4)
{
// next page
music.playef(Sound_VIRIDIAN);
if ((size_t) ((game.cutscenetest_menu_page*14)+14) >= loc::testable_script_ids.size())
{
game.cutscenetest_menu_page = 0;
}
else
{
game.cutscenetest_menu_page++;
}
game.createmenu(Menu::translator_options_cutscenetest, true);
game.currentmenuoption=game.menuoptions.size()-4;
map.nexttowercolour();
}
else if (game.currentmenuoption == (int)game.menuoptions.size()-3)
{
// previous page
music.playef(Sound_VIRIDIAN);
if (game.cutscenetest_menu_page == 0)
{
game.cutscenetest_menu_page = (loc::testable_script_ids.size()-1)/14;
}
else
{
game.cutscenetest_menu_page--;
}
game.createmenu(Menu::translator_options_cutscenetest, true);
game.currentmenuoption=game.menuoptions.size()-3;
map.nexttowercolour();
}
else if (game.currentmenuoption == (int)game.menuoptions.size()-2)
{
// play the cutscene, from clipboard
game.cutscenetest_menu_play_id = std::string(SDL_GetClipboardText());
startmode(Start_CUTSCENETEST);
}
else if (game.currentmenuoption == (int)game.menuoptions.size()-1)
{
// go back to menu
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
}
else
{
// play the cutscene!
game.cutscenetest_menu_play_id = loc::testable_script_ids[(game.cutscenetest_menu_page*14)+game.currentmenuoption];
startmode(Start_CUTSCENETEST);
}
break;
case Menu::translator_maintenance:
music.playef(Sound_VIRIDIAN);
switch (game.currentmenuoption)
{
case 0:
// sync languages
game.createmenu(Menu::translator_maintenance_sync);
map.nexttowercolour();
break;
case 1:
// global statistics
// TODO
map.nexttowercolour();
break;
case 2:
// global limits check
loc::global_limits_check();
game.createmenu(Menu::translator_options_limitscheck);
map.nexttowercolour();
break;
default:
// return
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::translator_maintenance_sync:
{
music.playef(Sound_VIRIDIAN);
bool sync_success = true;
if (game.currentmenuoption == 0)
{
// yes, sync files
sync_success = loc::sync_lang_files();
}
game.returnmenu();
map.nexttowercolour();
if (!sync_success)
{
game.createmenu(Menu::translator_error_setlangwritedir);
}
break;
}
case Menu::translator_error_setlangwritedir:
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
case Menu::unlockmenutrials:
switch (game.currentmenuoption)
{
case 0: //unlock 1
game.unlock[Unlock_TIMETRIAL_SPACESTATION1] = true;
game.unlocknotify[Unlock_TIMETRIAL_SPACESTATION1] = true;
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::unlockmenutrials, true);
game.savestatsandsettings_menu();
break;
case 1: //unlock 2
game.unlock[Unlock_TIMETRIAL_LABORATORY] = true;
game.unlocknotify[Unlock_TIMETRIAL_LABORATORY] = true;
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::unlockmenutrials, true);
game.savestatsandsettings_menu();
break;
case 2: //unlock 3
game.unlock[Unlock_TIMETRIAL_TOWER] = true;
game.unlocknotify[Unlock_TIMETRIAL_TOWER] = true;
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::unlockmenutrials, true);
game.savestatsandsettings_menu();
break;
case 3: //unlock 4
game.unlock[Unlock_TIMETRIAL_SPACESTATION2] = true;
game.unlocknotify[Unlock_TIMETRIAL_SPACESTATION2] = true;
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::unlockmenutrials, true);
game.savestatsandsettings_menu();
break;
case 4: //unlock 5
game.unlock[Unlock_TIMETRIAL_WARPZONE] = true;
game.unlocknotify[Unlock_TIMETRIAL_WARPZONE] = true;
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::unlockmenutrials, true);
game.savestatsandsettings_menu();
break;
case 5: //unlock 6
game.unlock[Unlock_TIMETRIAL_FINALLEVEL] = true;
game.unlocknotify[Unlock_TIMETRIAL_FINALLEVEL] = true;
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::unlockmenutrials, true);
game.savestatsandsettings_menu();
break;
case 6: //back
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::unlockmenu:
switch (game.currentmenuoption)
{
case 0:
//unlock time trials separately...
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::unlockmenutrials);
map.nexttowercolour();
break;
case 1:
//unlock intermissions
music.playef(Sound_VIRIDIAN);
game.unlock[Unlock_INTERMISSION_REPLAYS] = true;
game.unlocknotify[Unlock_INTERMISSION_REPLAYS] = true;
game.unlock[Unlock_INTERMISSION1_COMPLETE] = true;
game.unlock[Unlock_INTERMISSION2_COMPLETE] = true;
game.createmenu(Menu::unlockmenu, true);
game.savestatsandsettings_menu();
break;
case 2:
//unlock no death mode
music.playef(Sound_VIRIDIAN);
game.unlock[Unlock_NODEATHMODE] = true;
game.unlocknotify[Unlock_NODEATHMODE] = true;
game.createmenu(Menu::unlockmenu, true);
game.savestatsandsettings_menu();
break;
case 3:
//unlock flip mode
music.playef(Sound_VIRIDIAN);
game.unlock[Unlock_FLIPMODE] = true;
game.unlocknotify[Unlock_FLIPMODE] = true;
game.createmenu(Menu::unlockmenu, true);
game.savestatsandsettings_menu();
break;
case 4:
//unlock jukebox
music.playef(Sound_VIRIDIAN);
game.stat_trinkets = 20;
game.createmenu(Menu::unlockmenu, true);
game.savestatsandsettings_menu();
break;
case 5:
//unlock secret lab
music.playef(Sound_VIRIDIAN);
game.unlock[Unlock_SECRETLAB] = true;
game.unlocknotify[Unlock_SECRETLAB] = true;
game.createmenu(Menu::unlockmenu, true);
game.savestatsandsettings_menu();
break;
default:
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::credits:
switch (game.currentmenuoption)
{
case 0:
//next page
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::credits2, true);
map.nexttowercolour();
break;
case 1:
//last page
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::credits6, true);
map.nexttowercolour();
break;
default:
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::credits2:
switch (game.currentmenuoption)
{
case 0:
//next page
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::credits25, true);
map.nexttowercolour();
break;
case 1:
//previous page
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::credits, true);
map.nexttowercolour();
break;
case 2:
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::credits25:
switch (game.currentmenuoption)
{
case 0:
//next page
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::credits_localisations_implementation, true);
map.nexttowercolour();
break;
case 1:
//previous page
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::credits2, true);
map.nexttowercolour();
break;
default:
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::credits_localisations_implementation:
switch (game.currentmenuoption)
{
case 0:
//next page
music.playef(Sound_VIRIDIAN);
game.translator_credits_pagenum = 0;
game.current_credits_list_index = 0;
game.createmenu(Menu::credits_localisations_translations, true);
map.nexttowercolour();
break;
case 1:
//previous page
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::credits25, true);
map.nexttowercolour();
break;
default:
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::credits_localisations_translations:
switch (game.currentmenuoption)
{
case 0:
//next page
music.playef(Sound_VIRIDIAN);
game.translator_credits_pagenum++;
if (game.translator_credits_pagenum >= (int)SDL_arraysize(Credits::translator_pagesize))
{
// No more translators. Move to the next credits section
game.current_credits_list_index = 0;
game.createmenu(Menu::credits3, true);
}
else
{
// There are more translators. Refresh the menu with the next ones
game.current_credits_list_index = 0;
for (int i = 0; i < game.translator_credits_pagenum; i += 1)
{
game.current_credits_list_index += Credits::translator_pagesize[i];
}
game.createmenu(Menu::credits_localisations_translations, true);
}
map.nexttowercolour();
break;
case 1:
//previous page
music.playef(Sound_VIRIDIAN);
game.translator_credits_pagenum--;
if (game.translator_credits_pagenum >= 0)
{
game.current_credits_list_index = 0;
for (int i = 0; i < game.translator_credits_pagenum; i += 1)
{
game.current_credits_list_index += Credits::translator_pagesize[i];
}
game.createmenu(Menu::credits_localisations_translations, true);
}else {
//No more translators. Move to the previous credits section
game.current_credits_list_index = 0;
game.createmenu(Menu::credits_localisations_implementation, true);
}
map.nexttowercolour();
break;
default:
//back
music.playef(Sound_VIRIDIAN);
game.current_credits_list_index = 0;
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::credits3:
switch (game.currentmenuoption)
{
case 0:
//next page
music.playef(Sound_VIRIDIAN);
game.current_credits_list_index += 9;
if (game.current_credits_list_index >= (int)SDL_arraysize(Credits::superpatrons))
{
// No more super patrons. Move to the next credits section
game.current_credits_list_index = 0;
game.createmenu(Menu::credits4, true);
}
else
{
// There are more super patrons. Refresh the menu with the next ones
game.createmenu(Menu::credits3, true);
}
map.nexttowercolour();
break;
case 1:
//previous page
music.playef(Sound_VIRIDIAN);
game.current_credits_list_index -= 9;
if (game.current_credits_list_index < 0)
{
//No more super patrons. Move to the previous credits section
game.translator_credits_pagenum = (int)SDL_arraysize(Credits::translator_pagesize) - 1;
game.current_credits_list_index = 0;
for (int i = 0; i < game.translator_credits_pagenum; i += 1)
{
game.current_credits_list_index += Credits::translator_pagesize[i];
}
game.createmenu(Menu::credits_localisations_translations, true);
}
else
{
//There are more super patrons. Refresh the menu with the next ones
game.createmenu(Menu::credits3, true);
}
map.nexttowercolour();
break;
default:
//back
music.playef(Sound_VIRIDIAN);
game.current_credits_list_index = 0;
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::credits4:
switch (game.currentmenuoption)
{
case 0:
//next page
music.playef(Sound_VIRIDIAN);
game.current_credits_list_index += 14;
if (game.current_credits_list_index >= (int)SDL_arraysize(Credits::patrons))
{
// No more patrons. Move to the next credits section
game.current_credits_list_index = 0;
game.createmenu(Menu::credits5, true);
}
else
{
// There are more patrons. Refresh the menu with the next ones
game.createmenu(Menu::credits4, true);
}
map.nexttowercolour();
break;
case 1:
//previous page
music.playef(Sound_VIRIDIAN);
game.current_credits_list_index -= 14;
if (game.current_credits_list_index < 0)
{
//No more patrons. Move to the previous credits section
game.current_credits_list_index = SDL_arraysize(Credits::superpatrons) - 1 - (SDL_arraysize(Credits::superpatrons)-1)%9;
game.createmenu(Menu::credits3, true);
}
else
{
//There are more patrons. Refresh the menu with the next ones
game.createmenu(Menu::credits4, true);
}
map.nexttowercolour();
break;
default:
//back
music.playef(Sound_VIRIDIAN);
game.current_credits_list_index = 0;
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::credits5:
switch (game.currentmenuoption)
{
case 0:
//next page
music.playef(Sound_VIRIDIAN);
game.current_credits_list_index += 9;
if (game.current_credits_list_index >= (int)SDL_arraysize(Credits::githubfriends))
{
// No more GitHub contributors. Move to the next credits section
game.current_credits_list_index = 0;
game.createmenu(Menu::credits6, true);
}
else
{
// There are more GitHub contributors. Refresh the menu with the next ones
game.createmenu(Menu::credits5, true);
}
map.nexttowercolour();
break;
case 1:
//previous page
music.playef(Sound_VIRIDIAN);
game.current_credits_list_index -= 9;
if (game.current_credits_list_index < 0)
{
//No more GitHub contributors. Move to the previous credits section
game.current_credits_list_index = SDL_arraysize(Credits::patrons) - 1 - (SDL_arraysize(Credits::patrons)-1)%14;
game.createmenu(Menu::credits4, true);
}
else
{
//There are more GitHub contributors. Refresh the menu with the next ones
game.createmenu(Menu::credits5, true);
}
map.nexttowercolour();
break;
default:
//back
music.playef(Sound_VIRIDIAN);
game.current_credits_list_index = 0;
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::credits6:
switch (game.currentmenuoption)
{
case 0:
//first page
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::credits, true);
map.nexttowercolour();
break;
case 1:
//previous page
music.playef(Sound_VIRIDIAN);
game.current_credits_list_index = SDL_arraysize(Credits::githubfriends) - 1 - (SDL_arraysize(Credits::githubfriends)-1)%9;
game.createmenu(Menu::credits5, true);
map.nexttowercolour();
break;
default:
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::play:
{
//Do we have the Secret Lab option?
int sloffset = game.unlock[Unlock_SECRETLAB] ? 0 : -1;
//Do we have a telesave or quicksave?
int ngoffset = game.save_exists() ? 0 : -1;
if (game.currentmenuoption == 0)
{
//continue
//right, this depends on what saves you've got
if (!game.save_exists())
{
//You have no saves but have something unlocked, or you couldn't have gotten here
music.playef(Sound_VIRIDIAN);
startmode(Start_MAINGAME);
}
else if (!game.last_telesave.exists)
{
//You at least have a quicksave, or you couldn't have gotten here
music.playef(Sound_VIRIDIAN);
startmode(Start_MAINGAME_QUICKSAVE);
}
else if (!game.last_quicksave.exists)
{
//You at least have a telesave, or you couldn't have gotten here
music.playef(Sound_VIRIDIAN);
startmode(Start_MAINGAME_TELESAVE);
}
else
{
//go to a menu!
music.playef(Sound_VIRIDIAN);
game.loadsummary(); //Prepare save slots to display
game.createmenu(Menu::continuemenu);
}
}
else if (game.currentmenuoption == 1 && game.unlock[Unlock_SECRETLAB])
{
music.playef(Sound_VIRIDIAN);
startmode(Start_SECRETLAB);
}
else if (game.currentmenuoption == sloffset+2)
{
//play modes
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::playmodes);
map.nexttowercolour();
}
else if (game.currentmenuoption == sloffset+3 && game.save_exists())
{
//newgame
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::newgamewarning);
map.nexttowercolour();
}
else if (game.currentmenuoption == sloffset+ngoffset+4)
{
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
}
break;
}
case Menu::newgamewarning:
switch (game.currentmenuoption)
{
case 0:
//yep
music.playef(Sound_VIRIDIAN);
startmode(Start_MAINGAME);
game.deletequick();
game.deletetele();
break;
default:
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::controller:
switch (game.currentmenuoption)
{
case 0:
key.sensitivity++;
music.playef(Sound_VIRIDIAN);
if(key.sensitivity > 4)
{
key.sensitivity = 0;
}
game.savestatsandsettings_menu();
break;
case 6:
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::cleardatamenu:
switch (game.currentmenuoption)
{
case 0:
//back
music.playef(Sound_VIRIDIAN);
break;
default:
//yep
music.playef(Sound_DESTROY);
game.deletequick();
game.deletetele();
game.deletestats();
game.deletesettings();
game.flashlight = 5;
game.screenshake = 15;
break;
}
game.returnmenu();
map.nexttowercolour();
break;
case Menu::clearcustomdatamenu:
switch (game.currentmenuoption)
{
default:
music.playef(Sound_VIRIDIAN);
break;
case 1:
game.deletecustomlevelstats();
FILESYSTEM_deleteLevelSaves();
music.playef(Sound_DESTROY);
game.flashlight = 5;
game.screenshake = 15;
break;
}
game.returnmenu();
map.nexttowercolour();
break;
case Menu::playmodes:
if (game.currentmenuoption == 0
&& !game.nocompetitive_unless_translator()) //go to the time trial menu
{
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::timetrials);
map.nexttowercolour();
}
else if (game.currentmenuoption == 1
&& game.unlock[Unlock_INTERMISSION_REPLAYS])
{
//intermission mode menu
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::intermissionmenu);
map.nexttowercolour();
}
else if (game.currentmenuoption == 2
&& game.unlock[Unlock_NODEATHMODE]
&& !game.nocompetitive()) //start a game in no death mode
{
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::startnodeathmode);
map.nexttowercolour();
}
else if (game.currentmenuoption == 3
&& game.unlock[Unlock_FLIPMODE]) //enable/disable flip mode
{
toggleflipmode();
}
else if (game.currentmenuoption == 4)
{
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
}
else
{
//Can't do yet!
music.playef(Sound_CRY);
}
break;
case Menu::startnodeathmode:
switch (game.currentmenuoption)
{
case 0: //start no death mode, disabling cutscenes
music.playef(Sound_VIRIDIAN);
startmode(Start_NODEATHMODE_NOCUTSCENES);
break;
case 1:
music.playef(Sound_VIRIDIAN);
startmode(Start_NODEATHMODE_WITHCUTSCENES);
break;
case 2:
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::continuemenu:
switch (game.currentmenuoption)
{
case 0:
music.playef(Sound_VIRIDIAN);
startmode(Start_MAINGAME_TELESAVE);
break;
case 1:
music.playef(Sound_VIRIDIAN);
startmode(Start_MAINGAME_QUICKSAVE);
break;
case 2:
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::intermissionmenu:
switch (game.currentmenuoption)
{
case 0:
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::playint1);
map.nexttowercolour();
break;
case 1:
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::playint2);
map.nexttowercolour();
break;
case 2:
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::playint1:
switch (game.currentmenuoption)
{
case 0:
music.playef(Sound_VIRIDIAN);
startmode(Start_INTERMISSION1_VITELLARY);
break;
case 1:
music.playef(Sound_VIRIDIAN);
startmode(Start_INTERMISSION1_VERMILION);
break;
case 2:
music.playef(Sound_VIRIDIAN);
startmode(Start_INTERMISSION1_VERDIGRIS);
break;
case 3:
music.playef(Sound_VIRIDIAN);
startmode(Start_INTERMISSION1_VICTORIA);
break;
case 4:
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::playint2:
switch (game.currentmenuoption)
{
case 0:
music.playef(Sound_VIRIDIAN);
startmode(Start_INTERMISSION2_VITELLARY);
break;
case 1:
music.playef(Sound_VIRIDIAN);
startmode(Start_INTERMISSION2_VERMILION);
break;
case 2:
music.playef(Sound_VIRIDIAN);
startmode(Start_INTERMISSION2_VERDIGRIS);
break;
case 3:
music.playef(Sound_VIRIDIAN);
startmode(Start_INTERMISSION2_VICTORIA);
break;
case 4:
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
}
break;
case Menu::gameover2:
//back
music.playef(Sound_VIRIDIAN);
music.play(Music_PRESENTINGVVVVVV);
game.returntomenu(Menu::playmodes);
map.nexttowercolour();
break;
case Menu::unlocktimetrials:
case Menu::unlocktimetrial:
case Menu::unlocknodeathmode:
case Menu::unlockintermission:
case Menu::unlockflipmode:
//back
music.playef(Sound_VIRIDIAN);
game.createmenu(Menu::play, true);
map.nexttowercolour();
break;
case Menu::timetrials:
if (game.currentmenuoption == 0
&& game.unlock[Unlock_TIMETRIAL_SPACESTATION1])
{
music.playef(Sound_VIRIDIAN);
startmode(Start_TIMETRIAL_SPACESTATION1);
}
else if (game.currentmenuoption == 1
&& game.unlock[Unlock_TIMETRIAL_LABORATORY])
{
music.playef(Sound_VIRIDIAN);
startmode(Start_TIMETRIAL_LABORATORY);
}
else if (game.currentmenuoption == 2
&& game.unlock[Unlock_TIMETRIAL_TOWER])
{
music.playef(Sound_VIRIDIAN);
startmode(Start_TIMETRIAL_TOWER);
}
else if (game.currentmenuoption == 3
&& game.unlock[Unlock_TIMETRIAL_SPACESTATION2])
{
music.playef(Sound_VIRIDIAN);
startmode(Start_TIMETRIAL_SPACESTATION2);
}
else if (game.currentmenuoption == 4
&& game.unlock[Unlock_TIMETRIAL_WARPZONE])
{
music.playef(Sound_VIRIDIAN);
startmode(Start_TIMETRIAL_WARPZONE);
}
else if (game.currentmenuoption == 5
&& game.unlock[Unlock_TIMETRIAL_FINALLEVEL])
{
music.playef(Sound_VIRIDIAN);
startmode(Start_TIMETRIAL_FINALLEVEL);
}
else if (game.currentmenuoption == 6)
{
//back
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
}
else
{
//Can't do yet!
music.playef(Sound_CRY);
}
break;
case Menu::timetrialcomplete3:
switch (game.currentmenuoption)
{
case 0:
//back
music.playef(Sound_VIRIDIAN);
music.play(Music_PRESENTINGVVVVVV);
game.returntomenu(Menu::timetrials);
map.nexttowercolour();
/* FIXME: This is kinda bad kludge... but if we unlocked No Death Mode
* while in a Time Trial, the player wouldn't be notified until they went
* back to Menu::play first. This is the only case where something can be
* unlocked without being immediately notified after returning to title. */
if (game.can_unlock_ndm())
{
game.unlock_ndm();
}
break;
case 1:
/* Replay time trial */
music.playef(Sound_VIRIDIAN);
startmode((enum StartMode) (game.timetriallevel + Start_FIRST_TIMETRIAL));
break;
}
break;
case Menu::gamecompletecontinue:
case Menu::nodeathmodecomplete2:
music.play(Music_PRESENTINGVVVVVV);
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
case Menu::errorsavingsettings:
if (game.currentmenuoption == 1)
{
game.silence_settings_error = true;
}
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
case Menu::errorloadinglevel:
case Menu::warninglevellist:
music.playef(Sound_VIRIDIAN);
game.returnmenu();
map.nexttowercolour();
break;
default:
break;
}
}
void titleinput(void)
{
//game.mx = (mouseX / 4);
//game.my = (mouseY / 4);
game.press_left = false;
game.press_right = false;
game.press_action = false;
game.press_map = false;
game.press_interact = false;
bool lang_press_horizontal = false;
if (graphics.flipmode)
{
if (key.isDown(KEYBOARD_LEFT) || key.isDown(KEYBOARD_DOWN) || key.isDown(KEYBOARD_a) || key.isDown(KEYBOARD_s) || key.controllerWantsRight(true)) game.press_left = true;
if (key.isDown(KEYBOARD_RIGHT) || key.isDown(KEYBOARD_UP) || key.isDown(KEYBOARD_d) || key.isDown(KEYBOARD_w) || key.controllerWantsLeft(true)) game.press_right = true;
}
else if (game.currentmenuname == Menu::language)
{
if (key.isDown(KEYBOARD_UP) || key.isDown(KEYBOARD_w) || key.controllerWantsUp())
{
game.press_left = true;
}
if (key.isDown(KEYBOARD_DOWN) || key.isDown(KEYBOARD_s) || key.controllerWantsDown())
{
game.press_right = true;
}
if (key.isDown(KEYBOARD_LEFT) || key.isDown(KEYBOARD_a) || key.controllerWantsLeft(false)
|| key.isDown(KEYBOARD_RIGHT) || key.isDown(KEYBOARD_d) || key.controllerWantsRight(false))
{
lang_press_horizontal = true;
game.press_right = true;
}
}
else
{
SDL_Keycode left, right, a, d;
bool controller_up = key.controllerWantsUp();
bool controller_down = key.controllerWantsDown();
if (!font::is_rtl(PR_FONT_INTERFACE))
{
left = KEYBOARD_LEFT;
right = KEYBOARD_RIGHT;
a = KEYBOARD_a;
d = KEYBOARD_d;
controller_up |= key.controllerWantsLeft(false);
controller_down |= key.controllerWantsRight(false);
}
else
{
left = KEYBOARD_RIGHT;
right = KEYBOARD_LEFT;
a = KEYBOARD_d;
d = KEYBOARD_a;
controller_up |= key.controllerWantsRight(false);
controller_down |= key.controllerWantsLeft(false);
}
if (key.isDown(left) || key.isDown(KEYBOARD_UP) || key.isDown(a) || key.isDown(KEYBOARD_w) || controller_up)
{
game.press_left = true;
}
if (key.isDown(right) || key.isDown(KEYBOARD_DOWN) || key.isDown(d) || key.isDown(KEYBOARD_s) || controller_down)
{
game.press_right = true;
}
}
if (key.isDown(KEYBOARD_z) || key.isDown(KEYBOARD_SPACE) || key.isDown(KEYBOARD_v) || key.isDown(game.controllerButton_flip)) game.press_action = true;
//|| key.isDown(KEYBOARD_UP) || key.isDown(KEYBOARD_DOWN)) game.press_action = true; //on menus, up and down don't work as action
if (key.isDown(KEYBOARD_ENTER)) game.press_map = true;
//In the menu system, all keypresses are single taps rather than holds. Therefore this test has to be done for all presses
if (!game.press_action && !game.press_left && !game.press_right && !key.isDown(27) && !key.isDown(game.controllerButton_esc)) game.jumpheld = false;
if (!game.press_map) game.mapheld = false;
if (!game.jumpheld && graphics.fademode == FADE_NONE)
{
if (game.press_action || game.press_left || game.press_right || game.press_map || key.isDown(27) || key.isDown(game.controllerButton_esc))
{
game.jumpheld = true;
}
if ( game.currentmenuname == Menu::controller &&
game.currentmenuoption > 0 &&
game.currentmenuoption < 6 &&
(game.separate_interact || game.currentmenuoption < 5) &&
key.controllerButtonDown() )
{
updatebuttonmappings(game.currentmenuoption);
music.playef(Sound_VIRIDIAN);
game.savestatsandsettings_menu();
return;
}
if (game.menustart
&& game.menucountdown <= 0
&& (key.isDown(27) || key.isDown(game.controllerButton_esc)))
{
if (game.currentmenuname == Menu::language && loc::pre_title_lang_menu)
{
/* Don't exit from the initial language screen,
* you can't do this on the loading/title screen either. */
return;
}
else
{
music.playef(Sound_VIRIDIAN);
}
if (game.menutestmode)
{
game.menutestmode = false;
game.returnmenu();
map.nexttowercolour();
}
else if (game.currentmenuname == Menu::mainmenu)
{
game.createmenu(Menu::youwannaquit);
map.nexttowercolour();
}
else
{
if (game.slidermode != SLIDER_NONE)
{
switch (game.slidermode)
{
/* Cancel volume change. */
case SLIDER_MUSICVOLUME:
case SLIDER_SOUNDVOLUME:
if (user_changing_volume == NULL)
{
SDL_assert(0 && "user_changing_volume is NULL!");
break;
}
*user_changing_volume = previous_volume;
deinitvolumeslider();
break;
default:
SDL_assert(0 && "Unhandled slider mode!");
break;
}
}
else if (game.ingame_titlemode
&& game.currentmenuname == Menu::options)
{
game.returntoingame();
}
else
{
game.returnmenu();
map.nexttowercolour();
}
}
}
if(game.menustart)
{
if (game.slidermode == SLIDER_NONE)
{
if (game.currentmenuname == Menu::language)
{
/* The language screen has two columns and navigation in four directions.
* The second column may have one less option than the first. */
int n_options = game.menuoptions.size();
int twocol_voptions = n_options - (n_options/2);
if (lang_press_horizontal)
{
if (game.currentmenuoption < twocol_voptions)
{
game.currentmenuoption += twocol_voptions;
if (game.currentmenuoption >= n_options)
{
game.currentmenuoption = n_options - 1;
}
}
else
{
game.currentmenuoption -= twocol_voptions;
}
}
else
{
/* Vertical movement */
int min_option;
int max_option;
if (game.currentmenuoption < twocol_voptions)
{
min_option = 0;
max_option = twocol_voptions-1;
}
else
{
min_option = twocol_voptions;
max_option = n_options-1;
}
if (game.press_left) /* Up, lol */
{
game.currentmenuoption--;
if (game.currentmenuoption < min_option)
{
game.currentmenuoption = max_option;
}
}
else if (game.press_right) /* Down, lol */
{
game.currentmenuoption++;
if (game.currentmenuoption > max_option)
{
game.currentmenuoption = min_option;
}
}
}
}
else if (game.press_left)
{
game.currentmenuoption--;
}
else if (game.press_right)
{
game.currentmenuoption++;
}
}
else
{
slidermodeinput();
}
}
if (game.currentmenuoption < 0) game.currentmenuoption = game.menuoptions.size()-1;
if (game.currentmenuoption >= (int) game.menuoptions.size() ) game.currentmenuoption = 0;
if (game.press_action)
{
if (!game.menustart)
{
game.menustart = true;
music.play(Music_PRESENTINGVVVVVV);
music.playef(Sound_GAMESAVED);
game.screenshake = 10;
game.flashlight = 5;
}
else
{
menuactionpress();
}
}
}
if (fadetomode)
{
handlefadetomode();
}
}
void gameinput(void)
{
//TODO mouse input
//game.mx = (mouseX / 2);
//game.my = (mouseY / 2);
if(!script.running)
{
if (roomname_translator::enabled && roomname_translator::overlay_input())
{
return;
}
game.press_left = false;
game.press_right = false;
game.press_action = false;
game.press_interact = false;
if (key.isDown(KEYBOARD_LEFT) || key.isDown(KEYBOARD_a) || key.controllerWantsLeft(false))
{
game.press_left = true;
}
if (key.isDown(KEYBOARD_RIGHT) || key.isDown(KEYBOARD_d) || key.controllerWantsRight(false))
{
game.press_right = true;
}
if (key.isDown(KEYBOARD_z) || key.isDown(KEYBOARD_SPACE) || key.isDown(KEYBOARD_v)
|| key.isDown(KEYBOARD_UP) || key.isDown(KEYBOARD_DOWN) || key.isDown(KEYBOARD_w) || key.isDown(KEYBOARD_s)|| key.isDown(game.controllerButton_flip))
{
game.press_action = true;
}
if (key.isDown(KEYBOARD_e) || key.isDown(game.controllerButton_interact))
{
game.press_interact = true;
}
}
game.press_map = false;
if (key.isDown(KEYBOARD_ENTER) || key.isDown(SDLK_KP_ENTER) || key.isDown(game.controllerButton_map) )
{
game.press_map = true;
}
level_debugger::input();
if (level_debugger::is_pausing())
{
return;
}
if (game.advancetext)
{
if (game.pausescript)
{
game.press_action = false;
if (key.isDown(KEYBOARD_z) || key.isDown(KEYBOARD_SPACE) || key.isDown(KEYBOARD_v)
|| key.isDown(KEYBOARD_UP) || key.isDown(KEYBOARD_DOWN) || key.isDown(KEYBOARD_w) || key.isDown(KEYBOARD_s) || key.isDown(game.controllerButton_flip)) game.press_action = true;
}
if (game.press_action && !game.jumpheld)
{
if (game.pausescript)
{
game.pausescript = false;
game.hascontrol = true;
game.jumpheld = true;
}
else
{
if (GlitchrunnerMode_less_than_or_equal(Glitchrunner2_0)
|| !game.glitchrunkludge)
{
game.state++;
}
game.jumpheld = true;
game.glitchrunkludge=true;
//Bug fix! You should only be able to do this ONCE.
//...Unless you're in glitchrunner mode
}
}
}
if (!game.press_map
//Extra conditionals as a kludge fix so if you open the quit menu during
//the script command gamemode(teleporter) and close it with Esc, it won't
//immediately open again
//We really need a better input system soon...
&& !key.isDown(27)
&& !key.isDown(game.controllerButton_esc))
{
game.mapheld = false;
}
if (!game.press_interact)
{
game.interactheld = false;
}
if (game.intimetrial && graphics.fademode == FADE_FULLY_BLACK && game.quickrestartkludge && !game.translator_exploring)
{
//restart the time trial
game.quickrestartkludge = false;
script.startgamemode((enum StartMode) (game.timetriallevel + Start_FIRST_TIMETRIAL));
game.deathseq = -1;
game.completestop = false;
game.hascontrol = false;
}
//Returning to editor mode must always be possible
if (map.custommode && !map.custommodeforreal)
{
if ((game.press_map || key.isDown(27)) && !game.mapheld)
{
if (!game.separate_interact
&& game.press_map
&& (INBOUNDS_VEC(game.activeactivity, obj.blocks)
|| (game.activetele && game.readytotele > 20)))
{
/* Pass, let code block below handle it */
}
else
{
game.returntoeditor();
game.mapheld = true;
}
}
}
//Entity type 0 is player controled
bool has_control = false;
bool enter_pressed = game.press_map && !game.mapheld;
bool enter_already_processed = false;
bool interact_pressed;
if (game.separate_interact)
{
interact_pressed = game.press_interact && !game.interactheld;
}
else
{
interact_pressed = enter_pressed;
}
for (size_t ie = 0; ie < obj.entities.size(); ++ie)
{
if (obj.entities[ie].rule == 0)
{
if (game.hascontrol && game.deathseq == -1 && game.lifeseq <= 5)
{
has_control = true;
if (interact_pressed)
{
game.interactheld = true;
if (!game.separate_interact)
{
game.mapheld = true;
}
}
if (interact_pressed && !script.running)
{
if (game.activetele && game.readytotele > 20 && (!game.intimetrial || game.translator_exploring_allowtele))
{
enter_already_processed = true;
if(int(SDL_fabsf(obj.entities[ie].vx))<=1 && int(obj.entities[ie].vy)==0)
{
//wait! space station 2 debug thingy
if (game.teleportscript != "")
{
//trace(game.recordstring);
//We're teleporting! Yey!
game.activetele = false;
game.hascontrol = false;
music.fadeout();
int player = obj.getplayer();
if (INBOUNDS_VEC(player, obj.entities))
{
obj.entities[player].colour = 102;
}
int teleporter = obj.getteleporter();
if (INBOUNDS_VEC(teleporter, obj.entities))
{
obj.entities[teleporter].tile = 6;
obj.entities[teleporter].colour = 102;
}
//which teleporter script do we use? it depends on the companion!
game.setstate(4000);
game.setstatedelay(0);
}
else if (game.companion == 0 && !game.translator_exploring_allowtele)
{
//Alright, normal teleporting
game.mapmenuchange(TELEPORTERMODE, true);
game.useteleporter = true;
game.initteleportermode();
}
else
{
//We're teleporting! Yey!
game.activetele = false;
game.hascontrol = false;
music.fadeout();
int player = obj.getplayer();
if (INBOUNDS_VEC(player, obj.entities))
{
obj.entities[player].colour = 102;
}
int companion = obj.getcompanion();
if(INBOUNDS_VEC(companion, obj.entities)) obj.entities[companion].colour = 102;
int teleporter = obj.getteleporter();
if (INBOUNDS_VEC(teleporter, obj.entities))
{
obj.entities[teleporter].tile = 6;
obj.entities[teleporter].colour = 102;
}
//which teleporter script do we use? it depends on the companion!
game.setstate(3000);
game.setstatedelay(0);
}
}
}
else if (INBOUNDS_VEC(game.activeactivity, obj.blocks))
{
enter_already_processed = true;
if((int(SDL_fabsf(obj.entities[ie].vx))<=1) && (int(obj.entities[ie].vy) == 0) )
{
script.load(obj.blocks[game.activeactivity].script);
obj.disableblock(game.activeactivity);
game.activeactivity = -1;
}
}
}
if(game.press_left)
{
obj.entities[ie].ax = -3;
obj.entities[ie].dir = 0;
}
else if (game.press_right)
{
obj.entities[ie].ax = 3;
obj.entities[ie].dir = 1;
}
}
}
}
if (has_control)
{
if (game.press_left)
{
game.tapleft++;
}
else
{
if (game.tapleft <= 4 && game.tapleft > 0)
{
for (size_t ie = 0; ie < obj.entities.size(); ++ie)
{
if (obj.entities[ie].rule == 0)
{
if (obj.entities[ie].vx < 0.0f)
{
obj.entities[ie].vx = 0.0f;
}
}
}
}
game.tapleft = 0;
}
if (game.press_right)
{
game.tapright++;
}
else
{
if (game.tapright <= 4 && game.tapright > 0)
{
for (size_t ie = 0; ie < obj.entities.size(); ++ie)
{
if (obj.entities[ie].rule == 0)
{
if (obj.entities[ie].vx > 0.0f)
{
obj.entities[ie].vx = 0.0f;
}
}
}
}
game.tapright = 0;
}
if (!game.press_action)
{
game.jumppressed = 0;
game.jumpheld = false;
}
if (game.press_action && !game.jumpheld)
{
game.jumppressed = 5;
game.jumpheld = true;
}
std::vector<size_t> player_entities;
for (size_t ie = 0; ie < obj.entities.size(); ie++)
{
if (obj.entities[ie].rule == 0)
{
player_entities.push_back(ie);
}
}
for (size_t ie = 0; ie < obj.entities.size(); ie++)
{
const bool process_flip = obj.entities[ie].rule == 0 &&
game.jumppressed > 0;
if (!process_flip)
{
continue;
}
game.jumppressed--;
if (obj.entities[ie].onground > 0 && game.gravitycontrol == 0)
{
game.gravitycontrol = 1;
for (size_t j = 0; j < player_entities.size(); j++)
{
const size_t e = player_entities[j];
if (obj.entities[e].onground > 0 || obj.entities[e].onroof > 0)
{
obj.entities[e].vy = -4;
obj.entities[e].ay = -3;
}
}
music.playef(Sound_FLIP);
game.jumppressed = 0;
game.totalflips++;
}
if (obj.entities[ie].onroof > 0 && game.gravitycontrol == 1)
{
game.gravitycontrol = 0;
for (size_t j = 0; j < player_entities.size(); j++)
{
const size_t e = player_entities[j];
if (obj.entities[e].onground > 0 || obj.entities[e].onroof > 0)
{
obj.entities[e].vy = 4;
obj.entities[e].ay = 3;
}
}
music.playef(Sound_UNFLIP);
game.jumppressed = 0;
game.totalflips++;
}
}
}
else
{
//Simple detection of keypresses outside player control, will probably scrap this (expand on
//advance text function)
if (!game.press_action)
{
game.jumppressed = 0;
game.jumpheld = false;
}
if (game.press_action && !game.jumpheld)
{
game.jumppressed = 5;
game.jumpheld = true;
}
}
/* The rest of the if-tree runs only if enter is pressed and it has not
* already been processed with 'separate interact' off.
*/
if (!enter_pressed || (enter_already_processed && !game.separate_interact))
{
// Do nothing
}
else if (game.swnmode == 1
&& (game.swngame == SWN_SUPERGRAVITRON ||
game.swngame == SWN_START_SUPERGRAVITRON_STEP_1 ||
game.swngame == SWN_START_SUPERGRAVITRON_STEP_2))
{
//quitting the super gravitron
game.mapheld = true;
//Quit menu, same conditions as in game menu
game.mapmenuchange(MAPMODE, true);
game.gamesaved = false;
game.gamesavefailed = false;
game.menupage = 20; // The Map Page
}
else if (game.intimetrial && graphics.fademode == FADE_NONE && !game.translator_exploring)
{
//Quick restart of time trial
graphics.fademode = FADE_START_FADEOUT;
game.completestop = true;
music.fadeout();
game.quickrestartkludge = true;
}
else if (game.intimetrial && !game.translator_exploring)
{
//Do nothing if we're in a Time Trial but a fade animation is playing
}
else if (map.custommode && !map.custommodeforreal)
{
// We're playtesting in the editor so don't do anything
}
else
{
//Normal map screen, do transition later
game.mapmenuchange(MAPMODE, true);
map.cursordelay = 0;
map.cursorstate = 0;
game.gamesaved = false;
game.gamesavefailed = false;
if (script.running)
{
game.menupage = 3; // Only allow saving
}
else
{
game.menupage = 0; // The Map Page
}
}
if (!game.mapheld
&& (key.isDown(27) || key.isDown(game.controllerButton_esc))
&& (!map.custommode || map.custommodeforreal))
{
game.mapheld = true;
//Quit menu, same conditions as in game menu
game.mapmenuchange(MAPMODE, true);
game.gamesaved = false;
game.gamesavefailed = false;
game.menupage = 30; // Pause screen
}
if (game.deathseq == -1 && (key.isDown(SDLK_r) || key.isDown(game.controllerButton_restart)) && !game.nodeathmode)// && map.custommode) //Have fun glitchrunners!
{
game.deathseq = 30;
}
}
static void mapmenuactionpress(bool version2_2);
void mapinput(void)
{
const bool version2_2 = GlitchrunnerMode_less_than_or_equal(Glitchrunner2_2);
//TODO Mouse Input!
//game.mx = (mouseX / 2);
//game.my = (mouseY / 2);
game.press_left = false;
game.press_right = false;
game.press_action = false;
game.press_map = false;
game.press_interact = false;
if (version2_2 && graphics.fademode == FADE_FULLY_BLACK && graphics.menuoffset == 0)
{
// Deliberate re-addition of the glitchy gamestate-based fadeout!
// First of all, detecting a black screen means if the glitchy fadeout
// gets interrupted but you're still on a black screen, opening a menu
// immediately quits you to the title. This has the side effect that if
// you accidentally press Esc during a cutscene when it's black, you'll
// immediately be quit and lose all your progress, but that's fair in
// glitchrunner mode.
// Also have to check graphics.menuoffset so this doesn't run every frame
// Have to close the menu in order to run gamestates
graphics.resumegamemode = true;
// Remove half-second delay
graphics.menuoffset = 250;
// Technically this was in <=2.2 as well
obj.removeallblocks();
if (game.menupage >= 20 && game.menupage <= 21)
{
game.setstate(96);
game.setstatedelay(0);
}
else
{
// Produces more glitchiness! Necessary for credits warp to work.
script.running = false;
graphics.textboxes.clear();
game.setstate(80);
game.setstatedelay(0);
}
}
if (game.fadetomenu && !version2_2)
{
if (game.fadetomenudelay > 0)
{
game.fadetomenudelay--;
}
else
{
game.quittomenu();
music.play(Music_PRESENTINGVVVVVV); // should be after game.quittomenu()
game.fadetomenu = false;
}
}
if (game.fadetolab && !version2_2)
{
if (game.fadetolabdelay > 0)
{
game.fadetolabdelay--;
}
else
{
game.returntolab();
game.fadetolab = false;
}
}
if(graphics.menuoffset==0
&& ((!version2_2 && !game.fadetomenu && game.fadetomenudelay <= 0 && !game.fadetolab && game.fadetolabdelay <= 0)
|| graphics.fademode == FADE_NONE))
{
SDL_Keycode left, right, a, d;
bool controller_up = key.controllerWantsUp();
bool controller_down = key.controllerWantsDown();
if (!font::is_rtl(PR_FONT_INTERFACE))
{
left = KEYBOARD_LEFT;
right = KEYBOARD_RIGHT;
a = KEYBOARD_a;
d = KEYBOARD_d;
controller_up |= key.controllerWantsLeft(false);
controller_down |= key.controllerWantsRight(false);
}
else
{
left = KEYBOARD_RIGHT;
right = KEYBOARD_LEFT;
a = KEYBOARD_d;
d = KEYBOARD_a;
controller_up |= key.controllerWantsRight(false);
controller_down |= key.controllerWantsLeft(false);
}
if (key.isDown(left) || key.isDown(KEYBOARD_UP) || key.isDown(a) || key.isDown(KEYBOARD_w)|| controller_up)
{
game.press_left = true;
}
if (key.isDown(right) || key.isDown(KEYBOARD_DOWN) || key.isDown(d) || key.isDown(KEYBOARD_s)|| controller_down)
{
game.press_right = true;
}
if (key.isDown(KEYBOARD_z) || key.isDown(KEYBOARD_SPACE) || key.isDown(KEYBOARD_v) || key.isDown(game.controllerButton_flip))
{
game.press_action = true;
}
if (game.menupage < 12
|| (game.menupage >= 20 && game.menupage <= 21)
|| (game.menupage >= 30 && game.menupage <= 32))
{
if (key.isDown(KEYBOARD_ENTER) || key.isDown(game.controllerButton_map) ) game.press_map = true;
if (key.isDown(27) && !game.mapheld)
{
game.mapheld = true;
if (game.menupage < 9
|| (game.menupage >= 20 && game.menupage <= 21))
{
game.menupage = 30;
}
else if (game.menupage < 12)
{
game.menupage = 32;
}
else
{
graphics.resumegamemode = true;
}
music.playef(Sound_VIRIDIAN);
}
}
else
{
if (key.isDown(KEYBOARD_ENTER) || key.isDown(27)|| key.isDown(game.controllerButton_map) ) game.press_map = true;
}
//In the menu system, all keypresses are single taps rather than holds. Therefore this test has to be done for all presses
if (!game.press_action && !game.press_left && !game.press_right)
{
game.jumpheld = false;
}
if (!game.press_map && !key.isDown(27))
{
game.mapheld = false;
}
}
else
{
game.mapheld = true;
game.jumpheld = true;
}
if (!game.mapheld)
{
if(game.press_map && game.menupage < 10)
{
//Normal map screen, do transition later
graphics.resumegamemode = true;
}
}
if (!game.jumpheld)
{
if (game.press_action || game.press_left || game.press_right || game.press_map)
{
game.jumpheld = true;
}
if (script.running && game.menupage == 3)
{
// Force the player to stay in the SAVE tab while in a cutscene
}
else if (game.press_left)
{
game.menupage--;
}
else if (game.press_right)
{
game.menupage++;
}
if (game.press_action)
{
mapmenuactionpress(version2_2);
}
if (game.menupage < 0) game.menupage = 3;
if (game.menupage > 3 && game.menupage < 9) game.menupage = 0;
if (game.menupage == 9) game.menupage = 11;
if (game.menupage == 12) game.menupage = 10;
if (game.menupage == 19) game.menupage = 21;
if (game.menupage == 22) game.menupage = 20;
if (game.menupage == 29) game.menupage = 32;
if (game.menupage == 33) game.menupage = 30;
}
}
static void mapmenuactionpress(const bool version2_2)
{
switch (game.menupage)
{
case 1:
if (obj.flags[67] && !game.inspecial() && !map.custommode)
{
//Warp back to the ship
graphics.resumegamemode = true;
game.teleport_to_x = 2;
game.teleport_to_y = 11;
//trace(game.recordstring);
//We're teleporting! Yey!
game.activetele = false;
game.hascontrol = false;
int i = obj.getplayer();
if (INBOUNDS_VEC(i, obj.entities))
{
obj.entities[i].colour = 102;
}
//which teleporter script do we use? it depends on the companion!
game.setstate(4000);
game.setstatedelay(0);
game.lockstate();
}
break;
case 3:
if (!game.gamesaved && !game.gamesavefailed && !game.inspecial())
{
game.flashlight = 5;
game.screenshake = 10;
music.playef(Sound_GAMESAVED);
game.savetime = game.timestring();
game.savetrinkets = game.trinkets();
bool success;
if(map.custommodeforreal)
{
success = game.customsavequick(cl.ListOfMetaData[game.playcustomlevel].filename);
}
else
{
success = game.savequick();
}
game.gamesaved = success;
game.gamesavefailed = !success;
}
break;
case 10:
//return to pause menu
music.playef(Sound_VIRIDIAN);
game.menupage = 32;
break;
case 11:
//quit to menu
graphics.fademode = FADE_START_FADEOUT;
music.fadeout();
map.nexttowercolour();
if (!version2_2)
{
game.fadetomenu = true;
game.fadetomenudelay = 19;
}
music.playef(Sound_VIRIDIAN);
break;
case 20:
//return to game
graphics.resumegamemode = true;
music.playef(Sound_VIRIDIAN);
break;
case 21:
//quit to menu
game.swnmode = false;
graphics.fademode = FADE_START_FADEOUT;
music.fadeout();
if (!version2_2)
{
game.fadetolab = true;
game.fadetolabdelay = 19;
}
music.playef(Sound_VIRIDIAN);
break;
case 30:
// Return to game
graphics.resumegamemode = true;
music.playef(Sound_VIRIDIAN);
break;
case 31:
// Graphic options and game options
music.playef(Sound_VIRIDIAN);
game.gamestate = TITLEMODE;
graphics.flipmode = false;
game.ingame_titlemode = true;
graphics.ingame_fademode = graphics.fademode;
graphics.fademode = FADE_NONE;
// Set this before we create the menu
game.kludge_ingametemp = game.currentmenuname;
game.createmenu(Menu::options);
map.nexttowercolour();
break;
case 32:
// Go to quit prompt
music.playef(Sound_VIRIDIAN);
game.menupage = 10;
break;
}
}
void teleporterinput(void)
{
//Todo Mouseinput!
//game.mx = (mouseX / 2);
//game.my = (mouseY / 2);
int tempx, tempy;
game.press_left = false;
game.press_right = false;
game.press_action = false;
game.press_map = false;
game.press_interact = false;
if(graphics.menuoffset==0)
{
if (key.isDown(KEYBOARD_LEFT)|| key.isDown(KEYBOARD_a) || key.controllerWantsLeft(false) ) game.press_left = true;
if (key.isDown(KEYBOARD_RIGHT) || key.isDown(KEYBOARD_d)|| key.controllerWantsRight(false) ) game.press_right = true;
if (key.isDown(KEYBOARD_z) || key.isDown(KEYBOARD_SPACE) || key.isDown(KEYBOARD_v)
|| key.isDown(KEYBOARD_UP) || key.isDown(KEYBOARD_DOWN)|| key.isDown(KEYBOARD_w)|| key.isDown(KEYBOARD_s) || key.isDown(game.controllerButton_flip)) game.press_action = true;
if (!game.separate_interact && (key.isDown(KEYBOARD_ENTER) || key.isDown(game.controllerButton_map)))
{
game.press_map = true;
}
if (key.isDown(KEYBOARD_e) || key.isDown(game.controllerButton_interact))
{
game.press_interact = true;
}
//In the menu system, all keypresses are single taps rather than holds. Therefore this test has to be done for all presses
if (!game.press_action && !game.press_left && !game.press_right && !game.press_interact) game.jumpheld = false;
if (!game.press_map) game.mapheld = false;
if (key.isDown(27))
{
if (!map.custommode || map.custommodeforreal)
{
// Go to pause menu
game.mapheld = true;
game.menupage = 30;
game.gamestate = MAPMODE;
}
else
{
// Close teleporter menu
graphics.resumegamemode = true;
}
music.playef(Sound_VIRIDIAN);
}
}
else
{
game.mapheld = true;
game.jumpheld = true;
}
if (!game.jumpheld)
{
if (game.press_action || game.press_left || game.press_right || game.press_map || game.press_interact)
{
game.jumpheld = true;
}
bool any_tele_unlocked = false;
if (game.press_left || game.press_right)
{
for (size_t i = 0; i < map.teleporters.size(); i++)
{
SDL_Point& tele = map.teleporters[i];
if (map.isexplored(tele.x, tele.y))
{
any_tele_unlocked = true;
break;
}
}
}
if (game.press_left && any_tele_unlocked)
{
do
{
game.teleport_to_teleporter--;
if (game.teleport_to_teleporter < 0) game.teleport_to_teleporter = map.teleporters.size() - 1;
tempx = map.teleporters[game.teleport_to_teleporter].x;
tempy = map.teleporters[game.teleport_to_teleporter].y;
}
while (!map.isexplored(tempx, tempy));
}
else if (game.press_right && any_tele_unlocked)
{
do
{
game.teleport_to_teleporter++;
if (game.teleport_to_teleporter >= (int) map.teleporters.size()) game.teleport_to_teleporter = 0;
tempx = map.teleporters[game.teleport_to_teleporter].x;
tempy = map.teleporters[game.teleport_to_teleporter].y;
}
while (!map.isexplored(tempx, tempy));
}
if ((game.separate_interact && game.press_interact) || game.press_map)
{
tempx = map.teleporters[game.teleport_to_teleporter].x;
tempy = map.teleporters[game.teleport_to_teleporter].y;
if (game.roomx == tempx + 100 && game.roomy == tempy + 100)
{
//cancel!
graphics.resumegamemode = true;
}
else
{
//teleport
graphics.resumegamemode = true;
game.teleport_to_x = tempx;
game.teleport_to_y = tempy;
//trace(game.recordstring);
//We're teleporting! Yey!
game.activetele = false;
game.hascontrol = false;
int i = obj.getplayer();
if (INBOUNDS_VEC(i, obj.entities))
{
obj.entities[i].colour = 102;
}
i = obj.getteleporter();
if (INBOUNDS_VEC(i, obj.entities))
{
obj.entities[i].tile = 6;
obj.entities[i].colour = 102;
}
//which teleporter script do we use? it depends on the companion!
game.setstate(4000);
game.setstatedelay(0);
}
}
}
}
void gamecompleteinput(void)
{
game.press_left = false;
game.press_right = false;
game.press_action = false;
game.press_map = false;
game.press_interact = false;
//Do this before we update map.bypos
if (!game.colourblindmode)
{
graphics.updatetowerbackground(graphics.titlebg);
}
//Do these here because input comes first
graphics.titlebg.bypos += graphics.titlebg.bscroll;
game.oldcreditposition = game.creditposition;
if (key.isDown(KEYBOARD_z) || key.isDown(KEYBOARD_SPACE) || key.isDown(KEYBOARD_v) || key.isDown(game.controllerButton_flip))
{
game.creditposition -= 6;
if (game.creditposition <= -Credits::creditmaxposition)
{
if (graphics.fademode == FADE_NONE)
{
graphics.fademode = FADE_START_FADEOUT;
}
game.creditposition = -Credits::creditmaxposition;
}
else
{
graphics.titlebg.bscroll = +7;
}
game.press_action = true;
}
if (key.isDown(KEYBOARD_ENTER)|| key.isDown(game.controllerButton_map)) game.press_map = true;
if (!game.mapheld)
{
if(game.press_map)
{
//Return to game
if(graphics.fademode == FADE_NONE)
{
graphics.fademode = FADE_START_FADEOUT;
}
}
}
if (!game.press_map)
{
game.mapheld = false;
}
}
void gamecompleteinput2(void)
{
game.press_left = false;
game.press_right = false;
game.press_action = false;
game.press_map = false;
game.press_interact = false;
//Do this here because input comes first
game.oldcreditposx = game.creditposx;
if (key.isDown(KEYBOARD_z) || key.isDown(KEYBOARD_SPACE) || key.isDown(KEYBOARD_v) || key.isDown(game.controllerButton_flip))
{
game.creditposx++;
game.oldcreditposx++;
if (game.creditposy >= 30)
{
if(graphics.fademode == FADE_NONE)
{
graphics.fademode = FADE_START_FADEOUT;
music.fadeout();
}
}
game.press_action = true;
}
if (key.isDown(KEYBOARD_ENTER) || key.isDown(game.controllerButton_map)) game.press_map = true;
if (!game.mapheld)
{
if(game.press_map)
{
//Return to game
if(graphics.fademode == FADE_NONE)
{
graphics.fademode = FADE_START_FADEOUT;
music.fadeout();
}
}
}
if (!game.press_map)
{
game.mapheld = false;
}
}