Created SongOptions Lua interface with a similar design to the PlayerOptions interface. Moved enums that were inside SongOptions out and made them Lua accessible. Removed sAutosyncType and associated things from AdjustSync.cpp because it was unused. Added DefaultNilArgs and FArgGTEZero to LuaBinding as helpers. Moved INTERFACE defines from PlayerOptions.cpp to OptionsBinding.h.
This commit is contained in:
@@ -780,6 +780,7 @@
|
||||
<Function name='GetSongDelay'/>
|
||||
<Function name='GetSongFreeze'/>
|
||||
<Function name='GetSongOptions'/>
|
||||
<Function name='GetSongOptionsObject'/>
|
||||
<Function name='GetSongOptionsString'/>
|
||||
<Function name='GetSongPercent'/>
|
||||
<Function name='GetSongPosition'/>
|
||||
@@ -1453,6 +1454,20 @@
|
||||
<Function name='WasLoadedFromAdditionalCourses'/>
|
||||
<Function name='WasLoadedFromAdditionalSongs'/>
|
||||
</Class>
|
||||
<Class name='SongOptions'>
|
||||
<Function name='LifeSetting'/>
|
||||
<Function name='DrainSetting'/>
|
||||
<Function name='AutosyncSetting'/>
|
||||
<Function name='BatteryLives'/>
|
||||
<Function name='AssistClap'/>
|
||||
<Function name='AssistMetronome'/>
|
||||
<Function name='StaticBackground'/>
|
||||
<Function name='RandomBGOnly'/>
|
||||
<Function name='SaveScore'/>
|
||||
<Function name='SaveReplay'/>
|
||||
<Function name='MusicRate'/>
|
||||
<Function name='Haste'/>
|
||||
</Class>
|
||||
<Class name='SongPosition'>
|
||||
<Function name='GetCurBPS'/>
|
||||
<Function name='GetDelay'/>
|
||||
@@ -1777,6 +1792,12 @@
|
||||
<EnumValue name=''AttractSoundFrequency_Every4Times'' value='4'/>
|
||||
<EnumValue name=''AttractSoundFrequency_Every5Times'' value='5'/>
|
||||
</Enum>
|
||||
<Enum name='AutosyncType'>
|
||||
<EnumValue name=''AutosyncType_Off'' value='0'/>
|
||||
<EnumValue name=''AutosyncType_Song'' value='1'/>
|
||||
<EnumValue name=''AutosyncType_Machine'' value='2'/>
|
||||
<EnumValue name=''AutosyncType_Tempo'' value='3'/>
|
||||
</Enum>
|
||||
<Enum name='BannerCacheMode'>
|
||||
<EnumValue name=''BannerCacheMode_Off'' value='0'/>
|
||||
<EnumValue name=''BannerCacheMode_LowResPreload'' value='1'/>
|
||||
@@ -1832,6 +1853,11 @@
|
||||
<EnumValue name=''DisplayBPM_Specified'' value='1'/>
|
||||
<EnumValue name=''DisplayBPM_Random'' value='2'/>
|
||||
</Enum>
|
||||
<Enum name='DrainType'>
|
||||
<EnumValue name=''DrainType_Normal'' value='0'/>
|
||||
<EnumValue name=''DrainType_NoRecover'' value='1'/>
|
||||
<EnumValue name=''DrainType_SuddenDeath'' value='2'/>
|
||||
</Enum>
|
||||
<Enum name='DrawMode'>
|
||||
<EnumValue name=''DrawMode_Quads'' value='0'/>
|
||||
<EnumValue name=''DrawMode_QuadStrip'' value='1'/>
|
||||
@@ -1951,6 +1977,11 @@
|
||||
<EnumValue name=''LayoutType_ShowAllInRow'' value='0'/>
|
||||
<EnumValue name=''LayoutType_ShowOneInRow'' value='1'/>
|
||||
</Enum>
|
||||
<Enum name='LifeType'>
|
||||
<EnumValue name=''LifeType_Bar'' value='0'/>
|
||||
<EnumValue name=''LifeType_Battery'' value='1'/>
|
||||
<EnumValue name=''LifeType_Time'' value='2'/>
|
||||
</Enum>
|
||||
<Enum name='LightsMode'>
|
||||
<EnumValue name=''LightsMode_Attract'' value='0'/>
|
||||
<EnumValue name=''LightsMode_Joining'' value='1'/>
|
||||
|
||||
@@ -2330,6 +2330,9 @@ save yourself some time, copy this for undocumented things:
|
||||
<Function name='GetSongOptionsString' return='string' arguments=''>
|
||||
Returns the song options as a string.
|
||||
</Function>
|
||||
<Function name='GetSongOptionsObject' return='SongOptions' arguments='ModsLevel ml'>
|
||||
Returns the song options for the specified ModsLevel as an object.
|
||||
</Function>
|
||||
<Function name='GetSongPercent' return='float' arguments='float fBeat'>
|
||||
Returns how much of the song is through at beat <code>fBeat</code>.
|
||||
</Function>
|
||||
@@ -2825,7 +2828,7 @@ save yourself some time, copy this for undocumented things:
|
||||
</Class>
|
||||
<Class name='PlayerOptions'>
|
||||
<Description>
|
||||
Most options fall into one of two types: float or bool.<br />
|
||||
Most options fall into one of four types: float, int, bool, or enum.<br />
|
||||
Float type options have this interface:<br />
|
||||
Option(value, approach_speed)<br />
|
||||
If value is a float, sets the TimeSpacing modifier to value.<br />
|
||||
@@ -2838,7 +2841,9 @@ save yourself some time, copy this for undocumented things:
|
||||
a,b= options:Boost(5) -- Sets a and b to the previous values, NOT to 5 and .5. Sets the value to 5 and leaves the approach speed at whatever it was.<br />
|
||||
<br />
|
||||
Setting the approach speed only matters when modifying the PlayerOptions from ModsLevel_Song.<br />
|
||||
Int type options are similar to float in that they return and take a number, but they do not have an approach speed.<br />
|
||||
Bool type options have an almost identical interface, the difference is that they can not have an approach speed.<br />
|
||||
Enum type options are almost identical to bool type. They take and return an enum value.<br />
|
||||
For brevity, the functions are only given a description if the option requires careful handling or does not follow the float or bool interfaces.<br />
|
||||
</Description>
|
||||
<Function name='IsEasierForCourseAndTrail' return='bool' arguments='Course c, Trail t'>
|
||||
@@ -4039,6 +4044,36 @@ save yourself some time, copy this for undocumented things:
|
||||
Returns <code>true</code> if the specified song was loaded from AdditionalSongs.
|
||||
</Function>
|
||||
</Class>
|
||||
<Class name='SongOptions'>
|
||||
<Description>
|
||||
See the description for PlayerOptions. The functions follow the same design.
|
||||
</Description>
|
||||
<Function name='LifeSetting' return='LifeType' arguments='LifeType type'>
|
||||
</Function>
|
||||
<Function name='DrainSetting' return= 'DrainType' arguments='DrainType type'>
|
||||
</Function>
|
||||
<Function name='AutosyncSetting' return='AutosyncType' arguments='AutosyncType type'>
|
||||
</Function>
|
||||
<Function name='BatteryLives' return='int' arguments='int num'>
|
||||
</Function>
|
||||
<Function name='AssistClap' return='bool' arguments='bool b'>
|
||||
</Function>
|
||||
<Function name='AssistMetronome' return='bool' arguments='bool b'>
|
||||
</Function>
|
||||
<Function name='StaticBackground' return='bool' arguments='bool b'>
|
||||
</Function>
|
||||
<Function name='RandomBGOnly' return='bool' arguments='bool b'>
|
||||
</Function>
|
||||
<Function name='SaveScore' return='bool' arguments='bool b'>
|
||||
</Function>
|
||||
<Function name='SaveReplay' return='bool' arguments='bool b'>
|
||||
</Function>
|
||||
<Function name='MusicRate' return='float' arguments='float rate'>
|
||||
Limited to the range 0 < rate <= 3 because speeds greater than 3 are likely to crash.
|
||||
</Function>
|
||||
<Function name='Haste' return='float' arguments='float h'>
|
||||
</Function>
|
||||
</Class>
|
||||
<Class name='SongPosition'>
|
||||
<Function name='GetCurBPS' return='float' arguments=''>
|
||||
Returns the current beats per second.
|
||||
|
||||
+9
-24
@@ -141,25 +141,22 @@ void AdjustSync::RevertSyncChanges()
|
||||
|
||||
static LocalizedString AUTOSYNC_CORRECTION_APPLIED ( "AdjustSync", "Autosync: Correction applied." );
|
||||
static LocalizedString AUTOSYNC_CORRECTION_NOT_APPLIED ( "AdjustSync", "Autosync: Correction NOT applied. Deviation too high." );
|
||||
static LocalizedString AUTOSYNC_SONG ( "AdjustSync", "Autosync Song" );
|
||||
static LocalizedString AUTOSYNC_MACHINE ( "AdjustSync", "Autosync Machine" );
|
||||
static LocalizedString AUTOSYNC_TEMPO ( "AdjustSync", "Autosync Tempo" );
|
||||
void AdjustSync::HandleAutosync( float fNoteOffBySeconds, float fStepTime )
|
||||
{
|
||||
if( GAMESTATE->IsCourseMode() )
|
||||
return;
|
||||
SongOptions::AutosyncType type = GAMESTATE->m_SongOptions.GetCurrent().m_AutosyncType;
|
||||
AutosyncType type = GAMESTATE->m_SongOptions.GetCurrent().m_AutosyncType;
|
||||
switch( type ) {
|
||||
case SongOptions::AUTOSYNC_OFF:
|
||||
case AutosyncType_Off:
|
||||
return;
|
||||
case SongOptions::AUTOSYNC_TEMPO:
|
||||
case AutosyncType_Tempo:
|
||||
{
|
||||
// We collect all of the data and process it at the end
|
||||
s_vAutosyncTempoData.push_back( make_pair(fStepTime, fNoteOffBySeconds) );
|
||||
break;
|
||||
}
|
||||
case SongOptions::AUTOSYNC_MACHINE:
|
||||
case SongOptions::AUTOSYNC_SONG:
|
||||
case AutosyncType_Machine:
|
||||
case AutosyncType_Song:
|
||||
{
|
||||
s_fAutosyncOffset[s_iAutosyncOffsetSample] = fNoteOffBySeconds;
|
||||
++s_iAutosyncOffsetSample;
|
||||
@@ -179,7 +176,7 @@ void AdjustSync::HandleSongEnd()
|
||||
{
|
||||
if( GAMESTATE->IsCourseMode() )
|
||||
return;
|
||||
if( GAMESTATE->m_SongOptions.GetCurrent().m_AutosyncType == SongOptions::AUTOSYNC_TEMPO )
|
||||
if( GAMESTATE->m_SongOptions.GetCurrent().m_AutosyncType == AutosyncType_Tempo )
|
||||
{
|
||||
AutosyncTempo();
|
||||
}
|
||||
@@ -192,25 +189,13 @@ void AdjustSync::AutosyncOffset()
|
||||
const float mean = calc_mean( s_fAutosyncOffset, s_fAutosyncOffset+OFFSET_SAMPLE_COUNT );
|
||||
const float stddev = calc_stddev( s_fAutosyncOffset, s_fAutosyncOffset+OFFSET_SAMPLE_COUNT );
|
||||
|
||||
RString sAutosyncType;
|
||||
SongOptions::AutosyncType type = GAMESTATE->m_SongOptions.GetCurrent().m_AutosyncType;
|
||||
switch( type )
|
||||
{
|
||||
case SongOptions::AUTOSYNC_SONG:
|
||||
sAutosyncType = AUTOSYNC_SONG;
|
||||
break;
|
||||
case SongOptions::AUTOSYNC_MACHINE:
|
||||
sAutosyncType = AUTOSYNC_MACHINE;
|
||||
break;
|
||||
default:
|
||||
FAIL_M(ssprintf("Invalid autosync type: %i", type));
|
||||
}
|
||||
AutosyncType type = GAMESTATE->m_SongOptions.GetCurrent().m_AutosyncType;
|
||||
|
||||
if( stddev < .03f ) // If they stepped with less than .03 error
|
||||
{
|
||||
switch( type )
|
||||
{
|
||||
case SongOptions::AUTOSYNC_SONG:
|
||||
case AutosyncType_Song:
|
||||
{
|
||||
GAMESTATE->m_pCurSong->m_SongTiming.m_fBeat0OffsetInSeconds += mean;
|
||||
const vector<Steps *>& vpSteps = GAMESTATE->m_pCurSong->GetAllSteps();
|
||||
@@ -224,7 +209,7 @@ void AdjustSync::AutosyncOffset()
|
||||
}
|
||||
break;
|
||||
}
|
||||
case SongOptions::AUTOSYNC_MACHINE:
|
||||
case AutosyncType_Machine:
|
||||
// Step timing is not needed for this operation.
|
||||
PREFSMAN->m_fGlobalOffsetSeconds.Set( PREFSMAN->m_fGlobalOffsetSeconds + mean );
|
||||
break;
|
||||
|
||||
+2
-2
@@ -805,9 +805,9 @@ void GameCommand::ApplySelf( const vector<PlayerNumber> &vpns ) const
|
||||
// we don't override the user's changes if they back out.
|
||||
if( GAMESTATE->m_PlayMode == PLAY_MODE_ONI &&
|
||||
GAMESTATE->m_PlayMode != OldPlayMode &&
|
||||
GAMESTATE->m_SongOptions.GetStage().m_LifeType == SongOptions::LIFE_BAR )
|
||||
GAMESTATE->m_SongOptions.GetStage().m_LifeType == LifeType_Bar )
|
||||
{
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Stage, m_LifeType, SongOptions::LIFE_BATTERY );
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Stage, m_LifeType, LifeType_Battery );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -2366,6 +2366,12 @@ public:
|
||||
LuaHelpers::Push( L, s );
|
||||
return 1;
|
||||
}
|
||||
static int GetSongOptionsObject( T* p, lua_State *L )
|
||||
{
|
||||
ModsLevel m = Enum::Check<ModsLevel>( L, 1 );
|
||||
p->m_SongOptions.Get(m).PushSelf(L);
|
||||
return 1;
|
||||
}
|
||||
static int GetDefaultSongOptions( T* p, lua_State *L )
|
||||
{
|
||||
SongOptions so;
|
||||
@@ -2643,6 +2649,7 @@ public:
|
||||
ADD_METHOD( GetPremium );
|
||||
ADD_METHOD( GetSongOptionsString );
|
||||
ADD_METHOD( GetSongOptions );
|
||||
ADD_METHOD( GetSongOptionsObject );
|
||||
ADD_METHOD( GetDefaultSongOptions );
|
||||
ADD_METHOD( ApplyPreferredModifiers );
|
||||
ADD_METHOD( ApplyStageModifiers );
|
||||
|
||||
+4
-4
@@ -4,13 +4,13 @@
|
||||
#include "LifeMeterBattery.h"
|
||||
#include "LifeMeterTime.h"
|
||||
|
||||
LifeMeter *LifeMeter::MakeLifeMeter( SongOptions::LifeType t )
|
||||
LifeMeter *LifeMeter::MakeLifeMeter( LifeType t )
|
||||
{
|
||||
switch( t )
|
||||
{
|
||||
case SongOptions::LIFE_BAR: return new LifeMeterBar;
|
||||
case SongOptions::LIFE_BATTERY: return new LifeMeterBattery;
|
||||
case SongOptions::LIFE_TIME: return new LifeMeterTime;
|
||||
case LifeType_Bar: return new LifeMeterBar;
|
||||
case LifeType_Battery: return new LifeMeterBattery;
|
||||
case LifeType_Time: return new LifeMeterTime;
|
||||
default:
|
||||
FAIL_M(ssprintf("Unrecognized LifeMeter type: %i", t));
|
||||
}
|
||||
|
||||
+1
-1
@@ -41,7 +41,7 @@ public:
|
||||
virtual float GetLife() const { return 0; } // for cosmetic use only
|
||||
virtual void UpdateNonstopLifebar() { }
|
||||
|
||||
static LifeMeter *MakeLifeMeter( SongOptions::LifeType t );
|
||||
static LifeMeter *MakeLifeMeter( LifeType t );
|
||||
|
||||
//
|
||||
// Lua
|
||||
|
||||
+14
-14
@@ -31,16 +31,16 @@ LifeMeterBar::LifeMeterBar()
|
||||
|
||||
m_pPlayerState = NULL;
|
||||
|
||||
SongOptions::DrainType dtype = GAMESTATE->m_SongOptions.GetStage().m_DrainType;
|
||||
DrainType dtype = GAMESTATE->m_SongOptions.GetStage().m_DrainType;
|
||||
switch( dtype )
|
||||
{
|
||||
case SongOptions::DRAIN_NORMAL:
|
||||
case DrainType_Normal:
|
||||
m_fLifePercentage = INITIAL_VALUE;
|
||||
break;
|
||||
|
||||
/* These types only go down, so they always start at full. */
|
||||
case SongOptions::DRAIN_NO_RECOVER:
|
||||
case SongOptions::DRAIN_SUDDEN_DEATH:
|
||||
case DrainType_NoRecover:
|
||||
case DrainType_SuddenDeath:
|
||||
m_fLifePercentage = 1.0f; break;
|
||||
default:
|
||||
FAIL_M(ssprintf("Invalid DrainType: %i", dtype));
|
||||
@@ -132,12 +132,12 @@ void LifeMeterBar::ChangeLife( TapNoteScore score )
|
||||
switch( GAMESTATE->m_SongOptions.GetSong().m_DrainType )
|
||||
{
|
||||
DEFAULT_FAIL( GAMESTATE->m_SongOptions.GetSong().m_DrainType );
|
||||
case SongOptions::DRAIN_NORMAL:
|
||||
case DrainType_Normal:
|
||||
break;
|
||||
case SongOptions::DRAIN_NO_RECOVER:
|
||||
case DrainType_NoRecover:
|
||||
fDeltaLife = min( fDeltaLife, 0 );
|
||||
break;
|
||||
case SongOptions::DRAIN_SUDDEN_DEATH:
|
||||
case DrainType_SuddenDeath:
|
||||
if( score < MIN_STAY_ALIVE )
|
||||
fDeltaLife = -1.0f;
|
||||
else
|
||||
@@ -151,10 +151,10 @@ void LifeMeterBar::ChangeLife( TapNoteScore score )
|
||||
void LifeMeterBar::ChangeLife( HoldNoteScore score, TapNoteScore tscore )
|
||||
{
|
||||
float fDeltaLife=0.f;
|
||||
SongOptions::DrainType dtype = GAMESTATE->m_SongOptions.GetSong().m_DrainType;
|
||||
DrainType dtype = GAMESTATE->m_SongOptions.GetSong().m_DrainType;
|
||||
switch( dtype )
|
||||
{
|
||||
case SongOptions::DRAIN_NORMAL:
|
||||
case DrainType_Normal:
|
||||
switch( score )
|
||||
{
|
||||
case HNS_Held: fDeltaLife = m_fLifePercentChange.GetValue(SE_Held); break;
|
||||
@@ -166,7 +166,7 @@ void LifeMeterBar::ChangeLife( HoldNoteScore score, TapNoteScore tscore )
|
||||
if( IsHot() && score == HNS_LetGo )
|
||||
fDeltaLife = -0.10f; // make it take a while to get back to "hot"
|
||||
break;
|
||||
case SongOptions::DRAIN_NO_RECOVER:
|
||||
case DrainType_NoRecover:
|
||||
switch( score )
|
||||
{
|
||||
case HNS_Held: fDeltaLife = +0.000f; break;
|
||||
@@ -176,7 +176,7 @@ void LifeMeterBar::ChangeLife( HoldNoteScore score, TapNoteScore tscore )
|
||||
FAIL_M(ssprintf("Invalid HoldNoteScore: %i", score));
|
||||
}
|
||||
break;
|
||||
case SongOptions::DRAIN_SUDDEN_DEATH:
|
||||
case DrainType_SuddenDeath:
|
||||
switch( score )
|
||||
{
|
||||
case HNS_Held: fDeltaLife = +0; break;
|
||||
@@ -221,14 +221,14 @@ void LifeMeterBar::ChangeLife( float fDeltaLife )
|
||||
|
||||
switch( GAMESTATE->m_SongOptions.GetSong().m_DrainType )
|
||||
{
|
||||
case SongOptions::DRAIN_NORMAL:
|
||||
case SongOptions::DRAIN_NO_RECOVER:
|
||||
case DrainType_Normal:
|
||||
case DrainType_NoRecover:
|
||||
if( fDeltaLife > 0 )
|
||||
fDeltaLife *= m_fLifeDifficulty;
|
||||
else
|
||||
fDeltaLife /= m_fLifeDifficulty;
|
||||
break;
|
||||
case SongOptions::DRAIN_SUDDEN_DEATH:
|
||||
case DrainType_SuddenDeath:
|
||||
// This should always -1.0f;
|
||||
if( fDeltaLife < 0 )
|
||||
fDeltaLife = -1.0f;
|
||||
|
||||
@@ -376,6 +376,25 @@ LuaClass::~LuaClass()
|
||||
LUA->Release( L );
|
||||
}
|
||||
|
||||
void DefaultNilArgs(lua_State* L, int n)
|
||||
{
|
||||
while(lua_gettop(L) < n)
|
||||
{
|
||||
lua_pushnil(L);
|
||||
}
|
||||
}
|
||||
|
||||
float FArgGTEZero(lua_State* L, int index)
|
||||
{
|
||||
float s= FArg(index);
|
||||
if(s < 0)
|
||||
{
|
||||
luaL_error(L, "Arg must be greater than or equal to zero.");
|
||||
}
|
||||
return s;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* (c) 2005 Glenn Maynard
|
||||
* All rights reserved.
|
||||
|
||||
@@ -170,6 +170,11 @@ public:
|
||||
#define LIST_METHOD( method_name ) \
|
||||
{ #method_name, method_name }
|
||||
|
||||
// Explicitly separates the stack into args and return values.
|
||||
// This way, the stack can safely be used to store the previous values.
|
||||
void DefaultNilArgs(lua_State* L, int n);
|
||||
float FArgGTEZero(lua_State* L, int index);
|
||||
|
||||
#endif
|
||||
|
||||
/*
|
||||
|
||||
+2
-2
@@ -628,7 +628,7 @@ void Player::Load()
|
||||
// TODO: Remove use of PlayerNumber.
|
||||
PlayerNumber pn = m_pPlayerState->m_PlayerNumber;
|
||||
|
||||
bool bOniDead = GAMESTATE->m_SongOptions.GetStage().m_LifeType == SongOptions::LIFE_BATTERY &&
|
||||
bool bOniDead = GAMESTATE->m_SongOptions.GetStage().m_LifeType == LifeType_Battery &&
|
||||
(m_pPlayerStageStats == NULL || m_pPlayerStageStats->m_bFailed);
|
||||
|
||||
/* The editor reuses Players ... so we really need to make sure everything
|
||||
@@ -1781,7 +1781,7 @@ int Player::GetClosestNonEmptyRow( int iNoteRow, int iMaxRowsAhead, int iMaxRows
|
||||
bool Player::IsOniDead() const
|
||||
{
|
||||
// If we're playing on oni and we've died, do nothing.
|
||||
return GAMESTATE->m_SongOptions.GetCurrent().m_LifeType == SongOptions::LIFE_BATTERY && m_pPlayerStageStats && m_pPlayerStageStats->m_bFailed;
|
||||
return GAMESTATE->m_SongOptions.GetCurrent().m_LifeType == LifeType_Battery && m_pPlayerStageStats && m_pPlayerStageStats->m_bFailed;
|
||||
}
|
||||
|
||||
void Player::Fret( int col, int row, const RageTimer &tm, bool bHeld, bool bRelease )
|
||||
|
||||
+55
-121
@@ -908,6 +908,7 @@ void PlayerOptions::ResetPrefs( ResetPrefsType type )
|
||||
|
||||
// lua start
|
||||
#include "LuaBinding.h"
|
||||
#include "OptionsBinding.h"
|
||||
|
||||
/** @brief Allow Lua to have access to PlayerOptions. */
|
||||
class LunaPlayerOptions: public Luna<PlayerOptions>
|
||||
@@ -930,107 +931,53 @@ public:
|
||||
return 1;
|
||||
}
|
||||
|
||||
static float CheckedApproachSpeed(lua_State* L, float s)
|
||||
{
|
||||
if(s < 0)
|
||||
{
|
||||
luaL_error(L, "Approach speed must be greater than or equal to zero.");
|
||||
}
|
||||
return s;
|
||||
}
|
||||
|
||||
// Explicitly separates the stack into args and return values.
|
||||
// This way, the stack can safely be used to store the previous values.
|
||||
static void DefaultNilArgs(lua_State* L, int n)
|
||||
{
|
||||
while(lua_gettop(L) < n)
|
||||
{
|
||||
lua_pushnil(L);
|
||||
}
|
||||
}
|
||||
|
||||
// Functions are designed to combine Get and Set into one, to be less clumsy to use. -Kyz
|
||||
// If a valid arg is passed, the value is set.
|
||||
// The previous value is returned.
|
||||
#define FLOAT_INTERFACE(func_name, member) \
|
||||
static int func_name(T* p, lua_State* L) \
|
||||
{ \
|
||||
DefaultNilArgs(L, 2); \
|
||||
lua_pushnumber(L, p->m_f ## member); \
|
||||
lua_pushnumber(L, p->m_Speedf ## member); \
|
||||
if(lua_isnumber(L, 1)) \
|
||||
{ \
|
||||
p->m_f ## member = FArg(1); \
|
||||
if(p->m_Speedf ## member <= 0.0f) \
|
||||
{ \
|
||||
p->m_Speedf ## member = 1.0f; \
|
||||
} \
|
||||
} \
|
||||
if(lua_isnumber(L, 2)) \
|
||||
{ \
|
||||
p->m_Speedf ## member = CheckedApproachSpeed(L, FArg(2)); \
|
||||
} \
|
||||
return 2; \
|
||||
}
|
||||
#define BOOL_INTERFACE(func_name, member) \
|
||||
static int func_name(T* p, lua_State* L) \
|
||||
{ \
|
||||
DefaultNilArgs(L, 1); \
|
||||
lua_pushboolean(L, p->m_b ## member); \
|
||||
if(lua_isboolean(L, 1)) \
|
||||
{ \
|
||||
p->m_b ## member = BArg(1); \
|
||||
} \
|
||||
return 1; \
|
||||
}
|
||||
|
||||
// Direct control functions, for themes that can handle it.
|
||||
|
||||
FLOAT_INTERFACE(TimeSpacing, TimeSpacing);
|
||||
FLOAT_INTERFACE(MaxScrollBPM, MaxScrollBPM);
|
||||
FLOAT_INTERFACE(ScrollSpeed, ScrollSpeed);
|
||||
FLOAT_INTERFACE(ScrollBPM, ScrollBPM);
|
||||
FLOAT_INTERFACE(Boost, Accels[PlayerOptions::ACCEL_BOOST]);
|
||||
FLOAT_INTERFACE(Brake, Accels[PlayerOptions::ACCEL_BRAKE]);
|
||||
FLOAT_INTERFACE(Wave, Accels[PlayerOptions::ACCEL_WAVE]);
|
||||
FLOAT_INTERFACE(Expand, Accels[PlayerOptions::ACCEL_EXPAND]);
|
||||
FLOAT_INTERFACE(Boomerang, Accels[PlayerOptions::ACCEL_BOOMERANG]);
|
||||
FLOAT_INTERFACE(Drunk, Effects[PlayerOptions::EFFECT_DRUNK]);
|
||||
FLOAT_INTERFACE(Dizzy, Effects[PlayerOptions::EFFECT_DIZZY]);
|
||||
FLOAT_INTERFACE(Confusion, Effects[PlayerOptions::EFFECT_CONFUSION]);
|
||||
FLOAT_INTERFACE(Mini, Effects[PlayerOptions::EFFECT_MINI]);
|
||||
FLOAT_INTERFACE(Tiny, Effects[PlayerOptions::EFFECT_TINY]);
|
||||
FLOAT_INTERFACE(Flip, Effects[PlayerOptions::EFFECT_FLIP]);
|
||||
FLOAT_INTERFACE(Invert, Effects[PlayerOptions::EFFECT_INVERT]);
|
||||
FLOAT_INTERFACE(Tornado, Effects[PlayerOptions::EFFECT_TORNADO]);
|
||||
FLOAT_INTERFACE(Tipsy, Effects[PlayerOptions::EFFECT_TIPSY]);
|
||||
FLOAT_INTERFACE(Bumpy, Effects[PlayerOptions::EFFECT_BUMPY]);
|
||||
FLOAT_INTERFACE(Beat, Effects[PlayerOptions::EFFECT_BEAT]);
|
||||
FLOAT_INTERFACE(Xmode, Effects[PlayerOptions::EFFECT_XMODE]);
|
||||
FLOAT_INTERFACE(Twirl, Effects[PlayerOptions::EFFECT_TWIRL]);
|
||||
FLOAT_INTERFACE(Roll, Effects[PlayerOptions::EFFECT_ROLL]);
|
||||
FLOAT_INTERFACE(Hidden, Appearances[PlayerOptions::APPEARANCE_HIDDEN]);
|
||||
FLOAT_INTERFACE(HiddenOffset, Appearances[PlayerOptions::APPEARANCE_HIDDEN_OFFSET]);
|
||||
FLOAT_INTERFACE(Sudden, Appearances[PlayerOptions::APPEARANCE_SUDDEN]);
|
||||
FLOAT_INTERFACE(SuddenOffset, Appearances[PlayerOptions::APPEARANCE_SUDDEN_OFFSET]);
|
||||
FLOAT_INTERFACE(Stealth, Appearances[PlayerOptions::APPEARANCE_STEALTH]);
|
||||
FLOAT_INTERFACE(Blink, Appearances[PlayerOptions::APPEARANCE_BLINK]);
|
||||
FLOAT_INTERFACE(RandomVanish, Appearances[PlayerOptions::APPEARANCE_RANDOMVANISH]);
|
||||
FLOAT_INTERFACE(Reverse, Scrolls[PlayerOptions::SCROLL_REVERSE]);
|
||||
FLOAT_INTERFACE(Split, Scrolls[PlayerOptions::SCROLL_SPLIT]);
|
||||
FLOAT_INTERFACE(Alternate, Scrolls[PlayerOptions::SCROLL_ALTERNATE]);
|
||||
FLOAT_INTERFACE(Cross, Scrolls[PlayerOptions::SCROLL_CROSS]);
|
||||
FLOAT_INTERFACE(Centered, Scrolls[PlayerOptions::SCROLL_CENTERED]);
|
||||
FLOAT_INTERFACE(Dark, Dark);
|
||||
FLOAT_INTERFACE(Blind, Blind);
|
||||
FLOAT_INTERFACE(Cover, Cover);
|
||||
FLOAT_INTERFACE(RandAttack, RandAttack);
|
||||
FLOAT_INTERFACE(NoAttack, NoAttack);
|
||||
FLOAT_INTERFACE(PlayerAutoPlay, PlayerAutoPlay);
|
||||
FLOAT_INTERFACE(Skew, Skew);
|
||||
FLOAT_INTERFACE(Tilt, PerspectiveTilt);
|
||||
FLOAT_INTERFACE(Passmark, Passmark); // Passmark is not sanity checked to the [0, 1] range because LifeMeterBar::IsFailing is the only thing that uses it, and it's used in a <= test. Any theme passing a value outside the [0, 1] range probably expects the result they get. -Kyz
|
||||
FLOAT_INTERFACE(RandomSpeed, RandomSpeed);
|
||||
FLOAT_INTERFACE(TimeSpacing, TimeSpacing, true);
|
||||
FLOAT_INTERFACE(MaxScrollBPM, MaxScrollBPM, true);
|
||||
FLOAT_INTERFACE(ScrollSpeed, ScrollSpeed, true);
|
||||
FLOAT_INTERFACE(ScrollBPM, ScrollBPM, true);
|
||||
FLOAT_INTERFACE(Boost, Accels[PlayerOptions::ACCEL_BOOST], true);
|
||||
FLOAT_INTERFACE(Brake, Accels[PlayerOptions::ACCEL_BRAKE], true);
|
||||
FLOAT_INTERFACE(Wave, Accels[PlayerOptions::ACCEL_WAVE], true);
|
||||
FLOAT_INTERFACE(Expand, Accels[PlayerOptions::ACCEL_EXPAND], true);
|
||||
FLOAT_INTERFACE(Boomerang, Accels[PlayerOptions::ACCEL_BOOMERANG], true);
|
||||
FLOAT_INTERFACE(Drunk, Effects[PlayerOptions::EFFECT_DRUNK], true);
|
||||
FLOAT_INTERFACE(Dizzy, Effects[PlayerOptions::EFFECT_DIZZY], true);
|
||||
FLOAT_INTERFACE(Confusion, Effects[PlayerOptions::EFFECT_CONFUSION], true);
|
||||
FLOAT_INTERFACE(Mini, Effects[PlayerOptions::EFFECT_MINI], true);
|
||||
FLOAT_INTERFACE(Tiny, Effects[PlayerOptions::EFFECT_TINY], true);
|
||||
FLOAT_INTERFACE(Flip, Effects[PlayerOptions::EFFECT_FLIP], true);
|
||||
FLOAT_INTERFACE(Invert, Effects[PlayerOptions::EFFECT_INVERT], true);
|
||||
FLOAT_INTERFACE(Tornado, Effects[PlayerOptions::EFFECT_TORNADO], true);
|
||||
FLOAT_INTERFACE(Tipsy, Effects[PlayerOptions::EFFECT_TIPSY], true);
|
||||
FLOAT_INTERFACE(Bumpy, Effects[PlayerOptions::EFFECT_BUMPY], true);
|
||||
FLOAT_INTERFACE(Beat, Effects[PlayerOptions::EFFECT_BEAT], true);
|
||||
FLOAT_INTERFACE(Xmode, Effects[PlayerOptions::EFFECT_XMODE], true);
|
||||
FLOAT_INTERFACE(Twirl, Effects[PlayerOptions::EFFECT_TWIRL], true);
|
||||
FLOAT_INTERFACE(Roll, Effects[PlayerOptions::EFFECT_ROLL], true);
|
||||
FLOAT_INTERFACE(Hidden, Appearances[PlayerOptions::APPEARANCE_HIDDEN], true);
|
||||
FLOAT_INTERFACE(HiddenOffset, Appearances[PlayerOptions::APPEARANCE_HIDDEN_OFFSET], true);
|
||||
FLOAT_INTERFACE(Sudden, Appearances[PlayerOptions::APPEARANCE_SUDDEN], true);
|
||||
FLOAT_INTERFACE(SuddenOffset, Appearances[PlayerOptions::APPEARANCE_SUDDEN_OFFSET], true);
|
||||
FLOAT_INTERFACE(Stealth, Appearances[PlayerOptions::APPEARANCE_STEALTH], true);
|
||||
FLOAT_INTERFACE(Blink, Appearances[PlayerOptions::APPEARANCE_BLINK], true);
|
||||
FLOAT_INTERFACE(RandomVanish, Appearances[PlayerOptions::APPEARANCE_RANDOMVANISH], true);
|
||||
FLOAT_INTERFACE(Reverse, Scrolls[PlayerOptions::SCROLL_REVERSE], true);
|
||||
FLOAT_INTERFACE(Split, Scrolls[PlayerOptions::SCROLL_SPLIT], true);
|
||||
FLOAT_INTERFACE(Alternate, Scrolls[PlayerOptions::SCROLL_ALTERNATE], true);
|
||||
FLOAT_INTERFACE(Cross, Scrolls[PlayerOptions::SCROLL_CROSS], true);
|
||||
FLOAT_INTERFACE(Centered, Scrolls[PlayerOptions::SCROLL_CENTERED], true);
|
||||
FLOAT_INTERFACE(Dark, Dark, true);
|
||||
FLOAT_INTERFACE(Blind, Blind, true);
|
||||
FLOAT_INTERFACE(Cover, Cover, true);
|
||||
FLOAT_INTERFACE(RandAttack, RandAttack, true);
|
||||
FLOAT_INTERFACE(NoAttack, NoAttack, true);
|
||||
FLOAT_INTERFACE(PlayerAutoPlay, PlayerAutoPlay, true);
|
||||
FLOAT_INTERFACE(Skew, Skew, true);
|
||||
FLOAT_INTERFACE(Tilt, PerspectiveTilt, true);
|
||||
FLOAT_INTERFACE(Passmark, Passmark, true); // Passmark is not sanity checked to the [0, 1] range because LifeMeterBar::IsFailing is the only thing that uses it, and it's used in a <= test. Any theme passing a value outside the [0, 1] range probably expects the result they get. -Kyz
|
||||
FLOAT_INTERFACE(RandomSpeed, RandomSpeed, true);
|
||||
BOOL_INTERFACE(TurnNone, Turns[PlayerOptions::TURN_NONE]);
|
||||
BOOL_INTERFACE(Mirror, Turns[PlayerOptions::TURN_MIRROR]);
|
||||
BOOL_INTERFACE(Backwards, Turns[PlayerOptions::TURN_BACKWARDS]);
|
||||
@@ -1063,9 +1010,7 @@ public:
|
||||
BOOL_INTERFACE(NoQuads, Transforms[PlayerOptions::TRANSFORM_NOQUADS]);
|
||||
BOOL_INTERFACE(NoStretch, Transforms[PlayerOptions::TRANSFORM_NOSTRETCH]);
|
||||
BOOL_INTERFACE(MuteOnError, MuteOnError);
|
||||
|
||||
#undef FLOAT_INTERFACE
|
||||
#undef BOOL_INTERFACE
|
||||
ENUM_INTERFACE(FailSetting, FailType, FailType);
|
||||
|
||||
// NoteSkins
|
||||
static int NoteSkin(T* p, lua_State* L)
|
||||
@@ -1098,17 +1043,6 @@ public:
|
||||
return 2;
|
||||
}
|
||||
|
||||
static int FailSetting(T* p, lua_State* L)
|
||||
{
|
||||
DefaultNilArgs(L, 1);
|
||||
Enum::Push(L, p->m_FailType);
|
||||
if(lua_isstring(L, 1))
|
||||
{
|
||||
p->m_FailType= Enum::Check<FailType>(L, 1);
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
static void SetSpeedModApproaches(T* p, float speed)
|
||||
{
|
||||
p->m_SpeedfScrollBPM= speed;
|
||||
@@ -1147,7 +1081,7 @@ public:
|
||||
}
|
||||
if(lua_isnumber(L, 2))
|
||||
{
|
||||
SetSpeedModApproaches(p, CheckedApproachSpeed(L, FArg(2)));
|
||||
SetSpeedModApproaches(p, FArgGTEZero(L, 2));
|
||||
}
|
||||
return 2;
|
||||
}
|
||||
@@ -1174,7 +1108,7 @@ public:
|
||||
}
|
||||
if(lua_isnumber(L, 2))
|
||||
{
|
||||
SetSpeedModApproaches(p, CheckedApproachSpeed(L, FArg(2)));
|
||||
SetSpeedModApproaches(p, FArgGTEZero(L, 2));
|
||||
}
|
||||
return 2;
|
||||
}
|
||||
@@ -1206,7 +1140,7 @@ public:
|
||||
}
|
||||
if(lua_isnumber(L, 2))
|
||||
{
|
||||
SetSpeedModApproaches(p, CheckedApproachSpeed(L, FArg(2)));
|
||||
SetSpeedModApproaches(p, FArgGTEZero(L, 2));
|
||||
}
|
||||
return 2;
|
||||
}
|
||||
@@ -1228,7 +1162,7 @@ public:
|
||||
}
|
||||
if(lua_isnumber(L, 2))
|
||||
{
|
||||
SetPerspectiveApproach(p, L, CheckedApproachSpeed(L, FArg(2)));
|
||||
SetPerspectiveApproach(p, L, FArgGTEZero(L, 2));
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
@@ -1255,7 +1189,7 @@ public:
|
||||
}
|
||||
if(lua_isnumber(L, 2))
|
||||
{
|
||||
SetPerspectiveApproach(p, L, CheckedApproachSpeed(L, FArg(2)));
|
||||
SetPerspectiveApproach(p, L, FArgGTEZero(L, 2));
|
||||
}
|
||||
return 2;
|
||||
}
|
||||
@@ -1282,7 +1216,7 @@ public:
|
||||
}
|
||||
if(lua_isnumber(L, 2))
|
||||
{
|
||||
SetPerspectiveApproach(p, L, CheckedApproachSpeed(L, FArg(2)));
|
||||
SetPerspectiveApproach(p, L, FArgGTEZero(L, 2));
|
||||
}
|
||||
return 2;
|
||||
}
|
||||
@@ -1307,7 +1241,7 @@ public:
|
||||
}
|
||||
if(lua_isnumber(L, 2))
|
||||
{
|
||||
SetPerspectiveApproach(p, L, CheckedApproachSpeed(L, FArg(2)));
|
||||
SetPerspectiveApproach(p, L, FArgGTEZero(L, 2));
|
||||
}
|
||||
return 2;
|
||||
}
|
||||
@@ -1332,7 +1266,7 @@ public:
|
||||
}
|
||||
if(lua_isnumber(L, 2))
|
||||
{
|
||||
SetPerspectiveApproach(p, L, CheckedApproachSpeed(L, FArg(2)));
|
||||
SetPerspectiveApproach(p, L, FArgGTEZero(L, 2));
|
||||
}
|
||||
return 2;
|
||||
}
|
||||
|
||||
+10
-10
@@ -647,28 +647,28 @@ class DebugLineAutosync : public IDebugLine
|
||||
virtual RString GetDisplayTitle() { return AUTOSYNC.GetValue(); }
|
||||
virtual RString GetDisplayValue()
|
||||
{
|
||||
SongOptions::AutosyncType type = GAMESTATE->m_SongOptions.GetSong().m_AutosyncType;
|
||||
AutosyncType type = GAMESTATE->m_SongOptions.GetSong().m_AutosyncType;
|
||||
switch( type )
|
||||
{
|
||||
case SongOptions::AUTOSYNC_OFF: return OFF.GetValue(); break;
|
||||
case SongOptions::AUTOSYNC_SONG: return SONG.GetValue(); break;
|
||||
case SongOptions::AUTOSYNC_MACHINE: return MACHINE.GetValue(); break;
|
||||
case SongOptions::AUTOSYNC_TEMPO: return SYNC_TEMPO.GetValue(); break;
|
||||
case AutosyncType_Off: return OFF.GetValue(); break;
|
||||
case AutosyncType_Song: return SONG.GetValue(); break;
|
||||
case AutosyncType_Machine: return MACHINE.GetValue(); break;
|
||||
case AutosyncType_Tempo: return SYNC_TEMPO.GetValue(); break;
|
||||
default:
|
||||
FAIL_M(ssprintf("Invalid autosync type: %i", type));
|
||||
}
|
||||
}
|
||||
virtual Type GetType() const { return IDebugLine::gameplay_only; }
|
||||
virtual bool IsEnabled() { return GAMESTATE->m_SongOptions.GetSong().m_AutosyncType!=SongOptions::AUTOSYNC_OFF; }
|
||||
virtual bool IsEnabled() { return GAMESTATE->m_SongOptions.GetSong().m_AutosyncType!=AutosyncType_Off; }
|
||||
virtual void DoAndLog( RString &sMessageOut )
|
||||
{
|
||||
int as = GAMESTATE->m_SongOptions.GetSong().m_AutosyncType + 1;
|
||||
bool bAllowSongAutosync = !GAMESTATE->IsCourseMode();
|
||||
if( !bAllowSongAutosync &&
|
||||
( as == SongOptions::AUTOSYNC_SONG || as == SongOptions::AUTOSYNC_TEMPO ) )
|
||||
as = SongOptions::AUTOSYNC_MACHINE;
|
||||
wrap( as, SongOptions::NUM_AUTOSYNC_TYPES );
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Song, m_AutosyncType, SongOptions::AutosyncType(as) );
|
||||
( as == AutosyncType_Song || as == AutosyncType_Tempo ) )
|
||||
as = AutosyncType_Machine;
|
||||
wrap( as, NUM_AutosyncType );
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Song, m_AutosyncType, AutosyncType(as) );
|
||||
MESSAGEMAN->Broadcast( Message_AutosyncChanged );
|
||||
IDebugLine::DoAndLog( sMessageOut );
|
||||
}
|
||||
|
||||
+10
-10
@@ -135,7 +135,7 @@ void PlayerInfo::Load( PlayerNumber pn, MultiPlayer mp, bool bShowNoteField, int
|
||||
break;
|
||||
case PLAY_MODE_ONI:
|
||||
case PLAY_MODE_ENDLESS:
|
||||
if( GAMESTATE->m_SongOptions.GetStage().m_LifeType == SongOptions::LIFE_TIME )
|
||||
if( GAMESTATE->m_SongOptions.GetStage().m_LifeType == LifeType_Time )
|
||||
m_pPrimaryScoreDisplay = new ScoreDisplayLifeTime;
|
||||
else
|
||||
m_pPrimaryScoreDisplay = new ScoreDisplayOni;
|
||||
@@ -570,7 +570,7 @@ void ScreenGameplay::Init()
|
||||
// not 100% sure of that. -freem
|
||||
if( !GAMESTATE->IsPlayerEnabled(pi->m_pn) && SHOW_LIFE_METER_FOR_DISABLED_PLAYERS )
|
||||
{
|
||||
if(GAMESTATE->m_SongOptions.GetStage().m_LifeType == SongOptions::LIFE_BAR)
|
||||
if(GAMESTATE->m_SongOptions.GetStage().m_LifeType == LifeType_Bar)
|
||||
static_cast<LifeMeterBar*>(pi->m_pLifeMeter)->ChangeLife(-1.0f);
|
||||
}
|
||||
}
|
||||
@@ -1017,9 +1017,9 @@ void ScreenGameplay::SetupSong( int iSongIndex )
|
||||
RString sType;
|
||||
switch( GAMESTATE->m_SongOptions.GetCurrent().m_SoundEffectType )
|
||||
{
|
||||
case SongOptions::SOUNDEFFECT_OFF: sType = "SoundEffectControl_Off"; break;
|
||||
case SongOptions::SOUNDEFFECT_SPEED: sType = "SoundEffectControl_Speed"; break;
|
||||
case SongOptions::SOUNDEFFECT_PITCH: sType = "SoundEffectControl_Pitch"; break;
|
||||
case SoundEffectType_Off: sType = "SoundEffectControl_Off"; break;
|
||||
case SoundEffectType_Speed: sType = "SoundEffectControl_Speed"; break;
|
||||
case SoundEffectType_Pitch: sType = "SoundEffectControl_Pitch"; break;
|
||||
default: break;
|
||||
}
|
||||
|
||||
@@ -1082,7 +1082,7 @@ void ScreenGameplay::LoadNextSong()
|
||||
|
||||
/* If we're in battery mode, force FailImmediate. We assume in Player::Step
|
||||
* that failed players can't step. */
|
||||
if( GAMESTATE->m_SongOptions.GetCurrent().m_LifeType == SongOptions::LIFE_BATTERY )
|
||||
if( GAMESTATE->m_SongOptions.GetCurrent().m_LifeType == LifeType_Battery )
|
||||
{
|
||||
FOREACH_EnabledPlayerInfo( m_vPlayerInfo, pi )
|
||||
PO_GROUP_ASSIGN( pi->GetPlayerState()->m_PlayerOptions, ModsLevel_Song, m_FailType, FailType_Immediate );
|
||||
@@ -1118,10 +1118,10 @@ void ScreenGameplay::LoadNextSong()
|
||||
// reset oni game over graphic
|
||||
SET_XY_AND_ON_COMMAND( pi->m_sprOniGameOver );
|
||||
|
||||
if( GAMESTATE->m_SongOptions.GetCurrent().m_LifeType==SongOptions::LIFE_BATTERY && pi->GetPlayerStageStats()->m_bFailed ) // already failed
|
||||
if( GAMESTATE->m_SongOptions.GetCurrent().m_LifeType==LifeType_Battery && pi->GetPlayerStageStats()->m_bFailed ) // already failed
|
||||
pi->ShowOniGameOver();
|
||||
|
||||
if( GAMESTATE->m_SongOptions.GetCurrent().m_LifeType==SongOptions::LIFE_BAR && pi->m_pLifeMeter )
|
||||
if( GAMESTATE->m_SongOptions.GetCurrent().m_LifeType==LifeType_Bar && pi->m_pLifeMeter )
|
||||
pi->m_pLifeMeter->UpdateNonstopLifebar();
|
||||
|
||||
if( pi->m_pStepsDisplay )
|
||||
@@ -1634,7 +1634,7 @@ void ScreenGameplay::Update( float fDeltaTime )
|
||||
PlayerNumber pn = pi->GetStepsAndTrailIndex();
|
||||
|
||||
FailType ft = GAMESTATE->GetPlayerFailType( pi->GetPlayerState() );
|
||||
SongOptions::LifeType lt = GAMESTATE->m_SongOptions.GetCurrent().m_LifeType;
|
||||
LifeType lt = GAMESTATE->m_SongOptions.GetCurrent().m_LifeType;
|
||||
|
||||
if( ft == FailType_Off || ft == FailType_EndOfSong )
|
||||
continue;
|
||||
@@ -1658,7 +1658,7 @@ void ScreenGameplay::Update( float fDeltaTime )
|
||||
bool bAllowOniDie = false;
|
||||
switch( lt )
|
||||
{
|
||||
case SongOptions::LIFE_BATTERY:
|
||||
case LifeType_Battery:
|
||||
bAllowOniDie = true;
|
||||
default:
|
||||
break;
|
||||
|
||||
@@ -45,7 +45,7 @@ void ScreenGameplaySyncMachine::Init()
|
||||
|
||||
ScreenGameplayNormal::Init();
|
||||
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Stage, m_AutosyncType, SongOptions::AUTOSYNC_MACHINE );
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Stage, m_AutosyncType, AutosyncType_Machine );
|
||||
|
||||
ClearMessageQueue(); // remove all of the messages set in ScreenGameplay that animate "ready", "here we go", etc.
|
||||
|
||||
|
||||
@@ -198,7 +198,7 @@ void ScreenJukebox::Init()
|
||||
PO_GROUP_ASSIGN( GAMESTATE->m_pPlayerState[p]->m_PlayerOptions, ModsLevel_Stage, m_fPerspectiveTilt, -1.0f );
|
||||
PO_GROUP_ASSIGN_N( GAMESTATE->m_pPlayerState[p]->m_PlayerOptions, ModsLevel_Stage, m_fEffects, PlayerOptions::EFFECT_TINY, 1.0f );
|
||||
}
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Stage, m_LifeType, SongOptions::LIFE_BATTERY );
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Stage, m_LifeType, LifeType_Battery );
|
||||
}
|
||||
|
||||
FOREACH_EnabledPlayer( p )
|
||||
|
||||
@@ -1247,11 +1247,11 @@ bool ScreenSelectMusic::MenuStart( const InputEventPlus &input )
|
||||
// apply #LIVES
|
||||
if( pCourse->m_iLives != -1 )
|
||||
{
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Stage, m_LifeType, SongOptions::LIFE_BATTERY );
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Stage, m_LifeType, LifeType_Battery );
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Stage, m_iBatteryLives, pCourse->m_iLives );
|
||||
}
|
||||
if( pCourse->GetCourseType() == COURSE_TYPE_SURVIVAL)
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Stage, m_LifeType, SongOptions::LIFE_TIME );
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Stage, m_LifeType, LifeType_Time );
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
@@ -113,13 +113,13 @@ void ScreenSyncOverlay::UpdateText()
|
||||
}
|
||||
}
|
||||
|
||||
SongOptions::AutosyncType type = GAMESTATE->m_SongOptions.GetCurrent().m_AutosyncType;
|
||||
AutosyncType type = GAMESTATE->m_SongOptions.GetCurrent().m_AutosyncType;
|
||||
switch( type )
|
||||
{
|
||||
case SongOptions::AUTOSYNC_OFF: break;
|
||||
case SongOptions::AUTOSYNC_SONG: vs.push_back(AUTO_SYNC_SONG); break;
|
||||
case SongOptions::AUTOSYNC_MACHINE: vs.push_back(AUTO_SYNC_MACHINE); break;
|
||||
case SongOptions::AUTOSYNC_TEMPO: vs.push_back(AUTO_SYNC_TEMPO); break;
|
||||
case AutosyncType_Off: break;
|
||||
case AutosyncType_Song: vs.push_back(AUTO_SYNC_SONG); break;
|
||||
case AutosyncType_Machine: vs.push_back(AUTO_SYNC_MACHINE); break;
|
||||
case AutosyncType_Tempo: vs.push_back(AUTO_SYNC_TEMPO); break;
|
||||
default:
|
||||
FAIL_M(ssprintf("Invalid autosync type: %i", type));
|
||||
}
|
||||
@@ -134,7 +134,7 @@ void ScreenSyncOverlay::UpdateText()
|
||||
|
||||
|
||||
// Update SyncInfo
|
||||
bool bVisible = GAMESTATE->m_SongOptions.GetCurrent().m_AutosyncType != SongOptions::AUTOSYNC_OFF;
|
||||
bool bVisible = GAMESTATE->m_SongOptions.GetCurrent().m_AutosyncType != AutosyncType_Off;
|
||||
m_textAdjustments.SetVisible( bVisible );
|
||||
if( bVisible )
|
||||
{
|
||||
|
||||
+112
-30
@@ -4,10 +4,47 @@
|
||||
#include "GameState.h"
|
||||
#include "CommonMetrics.h"
|
||||
|
||||
static const char *LifeTypeNames[] = {
|
||||
"Bar",
|
||||
"Battery",
|
||||
"Time",
|
||||
};
|
||||
XToString( LifeType );
|
||||
XToLocalizedString( LifeType );
|
||||
LuaXType( LifeType );
|
||||
|
||||
static const char *DrainTypeNames[] = {
|
||||
"Normal",
|
||||
"NoRecover",
|
||||
"SuddenDeath",
|
||||
};
|
||||
XToString( DrainType );
|
||||
XToLocalizedString( DrainType );
|
||||
LuaXType( DrainType );
|
||||
|
||||
static const char *AutosyncTypeNames[] = {
|
||||
"Off",
|
||||
"Song",
|
||||
"Machine",
|
||||
"Tempo",
|
||||
};
|
||||
XToString( AutosyncType );
|
||||
XToLocalizedString( AutosyncType );
|
||||
LuaXType( AutosyncType );
|
||||
|
||||
static const char *SoundEffectTypeNames[] = {
|
||||
"Off",
|
||||
"Speed",
|
||||
"Pitch",
|
||||
};
|
||||
XToString( SoundEffectType );
|
||||
XToLocalizedString( SoundEffectType );
|
||||
LuaXType( SoundEffectType );
|
||||
|
||||
void SongOptions::Init()
|
||||
{
|
||||
m_LifeType = LIFE_BAR;
|
||||
m_DrainType = DRAIN_NORMAL;
|
||||
m_LifeType = LifeType_Bar;
|
||||
m_DrainType = DrainType_Normal;
|
||||
m_iBatteryLives = 4;
|
||||
m_bAssistClap = false;
|
||||
m_bAssistMetronome = false;
|
||||
@@ -15,8 +52,8 @@ void SongOptions::Init()
|
||||
m_SpeedfMusicRate = 1.0f;
|
||||
m_fHaste = 0.0f;
|
||||
m_SpeedfHaste = 1.0f;
|
||||
m_AutosyncType = AUTOSYNC_OFF;
|
||||
m_SoundEffectType = SOUNDEFFECT_OFF;
|
||||
m_AutosyncType = AutosyncType_Off;
|
||||
m_SoundEffectType = SoundEffectType_Off;
|
||||
m_bStaticBackground = false;
|
||||
m_bRandomBGOnly = false;
|
||||
m_bSaveScore = true;
|
||||
@@ -61,18 +98,18 @@ void SongOptions::GetMods( vector<RString> &AddTo ) const
|
||||
{
|
||||
switch( m_LifeType )
|
||||
{
|
||||
case LIFE_BAR:
|
||||
case LifeType_Bar:
|
||||
switch( m_DrainType )
|
||||
{
|
||||
case DRAIN_NORMAL: break;
|
||||
case DRAIN_NO_RECOVER: AddTo.push_back("NoRecover"); break;
|
||||
case DRAIN_SUDDEN_DEATH: AddTo.push_back("SuddenDeath"); break;
|
||||
case DrainType_Normal: break;
|
||||
case DrainType_NoRecover: AddTo.push_back("NoRecover"); break;
|
||||
case DrainType_SuddenDeath: AddTo.push_back("SuddenDeath"); break;
|
||||
}
|
||||
break;
|
||||
case LIFE_BATTERY:
|
||||
case LifeType_Battery:
|
||||
AddTo.push_back( ssprintf( "%dLives", m_iBatteryLives ) );
|
||||
break;
|
||||
case LIFE_TIME:
|
||||
case LifeType_Time:
|
||||
AddTo.push_back( "LifeTime" );
|
||||
break;
|
||||
default:
|
||||
@@ -92,19 +129,19 @@ void SongOptions::GetMods( vector<RString> &AddTo ) const
|
||||
|
||||
switch( m_AutosyncType )
|
||||
{
|
||||
case AUTOSYNC_OFF: break;
|
||||
case AUTOSYNC_SONG: AddTo.push_back("AutosyncSong"); break;
|
||||
case AUTOSYNC_MACHINE: AddTo.push_back("AutosyncMachine"); break;
|
||||
case AUTOSYNC_TEMPO: AddTo.push_back("AutosyncTempo"); break;
|
||||
case AutosyncType_Off: break;
|
||||
case AutosyncType_Song: AddTo.push_back("AutosyncSong"); break;
|
||||
case AutosyncType_Machine: AddTo.push_back("AutosyncMachine"); break;
|
||||
case AutosyncType_Tempo: AddTo.push_back("AutosyncTempo"); break;
|
||||
default:
|
||||
FAIL_M(ssprintf("Invalid autosync type: %i", m_AutosyncType));
|
||||
}
|
||||
|
||||
switch( m_SoundEffectType )
|
||||
{
|
||||
case SOUNDEFFECT_OFF: break;
|
||||
case SOUNDEFFECT_SPEED: AddTo.push_back("EffectSpeed"); break;
|
||||
case SOUNDEFFECT_PITCH: AddTo.push_back("EffectPitch"); break;
|
||||
case SoundEffectType_Off: break;
|
||||
case SoundEffectType_Speed: AddTo.push_back("EffectSpeed"); break;
|
||||
case SoundEffectType_Pitch: AddTo.push_back("EffectPitch"); break;
|
||||
default:
|
||||
FAIL_M(ssprintf("Invalid sound effect type: %i", m_SoundEffectType));
|
||||
}
|
||||
@@ -190,26 +227,26 @@ bool SongOptions::FromOneModString( const RString &sOneMod, RString &sErrorOut )
|
||||
on = false;
|
||||
}
|
||||
|
||||
if( sBit == "norecover" ) m_DrainType = DRAIN_NO_RECOVER;
|
||||
else if( sBit == "suddendeath" || sBit == "death" ) m_DrainType = DRAIN_SUDDEN_DEATH;
|
||||
else if( sBit == "power-drop" ) m_DrainType = DRAIN_NO_RECOVER;
|
||||
else if( sBit == "normal-drain" ) m_DrainType = DRAIN_NORMAL;
|
||||
if( sBit == "norecover" ) m_DrainType = DrainType_NoRecover;
|
||||
else if( sBit == "suddendeath" || sBit == "death" ) m_DrainType = DrainType_SuddenDeath;
|
||||
else if( sBit == "power-drop" ) m_DrainType = DrainType_NoRecover;
|
||||
else if( sBit == "normal-drain" ) m_DrainType = DrainType_Normal;
|
||||
|
||||
else if( sBit == "clap" ) m_bAssistClap = on;
|
||||
else if( sBit == "metronome" ) m_bAssistMetronome = on;
|
||||
else if( sBit == "autosync" || sBit == "autosyncsong" ) m_AutosyncType = on ? AUTOSYNC_SONG : AUTOSYNC_OFF;
|
||||
else if( sBit == "autosyncmachine" ) m_AutosyncType = on ? AUTOSYNC_MACHINE : AUTOSYNC_OFF;
|
||||
else if( sBit == "autosynctempo" ) m_AutosyncType = on ? AUTOSYNC_TEMPO : AUTOSYNC_OFF;
|
||||
else if( sBit == "effect" && !on ) m_SoundEffectType = SOUNDEFFECT_OFF;
|
||||
else if( sBit == "effectspeed" ) m_SoundEffectType = on ? SOUNDEFFECT_SPEED : SOUNDEFFECT_OFF;
|
||||
else if( sBit == "effectpitch" ) m_SoundEffectType = on ? SOUNDEFFECT_PITCH : SOUNDEFFECT_OFF;
|
||||
else if( sBit == "autosync" || sBit == "autosyncsong" ) m_AutosyncType = on ? AutosyncType_Song : AutosyncType_Off;
|
||||
else if( sBit == "autosyncmachine" ) m_AutosyncType = on ? AutosyncType_Machine : AutosyncType_Off;
|
||||
else if( sBit == "autosynctempo" ) m_AutosyncType = on ? AutosyncType_Tempo : AutosyncType_Off;
|
||||
else if( sBit == "effect" && !on ) m_SoundEffectType = SoundEffectType_Off;
|
||||
else if( sBit == "effectspeed" ) m_SoundEffectType = on ? SoundEffectType_Speed : SoundEffectType_Off;
|
||||
else if( sBit == "effectpitch" ) m_SoundEffectType = on ? SoundEffectType_Pitch : SoundEffectType_Off;
|
||||
else if( sBit == "staticbg" ) m_bStaticBackground = on;
|
||||
else if( sBit == "randombg" ) m_bRandomBGOnly = on;
|
||||
else if( sBit == "savescore" ) m_bSaveScore = on;
|
||||
else if( sBit == "savereplay" ) m_bSaveReplay = on;
|
||||
else if( sBit == "bar" ) m_LifeType = LIFE_BAR;
|
||||
else if( sBit == "battery" ) m_LifeType = LIFE_BATTERY;
|
||||
else if( sBit == "lifetime" ) m_LifeType = LIFE_TIME;
|
||||
else if( sBit == "bar" ) m_LifeType = LifeType_Bar;
|
||||
else if( sBit == "battery" ) m_LifeType = LifeType_Battery;
|
||||
else if( sBit == "lifetime" ) m_LifeType = LifeType_Time;
|
||||
else if( sBit == "haste" ) m_fHaste = on? 1.0f:0.0f;
|
||||
else
|
||||
return false;
|
||||
@@ -237,6 +274,51 @@ bool SongOptions::operator==( const SongOptions &other ) const
|
||||
return true;
|
||||
}
|
||||
|
||||
// lua start
|
||||
#include "LuaBinding.h"
|
||||
#include "OptionsBinding.h"
|
||||
|
||||
/** @brief Allow Lua to have access to SongOptions. */
|
||||
class LunaSongOptions: public Luna<SongOptions>
|
||||
{
|
||||
public:
|
||||
|
||||
ENUM_INTERFACE(LifeSetting, LifeType, LifeType);
|
||||
ENUM_INTERFACE(DrainSetting, DrainType, DrainType);
|
||||
ENUM_INTERFACE(AutosyncSetting, AutosyncType, AutosyncType);
|
||||
//ENUM_INTERFACE(SoundEffectSetting, SoundEffectType, SoundEffectType);
|
||||
// Broken, SoundEffectType_Speed disables rate mod, other settings have no effect. -Kyz
|
||||
INT_INTERFACE(BatteryLives, BatteryLives);
|
||||
BOOL_INTERFACE(AssistClap, AssistClap);
|
||||
BOOL_INTERFACE(AssistMetronome, AssistMetronome);
|
||||
BOOL_INTERFACE(StaticBackground, StaticBackground);
|
||||
BOOL_INTERFACE(RandomBGOnly, RandomBGOnly);
|
||||
BOOL_INTERFACE(SaveScore, SaveScore);
|
||||
BOOL_INTERFACE(SaveReplay, SaveReplay);
|
||||
FLOAT_INTERFACE(MusicRate, MusicRate, (v > 0.0f && v <= 3.0f)); // Greater than 3 seems to crash frequently, haven't investigated why. -Kyz
|
||||
FLOAT_INTERFACE(Haste, Haste, true);
|
||||
|
||||
LunaSongOptions()
|
||||
{
|
||||
ADD_METHOD(LifeSetting);
|
||||
ADD_METHOD(DrainSetting);
|
||||
ADD_METHOD(AutosyncSetting);
|
||||
//ADD_METHOD(SoundEffectSetting);
|
||||
ADD_METHOD(BatteryLives);
|
||||
ADD_METHOD(AssistClap);
|
||||
ADD_METHOD(AssistMetronome);
|
||||
ADD_METHOD(StaticBackground);
|
||||
ADD_METHOD(RandomBGOnly);
|
||||
ADD_METHOD(SaveScore);
|
||||
ADD_METHOD(SaveReplay);
|
||||
ADD_METHOD(MusicRate);
|
||||
ADD_METHOD(Haste);
|
||||
}
|
||||
};
|
||||
|
||||
LUA_REGISTER_CLASS( SongOptions )
|
||||
// lua end
|
||||
|
||||
/*
|
||||
* (c) 2001-2004 Chris Danford, Glenn Maynard
|
||||
* All rights reserved.
|
||||
|
||||
+57
-29
@@ -3,43 +3,68 @@
|
||||
#ifndef SONG_OPTIONS_H
|
||||
#define SONG_OPTIONS_H
|
||||
|
||||
#include "EnumHelper.h"
|
||||
|
||||
enum LifeType
|
||||
{
|
||||
LifeType_Bar,
|
||||
LifeType_Battery,
|
||||
LifeType_Time,
|
||||
NUM_LifeType,
|
||||
LifeType_Invalid
|
||||
};
|
||||
const RString& LifeTypeToString( LifeType cat );
|
||||
const RString& LifeTypeToLocalizedString( LifeType cat );
|
||||
LuaDeclareType( LifeType );
|
||||
|
||||
enum DrainType
|
||||
{
|
||||
DrainType_Normal,
|
||||
DrainType_NoRecover,
|
||||
DrainType_SuddenDeath,
|
||||
NUM_DrainType,
|
||||
DrainType_Invalid
|
||||
};
|
||||
const RString& DrainTypeToString( DrainType cat );
|
||||
const RString& DrainTypeToLocalizedString( DrainType cat );
|
||||
LuaDeclareType( DrainType );
|
||||
|
||||
enum AutosyncType
|
||||
{
|
||||
AutosyncType_Off,
|
||||
AutosyncType_Song,
|
||||
AutosyncType_Machine,
|
||||
AutosyncType_Tempo,
|
||||
NUM_AutosyncType,
|
||||
AutosyncType_Invalid
|
||||
};
|
||||
const RString& AutosyncTypeToString( AutosyncType cat );
|
||||
const RString& AutosyncTypeToLocalizedString( AutosyncType cat );
|
||||
LuaDeclareType( AutosyncType );
|
||||
|
||||
enum SoundEffectType
|
||||
{
|
||||
SoundEffectType_Off,
|
||||
SoundEffectType_Speed,
|
||||
SoundEffectType_Pitch,
|
||||
NUM_SoundEffectType,
|
||||
SoundEffectType_Invalid
|
||||
};
|
||||
const RString& SoundEffectTypeToString( SoundEffectType cat );
|
||||
const RString& SoundEffectTypeToLocalizedString( SoundEffectType cat );
|
||||
LuaDeclareType( SoundEffectType );
|
||||
|
||||
class SongOptions
|
||||
{
|
||||
public:
|
||||
enum LifeType
|
||||
{
|
||||
LIFE_BAR=0,
|
||||
LIFE_BATTERY,
|
||||
LIFE_TIME,
|
||||
NUM_LIFE_TYPES
|
||||
};
|
||||
LifeType m_LifeType;
|
||||
enum DrainType
|
||||
{
|
||||
DRAIN_NORMAL,
|
||||
DRAIN_NO_RECOVER,
|
||||
DRAIN_SUDDEN_DEATH
|
||||
};
|
||||
DrainType m_DrainType; // only used with LifeBar
|
||||
int m_iBatteryLives;
|
||||
bool m_bAssistClap;
|
||||
bool m_bAssistMetronome;
|
||||
float m_fMusicRate, m_SpeedfMusicRate;
|
||||
float m_fHaste, m_SpeedfHaste;
|
||||
enum AutosyncType {
|
||||
AUTOSYNC_OFF,
|
||||
AUTOSYNC_SONG,
|
||||
AUTOSYNC_MACHINE,
|
||||
AUTOSYNC_TEMPO,
|
||||
NUM_AUTOSYNC_TYPES
|
||||
};
|
||||
AutosyncType m_AutosyncType;
|
||||
enum SoundEffectType {
|
||||
SOUNDEFFECT_OFF,
|
||||
SOUNDEFFECT_SPEED,
|
||||
SOUNDEFFECT_PITCH,
|
||||
NUM_SOUNDEFFECT
|
||||
};
|
||||
SoundEffectType m_SoundEffectType;
|
||||
bool m_bStaticBackground;
|
||||
bool m_bRandomBGOnly;
|
||||
@@ -51,12 +76,12 @@ public:
|
||||
*
|
||||
* This is taken from Init(), but uses the intended
|
||||
* initialization lists. */
|
||||
SongOptions(): m_LifeType(LIFE_BAR), m_DrainType(DRAIN_NORMAL),
|
||||
SongOptions(): m_LifeType(LifeType_Bar), m_DrainType(DrainType_Normal),
|
||||
m_iBatteryLives(4), m_bAssistClap(false),
|
||||
m_bAssistMetronome(false), m_fMusicRate(1.0f),
|
||||
m_SpeedfMusicRate(1.0f), m_fHaste(0.0f),
|
||||
m_SpeedfHaste(1.0f), m_AutosyncType(AUTOSYNC_OFF),
|
||||
m_SoundEffectType(SOUNDEFFECT_OFF),
|
||||
m_SpeedfHaste(1.0f), m_AutosyncType(AutosyncType_Off),
|
||||
m_SoundEffectType(SoundEffectType_Off),
|
||||
m_bStaticBackground(false), m_bRandomBGOnly(false),
|
||||
m_bSaveScore(true), m_bSaveReplay(false) {};
|
||||
void Init();
|
||||
@@ -70,6 +95,9 @@ public:
|
||||
|
||||
bool operator==( const SongOptions &other ) const;
|
||||
bool operator!=( const SongOptions &other ) const { return !operator==(other); }
|
||||
|
||||
// Lua
|
||||
void PushSelf( lua_State *L );
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
Reference in New Issue
Block a user