diff --git a/Docs/Changelog_sm5.txt b/Docs/Changelog_sm5.txt
index 7ec3bd71c6..283da29a30 100644
--- a/Docs/Changelog_sm5.txt
+++ b/Docs/Changelog_sm5.txt
@@ -4,6 +4,18 @@ The StepMania 5 Changelog covers all post-sm-ssc changes. For a list of changes
from StepMania 4 alpha 5 to sm-ssc v1.2.5, see Changelog_sm-ssc.txt.
________________________________________________________________________________
+2016/02/03
+----------
+* [ScreenManager] Added PlayInvalidSound, PlayStartSound, PlayCoinSound,
+ PlayCancelSound, and PlayScreenshotSound lua bindings. [kyzentun]
+ Added get_input_redirected and set_input_redirected to allow the theme to
+ disable the normal input functions. (Example: a custom lua menu on
+ Select Music. When the menu is up, the theme doesn't want the player's
+ input to move the music wheel.) This is in SCREENMAN so that it will work
+ on all screens. [kyzentun]
+* [ScreenSelectMusic] Added CanOpenOptionsList lua binding. OpenOptionsList
+ will do nothing if CanOpenOptionsList returns false. [kyzentun]
+
2016/01/18
----------
* [Edit Mode] Added "Clear timing in region" to timing menu. [kyzentun]
diff --git a/Docs/Luadoc/Lua.xml b/Docs/Luadoc/Lua.xml
index 4fd6aa5f36..660c376c16 100644
--- a/Docs/Luadoc/Lua.xml
+++ b/Docs/Luadoc/Lua.xml
@@ -1488,10 +1488,17 @@
+
+
+
+
+
+
+
@@ -1529,6 +1536,7 @@
+
diff --git a/Docs/Luadoc/LuaDocumentation.xml b/Docs/Luadoc/LuaDocumentation.xml
index b4f5ce277f..0522f84c28 100644
--- a/Docs/Luadoc/LuaDocumentation.xml
+++ b/Docs/Luadoc/LuaDocumentation.xml
@@ -4389,6 +4389,24 @@ save yourself some time, copy this for undocumented things:
Gets the screen at the top of the screen stack.
+
+ Returns whether the input for the player has been redirected away from the normal screen input function. Input that has been redirected is only sent to lua input callbacks.
+
+
+ Plays the invalid sound.
+
+
+ Plays the start sound.
+
+
+ Plays the coin sound.
+
+
+ Plays the cancel sound.
+
+
+ Plays the screenshot sound.
+
Reloads any loaded overlay screens.
@@ -4401,6 +4419,10 @@ save yourself some time, copy this for undocumented things:
Sets the next screen to s.
+
+ Sets whether the input for the player has been redirected away from the normal screen input function. Input that has been redirected is only sent to lua input callbacks.
+ This can be useful when putting a custom menu on a screen, and you want to disable the built in actors while the menu is open. Then you handle input through an input callback until the player closes the menu.
+
Broadcasts a system message.
@@ -4482,6 +4504,9 @@ save yourself some time, copy this for undocumented things:
+
+ Returns false if the options list is already open or the UseOptionsList metric is false.
+
Returns true if the player is going to the options screen.
diff --git a/src/Font.cpp b/src/Font.cpp
index 2d46908580..99610d8c4d 100644
--- a/src/Font.cpp
+++ b/src/Font.cpp
@@ -610,7 +610,7 @@ void Font::LoadFontPageSettings( FontPageSettings &cfg, IniFile &ini, const RStr
{
LuaHelpers::ReportScriptErrorFmt(
"The font definition \"%s\" tries to assign line %i, "
- "but the font is only %i characters high."
+ "but the font is only %i characters high. "
"Line numbers start at 0.",
ini.GetPath().c_str(), first_frame, num_frames_high);
continue;
diff --git a/src/RageSound.cpp b/src/RageSound.cpp
index 81fafdcfe4..d3dd0c2a0e 100644
--- a/src/RageSound.cpp
+++ b/src/RageSound.cpp
@@ -86,7 +86,10 @@ RageSound &RageSound::operator=( const RageSound &cpy )
m_bPlaying = false;
m_bDeleteWhenFinished = false;
- delete m_pSource;
+ if(m_pSource != NULL)
+ {
+ delete m_pSource;
+ }
if( cpy.m_pSource )
m_pSource = cpy.m_pSource->Copy();
else
@@ -104,7 +107,10 @@ void RageSound::Unload()
LockMut(m_Mutex);
- delete m_pSource;
+ if(m_pSource != NULL)
+ {
+ delete m_pSource;
+ }
m_pSource = NULL;
m_sFilePath = "";
diff --git a/src/RageSoundReader_Vorbisfile.cpp b/src/RageSoundReader_Vorbisfile.cpp
index 5d6fb69da4..2c403e84fe 100644
--- a/src/RageSoundReader_Vorbisfile.cpp
+++ b/src/RageSoundReader_Vorbisfile.cpp
@@ -46,6 +46,11 @@ static RString ov_ssprintf( int err, const char *fmt, ...)
RString errstr;
switch( err )
{
+ // OV_FALSE, OV_EOF, and OV_HOLE were added to this switch because
+ // OV_EOF cases were being reported as unknown. -Kyz
+ case OV_FALSE: errstr = "OV_FALSE"; break;
+ case OV_EOF: errstr = "OV_EOF"; break;
+ case OV_HOLE: errstr = "OV_HOLE"; break;
/* XXX: In the case of OV_EREAD, can we snoop at errno? */
case OV_EREAD: errstr = "Read error"; break;
case OV_EFAULT: errstr = "Internal error"; break;
@@ -123,7 +128,7 @@ int RageSoundReader_Vorbisfile::SetPosition( int iFrame )
if(ret < 0)
{
/* Returns OV_EINVAL on EOF. */
- if( ret == OV_EINVAL )
+ if( ret == OV_EINVAL || ret == OV_EOF)
{
eof = true;
return 0;
diff --git a/src/ScreenManager.cpp b/src/ScreenManager.cpp
index f9e4555ae4..9df8a92115 100644
--- a/src/ScreenManager.cpp
+++ b/src/ScreenManager.cpp
@@ -72,6 +72,7 @@
#include "ScreenDimensions.h"
#include "Foreach.h"
#include "ActorUtil.h"
+#include "InputEventPlus.h"
ScreenManager* SCREENMAN = NULL; // global and accessible from anywhere in our program
@@ -366,6 +367,24 @@ bool ScreenManager::IsStackedScreen( const Screen *pScreen ) const
return false;
}
+bool ScreenManager::get_input_redirected(PlayerNumber pn)
+{
+ if(pn >= m_input_redirected.size())
+ {
+ return false;
+ }
+ return m_input_redirected[pn];
+}
+
+void ScreenManager::set_input_redirected(PlayerNumber pn, bool redir)
+{
+ while(pn >= m_input_redirected.size())
+ {
+ m_input_redirected.push_back(false);
+ }
+ m_input_redirected[pn]= redir;
+}
+
/* Pop the top screen off the stack, sending SM_LoseFocus messages and
* returning the message the popped screen wants sent to the new top
* screen. Does not send SM_GainFocus. */
@@ -534,7 +553,10 @@ void ScreenManager::Input( const InputEventPlus &input )
if( g_ScreenStack.empty() )
return;
- g_ScreenStack.back().m_pScreen->Input( input );
+ if(!get_input_redirected(input.pn))
+ {
+ g_ScreenStack.back().m_pScreen->Input( input );
+ }
g_ScreenStack.back().m_pScreen->PassInputToLua( input );
}
@@ -945,6 +967,32 @@ public:
//static int GetScreenStackSize( T* p, lua_State *L ) { lua_pushnumber( L, ScreenManagerUtil::g_ScreenStack.size() ); return 1; }
static int ReloadOverlayScreens( T* p, lua_State *L ) { p->ReloadOverlayScreens(); COMMON_RETURN_SELF; }
+ static int get_input_redirected(T* p, lua_State* L)
+ {
+ PlayerNumber pn= Enum::Check(L, 1);
+ lua_pushboolean(L, p->get_input_redirected(pn));
+ return 1;
+ }
+ static int set_input_redirected(T* p, lua_State* L)
+ {
+ PlayerNumber pn= Enum::Check(L, 1);
+ p->set_input_redirected(pn, BArg(2));
+ COMMON_RETURN_SELF;
+ }
+
+#define SCRMAN_PLAY_SOUND(sound_name) \
+ static int Play##sound_name(T* p, lua_State* L) \
+ { \
+ p->Play##sound_name(); \
+ COMMON_RETURN_SELF; \
+ }
+ SCRMAN_PLAY_SOUND(InvalidSound);
+ SCRMAN_PLAY_SOUND(StartSound);
+ SCRMAN_PLAY_SOUND(CoinSound);
+ SCRMAN_PLAY_SOUND(CancelSound);
+ SCRMAN_PLAY_SOUND(ScreenshotSound);
+#undef SCRMAN_PLAY_SOUND
+
LunaScreenManager()
{
ADD_METHOD( SetNewScreen );
@@ -955,6 +1003,12 @@ public:
ADD_METHOD( AddNewScreenToTop );
//ADD_METHOD( GetScreenStackSize );
ADD_METHOD( ReloadOverlayScreens );
+ ADD_METHOD(PlayInvalidSound);
+ ADD_METHOD(PlayStartSound);
+ ADD_METHOD(PlayCoinSound);
+ ADD_METHOD(PlayCancelSound);
+ ADD_METHOD(PlayScreenshotSound);
+ ADD_GET_SET_METHODS(input_redirected);
}
};
diff --git a/src/ScreenManager.h b/src/ScreenManager.h
index f43b000b66..7380629f69 100644
--- a/src/ScreenManager.h
+++ b/src/ScreenManager.h
@@ -3,6 +3,7 @@
#include "ScreenMessage.h"
#include "RageSound.h"
+#include "PlayerNumber.h"
class Actor;
class Screen;
@@ -64,6 +65,9 @@ public:
* @return true if it's on the stack while not on the bottom, or false otherwise. */
bool IsStackedScreen( const Screen *pScreen ) const;
+ bool get_input_redirected(PlayerNumber pn);
+ void set_input_redirected(PlayerNumber pn, bool redir);
+
// Lua
void PushSelf( lua_State *L );
@@ -86,6 +90,13 @@ private:
// It's "AfterInput" because the debug overlay carries out actions in Input.
bool m_bReloadOverlayScreensAfterInput;
+ // m_input_redirected exists to allow the theme to prevent input being
+ // passed to the normal Screen::Input function, on a per-player basis.
+ // Input is still passed to lua callbacks, so it's intended for the case
+ // where someone has a custom menu on a screen and needs to disable normal
+ // input for navigating the custom menu to work. -Kyz
+ std::vector m_input_redirected;
+
Screen *MakeNewScreen( const RString &sName );
void LoadDelayedScreen();
bool ActivatePreparedScreenAndBackground( const RString &sScreenName );
diff --git a/src/ScreenSelectMusic.cpp b/src/ScreenSelectMusic.cpp
index d98d2031ac..a69e841570 100644
--- a/src/ScreenSelectMusic.cpp
+++ b/src/ScreenSelectMusic.cpp
@@ -2000,6 +2000,23 @@ void ScreenSelectMusic::OnConfirmSongDeletion()
m_pSongAwaitingDeletionConfirmation = NULL;
}
+bool ScreenSelectMusic::can_open_options_list(PlayerNumber pn)
+{
+ if(!USE_OPTIONS_LIST)
+ {
+ return false;
+ }
+ if(pn >= NUM_PLAYERS)
+ {
+ return false;
+ }
+ if(m_OptionsList[pn].IsOpened())
+ {
+ return false;
+ }
+ return true;
+}
+
// lua start
#include "LuaBinding.h"
@@ -2013,13 +2030,28 @@ public:
p->GetMusicWheel()->PushSelf(L);
return 1;
}
- static int OpenOptionsList( T* p, lua_State *L ) { PlayerNumber pn = Enum::Check(L, 1); p->OpenOptionsList(pn); COMMON_RETURN_SELF; }
+ static int OpenOptionsList( T* p, lua_State *L )
+ {
+ PlayerNumber pn = Enum::Check(L, 1);
+ if(p->can_open_options_list(pn))
+ {
+ p->OpenOptionsList(pn);
+ }
+ COMMON_RETURN_SELF;
+ }
+ static int CanOpenOptionsList( T* p, lua_State *L )
+ {
+ PlayerNumber pn = Enum::Check(L, 1);
+ lua_pushboolean(L, p->can_open_options_list(pn));
+ return 1;
+ }
LunaScreenSelectMusic()
{
ADD_METHOD( GetGoToOptions );
ADD_METHOD( GetMusicWheel );
ADD_METHOD( OpenOptionsList );
+ ADD_METHOD( CanOpenOptionsList );
}
};
diff --git a/src/ScreenSelectMusic.h b/src/ScreenSelectMusic.h
index 2dddba6e64..ead8112e99 100644
--- a/src/ScreenSelectMusic.h
+++ b/src/ScreenSelectMusic.h
@@ -50,6 +50,8 @@ public:
void OpenOptionsList( PlayerNumber pn );
void OnConfirmSongDeletion();
+ bool can_open_options_list(PlayerNumber pn);
+
// Lua
virtual void PushSelf( lua_State *L );